@ontrails/core 1.0.0-beta.39 → 1.0.0-beta.41

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.
@@ -17,7 +17,13 @@ type ExampleBearingSchema<TSchema extends z.ZodType> = TSchema & {
17
17
 
18
18
  interface IngestBaseOptions<TSchema extends z.ZodType, TSignal> extends Omit<
19
19
  TrailSpec<SchemaValue<TSchema>, void>,
20
- 'blaze' | 'examples' | 'fires' | 'input' | 'intent' | 'output' | 'pattern'
20
+ | 'implementation'
21
+ | 'examples'
22
+ | 'fires'
23
+ | 'input'
24
+ | 'intent'
25
+ | 'output'
26
+ | 'pattern'
21
27
  > {
22
28
  /** Override the derived trail id. Defaults to `${signal}.ingest`. */
23
29
  readonly id?: string | undefined;
@@ -63,7 +69,7 @@ const deriveExamples = <TSchema extends z.ZodType>(
63
69
  );
64
70
  };
65
71
 
66
- const createIngestBlaze =
72
+ const createIngestImplementation =
67
73
  <TSchema extends z.ZodType, TSignal>(
68
74
  signalRef: Signal<TSignal>,
69
75
  signalId: string,
@@ -108,7 +114,7 @@ export const ingest = <
108
114
  const signalId = options.signal.id;
109
115
  const id = options.id ?? `${signalId}.ingest`;
110
116
  const { id: _id, schema, signal, transform, verify, ...trailSpec } = options;
111
- const baseBlaze = createIngestBlaze<TSchema, TSignal>(
117
+ const baseImplementation = createIngestImplementation<TSchema, TSignal>(
112
118
  signal,
113
119
  signalId,
114
120
  id,
@@ -116,9 +122,12 @@ export const ingest = <
116
122
  );
117
123
  const baseSpec = {
118
124
  ...trailSpec,
119
- blaze: baseBlaze as TrailSpec<unknown, unknown>['blaze'],
120
125
  examples: deriveExamples(schema as ExampleBearingSchema<TSchema>, signalId),
121
126
  fires: [signal],
127
+ implementation: baseImplementation as TrailSpec<
128
+ unknown,
129
+ unknown
130
+ >['implementation'],
122
131
  input: schema as z.ZodType<unknown>,
123
132
  intent: 'write',
124
133
  output: z.void(),
@@ -134,6 +143,10 @@ export const ingest = <
134
143
  // mutating runner-wide layer configuration.
135
144
  return Object.freeze({
136
145
  ...baseTrail,
137
- blaze: composeLayers([verify], baseTrail, baseTrail.blaze),
146
+ implementation: composeLayers(
147
+ [verify],
148
+ baseTrail,
149
+ baseTrail.implementation
150
+ ),
138
151
  }) as Trail<SchemaValue<TSchema>, void>;
139
152
  };
package/src/trails-db.ts CHANGED
@@ -6,7 +6,7 @@ import { sha256Hex } from './sha256.js';
6
6
 
7
7
  // Altitude ruling (TRL-1198, ADR-0051 lens): trails-db stays core-owned
8
8
  // shared framework infrastructure (ADR-0014) and stays on the barrel —
9
- // topographer, tracing, warden, wayfinder, and the operator app all
9
+ // topography, tracing, warden, wayfinder, and the operator app all
10
10
  // consume it from `@ontrails/core`. What it may NOT do is assume runtime
11
11
  // capabilities eagerly: `bun:sqlite` and the node builtins load lazily at
12
12
  // first use so the barrel's module graph stays execution-portable.
package/src/type-utils.ts CHANGED
@@ -42,7 +42,7 @@ export type TrailInput<T extends AnyTrail> = T extends {
42
42
 
43
43
  /** Extract the output type from a Trail. */
44
44
  export type TrailOutput<T extends AnyTrail> = T extends {
45
- readonly blaze: Implementation<any, infer O>;
45
+ readonly implementation: Implementation<any, infer O>;
46
46
  }
47
47
  ? O
48
48
  : never;
package/src/types.ts CHANGED
@@ -11,7 +11,7 @@ import type { TrailVersionReference } from './version-resolution.js';
11
11
  // Detour
12
12
  // ---------------------------------------------------------------------------
13
13
 
14
- /** A recovery path that activates when a trail's blaze fails with a matching error. */
14
+ /** A recovery path that activates when a trail's implementation fails with a matching error. */
15
15
  export interface Detour<Input, Output, TErr extends TrailsError = TrailsError> {
16
16
  /* oxlint-disable-next-line no-explicit-any -- standard pattern for matching abstract+concrete class constructors */
17
17
  readonly on: abstract new (...args: any[]) => TErr;
@@ -69,7 +69,7 @@ export interface ComposeOptions {
69
69
  * Execute a specific live version of the composed trail.
70
70
  *
71
71
  * Omit to keep composition current by default. Historical revision entries
72
- * transpose through the current trail; fork entries run their own blaze.
72
+ * transpose through the current trail; fork entries run their own implementation.
73
73
  */
74
74
  readonly version?: TrailVersionReference | undefined;
75
75
  }
@@ -277,7 +277,7 @@ export interface TrailContext {
277
277
  readonly trace?: TraceFn | undefined;
278
278
  }
279
279
 
280
- /** Trail context for blazes that declare trail composition. */
280
+ /** Trail context for implementations that declare trail composition. */
281
281
  export interface ComposeTrailContext extends TrailContext {
282
282
  readonly compose: ComposeFn;
283
283
  }
@@ -12,6 +12,7 @@ const PROJECTION_BLOCKING_RULES = new Set([
12
12
  'activation-source-definition-unique',
13
13
  'activation-source-edge-unique',
14
14
  'activation-source-kind-known',
15
+ 'activation-queue-valid',
15
16
  'activation-schedule-valid',
16
17
  'resource-exists',
17
18
  'signal-fire-exists',
@@ -19,6 +20,11 @@ const PROJECTION_BLOCKING_RULES = new Set([
19
20
  'signal-origin-exists',
20
21
  ]);
21
22
 
23
+ const isProjectionBlockingIssue = (issue: TopoDiagnostic): boolean =>
24
+ PROJECTION_BLOCKING_RULES.has(issue.rule) ||
25
+ (issue.rule === 'activation-source-input-compatible' &&
26
+ issue.sourceKind === 'queue');
27
+
22
28
  const keepProjectionBlockingIssues = (
23
29
  result: ReturnType<typeof validateTopo>
24
30
  ) => {
@@ -29,9 +35,7 @@ const keepProjectionBlockingIssues = (
29
35
  const issues = (
30
36
  result.error.context as { issues?: readonly TopoDiagnostic[] } | undefined
31
37
  )?.issues;
32
- const remainingIssues = issues?.filter((issue) =>
33
- PROJECTION_BLOCKING_RULES.has(issue.rule)
34
- );
38
+ const remainingIssues = issues?.filter(isProjectionBlockingIssue);
35
39
 
36
40
  if (remainingIssues === undefined || remainingIssues.length === 0) {
37
41
  return Result.ok();
@@ -12,12 +12,13 @@ import {
12
12
  activationSourceDeclarationSignature,
13
13
  activationSourceKey,
14
14
  } from './activation-source-projection.js';
15
- import type { AnyContour } from './contour.js';
16
- import { getContourReferences } from './contour.js';
15
+ import type { AnyEntity } from './entity.js';
16
+ import { getEntityReferences } from './entity.js';
17
17
  import { ValidationError } from './errors.js';
18
18
  import type { ActivationEntry } from './activation-source.js';
19
19
  import { isKnownActivationSourceKind } from './activation-source.js';
20
20
  import { isDraftId } from './draft.js';
21
+ import { validateQueueSource } from './queue.js';
21
22
  import type { AnySignal } from './signal.js';
22
23
  import { validateScheduleSource } from './schedule.js';
23
24
  import { Result } from './result.js';
@@ -38,14 +39,14 @@ export type TopoDiagnosticCode = 'topo.missing-reference';
38
39
 
39
40
  export type TopoReferenceKind =
40
41
  | 'compose'
41
- | 'contour-reference'
42
+ | 'entity-reference'
42
43
  | 'resource'
43
44
  | 'signal-fire'
44
45
  | 'signal-on'
45
46
  | 'signal-origin';
46
47
 
47
48
  export type TopoReferenceOwnerKind =
48
- | 'contour'
49
+ | 'entity'
49
50
  | 'signal'
50
51
  | 'trail'
51
52
  | 'trail-version';
@@ -526,6 +527,21 @@ const checkActivationSources = (
526
527
  }
527
528
  }
528
529
 
530
+ const queueIssues = validateQueueSource(activation.source);
531
+ for (const issue of queueIssues) {
532
+ issues.push({
533
+ inputPath: [issue.field],
534
+ message: `Trail declares queue source "${activation.source.id}" with invalid ${issue.field}: ${issue.message}`,
535
+ rule: 'activation-queue-valid',
536
+ schemaIssues: [
537
+ { code: issue.field, message: issue.message, path: [issue.field] },
538
+ ],
539
+ sourceId: activation.source.id,
540
+ sourceKind: activation.source.kind,
541
+ trailId: id,
542
+ });
543
+ }
544
+
529
545
  const scheduleIssues = validateScheduleSource(activation.source);
530
546
  for (const issue of scheduleIssues) {
531
547
  issues.push({
@@ -626,25 +642,25 @@ const checkActivationSourceInputCompatibility = (
626
642
  return issues;
627
643
  };
628
644
 
629
- const checkContourReferences = (
630
- contours: ReadonlyMap<string, AnyContour>,
645
+ const checkEntityReferences = (
646
+ entities: ReadonlyMap<string, AnyEntity>,
631
647
  topo: Topo
632
648
  ): TopoDiagnostic[] => {
633
649
  const issues: TopoDiagnostic[] = [];
634
650
 
635
- for (const [name, contourDef] of contours) {
636
- for (const ref of getContourReferences(contourDef)) {
637
- if (!topo.hasContour(ref.contour) && !isDraftId(ref.contour)) {
651
+ for (const [name, entityDef] of entities) {
652
+ for (const ref of getEntityReferences(entityDef)) {
653
+ if (!topo.hasEntity(ref.entity) && !isDraftId(ref.entity)) {
638
654
  issues.push(
639
655
  missingReferenceDiagnostic({
640
- message: `Contour "${name}" references "${ref.contour}" which is not in the topo`,
656
+ message: `Entity "${name}" references "${ref.entity}" which is not in the topo`,
641
657
  reference: {
642
658
  fromId: name,
643
- fromKind: 'contour',
644
- missingId: ref.contour,
645
- referenceKind: 'contour-reference',
659
+ fromKind: 'entity',
660
+ missingId: ref.entity,
661
+ referenceKind: 'entity-reference',
646
662
  },
647
- rule: 'contour-reference-exists',
663
+ rule: 'entity-reference-exists',
648
664
  trailId: name,
649
665
  })
650
666
  );
@@ -686,7 +702,7 @@ export const validateTopo = (topo: Topo): Result<void, ValidationError> => {
686
702
  const issues = [
687
703
  ...checkComposes(topo.trails, topo),
688
704
  ...checkResources(topo.trails, topo),
689
- ...checkContourReferences(topo.contours, topo),
705
+ ...checkEntityReferences(topo.entities, topo),
690
706
  ...checkExamples(topo.trails),
691
707
  ...checkSignalOrigins(topo.signals, topo),
692
708
  ...checkSignalReferences(topo.trails, topo.signals),