@reallyme/codec 0.1.22 → 0.2.0
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/NOTICE +16 -0
- package/README.md +52 -15
- package/dist/boundary.d.ts +8 -2
- package/dist/boundary.js +31 -4
- package/dist/cbor.d.ts +67 -4
- package/dist/cbor.js +1170 -74
- package/dist/deterministicCborBoundary.d.ts +11 -0
- package/dist/deterministicCborBoundary.js +17 -0
- package/dist/index.d.ts +37 -23
- package/dist/index.js +14 -22
- package/dist/multiformat.d.ts +10 -12
- package/dist/multiformat.js +149 -128
- package/dist/operationContract.d.ts +31 -0
- package/dist/operationContract.js +754 -0
- package/dist/pem.d.ts +0 -3
- package/dist/pem.js +111 -34
- package/dist/proto/generated/reallyme/codec/v1/codec_pb.d.ts +641 -38
- package/dist/proto/generated/reallyme/codec/v1/codec_pb.js +187 -43
- package/dist/proto.d.ts +2 -2
- package/dist/proto.js +1 -1
- package/dist/readOutput.d.ts +7 -6
- package/dist/readOutput.js +62 -11
- package/dist/wasm/reallyme_codec_wasm.d.ts +7 -62
- package/dist/wasm/reallyme_codec_wasm.js +11 -168
- package/dist/wasm/reallyme_codec_wasm_bg.wasm +0 -0
- package/dist/wasmProvider.d.ts +5 -17
- package/dist/wasmProvider.js +4 -30
- package/package.json +4 -1
- package/dist/protoProcess.d.ts +0 -16
- package/dist/protoProcess.js +0 -282
package/dist/protoProcess.js
DELETED
|
@@ -1,282 +0,0 @@
|
|
|
1
|
-
// SPDX-FileCopyrightText: Copyright © 2026 ReallyMe LLC. All rights reserved
|
|
2
|
-
//
|
|
3
|
-
// SPDX-License-Identifier: Apache-2.0
|
|
4
|
-
import { create, fromBinary, toBinary } from "@bufbuild/protobuf";
|
|
5
|
-
import { MAX_CODEC_PROTO_JSON_BYTES, MAX_CODEC_PROTO_MESSAGE_BYTES, requireBoundaryAggregate, utf8ByteLength, } from "./boundary.js";
|
|
6
|
-
import { ReallyMeCodecError } from "./errors.js";
|
|
7
|
-
import { CodecBoundaryErrorSchema, CodecErrorReason, CodecErrorSchema, CodecOperationRequestSchema, CodecProtoResultEnvelopeSchema, CodecProtoResultStatus, } from "./proto/generated/reallyme/codec/v1/codec_pb.js";
|
|
8
|
-
import { ensureBytesInput, readIndependentBoundedBytesOutput, } from "./readOutput.js";
|
|
9
|
-
import { requireReallyMeCodecWasmProvider } from "./wasmProvider.js";
|
|
10
|
-
const MAX_CODEC_PROTO_RESULT_ENVELOPE_BYTES = 1_048_592;
|
|
11
|
-
const PROTO_REQUEST_OVERHEAD_BUDGET = 64;
|
|
12
|
-
const requireProtoBytes = (value) => {
|
|
13
|
-
if (!(value instanceof Uint8Array)) {
|
|
14
|
-
throw new ReallyMeCodecError("invalid-input");
|
|
15
|
-
}
|
|
16
|
-
return value.length;
|
|
17
|
-
};
|
|
18
|
-
const requireProtoString = (value) => {
|
|
19
|
-
if (typeof value !== "string") {
|
|
20
|
-
throw new ReallyMeCodecError("invalid-input");
|
|
21
|
-
}
|
|
22
|
-
return value;
|
|
23
|
-
};
|
|
24
|
-
const protoUtf8Length = (value) => {
|
|
25
|
-
const text = requireProtoString(value);
|
|
26
|
-
try {
|
|
27
|
-
return utf8ByteLength(text);
|
|
28
|
-
}
|
|
29
|
-
catch (error) {
|
|
30
|
-
if (error instanceof ReallyMeCodecError) {
|
|
31
|
-
return undefined;
|
|
32
|
-
}
|
|
33
|
-
throw error;
|
|
34
|
-
}
|
|
35
|
-
};
|
|
36
|
-
const validateGeneratedProtoRequest = (request) => {
|
|
37
|
-
const lengths = [PROTO_REQUEST_OVERHEAD_BUDGET];
|
|
38
|
-
switch (request.operation.case) {
|
|
39
|
-
case undefined:
|
|
40
|
-
case "multicodecTable":
|
|
41
|
-
break;
|
|
42
|
-
case "multicodecPrefixForName":
|
|
43
|
-
{
|
|
44
|
-
const length = protoUtf8Length(request.operation.value.name);
|
|
45
|
-
if (length === undefined) {
|
|
46
|
-
return false;
|
|
47
|
-
}
|
|
48
|
-
lengths.push(length);
|
|
49
|
-
}
|
|
50
|
-
break;
|
|
51
|
-
case "multicodecLookupPrefix":
|
|
52
|
-
lengths.push(requireProtoBytes(request.operation.value.value));
|
|
53
|
-
break;
|
|
54
|
-
case "multikeyParse":
|
|
55
|
-
{
|
|
56
|
-
const length = protoUtf8Length(request.operation.value.multikey);
|
|
57
|
-
if (length === undefined) {
|
|
58
|
-
return false;
|
|
59
|
-
}
|
|
60
|
-
lengths.push(length);
|
|
61
|
-
}
|
|
62
|
-
break;
|
|
63
|
-
case "dagCborVerifyCid":
|
|
64
|
-
{
|
|
65
|
-
const length = protoUtf8Length(request.operation.value.cid);
|
|
66
|
-
if (length === undefined) {
|
|
67
|
-
return false;
|
|
68
|
-
}
|
|
69
|
-
lengths.push(length);
|
|
70
|
-
}
|
|
71
|
-
lengths.push(requireProtoBytes(request.operation.value.payload));
|
|
72
|
-
break;
|
|
73
|
-
case "pemDecode": {
|
|
74
|
-
lengths.push(requireProtoBytes(request.operation.value.pem));
|
|
75
|
-
const options = request.operation.value.options;
|
|
76
|
-
if (options !== undefined) {
|
|
77
|
-
if (!Array.isArray(options.allowedLabels)) {
|
|
78
|
-
throw new ReallyMeCodecError("invalid-input");
|
|
79
|
-
}
|
|
80
|
-
if (options.allowedLabels.length > MAX_CODEC_PROTO_MESSAGE_BYTES / 5) {
|
|
81
|
-
return false;
|
|
82
|
-
}
|
|
83
|
-
lengths.push(options.allowedLabels.length * 5);
|
|
84
|
-
}
|
|
85
|
-
break;
|
|
86
|
-
}
|
|
87
|
-
default:
|
|
88
|
-
throw new ReallyMeCodecError("invalid-input");
|
|
89
|
-
}
|
|
90
|
-
try {
|
|
91
|
-
requireBoundaryAggregate(lengths, MAX_CODEC_PROTO_MESSAGE_BYTES);
|
|
92
|
-
return true;
|
|
93
|
-
}
|
|
94
|
-
catch (error) {
|
|
95
|
-
if (error instanceof ReallyMeCodecError) {
|
|
96
|
-
return false;
|
|
97
|
-
}
|
|
98
|
-
throw error;
|
|
99
|
-
}
|
|
100
|
-
};
|
|
101
|
-
const boundaryResourceLimitResult = () => {
|
|
102
|
-
try {
|
|
103
|
-
return {
|
|
104
|
-
status: "codec-error",
|
|
105
|
-
bytes: toBinary(CodecErrorSchema, create(CodecErrorSchema, {
|
|
106
|
-
error: {
|
|
107
|
-
case: "boundary",
|
|
108
|
-
value: create(CodecBoundaryErrorSchema, {
|
|
109
|
-
reason: CodecErrorReason.BOUNDARY_RESOURCE_LIMIT_EXCEEDED,
|
|
110
|
-
}),
|
|
111
|
-
},
|
|
112
|
-
})),
|
|
113
|
-
isCodecError: true,
|
|
114
|
-
};
|
|
115
|
-
}
|
|
116
|
-
catch (_error) {
|
|
117
|
-
throw new ReallyMeCodecError("provider-failure");
|
|
118
|
-
}
|
|
119
|
-
};
|
|
120
|
-
const boundaryResourceLimitEnvelope = () => {
|
|
121
|
-
const result = boundaryResourceLimitResult();
|
|
122
|
-
try {
|
|
123
|
-
return toBinary(CodecProtoResultEnvelopeSchema, create(CodecProtoResultEnvelopeSchema, {
|
|
124
|
-
status: CodecProtoResultStatus.CODEC_ERROR,
|
|
125
|
-
payload: result.bytes,
|
|
126
|
-
}));
|
|
127
|
-
}
|
|
128
|
-
catch (_error) {
|
|
129
|
-
throw new ReallyMeCodecError("provider-failure");
|
|
130
|
-
}
|
|
131
|
-
finally {
|
|
132
|
-
result.bytes.fill(0);
|
|
133
|
-
}
|
|
134
|
-
};
|
|
135
|
-
const decodeResultEnvelope = (envelopeBytes) => {
|
|
136
|
-
try {
|
|
137
|
-
const envelope = fromBinary(CodecProtoResultEnvelopeSchema, envelopeBytes);
|
|
138
|
-
try {
|
|
139
|
-
switch (envelope.status) {
|
|
140
|
-
case CodecProtoResultStatus.RESULT:
|
|
141
|
-
return {
|
|
142
|
-
status: "result",
|
|
143
|
-
bytes: envelope.payload.slice(),
|
|
144
|
-
isCodecError: false,
|
|
145
|
-
};
|
|
146
|
-
case CodecProtoResultStatus.CODEC_ERROR:
|
|
147
|
-
return {
|
|
148
|
-
status: "codec-error",
|
|
149
|
-
bytes: envelope.payload.slice(),
|
|
150
|
-
isCodecError: true,
|
|
151
|
-
};
|
|
152
|
-
case CodecProtoResultStatus.UNSPECIFIED:
|
|
153
|
-
throw new ReallyMeCodecError("provider-failure");
|
|
154
|
-
}
|
|
155
|
-
}
|
|
156
|
-
finally {
|
|
157
|
-
envelope.payload.fill(0);
|
|
158
|
-
}
|
|
159
|
-
}
|
|
160
|
-
catch (error) {
|
|
161
|
-
if (error instanceof ReallyMeCodecError) {
|
|
162
|
-
throw error;
|
|
163
|
-
}
|
|
164
|
-
throw new ReallyMeCodecError("provider-failure");
|
|
165
|
-
}
|
|
166
|
-
};
|
|
167
|
-
/**
|
|
168
|
-
* Execute one binary generated-protobuf request.
|
|
169
|
-
*
|
|
170
|
-
* The returned bytes are always a `CodecProtoResultEnvelope`; malformed or
|
|
171
|
-
* unsupported requests are represented inside that envelope.
|
|
172
|
-
*/
|
|
173
|
-
export const processProto = (requestBytes) => {
|
|
174
|
-
ensureBytesInput(requestBytes);
|
|
175
|
-
if (requestBytes.length > MAX_CODEC_PROTO_MESSAGE_BYTES) {
|
|
176
|
-
return boundaryResourceLimitEnvelope();
|
|
177
|
-
}
|
|
178
|
-
return readIndependentBoundedBytesOutput(requireReallyMeCodecWasmProvider().processProto(requestBytes), requestBytes, MAX_CODEC_PROTO_RESULT_ENVELOPE_BYTES);
|
|
179
|
-
};
|
|
180
|
-
/**
|
|
181
|
-
* Execute one generated ProtoJSON request and return the same binary envelope
|
|
182
|
-
* used by `processProto`.
|
|
183
|
-
*/
|
|
184
|
-
export const processProtoJson = (requestJson) => {
|
|
185
|
-
ensureBytesInput(requestJson);
|
|
186
|
-
if (requestJson.length > MAX_CODEC_PROTO_JSON_BYTES) {
|
|
187
|
-
return boundaryResourceLimitEnvelope();
|
|
188
|
-
}
|
|
189
|
-
return readIndependentBoundedBytesOutput(requireReallyMeCodecWasmProvider().processProtoJson(requestJson), requestJson, MAX_CODEC_PROTO_RESULT_ENVELOPE_BYTES);
|
|
190
|
-
};
|
|
191
|
-
export const processGeneratedProtoRequest = (request) => {
|
|
192
|
-
let withinBoundary;
|
|
193
|
-
try {
|
|
194
|
-
withinBoundary = validateGeneratedProtoRequest(request);
|
|
195
|
-
}
|
|
196
|
-
catch (error) {
|
|
197
|
-
if (error instanceof ReallyMeCodecError) {
|
|
198
|
-
throw error;
|
|
199
|
-
}
|
|
200
|
-
throw new ReallyMeCodecError("invalid-input");
|
|
201
|
-
}
|
|
202
|
-
if (!withinBoundary) {
|
|
203
|
-
return boundaryResourceLimitResult();
|
|
204
|
-
}
|
|
205
|
-
let requestBytes;
|
|
206
|
-
try {
|
|
207
|
-
requestBytes = toBinary(CodecOperationRequestSchema, request);
|
|
208
|
-
}
|
|
209
|
-
catch (_error) {
|
|
210
|
-
throw new ReallyMeCodecError("provider-failure");
|
|
211
|
-
}
|
|
212
|
-
try {
|
|
213
|
-
if (requestBytes.length > MAX_CODEC_PROTO_MESSAGE_BYTES) {
|
|
214
|
-
throw new ReallyMeCodecError("invalid-input");
|
|
215
|
-
}
|
|
216
|
-
const envelopeBytes = processProto(requestBytes);
|
|
217
|
-
try {
|
|
218
|
-
return decodeResultEnvelope(envelopeBytes);
|
|
219
|
-
}
|
|
220
|
-
finally {
|
|
221
|
-
envelopeBytes.fill(0);
|
|
222
|
-
}
|
|
223
|
-
}
|
|
224
|
-
finally {
|
|
225
|
-
requestBytes.fill(0);
|
|
226
|
-
}
|
|
227
|
-
};
|
|
228
|
-
const errorCodeForCodecError = (bytes) => {
|
|
229
|
-
let error;
|
|
230
|
-
try {
|
|
231
|
-
error = fromBinary(CodecErrorSchema, bytes);
|
|
232
|
-
}
|
|
233
|
-
catch (_error) {
|
|
234
|
-
return "provider-failure";
|
|
235
|
-
}
|
|
236
|
-
const reason = error.error.value?.reason;
|
|
237
|
-
const reasonIsKnown = reason !== undefined &&
|
|
238
|
-
Object.values(CodecErrorReason).some((candidate) => candidate === reason);
|
|
239
|
-
if (!reasonIsKnown) {
|
|
240
|
-
return "provider-failure";
|
|
241
|
-
}
|
|
242
|
-
switch (error.error.case) {
|
|
243
|
-
case "baseEncoding":
|
|
244
|
-
return reason >= 100 && reason <= 199
|
|
245
|
-
? "invalid-input"
|
|
246
|
-
: "provider-failure";
|
|
247
|
-
case "pem":
|
|
248
|
-
return reason >= 200 && reason <= 299
|
|
249
|
-
? "invalid-input"
|
|
250
|
-
: "provider-failure";
|
|
251
|
-
case "multiformat":
|
|
252
|
-
return reason >= 300 && reason <= 399
|
|
253
|
-
? "invalid-input"
|
|
254
|
-
: "provider-failure";
|
|
255
|
-
case "canonicalization":
|
|
256
|
-
if (reason === CodecErrorReason.CANONICAL_INTERNAL) {
|
|
257
|
-
return "provider-failure";
|
|
258
|
-
}
|
|
259
|
-
return reason >= 400 && reason <= 499
|
|
260
|
-
? "invalid-input"
|
|
261
|
-
: "provider-failure";
|
|
262
|
-
case "backend":
|
|
263
|
-
return "provider-failure";
|
|
264
|
-
case "boundary":
|
|
265
|
-
// This is the only boundary error the generated facade creates from
|
|
266
|
-
// caller input. Malformed/missing generated requests indicate provider
|
|
267
|
-
// corruption or skew, not bad input supplied to the high-level API.
|
|
268
|
-
return reason === CodecErrorReason.BOUNDARY_RESOURCE_LIMIT_EXCEEDED
|
|
269
|
-
? "invalid-input"
|
|
270
|
-
: "provider-failure";
|
|
271
|
-
case undefined:
|
|
272
|
-
return "provider-failure";
|
|
273
|
-
}
|
|
274
|
-
};
|
|
275
|
-
export const protoPayloadOrThrow = (result) => {
|
|
276
|
-
if (result.isCodecError) {
|
|
277
|
-
const code = errorCodeForCodecError(result.bytes);
|
|
278
|
-
result.bytes.fill(0);
|
|
279
|
-
throw new ReallyMeCodecError(code);
|
|
280
|
-
}
|
|
281
|
-
return result.bytes;
|
|
282
|
-
};
|