@astrale-os/kernel-dsl 0.2.0-beta.32 → 0.2.0-beta.34

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.
@@ -12,7 +12,7 @@ export { acceptDomainSchema as accept } from './admission/accept.js';
12
12
  export { decodeDomainSchema as decode, encodeDomainSchema as encode, serializeDomainSchema as serialize, } from './codec/schema.js';
13
13
  export { revisionOfDomainSchema as revision } from './canonical/revision.js';
14
14
  export { compareDependencyMeaning, compareMemberMeaning } from './compatibility/meaning.js';
15
- export type { DependencyMeaningChange, DependencyMeaningChangeKind, DependencyMeaningComparison, MeaningFingerprint, } from './compatibility/meaning.js';
15
+ export type { DependencyMeaningChange, DependencyMeaningChangeKind, DependencyMeaningComparison, DependencyMeaningLevel, MeaningFingerprint, } from './compatibility/meaning.js';
16
16
  export { header } from './codec/header.js';
17
17
  export { DOMAIN_FORMAT as FORMAT, DOMAIN_VERSION as VERSION } from './model/format.js';
18
18
  export { compile, load } from '../compiled/index.js';
@@ -4,11 +4,22 @@ import type { ClassDefinition } from '../../language/class/model/class.js';
4
4
  import type { PolicyDefinition } from '../../language/policy/model/policy.js';
5
5
  import type { JsonSchema } from '../../language/value/model/schema.js';
6
6
  import type { DomainSchemaIR } from '../model/schema.js';
7
+ /**
8
+ * Where one schema references a Definition. `extends` and `core` mean the schema inherits from or
9
+ * instantiates the Definition; every other site only refers to it.
10
+ */
11
+ export type ReferenceSite = 'extends' | 'endpoint' | 'value' | 'policy' | 'view' | 'core';
12
+ export type ReferenceCollector = (ref: DefinitionRef, site: ReferenceSite) => void;
7
13
  /** Collect only semantic refs, never strings or objects embedded as JSON data. */
8
14
  export declare function collectUsedForeignOrigins(schema: DomainSchemaIR): ReadonlySet<string>;
9
15
  /** Complete structured references in one schema, in canonical order. */
10
16
  export declare function collectDomainDefinitionRefs(schema: DomainSchemaIR): readonly DefinitionRef[];
11
- export declare function collectClassRefs(declaration: ClassDefinition, add: (ref: DefinitionRef) => void): void;
12
- export declare function collectCallableRefs(declaration: FunctionDefinition | MethodDefinition, add: (ref: DefinitionRef) => void): void;
13
- export declare function collectPolicyDefinitionRefs(declaration: PolicyDefinition, add: (ref: DefinitionRef) => void): void;
14
- export declare function collectValueDefinitionRefs(schema: JsonSchema, add: (ref: DefinitionRef) => void): void;
17
+ export declare function collectCoreRefs(schema: DomainSchemaIR, add: ReferenceCollector): void;
18
+ export declare function collectClassRefs(declaration: ClassDefinition, add: ReferenceCollector): void;
19
+ export declare function collectClassPolicyRefs(declaration: ClassDefinition, add: ReferenceCollector): void;
20
+ export declare function collectEndpointRefs(declaration: Extract<ClassDefinition, {
21
+ readonly kind: 'edge';
22
+ }>, add: ReferenceCollector): void;
23
+ export declare function collectCallableRefs(declaration: FunctionDefinition | MethodDefinition, add: ReferenceCollector): void;
24
+ export declare function collectPolicyDefinitionRefs(declaration: PolicyDefinition, add: ReferenceCollector): void;
25
+ export declare function collectValueDefinitionRefs(schema: JsonSchema, add: ReferenceCollector): void;
@@ -24,39 +24,46 @@ export function collectDomainDefinitionRefs(schema) {
24
24
  collectPolicyDefinitionRefs(declaration, add);
25
25
  }
26
26
  for (const declaration of Object.values(schema.views)) {
27
- if (declaration.target.kind === 'definition')
28
- declaration.target.definitions.forEach(add);
27
+ if (declaration.target.kind === 'definition') {
28
+ declaration.target.definitions.forEach((ref) => add(ref, 'view'));
29
+ }
29
30
  }
