@openprose/reactor-cradle 0.1.0-rc.1

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.
Files changed (90) hide show
  1. package/LICENSE +21 -0
  2. package/README.md +270 -0
  3. package/dist/assert/index.d.ts +35 -0
  4. package/dist/assert/index.d.ts.map +1 -0
  5. package/dist/assert/index.js +398 -0
  6. package/dist/baselines/cost-thesis/index.d.ts +103 -0
  7. package/dist/baselines/cost-thesis/index.d.ts.map +1 -0
  8. package/dist/baselines/cost-thesis/index.js +337 -0
  9. package/dist/baselines/naive-loop/index.d.ts +46 -0
  10. package/dist/baselines/naive-loop/index.d.ts.map +1 -0
  11. package/dist/baselines/naive-loop/index.js +188 -0
  12. package/dist/baselines/no-memo/index.d.ts +84 -0
  13. package/dist/baselines/no-memo/index.d.ts.map +1 -0
  14. package/dist/baselines/no-memo/index.js +226 -0
  15. package/dist/doubles/clock.d.ts +9 -0
  16. package/dist/doubles/clock.d.ts.map +1 -0
  17. package/dist/doubles/clock.js +42 -0
  18. package/dist/doubles/storage.d.ts +24 -0
  19. package/dist/doubles/storage.d.ts.map +1 -0
  20. package/dist/doubles/storage.js +191 -0
  21. package/dist/eval/index.d.ts +204 -0
  22. package/dist/eval/index.d.ts.map +1 -0
  23. package/dist/eval/index.js +596 -0
  24. package/dist/index.d.ts +24 -0
  25. package/dist/index.d.ts.map +1 -0
  26. package/dist/index.js +39 -0
  27. package/dist/policy-author/index.d.ts +103 -0
  28. package/dist/policy-author/index.d.ts.map +1 -0
  29. package/dist/policy-author/index.js +358 -0
  30. package/dist/policy-drift/index.d.ts +64 -0
  31. package/dist/policy-drift/index.d.ts.map +1 -0
  32. package/dist/policy-drift/index.js +495 -0
  33. package/dist/policy-replay/index.d.ts +106 -0
  34. package/dist/policy-replay/index.d.ts.map +1 -0
  35. package/dist/policy-replay/index.js +361 -0
  36. package/dist/provider-parity/index.d.ts +91 -0
  37. package/dist/provider-parity/index.d.ts.map +1 -0
  38. package/dist/provider-parity/index.js +439 -0
  39. package/dist/recompile/index.d.ts +161 -0
  40. package/dist/recompile/index.d.ts.map +1 -0
  41. package/dist/recompile/index.js +690 -0
  42. package/dist/release-candidate/index.d.ts +139 -0
  43. package/dist/release-candidate/index.d.ts.map +1 -0
  44. package/dist/release-candidate/index.js +553 -0
  45. package/dist/release-parity/index.d.ts +80 -0
  46. package/dist/release-parity/index.d.ts.map +1 -0
  47. package/dist/release-parity/index.js +1035 -0
  48. package/dist/replay/model-gateway.d.ts +25 -0
  49. package/dist/replay/model-gateway.d.ts.map +1 -0
  50. package/dist/replay/model-gateway.js +166 -0
  51. package/dist/replay/parity.d.ts +110 -0
  52. package/dist/replay/parity.d.ts.map +1 -0
  53. package/dist/replay/parity.js +232 -0
  54. package/dist/rollback/index.d.ts +106 -0
  55. package/dist/rollback/index.d.ts.map +1 -0
  56. package/dist/rollback/index.js +694 -0
  57. package/dist/scenario/parser.d.ts +11 -0
  58. package/dist/scenario/parser.d.ts.map +1 -0
  59. package/dist/scenario/parser.js +490 -0
  60. package/dist/scenario/runner.d.ts +12 -0
  61. package/dist/scenario/runner.d.ts.map +1 -0
  62. package/dist/scenario/runner.js +345 -0
  63. package/dist/scenario/synthetic-world-adapter.d.ts +4 -0
  64. package/dist/scenario/synthetic-world-adapter.d.ts.map +1 -0
  65. package/dist/scenario/synthetic-world-adapter.js +82 -0
  66. package/dist/scenario/time.d.ts +4 -0
  67. package/dist/scenario/time.d.ts.map +1 -0
  68. package/dist/scenario/time.js +45 -0
  69. package/dist/scenario/types.d.ts +149 -0
  70. package/dist/scenario/types.d.ts.map +1 -0
  71. package/dist/scenario/types.js +5 -0
  72. package/dist/spikes/index.d.ts +10 -0
  73. package/dist/spikes/index.d.ts.map +1 -0
  74. package/dist/spikes/index.js +29 -0
  75. package/dist/spikes/k1-ensemble-spread.d.ts +88 -0
  76. package/dist/spikes/k1-ensemble-spread.d.ts.map +1 -0
  77. package/dist/spikes/k1-ensemble-spread.js +396 -0
  78. package/dist/spikes/k2-policy-author.d.ts +25 -0
  79. package/dist/spikes/k2-policy-author.d.ts.map +1 -0
  80. package/dist/spikes/k2-policy-author.js +503 -0
  81. package/dist/spikes/live-refresh.d.ts +150 -0
  82. package/dist/spikes/live-refresh.d.ts.map +1 -0
  83. package/dist/spikes/live-refresh.js +511 -0
  84. package/dist/world/index.d.ts +2 -0
  85. package/dist/world/index.d.ts.map +1 -0
  86. package/dist/world/index.js +17 -0
  87. package/dist/world/synthetic-world.d.ts +104 -0
  88. package/dist/world/synthetic-world.d.ts.map +1 -0
  89. package/dist/world/synthetic-world.js +449 -0
  90. package/package.json +139 -0
