@wasm-oj/contracts 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/LICENSE ADDED
@@ -0,0 +1,21 @@
1
+ MIT License
2
+
3
+ Copyright (c) 2026 JacobLinCool
4
+
5
+ Permission is hereby granted, free of charge, to any person obtaining a copy
6
+ of this software and associated documentation files (the "Software"), to deal
7
+ in the Software without restriction, including without limitation the rights
8
+ to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
9
+ copies of the Software, and to permit persons to whom the Software is
10
+ furnished to do so, subject to the following conditions:
11
+
12
+ The above copyright notice and this permission notice shall be included in all
13
+ copies or substantial portions of the Software.
14
+
15
+ THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
16
+ IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
17
+ FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
18
+ AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
19
+ LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
20
+ OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE
21
+ SOFTWARE.
package/README.md ADDED
@@ -0,0 +1,4 @@
1
+ # `@wasm-oj/contracts`
2
+
3
+ Environment-neutral WASM-OJ SDK contracts, wire models, errors, and toolchain source types.
4
+ This package has no runtime dependencies and is safe to import from Node.js, browsers, and Workers.
@@ -0,0 +1,468 @@
1
+ /**
2
+ * The single compatibility boundary shared by WASM-OJ compilers, runners,
3
+ * artifacts, judge specifications, caches, and conformance evidence.
4
+ *
5
+ * Package and upstream toolchain versions remain independent release metadata;
6
+ * they do not define WASM-OJ protocol compatibility.
7
+ */
8
+ declare const WASM_OJ_CONTRACT_VERSION: 2;
9
+ declare const WASM_OJ_CONTRACT_ID: "wasm-oj-v2";
10
+ declare const WASM_OJ_SCHEMAS: Readonly<{
11
+ readonly clangPins: "wasm-oj-v2/clang-pins";
12
+ readonly clangLibcxxPch: "wasm-oj-v2/clang-libcxx-pch";
13
+ readonly clangToolchain: "wasm-oj-v2/clang-toolchain";
14
+ readonly compileBatch: "wasm-oj-v2/compile-batch";
15
+ readonly compileTrace: "wasm-oj-v2/compile-trace";
16
+ readonly conformance: "wasm-oj-v2/conformance";
17
+ readonly conformanceEvidence: "wasm-oj-v2/conformance-evidence";
18
+ readonly conformanceMatrix: "wasm-oj-v2/conformance-matrix";
19
+ readonly cppDependencyLock: "wasm-oj-v2/cpp-dependency-lock";
20
+ readonly dependencyLock: "wasm-oj-v2/dependency-lock";
21
+ readonly dependencyOfflineBundle: "wasm-oj-v2/dependency-offline-bundle";
22
+ readonly incrementalBuildGraph: "wasm-oj-v2/incremental-build-graph";
23
+ readonly interactiveRequest: "wasm-oj-v2/interactive-request";
24
+ readonly goToolchain: "wasm-oj-v2/go-toolchain";
25
+ readonly objectCache: "wasm-oj-v2/object-cache";
26
+ readonly pythonToolchain: "wasm-oj-v2/python-toolchain";
27
+ readonly replayBundle: "wasm-oj-v2/replay-bundle";
28
+ readonly releaseManifest: "wasm-oj-v2/release-manifest";
29
+ readonly rustToolchain: "wasm-oj-v2/rust-toolchain";
30
+ readonly runRequest: "wasm-oj-v2/run-request";
31
+ readonly runtimeBundle: "wasm-oj-v2/runtime-bundle";
32
+ readonly runtimeCoreLicenses: "wasm-oj-v2/runtime-core-licenses";
33
+ readonly thirdPartyComponents: "wasm-oj-v2/third-party-components";
34
+ readonly wasmerSdkLicenses: "wasm-oj-v2/wasmer-sdk-licenses";
35
+ readonly toolchainPackage: "wasm-oj-v2/toolchain-package";
36
+ }>;
37
+ declare const WASM_OJ_STORAGE: Readonly<{
38
+ readonly database: "wasm-oj-v2:storage";
39
+ readonly databaseVersion: 2;
40
+ readonly dependencyCache: "wasm-oj-v2:dependencies";
41
+ readonly incrementalBuildCache: "wasm-oj-v2:incremental-build-cache";
42
+ readonly runtimeFilesCache: "wasm-oj-v2:runtime-files";
43
+ readonly toolchainCache: "wasm-oj-v2:toolchains";
44
+ }>;
45
+
46
+ declare const LANGUAGES: readonly ["c", "cpp", "rust", "python", "javascript", "typescript", "go"];
47
+ type BuiltinLanguage = (typeof LANGUAGES)[number];
48
+ /**
49
+ * Stable language identity carried by projects and artifacts.
50
+ *
51
+ * WASM-OJ ships the values in `LANGUAGES`; downstream compiler implementations
52
+ * may use their own non-empty identifier without forking the contract.
53
+ */
54
+ type Language = BuiltinLanguage | (string & {});
55
+ declare function assertLanguageIdentifier(language: unknown): asserts language is Language;
56
+ declare function isBuiltinLanguage(language: string): language is BuiltinLanguage;
57
+ type TargetAbi = "wasip1" | "wasix";
58
+ type OptimizationLevel = "debug" | "release";
59
+ declare const DEPENDENCY_ECOSYSTEMS: readonly ["cargo", "npm", "pypi", "go", "cpp"];
60
+ type DependencyEcosystem = (typeof DEPENDENCY_ECOSYSTEMS)[number];
61
+ interface DependencyRequirement {
62
+ ecosystem: DependencyEcosystem;
63
+ name: string;
64
+ requirement: string;
65
+ features?: readonly string[];
66
+ }
67
+ interface DependencySourceFile {
68
+ ecosystem: DependencyEcosystem;
69
+ role: "manifest" | "lockfile" | "source";
70
+ path: string;
71
+ contents: string;
72
+ }
73
+ interface DependencyManifest {
74
+ requirements: readonly DependencyRequirement[];
75
+ sourceFiles?: readonly DependencySourceFile[];
76
+ }
77
+ interface LockedDependencyPackage {
78
+ id: string;
79
+ ecosystem: DependencyEcosystem;
80
+ name: string;
81
+ version: string;
82
+ source: string;
83
+ integritySha256: string;
84
+ dependencies: readonly string[];
85
+ features?: readonly string[];
86
+ }
87
+ interface DependencyLock {
88
+ schema: typeof WASM_OJ_SCHEMAS.dependencyLock;
89
+ wasmOjContract: typeof WASM_OJ_CONTRACT_VERSION;
90
+ manifestSha256: string;
91
+ roots: readonly string[];
92
+ packages: readonly LockedDependencyPackage[];
93
+ }
94
+ interface MaterializedDependencyPackage {
95
+ package: LockedDependencyPackage;
96
+ filesSha256: string;
97
+ files: Readonly<Record<string, Uint8Array>>;
98
+ }
99
+ /** Archive-independent, fully verified dependency input admitted by compilers. */
100
+ interface DependencyBuildBundle {
101
+ lock: DependencyLock;
102
+ lockSha256: string;
103
+ packages: readonly MaterializedDependencyPackage[];
104
+ }
105
+ interface ProjectFile {
106
+ path: string;
107
+ language: Language;
108
+ content: string;
109
+ }
110
+ interface BuildConfig {
111
+ language: Language;
112
+ target: TargetAbi;
113
+ optimization: OptimizationLevel;
114
+ entry: string;
115
+ }
116
+ interface DeterminismConfig {
117
+ /** Unsigned 32-bit seed used by every guest entropy source. */
118
+ randomSeed: number;
119
+ /** Unix epoch exposed by the first realtime-clock observation. */
120
+ realtimeEpochMs: number;
121
+ /** Virtual clock advancement after each clock observation. */
122
+ clockStepNs: number;
123
+ }
124
+ interface ResourcePolicy {
125
+ /** Versioned baseline-normalized weighted Wasm instruction budget. */
126
+ instructionBudget: number;
127
+ /** Deterministic virtual elapsed-time budget, including sleeps and clock observations. */
128
+ logicalTimeLimitMs: number;
129
+ /** Hard upper bound for guest linear memory. */
130
+ memoryLimitBytes: number;
131
+ /** Combined stdout and stderr upper bound. */
132
+ outputLimitBytes: number;
133
+ /** Additional live VFS file bytes permitted above the mounted baseline. */
134
+ filesystemWriteLimitBytes: number;
135
+ /** Additional live VFS entries permitted above the mounted baseline. */
136
+ filesystemEntryLimit: number;
137
+ /** Host safety deadline; excluded from the deterministic transcript. */
138
+ wallTimeLimitMs: number;
139
+ }
140
+ type ExecutionTermination = "exited" | "instruction-limit" | "logical-time-limit" | "memory-limit" | "output-limit" | "filesystem-limit" | "wall-time-limit" | "trap";
141
+ interface ExecutionMetrics {
142
+ /** Baseline-normalized weighted deterministic cost used for judging. */
143
+ cost: number | null;
144
+ /** Unadjusted weighted cost observed by the runtime core. */
145
+ rawCost: number | null;
146
+ /** Empty-program cost subtracted from rawCost. */
147
+ baselineCost: number;
148
+ /** Versioned compiler/runtime baseline identity. */
149
+ costProfile: string;
150
+ /** Meter policy used to interpret cost. */
151
+ costModel: string;
152
+ /** WARK-compatible static counts of original Wasm operators. */
153
+ operations: Readonly<Record<string, number>> | null;
154
+ /** Peak linear-memory allocation observed by the runner. */
155
+ memoryBytes: number | null;
156
+ /** Deterministic virtual time elapsed during execution. */
157
+ logicalTimeNs: number | null;
158
+ /** Peak live VFS file bytes, including the mounted baseline. */
159
+ filesystemBytes: number | null;
160
+ /** Peak live VFS inode count, excluding the root inode. */
161
+ filesystemEntries: number | null;
162
+ stdoutBytes: number | null;
163
+ stderrBytes: number | null;
164
+ }
165
+ interface RunConfig {
166
+ args: string[];
167
+ stdin: string;
168
+ env: Record<string, string>;
169
+ /** Absolute, normalized guest files mounted before execution. */
170
+ files?: Record<string, Uint8Array>;
171
+ /** Absolute, normalized guest files collected after execution. */
172
+ outputPaths?: string[];
173
+ /** Absolute, normalized initial working directory. */
174
+ cwd?: string;
175
+ determinism: DeterminismConfig;
176
+ resources: ResourcePolicy;
177
+ }
178
+ interface ProjectConfig extends BuildConfig, RunConfig {
179
+ }
180
+ interface Project {
181
+ id: string;
182
+ name: string;
183
+ files: ProjectFile[];
184
+ config: ProjectConfig;
185
+ activeFile: string;
186
+ updatedAt: number;
187
+ /** Verified archive-independent dependency input, if this project uses packages. */
188
+ dependencies?: DependencyBuildBundle;
189
+ }
190
+ type DiagnosticSeverity = "error" | "warning" | "info";
191
+ interface Diagnostic {
192
+ severity: DiagnosticSeverity;
193
+ message: string;
194
+ file: string;
195
+ line: number;
196
+ column: number;
197
+ endLine?: number;
198
+ endColumn?: number;
199
+ source: string;
200
+ code?: string;
201
+ }
202
+ interface ArtifactMetadata {
203
+ /** WASM-OJ compatibility contract required to consume this artifact. */
204
+ wasmOjContract: typeof WASM_OJ_CONTRACT_VERSION;
205
+ id: string;
206
+ projectId: string;
207
+ cacheKey: string;
208
+ name: string;
209
+ language: Language;
210
+ target: TargetAbi;
211
+ optimization: OptimizationLevel;
212
+ createdAt: number;
213
+ durationMs: number;
214
+ size: number;
215
+ toolchains: string[];
216
+ /** Trusted empty-program cost profile selected by the compiler contract. */
217
+ costProfile: string;
218
+ /** Canonical dependency lock used for this build. */
219
+ dependencyLockSha256?: string;
220
+ }
221
+ interface WasmArtifact extends ArtifactMetadata {
222
+ kind: "wasm";
223
+ bytes: Uint8Array;
224
+ }
225
+ interface RuntimeBundleArtifact extends ArtifactMetadata {
226
+ kind: "runtime-bundle";
227
+ runtimePackage: string;
228
+ command: string;
229
+ entry: string;
230
+ files: Record<string, string | Uint8Array>;
231
+ manifest: string;
232
+ }
233
+ type BuildArtifact = WasmArtifact | RuntimeBundleArtifact;
234
+ interface BuildResult {
235
+ success: boolean;
236
+ diagnostics: Diagnostic[];
237
+ artifact?: BuildArtifact;
238
+ stdout: string;
239
+ stderr: string;
240
+ cacheHit: boolean;
241
+ buildGraph?: {
242
+ hits: Partial<Record<"pch" | "object" | "link-result", number>>;
243
+ misses: Partial<Record<"pch" | "object" | "link-result", number>>;
244
+ stores: Partial<Record<"pch" | "object" | "link-result", number>>;
245
+ };
246
+ }
247
+ interface RunResult {
248
+ code: number;
249
+ stdout: string;
250
+ stderr: string;
251
+ /** Requested output files that existed when the process terminated. */
252
+ files: Record<string, Uint8Array>;
253
+ durationMs: number;
254
+ determinism: DeterminismConfig;
255
+ resources: ResourcePolicy;
256
+ termination: ExecutionTermination;
257
+ /** Runtime trap text when termination is `trap`; absent for normal guest exits. */
258
+ trapMessage?: string;
259
+ metrics: ExecutionMetrics;
260
+ }
261
+ interface InteractiveProgramConfig {
262
+ args: string[];
263
+ env: Record<string, string>;
264
+ files?: Record<string, Uint8Array>;
265
+ cwd?: string;
266
+ resources: ResourcePolicy;
267
+ }
268
+ interface InteractiveRunConfig {
269
+ contestant: InteractiveProgramConfig;
270
+ interactor: InteractiveProgramConfig;
271
+ determinism: DeterminismConfig;
272
+ }
273
+ interface InteractiveProcessResult {
274
+ code: number;
275
+ stderr: string;
276
+ termination: ExecutionTermination;
277
+ metrics: ExecutionMetrics;
278
+ }
279
+ interface InteractiveRunResult {
280
+ contestant: InteractiveProcessResult;
281
+ interactor: InteractiveProcessResult;
282
+ contestantToInteractor: string;
283
+ interactorToContestant: string;
284
+ durationMs: number;
285
+ determinism: DeterminismConfig;
286
+ }
287
+ type WorkerPhase = "initializing" | "restoring-cache" | "loading-toolchain" | "checking" | "compiling" | "linking" | "packaging" | "running";
288
+ interface WorkerProgress {
289
+ phase: WorkerPhase;
290
+ label: string;
291
+ progress?: number;
292
+ }
293
+ /** Content-pinned host extension loaded inside the browser runner Worker. */
294
+ interface BrowserRuntimeDriverPlugin {
295
+ /** Stable host-selected identity; the constructed RuntimeDriver must use the same ID. */
296
+ id: string;
297
+ /** Same-origin URL of one self-contained ESM module. */
298
+ moduleUrl: string;
299
+ /** Lowercase SHA-256 of the exact ESM source bytes. */
300
+ sha256: string;
301
+ /** Named factory export. Defaults to `createRuntimeDriver`. */
302
+ exportName?: string;
303
+ }
304
+ interface ToolchainProfile {
305
+ language: Language;
306
+ target: TargetAbi;
307
+ optimization: OptimizationLevel;
308
+ }
309
+ interface ToolchainAssetDescriptor {
310
+ /** Logical filename expected by the compiler/runtime implementation. */
311
+ path: string;
312
+ bytes: number;
313
+ sha256: string;
314
+ /** Exact package export used by deployment tooling. */
315
+ exportPath: string;
316
+ }
317
+ interface ToolchainDescriptor {
318
+ schema: typeof WASM_OJ_SCHEMAS.toolchainPackage;
319
+ id: string;
320
+ version: string;
321
+ wasmOjContract: typeof WASM_OJ_CONTRACT_VERSION;
322
+ languages: readonly Language[];
323
+ profiles: readonly ToolchainProfile[];
324
+ assets: readonly ToolchainAssetDescriptor[];
325
+ }
326
+ interface BrowserToolchainSource {
327
+ kind: "browser";
328
+ descriptor: ToolchainDescriptor;
329
+ baseUrl: string;
330
+ }
331
+ interface ServerToolchainSource {
332
+ kind: "server";
333
+ descriptor: ToolchainDescriptor;
334
+ directory: URL;
335
+ }
336
+ type ToolchainSource = BrowserToolchainSource | ServerToolchainSource;
337
+ type CompilerTraceOperation = "workerInitialize" | "toolchainFetch" | "toolchainDecode" | "toolchainLoad" | "filesystemPrepare" | "commandStart" | "commandWait" | "projectCompile" | "runtimeShimCompile" | "link" | "projectSpawn" | "projectWait" | "runtimeShimSpawn" | "runtimeShimWait" | "linkSpawn" | "linkWait" | "projectOutputReady" | "runtimeShimOutputReady" | "linkOutputReady" | "artifactReadback";
338
+ /** Host-observed compiler timing mark; excluded from deterministic contracts and cache keys. */
339
+ interface CompilerTraceEvent {
340
+ schema: typeof WASM_OJ_SCHEMAS.compileTrace;
341
+ operation: CompilerTraceOperation;
342
+ state: "start" | "end";
343
+ monotonicMs: number;
344
+ }
345
+ type CompilerRequest = {
346
+ type: "initialize";
347
+ requestId: string;
348
+ toolchains: readonly BrowserToolchainSource[];
349
+ } | {
350
+ type: "build";
351
+ requestId: string;
352
+ project: Project;
353
+ cacheKey: string;
354
+ } | {
355
+ type: "quiesce";
356
+ requestId: string;
357
+ };
358
+ type RunnerRequest = {
359
+ type: "initialize";
360
+ requestId: string;
361
+ toolchains: readonly BrowserToolchainSource[];
362
+ additionalCostBaselines?: Readonly<Record<string, number>>;
363
+ runtimeDriverPlugins?: readonly BrowserRuntimeDriverPlugin[];
364
+ } | {
365
+ type: "run";
366
+ requestId: string;
367
+ artifact: BuildArtifact;
368
+ config: RunConfig;
369
+ } | {
370
+ type: "interact";
371
+ requestId: string;
372
+ contestant: BuildArtifact;
373
+ interactor: BuildArtifact;
374
+ config: InteractiveRunConfig;
375
+ } | {
376
+ type: "clear-runtime-cache";
377
+ requestId: string;
378
+ };
379
+ type CompilerResponse = {
380
+ type: "ready";
381
+ requestId: string;
382
+ } | {
383
+ type: "quiesced";
384
+ requestId: string;
385
+ } | {
386
+ type: "progress";
387
+ requestId: string;
388
+ progress: WorkerProgress;
389
+ } | {
390
+ type: "compile-trace";
391
+ requestId: string;
392
+ event: CompilerTraceEvent;
393
+ } | {
394
+ type: "build-result";
395
+ requestId: string;
396
+ result: BuildResult;
397
+ } | {
398
+ type: "error";
399
+ requestId: string;
400
+ code: string;
401
+ message: string;
402
+ stack?: string;
403
+ };
404
+ type RunnerResponse = {
405
+ type: "ready";
406
+ requestId: string;
407
+ } | {
408
+ type: "progress";
409
+ requestId: string;
410
+ progress: WorkerProgress;
411
+ } | {
412
+ type: "stream";
413
+ requestId: string;
414
+ stream: "stdout" | "stderr";
415
+ chunk: string;
416
+ } | {
417
+ type: "run-result";
418
+ requestId: string;
419
+ result: RunResult;
420
+ } | {
421
+ type: "interactive-result";
422
+ requestId: string;
423
+ result: InteractiveRunResult;
424
+ } | {
425
+ type: "runtime-cache-cleared";
426
+ requestId: string;
427
+ } | {
428
+ type: "error";
429
+ requestId: string;
430
+ code: string;
431
+ message: string;
432
+ stack?: string;
433
+ };
434
+
435
+ declare const WASM_OJ_ERROR_CODES: readonly ["operation-cancelled", "operation-conflict", "invalid-input", "unsupported", "integrity-failure", "compiler-failure", "runner-failure", "judge-failure", "replay-failure", "dependency-failure", "storage-failure", "initialization-failure", "disposed", "internal-failure"];
436
+ type WasmOjErrorCode = (typeof WASM_OJ_ERROR_CODES)[number];
437
+ declare const WASM_OJ_ERROR_STAGES: readonly ["operation", "compile", "prepare", "run", "judge", "replay", "dependency", "storage", "initialize"];
438
+ type WasmOjErrorStage = (typeof WASM_OJ_ERROR_STAGES)[number];
439
+ interface WasmOjErrorOptions extends ErrorOptions {
440
+ code: WasmOjErrorCode;
441
+ stage: WasmOjErrorStage;
442
+ retryable?: boolean;
443
+ operationId?: string;
444
+ details?: Readonly<Record<string, string | number | boolean | null>>;
445
+ }
446
+ interface WasmOjErrorRecord {
447
+ name: "WasmOjError";
448
+ message: string;
449
+ code: WasmOjErrorCode;
450
+ stage: WasmOjErrorStage;
451
+ retryable: boolean;
452
+ operationId?: string;
453
+ details?: Readonly<Record<string, string | number | boolean | null>>;
454
+ }
455
+ /** Stable infrastructure failure exposed at public asynchronous boundaries. */
456
+ declare class WasmOjError extends Error {
457
+ readonly code: WasmOjErrorCode;
458
+ readonly stage: WasmOjErrorStage;
459
+ readonly retryable: boolean;
460
+ readonly operationId?: string;
461
+ readonly details?: Readonly<Record<string, string | number | boolean | null>>;
462
+ constructor(message: string, options: WasmOjErrorOptions);
463
+ toJSON(): WasmOjErrorRecord;
464
+ }
465
+ declare function asWasmOjError(error: unknown, options: Omit<WasmOjErrorOptions, "cause">): WasmOjError;
466
+
467
+ export { DEPENDENCY_ECOSYSTEMS, LANGUAGES, WASM_OJ_CONTRACT_ID, WASM_OJ_CONTRACT_VERSION, WASM_OJ_ERROR_CODES, WASM_OJ_ERROR_STAGES, WASM_OJ_SCHEMAS, WASM_OJ_STORAGE, WasmOjError, asWasmOjError, assertLanguageIdentifier, isBuiltinLanguage };
468
+ export type { ArtifactMetadata, BrowserRuntimeDriverPlugin, BrowserToolchainSource, BuildArtifact, BuildConfig, BuildResult, BuiltinLanguage, CompilerRequest, CompilerResponse, CompilerTraceEvent, CompilerTraceOperation, DependencyBuildBundle, DependencyEcosystem, DependencyLock, DependencyManifest, DependencyRequirement, DependencySourceFile, DeterminismConfig, Diagnostic, DiagnosticSeverity, ExecutionMetrics, ExecutionTermination, InteractiveProcessResult, InteractiveProgramConfig, InteractiveRunConfig, InteractiveRunResult, Language, LockedDependencyPackage, MaterializedDependencyPackage, OptimizationLevel, Project, ProjectConfig, ProjectFile, ResourcePolicy, RunConfig, RunResult, RunnerRequest, RunnerResponse, RuntimeBundleArtifact, ServerToolchainSource, TargetAbi, ToolchainAssetDescriptor, ToolchainDescriptor, ToolchainProfile, ToolchainSource, WasmArtifact, WasmOjErrorCode, WasmOjErrorOptions, WasmOjErrorRecord, WasmOjErrorStage, WorkerPhase, WorkerProgress };
package/dist/index.js ADDED
@@ -0,0 +1,166 @@
1
+ //#region src/core/contract.ts
2
+ /**
3
+ * The single compatibility boundary shared by WASM-OJ compilers, runners,
4
+ * artifacts, judge specifications, caches, and conformance evidence.
5
+ *
6
+ * Package and upstream toolchain versions remain independent release metadata;
7
+ * they do not define WASM-OJ protocol compatibility.
8
+ */
9
+ var WASM_OJ_CONTRACT_VERSION = 2;
10
+ var WASM_OJ_CONTRACT_ID = `wasm-oj-v2`;
11
+ var WASM_OJ_SCHEMAS = Object.freeze({
12
+ clangPins: `${WASM_OJ_CONTRACT_ID}/clang-pins`,
13
+ clangLibcxxPch: `${WASM_OJ_CONTRACT_ID}/clang-libcxx-pch`,
14
+ clangToolchain: `${WASM_OJ_CONTRACT_ID}/clang-toolchain`,
15
+ compileBatch: `${WASM_OJ_CONTRACT_ID}/compile-batch`,
16
+ compileTrace: `${WASM_OJ_CONTRACT_ID}/compile-trace`,
17
+ conformance: `${WASM_OJ_CONTRACT_ID}/conformance`,
18
+ conformanceEvidence: `${WASM_OJ_CONTRACT_ID}/conformance-evidence`,
19
+ conformanceMatrix: `${WASM_OJ_CONTRACT_ID}/conformance-matrix`,
20
+ cppDependencyLock: `${WASM_OJ_CONTRACT_ID}/cpp-dependency-lock`,
21
+ dependencyLock: `${WASM_OJ_CONTRACT_ID}/dependency-lock`,
22
+ dependencyOfflineBundle: `${WASM_OJ_CONTRACT_ID}/dependency-offline-bundle`,
23
+ incrementalBuildGraph: `${WASM_OJ_CONTRACT_ID}/incremental-build-graph`,
24
+ interactiveRequest: `${WASM_OJ_CONTRACT_ID}/interactive-request`,
25
+ goToolchain: `${WASM_OJ_CONTRACT_ID}/go-toolchain`,
26
+ objectCache: `${WASM_OJ_CONTRACT_ID}/object-cache`,
27
+ pythonToolchain: `${WASM_OJ_CONTRACT_ID}/python-toolchain`,
28
+ replayBundle: `${WASM_OJ_CONTRACT_ID}/replay-bundle`,
29
+ releaseManifest: `${WASM_OJ_CONTRACT_ID}/release-manifest`,
30
+ rustToolchain: `${WASM_OJ_CONTRACT_ID}/rust-toolchain`,
31
+ runRequest: `${WASM_OJ_CONTRACT_ID}/run-request`,
32
+ runtimeBundle: `${WASM_OJ_CONTRACT_ID}/runtime-bundle`,
33
+ runtimeCoreLicenses: `${WASM_OJ_CONTRACT_ID}/runtime-core-licenses`,
34
+ thirdPartyComponents: `${WASM_OJ_CONTRACT_ID}/third-party-components`,
35
+ wasmerSdkLicenses: `${WASM_OJ_CONTRACT_ID}/wasmer-sdk-licenses`,
36
+ toolchainPackage: `${WASM_OJ_CONTRACT_ID}/toolchain-package`
37
+ });
38
+ var WASM_OJ_STORAGE = Object.freeze({
39
+ database: `${WASM_OJ_CONTRACT_ID}:storage`,
40
+ databaseVersion: 2,
41
+ dependencyCache: `${WASM_OJ_CONTRACT_ID}:dependencies`,
42
+ incrementalBuildCache: `${WASM_OJ_CONTRACT_ID}:incremental-build-cache`,
43
+ runtimeFilesCache: `${WASM_OJ_CONTRACT_ID}:runtime-files`,
44
+ toolchainCache: `${WASM_OJ_CONTRACT_ID}:toolchains`
45
+ });
46
+ //#endregion
47
+ //#region src/core/types.ts
48
+ var LANGUAGES = Object.freeze([
49
+ "c",
50
+ "cpp",
51
+ "rust",
52
+ "python",
53
+ "javascript",
54
+ "typescript",
55
+ "go"
56
+ ]);
57
+ function assertLanguageIdentifier(language) {
58
+ if (typeof language !== "string" || !language || language !== language.trim() || language.length > 128) throw new Error("Language identifiers must be non-empty, trimmed, and at most 128 characters.");
59
+ }
60
+ function isBuiltinLanguage(language) {
61
+ return LANGUAGES.includes(language);
62
+ }
63
+ var DEPENDENCY_ECOSYSTEMS = Object.freeze([
64
+ "cargo",
65
+ "npm",
66
+ "pypi",
67
+ "go",
68
+ "cpp"
69
+ ]);
70
+ //#endregion
71
+ //#region src/core/errors.ts
72
+ var WASM_OJ_ERROR_CODES = Object.freeze([
73
+ "operation-cancelled",
74
+ "operation-conflict",
75
+ "invalid-input",
76
+ "unsupported",
77
+ "integrity-failure",
78
+ "compiler-failure",
79
+ "runner-failure",
80
+ "judge-failure",
81
+ "replay-failure",
82
+ "dependency-failure",
83
+ "storage-failure",
84
+ "initialization-failure",
85
+ "disposed",
86
+ "internal-failure"
87
+ ]);
88
+ var WASM_OJ_ERROR_STAGES = Object.freeze([
89
+ "operation",
90
+ "compile",
91
+ "prepare",
92
+ "run",
93
+ "judge",
94
+ "replay",
95
+ "dependency",
96
+ "storage",
97
+ "initialize"
98
+ ]);
99
+ /** Stable infrastructure failure exposed at public asynchronous boundaries. */
100
+ var WasmOjError = class extends Error {
101
+ code;
102
+ stage;
103
+ retryable;
104
+ operationId;
105
+ details;
106
+ constructor(message, options) {
107
+ super(message, options);
108
+ if (!WASM_OJ_ERROR_CODES.includes(options.code)) throw new TypeError(`Invalid WASM-OJ error code '${String(options.code)}'.`);
109
+ if (!WASM_OJ_ERROR_STAGES.includes(options.stage)) throw new TypeError(`Invalid WASM-OJ error stage '${String(options.stage)}'.`);
110
+ if (options.retryable !== void 0 && typeof options.retryable !== "boolean") throw new TypeError("WASM-OJ error retryable must be a boolean.");
111
+ if (options.operationId !== void 0 && (typeof options.operationId !== "string" || !options.operationId || options.operationId !== options.operationId.trim() || options.operationId.length > 128)) throw new TypeError("WASM-OJ error operationId must be non-empty, trimmed, and at most 128 characters.");
112
+ this.name = "WasmOjError";
113
+ this.code = options.code;
114
+ this.stage = options.stage;
115
+ this.retryable = options.retryable ?? false;
116
+ this.operationId = options.operationId;
117
+ this.details = validatedDetails(options.details);
118
+ }
119
+ toJSON() {
120
+ return {
121
+ name: "WasmOjError",
122
+ message: this.message,
123
+ code: this.code,
124
+ stage: this.stage,
125
+ retryable: this.retryable,
126
+ ...this.operationId === void 0 ? {} : { operationId: this.operationId },
127
+ ...this.details === void 0 ? {} : { details: { ...this.details } }
128
+ };
129
+ }
130
+ };
131
+ function validatedDetails(value) {
132
+ if (value === void 0) return void 0;
133
+ if (value === null || typeof value !== "object" || Array.isArray(value)) throw new TypeError("WASM-OJ error details must be a plain object.");
134
+ const prototype = Object.getPrototypeOf(value);
135
+ if (prototype !== Object.prototype && prototype !== null) throw new TypeError("WASM-OJ error details must be a plain object.");
136
+ const entries = Object.entries(value);
137
+ if (entries.length > 32) throw new RangeError("WASM-OJ error details may contain at most 32 entries.");
138
+ const details = {};
139
+ for (const [key, detail] of entries) {
140
+ if (!key || key !== key.trim() || key.length > 128) throw new TypeError("WASM-OJ error detail keys must be non-empty, trimmed, and at most 128 characters.");
141
+ if (typeof detail === "string" && detail.length <= 4096) details[key] = detail;
142
+ else if (typeof detail === "number" && Number.isFinite(detail)) details[key] = detail;
143
+ else if (typeof detail === "boolean" || detail === null) details[key] = detail;
144
+ else throw new TypeError(`WASM-OJ error detail '${key}' has an unsupported value.`);
145
+ }
146
+ return Object.freeze(details);
147
+ }
148
+ function asWasmOjError(error, options) {
149
+ if (error instanceof WasmOjError) {
150
+ if (error.operationId !== void 0 || options.operationId === void 0) return error;
151
+ return new WasmOjError(error.message, {
152
+ code: error.code,
153
+ stage: error.stage,
154
+ retryable: error.retryable,
155
+ operationId: options.operationId,
156
+ details: error.details,
157
+ cause: error
158
+ });
159
+ }
160
+ return new WasmOjError(error instanceof Error ? error.message : String(error), {
161
+ ...options,
162
+ cause: error
163
+ });
164
+ }
165
+ //#endregion
166
+ export { DEPENDENCY_ECOSYSTEMS, LANGUAGES, WASM_OJ_CONTRACT_ID, WASM_OJ_CONTRACT_VERSION, WASM_OJ_ERROR_CODES, WASM_OJ_ERROR_STAGES, WASM_OJ_SCHEMAS, WASM_OJ_STORAGE, WasmOjError, asWasmOjError, assertLanguageIdentifier, isBuiltinLanguage };
package/package.json ADDED
@@ -0,0 +1,46 @@
1
+ {
2
+ "name": "@wasm-oj/contracts",
3
+ "version": "0.2.0",
4
+ "description": "Environment-neutral contracts and wire types for the WASM-OJ SDK.",
5
+ "license": "MIT",
6
+ "author": "JacobLinCool",
7
+ "repository": {
8
+ "type": "git",
9
+ "url": "git+https://github.com/wasm-oj/forge.git",
10
+ "directory": "packages/contracts"
11
+ },
12
+ "homepage": "https://github.com/wasm-oj/forge#readme",
13
+ "bugs": {
14
+ "url": "https://github.com/wasm-oj/forge/issues"
15
+ },
16
+ "keywords": [
17
+ "online-judge",
18
+ "wasi",
19
+ "wasm"
20
+ ],
21
+ "publishConfig": {
22
+ "access": "public",
23
+ "registry": "https://registry.npmjs.org/"
24
+ },
25
+ "type": "module",
26
+ "sideEffects": false,
27
+ "types": "./dist/index.d.ts",
28
+ "exports": {
29
+ ".": {
30
+ "types": "./dist/index.d.ts",
31
+ "import": "./dist/index.js"
32
+ },
33
+ "./package.json": "./package.json"
34
+ },
35
+ "files": [
36
+ "dist",
37
+ "README.md",
38
+ "LICENSE"
39
+ ],
40
+ "engines": {
41
+ "node": ">=24.18.0 <25"
42
+ },
43
+ "scripts": {
44
+ "build": "node ../../scripts/build-library.mjs --package @wasm-oj/contracts"
45
+ }
46
+ }