31
+ collectCoreRefs(schema, add);
32
+ return Object.freeze([...result.values()].sort(compareDefinitionRefs));
33
+ }
34
+ export function collectCoreRefs(schema, add) {
30
35
  for (const node of Object.values(schema.core.nodes))
31
- add(node.class);
36
+ add(node.class, 'core');
32
37
  for (const edge of schema.core.edges) {
33
- add(edge.class);
38
+ add(edge.class, 'core');
34
39
  if (edge.source.kind !== 'domain')
35
- add(edge.source);
40
+ add(edge.source, 'core');
36
41
  if (edge.target.kind !== 'domain')
37
- add(edge.target);
42
+ add(edge.target, 'core');
38
43
  }
39
- return Object.freeze([...result.values()].sort(compareDefinitionRefs));
40
44
  }
41
45
  export function collectClassRefs(declaration, add) {
42
- declaration.extends.forEach(add);
46
+ declaration.extends.forEach((ref) => add(ref, 'extends'));
43
47
  Object.values(declaration.properties).forEach((property) => collectValueDefinitionRefs(property.schema, add));
44
- if (declaration.policies.read !== undefined)
45
- add(declaration.policies.read);
46
- if (declaration.policies.traverse !== undefined)
47
- add(declaration.policies.traverse);
48
+ collectClassPolicyRefs(declaration, add);
48
49
  if (declaration.kind === 'edge') {
49
50
  collectEndpointRefs(declaration, add);
50
51
  return;
51
52
  }
52
53
  Object.values(declaration.methods).forEach((method) => collectCallableRefs(method, add));
53
54
  }
54
- function collectEndpointRefs(declaration, add) {
55
+ export function collectClassPolicyRefs(declaration, add) {
56
+ if (declaration.policies.read !== undefined)
57
+ add(declaration.policies.read, 'policy');
58
+ if (declaration.policies.traverse !== undefined)
59
+ add(declaration.policies.traverse, 'policy');
60
+ }
61
+ export function collectEndpointRefs(declaration, add) {
55
62
  const endpoints = declaration.orientation === 'directed'
56
63
  ? [declaration.endpoints.source, declaration.endpoints.target]
57
64
  : declaration.endpoints;
58
- endpoints[0].accepts.forEach(add);
59
- endpoints[1].accepts.forEach(add);
65
+ endpoints[0].accepts.forEach((ref) => add(ref, 'endpoint'));
66
+ endpoints[1].accepts.forEach((ref) => add(ref, 'endpoint'));
60
67
  }
61
68
  export function collectCallableRefs(declaration, add) {
62
69
  collectValueDefinitionRefs(declaration.input, add);
@@ -76,27 +83,27 @@ function collectPolicyExpressionRefs(expression, add) {
76
83
  return;
77
84
  }
78
85
  const refs = 'allOf' in expression ? expression.allOf : expression.anyOf;
79
- refs.forEach(add);
86
+ refs.forEach((ref) => add(ref, 'policy'));
80
87
  }
81
88
  function collectPolicyPatternRefs(expression, add) {
82
89
  if ('sameNode' in expression) {
83
90
  for (const term of [expression.sameNode.left, expression.sameNode.right])
84
91
  if (term.kind === 'ref')
85
- add(term.ref.kind === 'method' ? term.ref.owner : term.ref);
92
+ add(term.ref.kind === 'method' ? term.ref.owner : term.ref, 'policy');
86
93
  return;
87
94
  }
88
95
  if ('source' in expression) {
89
96
  for (const term of [expression.source, expression.target])
90
97
  if (term.kind === 'ref')
91
- add(term.ref.kind === 'method' ? term.ref.owner : term.ref);
92
- add(expression.class);
98
+ add(term.ref.kind === 'method' ? term.ref.owner : term.ref, 'policy');
99
+ add(expression.class, 'policy');
93
100
  return;
94
101
  }
95
102
  if ('exists' in expression) {
96
103
  expression.exists.nodes.forEach((node) => {
97
104
  const ref = policyVariableClass(node);
98
105
  if (ref !== undefined)
99
- add(ref);
106
+ add(ref, 'policy');
100
107
  });
101
108
  collectPolicyPatternRefs(expression.exists.where, add);
102
109
  return;
@@ -108,15 +115,15 @@ function collectPolicyCheckRefs(expression, add) {
108
115
  if ('sameNode' in expression) {
109
116
  for (const term of [expression.sameNode.left, expression.sameNode.right])
110
117
  if (term.kind === 'ref')
111
- add(term.ref.kind === 'method' ? term.ref.owner : term.ref);
118
+ add(term.ref.kind === 'method' ? term.ref.owner : term.ref, 'policy');
112
119
  return;
113
120
  }
114
121
  if ('check' in expression) {
115
- add(expression.check);
122
+ add(expression.check, 'policy');
116
123
  if (expression.object.kind === 'ref')
117
124
  add(expression.object.ref.kind === 'method'
118
125
  ? expression.object.ref.owner
119
- : expression.object.ref);
126
+ : expression.object.ref, 'policy');
120
127
  return;
121
128
  }
122
129
  const children = 'allOf' in expression ? expression.allOf : expression.anyOf;
@@ -134,7 +141,7 @@ export function collectValueDefinitionRefs(schema, add) {
134
141
  typeof candidate.origin === 'string' &&
135
142
  typeof candidate.kind === 'string' &&
136
143
  typeof candidate.name === 'string') {
137
- add(candidate);
144
+ add(candidate, 'value');
138
145
  }
139
146
  }
140
147
  });