@@ -0,0 +1,449 @@
1
+ "use strict";
2
+ Object.defineProperty(exports, "__esModule", { value: true });
3
+ exports.SyntheticWorldConnectorV0 = exports.STATIC_SURPRISE_PROFILE_V0 = exports.SYNTHETIC_WORLD_VERSION_V0 = exports.SYNTHETIC_WORLD_SCHEMA_V0 = void 0;
4
+ exports.createSyntheticWorldV0 = createSyntheticWorldV0;
5
+ exports.createSyntheticWorldConnectorV0 = createSyntheticWorldConnectorV0;
6
+ const node_crypto_1 = require("node:crypto");
7
+ exports.SYNTHETIC_WORLD_SCHEMA_V0 = "openprose.reactor.synthetic-world";
8
+ exports.SYNTHETIC_WORLD_VERSION_V0 = 0;
9
+ const ISO_INSTANT_PATTERN = /^\d{4}-\d{2}-\d{2}T\d{2}:\d{2}:\d{2}(?:\.\d{3})?Z$/;
10
+ exports.STATIC_SURPRISE_PROFILE_V0 = Object.freeze({ kind: "static" });
11
+ class SyntheticWorldConnectorV0 {
12
+ #profile;
13
+ #sources = new Map();
14
+ #history = [];
15
+ #asOf;
16
+ #asOfEpochMs;
17
+ constructor(input) {
18
+ const profile = cloneProfile(input.profile);
19
+ if (profile.kind === "adversarial-silent") {
20
+ throw new Error(`synthetic world surprise profile ${profile.kind} is typed but not implemented in C2`);
21
+ }
22
+ this.#profile = profile;
23
+ this.#asOfEpochMs = parseReplayableInstant(input.initial_as_of, "initial_as_of");
24
+ this.#asOf = canonicalizeInstant(input.initial_as_of, this.#asOfEpochMs);
25
+ for (const source of input.sources) {
26
+ this.#addSource(source);
27
+ }
28
+ }
29
+ read(request) {
30
+ const asOfEpochMs = parseReplayableInstant(request.as_of, "as_of");
31
+ const asOf = canonicalizeInstant(request.as_of, asOfEpochMs);
32
+ assertNotAfter(asOfEpochMs, this.#asOfEpochMs, "read as_of", "world time");
33
+ const source = this.#readSource(request.source_id);
34
+ const revision = readRevisionAt(source, asOfEpochMs, asOf);
35
+ const surprise = createZeroSurpriseReport({
36
+ profile: this.#profile.kind,
37
+ as_of: asOf,
38
+ event_index: this.#history.length,
39
+ });
40
+ const readPayload = this.#readPayload({
41
+ source,
42
+ revision,
43
+ as_of: asOf,
44
+ surprise,
45
+ });
46
+ return {
47
+ payload: deepFreezeJsonObject(readPayload),
48
+ };
49
+ }
50
+ advance(input) {
51
+ const nextEpochMs = parseReplayableInstant(input.as_of, "as_of");
52
+ const asOf = canonicalizeInstant(input.as_of, nextEpochMs);
53
+ assertNotBefore(nextEpochMs, this.#asOfEpochMs, "advance as_of", "world time");
54
+ this.#asOf = asOf;
55
+ this.#asOfEpochMs = nextEpochMs;
56
+ if (input.kind === "time") {
57
+ const advanceInput = input.event_id === undefined
58
+ ? {
59
+ kind: "time",
60
+ as_of: asOf,
61
+ }
62
+ : {
63
+ kind: "time",
64
+ as_of: asOf,
65
+ event_id: input.event_id,
66
+ };
67
+ return this.#recordAdvance(advanceInput);
68
+ }
69
+ const source = this.#readSource(input.source_id);
70
+ let materialChange = false;
71
+ if (input.payload !== undefined) {
72
+ const payload = createPayloadSnapshot(input.payload);
73
+ const current = latestRevision(source);
74
+ if (payload.canonical !== current.payload_canonical) {
75
+ materialChange = true;
76
+ assertMaterialChangeAllowed({
77
+ profile: this.#profile,
78
+ source_event_ordinal: nextSourceEventOrdinal(this.#history),
79
+ });
80
+ source.revisions.push(createSourceRevision({
81
+ material_version: current.material_version + 1,
82
+ materialized_at: asOf,
83
+ materialized_at_epoch_ms: nextEpochMs,
84
+ payload,
85
+ payload_hash: payloadContentHash(payload.canonical),
86
+ }));
87
+ }
88
+ }
89
+ const advanceInput = input.event_id === undefined
90
+ ? {
91
+ kind: "source-event",
92
+ as_of: asOf,
93
+ source_id: source.source_id,
94
+ }
95
+ : {
96
+ kind: "source-event",
97
+ as_of: asOf,
98
+ event_id: input.event_id,
99
+ source_id: source.source_id,
100
+ };
101
+ return this.#recordAdvance({
102
+ ...advanceInput,
103
+ material_change: materialChange,
104
+ });
105
+ }
106
+ currentAsOf() {
107
+ return this.#asOf;
108
+ }
109
+ history() {
110
+ return Object.freeze(this.#history.map((record) => cloneAdvanceRecord(record)));
111
+ }
112
+ #addSource(seed) {
113
+ assertNonEmptyString(seed.source_id, "source_id");
114
+ if (this.#sources.has(seed.source_id)) {
115
+ throw new Error(`duplicate synthetic world source_id ${seed.source_id}`);
116
+ }
117
+ if (seed.payload_hash !== undefined) {
118
+ assertNonEmptyString(seed.payload_hash, "payload_hash");
119
+ }
120
+ const sourceAsOfRaw = seed.materialized_at ?? this.#asOf;
121
+ const sourceEpochMs = parseReplayableInstant(sourceAsOfRaw, `source ${seed.source_id} materialized_at`);
122
+ assertNotAfter(sourceEpochMs, this.#asOfEpochMs, `source ${seed.source_id} materialized_at`, "initial_as_of");
123
+ const payload = createPayloadSnapshot(seed.payload);
124
+ const revisionBase = {
125
+ material_version: 0,
126
+ materialized_at: canonicalizeInstant(sourceAsOfRaw, sourceEpochMs),
127
+ materialized_at_epoch_ms: sourceEpochMs,
128
+ payload: payload.value,
129
+ payload_canonical: payload.canonical,
130
+ };
131
+ const revision = seed.payload_hash === undefined
132
+ ? revisionBase
133
+ : { ...revisionBase, payload_hash: seed.payload_hash };
134
+ this.#sources.set(seed.source_id, {
135
+ source_id: seed.source_id,
136
+ revisions: [revision],
137
+ });
138
+ }
139
+ #readSource(sourceId) {
140
+ assertNonEmptyString(sourceId, "source_id");
141
+ const source = this.#sources.get(sourceId);
142
+ if (source === undefined) {
143
+ throw new Error(`unknown synthetic world source_id ${sourceId}`);
144
+ }
145
+ return source;
146
+ }
147
+ #recordAdvance(input) {
148
+ const eventIndex = this.#history.length;
149
+ const eventId = input.event_id ?? `synthetic-world-event-${eventIndex}`;
150
+ assertNonEmptyString(eventId, "event_id");
151
+ const surpriseEvents = createSurpriseEvents({
152
+ profile: this.#profile.kind,
153
+ as_of: input.as_of,
154
+ event_id: eventId,
155
+ material_change: input.material_change ?? false,
156
+ ...(input.source_id === undefined ? {} : { source_id: input.source_id }),
157
+ });
158
+ const base = {
159
+ kind: input.kind,
160
+ event_id: eventId,
161
+ event_index: eventIndex,
162
+ as_of: input.as_of,
163
+ surprise: createSurpriseReport({
164
+ profile: this.#profile.kind,
165
+ as_of: input.as_of,
166
+ event_index: eventIndex,
167
+ surprise_events: surpriseEvents,
168
+ }),
169
+ };
170
+ const record = input.source_id === undefined
171
+ ? base
172
+ : { ...base, source_id: input.source_id };
173
+ this.#history.push(record);
174
+ return cloneAdvanceRecord(record);
175
+ }
176
+ #readPayload(input) {
177
+ const base = {
178
+ schema: exports.SYNTHETIC_WORLD_SCHEMA_V0,
179
+ v: exports.SYNTHETIC_WORLD_VERSION_V0,
180
+ profile: this.#profile.kind,
181
+ source_id: input.source.source_id,
182
+ as_of: input.as_of,
183
+ materialized_at: input.revision.materialized_at,
184
+ material_version: input.revision.material_version,
185
+ state: cloneJsonValue(input.revision.payload),
186
+ surprise: input.surprise,
187
+ };
188
+ return input.revision.payload_hash === undefined
189
+ ? base
190
+ : {
191
+ ...base,
192
+ payload_hash: input.revision.payload_hash,
193
+ };
194
+ }
195
+ }
196
+ exports.SyntheticWorldConnectorV0 = SyntheticWorldConnectorV0;
197
+ function createSyntheticWorldV0(input) {
198
+ return new SyntheticWorldConnectorV0({
199
+ initial_as_of: input.initial_instant,
200
+ profile: normalizeProfile(input.profile),
201
+ sources: input.sources.map((source) => normalizeCreateSource(source)),
202
+ });
203
+ }
204
+ function createSyntheticWorldConnectorV0(input) {
205
+ if (input instanceof SyntheticWorldConnectorV0) {
206
+ return input;
207
+ }
208
+ return new SyntheticWorldConnectorV0(input);
209
+ }
210
+ function normalizeProfile(profile) {
211
+ if (typeof profile !== "string") {
212
+ return profile;
213
+ }
214
+ switch (profile) {
215
+ case "static":
216
+ return exports.STATIC_SURPRISE_PROFILE_V0;
217
+ case "periodic-surprise":
218
+ throw new Error("periodic-surprise profile requires an explicit every_events config");
219
+ case "adversarial-silent":
220
+ throw new Error("adversarial-silent profile requires an explicit silent_after_events config");
221
+ }
222
+ }
223
+ function normalizeCreateSource(source) {
224
+ const base = {
225
+ source_id: source.id,
226
+ payload: source.payload,
227
+ };
228
+ const withPayloadHash = source.payload_hash === undefined
229
+ ? base
230
+ : { ...base, payload_hash: source.payload_hash };
231
+ return source.materialized_at === undefined
232
+ ? withPayloadHash
233
+ : { ...withPayloadHash, materialized_at: source.materialized_at };
234
+ }
235
+ function createZeroSurpriseReport(input) {
236
+ return createSurpriseReport({ ...input, surprise_events: [] });
237
+ }
238
+ function createSurpriseReport(input) {
239
+ return deepFreezeJsonObject({
240
+ profile: input.profile,
241
+ as_of: input.as_of,
242
+ event_index: input.event_index,
243
+ surprise_count: input.surprise_events.length,
244
+ material_change: input.surprise_events.some((event) => event.kind === "material-change"),
245
+ surprise_events: input.surprise_events.map((event) => ({ ...event })),
246
+ });
247
+ }
248
+ function createSurpriseEvents(input) {
249
+ if (!input.material_change || input.source_id === undefined) {
250
+ return [];
251
+ }
252
+ return Object.freeze([
253
+ {
254
+ kind: "material-change",
255
+ source_id: input.source_id,
256
+ as_of: input.as_of,
257
+ event_id: input.event_id,
258
+ profile: input.profile,
259
+ },
260
+ ]);
261
+ }
262
+ function cloneAdvanceRecord(record) {
263
+ const base = {
264
+ kind: record.kind,
265
+ event_id: record.event_id,
266
+ event_index: record.event_index,
267
+ as_of: record.as_of,
268
+ surprise: cloneSurpriseReport(record.surprise),
269
+ };
270
+ return Object.freeze(record.source_id === undefined
271
+ ? base
272
+ : { ...base, source_id: record.source_id });
273
+ }
274
+ function cloneSurpriseReport(report) {
275
+ return deepFreezeJsonObject({
276
+ profile: report.profile,
277
+ as_of: report.as_of,
278
+ event_index: report.event_index,
279
+ surprise_count: report.surprise_count,
280
+ material_change: report.material_change,
281
+ surprise_events: report.surprise_events.map((event) => ({ ...event })),
282
+ });
283
+ }
284
+ function readRevisionAt(source, asOfEpochMs, asOf) {
285
+ for (let index = source.revisions.length - 1; index >= 0; index -= 1) {
286
+ const revision = source.revisions[index];
287
+ if (revision !== undefined &&
288
+ revision.materialized_at_epoch_ms <= asOfEpochMs) {
289
+ return revision;
290
+ }
291
+ }
292
+ throw new Error(`source_id ${source.source_id} has no synthetic world state at ${asOf}`);
293
+ }
294
+ function latestRevision(source) {
295
+ const revision = source.revisions[source.revisions.length - 1];
296
+ if (revision === undefined) {
297
+ throw new Error(`source_id ${source.source_id} has no revisions`);
298
+ }
299
+ return revision;
300
+ }
301
+ function createSourceRevision(input) {
302
+ const base = {
303
+ material_version: input.material_version,
304
+ materialized_at: input.materialized_at,
305
+ materialized_at_epoch_ms: input.materialized_at_epoch_ms,
306
+ payload: input.payload.value,
307
+ payload_canonical: input.payload.canonical,
308
+ };
309
+ return input.payload_hash === undefined
310
+ ? base
311
+ : { ...base, payload_hash: input.payload_hash };
312
+ }
313
+ function nextSourceEventOrdinal(history) {
314
+ return history.filter((record) => record.kind === "source-event").length + 1;
315
+ }
316
+ function assertMaterialChangeAllowed(input) {
317
+ switch (input.profile.kind) {
318
+ case "static":
319
+ throw new Error("static surprise profile cannot apply material source changes");
320
+ case "periodic-surprise":
321
+ if (input.source_event_ordinal % input.profile.every_events !== 0) {
322
+ throw new Error(`periodic-surprise material changes are only allowed on every ${input.profile.every_events} source events`);
323
+ }
324
+ return;
325
+ }
326
+ }
327
+ function cloneProfile(profile) {
328
+ switch (profile.kind) {
329
+ case "static":
330
+ return exports.STATIC_SURPRISE_PROFILE_V0;
331
+ case "periodic-surprise":
332
+ if (!Number.isSafeInteger(profile.every_events) ||
333
+ profile.every_events <= 0) {
334
+ throw new RangeError("periodic-surprise every_events must be a positive safe integer");
335
+ }
336
+ return Object.freeze({
337
+ kind: "periodic-surprise",
338
+ every_events: profile.every_events,
339
+ });
340
+ case "adversarial-silent":
341
+ return Object.freeze({
342
+ kind: "adversarial-silent",
343
+ silent_after_events: Object.freeze([...profile.silent_after_events]),
344
+ });
345
+ }
346
+ }
347
+ function createPayloadSnapshot(payload) {
348
+ const canonical = renderCanonical(payload);
349
+ return {
350
+ value: cloneJsonValue(payload),
351
+ canonical,
352
+ };
353
+ }
354
+ function payloadContentHash(canonical) {
355
+ const digest = (0, node_crypto_1.createHash)("sha256").update(canonical).digest("hex");
356
+ return `sha256:${digest}`;
357
+ }
358
+ function cloneJsonValue(value) {
359
+ return deepFreezeJsonValue(JSON.parse(renderCanonical(value)));
360
+ }
361
+ function deepFreezeJsonObject(value) {
362
+ return deepFreezeJsonValue(value);
363
+ }
364
+ function deepFreezeJsonValue(value) {
365
+ if (value !== null && typeof value === "object") {
366
+ if (Array.isArray(value)) {
367
+ for (const item of value) {
368
+ deepFreezeJsonValue(item);
369
+ }
370
+ }
371
+ else {
372
+ for (const item of Object.values(value)) {
373
+ deepFreezeJsonValue(item);
374
+ }
375
+ }
376
+ Object.freeze(value);
377
+ }
378
+ return value;
379
+ }
380
+ function parseReplayableInstant(instant, label) {
381
+ if (!ISO_INSTANT_PATTERN.test(instant)) {
382
+ throw new RangeError(`${label} must be an ISO-8601 UTC instant`);
383
+ }
384
+ const epochMs = Date.parse(instant);
385
+ if (!Number.isFinite(epochMs)) {
386
+ throw new RangeError(`${label} must be a valid ISO-8601 UTC instant`);
387
+ }
388
+ const canonical = new Date(epochMs).toISOString();
389
+ if (instant !== canonical && instant !== canonical.replace(".000Z", "Z")) {
390
+ throw new RangeError(`${label} must be a valid ISO-8601 UTC instant`);
391
+ }
392
+ return epochMs;
393
+ }
394
+ function canonicalizeInstant(instant, epochMs) {
395
+ const canonical = new Date(epochMs).toISOString();
396
+ return instant === canonical ? instant : canonical;
397
+ }
398
+ function assertNotBefore(actualEpochMs, minimumEpochMs, actualLabel, minimumLabel) {
399
+ if (actualEpochMs < minimumEpochMs) {
400
+ throw new RangeError(`${actualLabel} must not be before ${minimumLabel}`);
401
+ }
402
+ }
403
+ function assertNotAfter(actualEpochMs, maximumEpochMs, actualLabel, maximumLabel) {
404
+ if (actualEpochMs > maximumEpochMs) {
405
+ throw new RangeError(`${actualLabel} must not be after ${maximumLabel}`);
406
+ }
407
+ }
408
+ function assertNonEmptyString(value, label) {
409
+ if (value.length === 0) {
410
+ throw new Error(`${label} must be non-empty`);
411
+ }
412
+ }
413
+ function renderCanonical(value) {
414
+ if (value === null) {
415
+ return "null";
416
+ }
417
+ switch (typeof value) {
418
+ case "boolean":
419
+ return value ? "true" : "false";
420
+ case "number":
421
+ if (!Number.isFinite(value)) {
422
+ throw new TypeError("Cannot canonicalize non-finite numbers");
423
+ }
424
+ return JSON.stringify(value);
425
+ case "string":
426
+ return JSON.stringify(value);
427
+ case "object":
428
+ if (Array.isArray(value)) {
429
+ return `[${value.map((item) => renderCanonical(item)).join(",")}]`;
430
+ }
431
+ return renderCanonicalObject(value);
432
+ case "undefined":
433
+ case "bigint":
434
+ case "function":
435
+ case "symbol":
436
+ throw new TypeError(`Cannot canonicalize ${typeof value}`);
437
+ }
438
+ }
439
+ function renderCanonicalObject(value) {
440
+ const fields = [];
441
+ for (const key of Object.keys(value).sort()) {
442
+ const item = value[key];
443
+ if (item === undefined) {
444
+ throw new TypeError(`Cannot canonicalize undefined field ${key}`);
445
+ }
446
+ fields.push(`${JSON.stringify(key)}:${renderCanonical(item)}`);
447
+ }
448
+ return `{${fields.join(",")}}`;
449
+ }
package/package.json ADDED
@@ -0,0 +1,139 @@
1
+ {
2
+ "name": "@openprose/reactor-cradle",
3
+ "version": "0.1.0-rc.1",
4
+ "description": "Deterministic Cradle test harness for the OpenProse Reactor.",
5
+ "type": "commonjs",
6
+ "main": "./dist/index.js",
7
+ "types": "./dist/index.d.ts",
8
+ "exports": {
9
+ ".": {
10
+ "types": "./dist/index.d.ts",
11
+ "default": "./dist/index.js"
12
+ },
13
+ "./assert": {
14
+ "types": "./dist/assert/index.d.ts",
15
+ "default": "./dist/assert/index.js"
16
+ },
17
+ "./eval": {
18
+ "types": "./dist/eval/index.d.ts",
19
+ "default": "./dist/eval/index.js"
20
+ },
21
+ "./spikes": {
22
+ "types": "./dist/spikes/index.d.ts",
23
+ "default": "./dist/spikes/index.js"
24
+ },
25
+ "./spikes/live-refresh": {
26
+ "types": "./dist/spikes/live-refresh.d.ts",
27
+ "default": "./dist/spikes/live-refresh.js"
28
+ },
29
+ "./spikes/k1-ensemble-spread": {
30
+ "types": "./dist/spikes/k1-ensemble-spread.d.ts",
31
+ "default": "./dist/spikes/k1-ensemble-spread.js"
32
+ },
33
+ "./spikes/k2-policy-author": {
34
+ "types": "./dist/spikes/k2-policy-author.d.ts",
35
+ "default": "./dist/spikes/k2-policy-author.js"
36
+ },
37
+ "./doubles/clock": {
38
+ "types": "./dist/doubles/clock.d.ts",
39
+ "default": "./dist/doubles/clock.js"
40
+ },
41
+ "./doubles/storage": {
42
+ "types": "./dist/doubles/storage.d.ts",
43
+ "default": "./dist/doubles/storage.js"
44
+ },
45
+ "./policy-author": {
46
+ "types": "./dist/policy-author/index.d.ts",
47
+ "default": "./dist/policy-author/index.js"
48
+ },
49
+ "./policy-drift": {
50
+ "types": "./dist/policy-drift/index.d.ts",
51
+ "default": "./dist/policy-drift/index.js"
52
+ },
53
+ "./policy-replay": {
54
+ "types": "./dist/policy-replay/index.d.ts",
55
+ "default": "./dist/policy-replay/index.js"
56
+ },
57
+ "./recompile": {
58
+ "types": "./dist/recompile/index.d.ts",
59
+ "default": "./dist/recompile/index.js"
60
+ },
61
+ "./release-parity": {
62
+ "types": "./dist/release-parity/index.d.ts",
63
+ "default": "./dist/release-parity/index.js"
64
+ },
65
+ "./release-candidate": {
66
+ "types": "./dist/release-candidate/index.d.ts",
67
+ "default": "./dist/release-candidate/index.js"
68
+ },
69
+ "./rollback": {
70
+ "types": "./dist/rollback/index.d.ts",
71
+ "default": "./dist/rollback/index.js"
72
+ },
73
+ "./replay/model-gateway": {
74
+ "types": "./dist/replay/model-gateway.d.ts",
75
+ "default": "./dist/replay/model-gateway.js"
76
+ },
77
+ "./replay/parity": {
78
+ "types": "./dist/replay/parity.d.ts",
79
+ "default": "./dist/replay/parity.js"
80
+ },
81
+ "./scenario/parser": {
82
+ "types": "./dist/scenario/parser.d.ts",
83
+ "default": "./dist/scenario/parser.js"
84
+ },
85
+ "./scenario/runner": {
86
+ "types": "./dist/scenario/runner.d.ts",
87
+ "default": "./dist/scenario/runner.js"
88
+ },
89
+ "./scenario/time": {
90
+ "types": "./dist/scenario/time.d.ts",
91
+ "default": "./dist/scenario/time.js"
92
+ },
93
+ "./scenario/types": {
94
+ "types": "./dist/scenario/types.d.ts",
95
+ "default": "./dist/scenario/types.js"
96
+ },
97
+ "./world": {
98
+ "types": "./dist/world/index.d.ts",
99
+ "default": "./dist/world/index.js"
100
+ }
101
+ },
102
+ "files": [
103
+ "dist/**/*.js",
104
+ "dist/**/*.d.ts",
105
+ "dist/**/*.d.ts.map",
106
+ "!dist/**/__tests__/**",
107
+ "!dist/**/*.test.js",
108
+ "!dist/**/*.test.d.ts",
109
+ "!dist/**/*.test.d.ts.map",
110
+ "README.md"
111
+ ],
112
+ "sideEffects": false,
113
+ "license": "MIT",
114
+ "repository": {
115
+ "type": "git",
116
+ "url": "git+https://github.com/openprose/prose.git",
117
+ "directory": "packages/reactor-cradle"
118
+ },
119
+ "dependencies": {
120
+ "@openprose/reactor": "0.1.0-rc.1"
121
+ },
122
+ "devDependencies": {
123
+ "@types/node": "^22.10.7",
124
+ "typescript": "^5.9.3"
125
+ },
126
+ "publishConfig": {
127
+ "access": "public",
128
+ "provenance": true
129
+ },
130
+ "engines": {
131
+ "node": ">=20.0.0"
132
+ },
133
+ "scripts": {
134
+ "build": "pnpm --dir ../.. --filter @openprose/reactor build && tsc -p tsconfig.build.json",
135
+ "typecheck": "pnpm --dir ../.. --filter @openprose/reactor build && tsc --noEmit -p tsconfig.json",
136
+ "test:runtime": "pnpm build && node --test $(find dist -name '*.test.js' -type f | sort)",
137
+ "test": "pnpm typecheck && pnpm test:runtime"
138
+ }
139
+ }