@@ -1,5 +1,6 @@
1
1
  import { Key } from '../../addressing/key.js';
2
2
  import { definitionRefIndex } from '../../addressing/ordering.js';
3
+ import { isMethodExecutable } from '../../language/callable/executable.js';
3
4
  import { admitStateTopology } from '../../language/state/topology.js';
4
5
  import { classifyOrdering } from '../../language/value/ordering.js';
5
6
  import { diagnostic } from '../diagnostic.js';
@@ -71,7 +72,7 @@ function validateFacet(environment, declaration, pointer, diagnostics) {
71
72
  return;
72
73
  for (const [name, method] of Object.entries(declaration.methods)) {
73
74
  const methodPointer = `${pointer}/methods/${escapePointer(name)}`;
74
- if (method.abstract === true && method.policy !== undefined) {
75
+ if (!isMethodExecutable(declaration, method) && method.policy !== undefined) {
75
76
  diagnostics.push(diagnostic('DV_METHOD_ABSTRACT', `${methodPointer}/policy`, 'Abstract Methods cannot have a Policy.'));
76
77
  }
77
78
  }
@@ -190,14 +190,6 @@ const methodDeclarationSchema = strictObject({
190
190
  static: boolean(),
191
191
  abstract: boolean(),
192
192
  }).superRefine((method, context) => {
193
- if (method.abstract === true && method.policy !== undefined) {
194
- context.addIssue({
195
- code: 'custom',
196
- path: ['policy'],
197
- message: 'An abstract method cannot declare a policy.',
198
- params: { structureCode: 'STRUCTURE_ABSTRACT_POLICY' },
199
- });
200
- }
201
193
  if (method.auth !== 'authorized' && method.policy !== undefined) {
202
194
  context.addIssue({
203
195
  code: 'custom',
@@ -1,4 +1,5 @@
1
1
  import { definitionRefIndex } from '../../../addressing/ordering.js';
2
+ import { isMethodExecutable } from '../../../language/callable/executable.js';
2
3
  import { policyObjectKey, policyObjectOrigin } from '../../../language/index.js';
3
4
  const KERNEL_ORIGIN = 'kernel.astrale.ai';
4
5
  const PROJECTION_CLASS = nodeClassRef('Class');
@@ -26,7 +27,7 @@ export function referenceContracts(validation, ref, pointer) {
26
27
  case 'method': {
27
28
  const declaringClass = owner.classes[ref.owner.name];
28
29
  const method = declaringClass?.kind === 'node' ? declaringClass.methods[ref.name] : undefined;
29
- return method === undefined || method.abstract
30
+ return method === undefined || !isMethodExecutable(declaringClass, method)
30
31
  ? invalidPolicyObjectRef(validation, ref, pointer)
31
32
  : [{ kind: 'exact', ref: PROJECTION_FUNCTION }];
32
33
  }
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "@astrale-os/kernel-dsl",
3
- "version": "0.2.0-beta.32",
3
+ "version": "0.2.0-beta.34",
4
4
  "description": "Astrale Kernel DSL - Schema authoring, inference, and IR serialization",
5
5
  "license": "Apache-2.0",
6
6
  "repository": {
@@ -105,7 +105,7 @@
105
105
  "generate:value-schema-validator": "node scripts/generate-value-schema-meta-validator.mjs",
106
106
  "layout:check": "node scripts/check-layout.mjs",
107
107
  "spec:typecheck": "tsgo --noEmit -p tsconfig.spec.json",
108
- "typecheck": "tsgo --noEmit && tsgo --noEmit -p tsconfig.types.json",
108
+ "typecheck": "tsgo --noEmit && tsgo --noEmit -p tsconfig.types.json && tsgo -p tsconfig.workers.json",
109
109
  "test": "pnpm run conformance && pnpm run layout:check && vitest run",
110
110
  "test:file": "vitest run",
111
111
  "test:semantic-lock": "pnpm run conformance && pnpm run layout:check && vitest run",