@shaclmate/compiler 4.0.13 → 4.0.15

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 (55) hide show
  1. package/dist/Compiler.d.ts +4 -1
  2. package/dist/Compiler.js +3 -1
  3. package/dist/ShapesGraphToAstTransformer.d.ts +10 -2
  4. package/dist/ShapesGraphToAstTransformer.js +74 -3
  5. package/dist/_ShapesGraphToAstTransformer/ShapeStack.js +6 -5
  6. package/dist/_ShapesGraphToAstTransformer/nodeShapeIdentifierMintingStrategy.d.ts +3 -2
  7. package/dist/_ShapesGraphToAstTransformer/nodeShapeIdentifierMintingStrategy.js +17 -13
  8. package/dist/_ShapesGraphToAstTransformer/nodeShapeTsFeatures.js +2 -1
  9. package/dist/_ShapesGraphToAstTransformer/shapeAstTypeName.js +6 -6
  10. package/dist/_ShapesGraphToAstTransformer/shapeNodeKinds.d.ts +2 -1
  11. package/dist/_ShapesGraphToAstTransformer/shapeNodeKinds.js +37 -30
  12. package/dist/_ShapesGraphToAstTransformer/shapeOntology.d.ts +5 -0
  13. package/dist/_ShapesGraphToAstTransformer/shapeOntology.js +25 -0
  14. package/dist/_ShapesGraphToAstTransformer/transformPropertyShapeToAstObjectTypeProperty.js +23 -16
  15. package/dist/_ShapesGraphToAstTransformer/transformShapeToAstCompoundType.js +10 -6
  16. package/dist/_ShapesGraphToAstTransformer/transformShapeToAstListType.js +22 -22
  17. package/dist/_ShapesGraphToAstTransformer/transformShapeToAstObjectType.js +127 -118
  18. package/dist/_ShapesGraphToAstTransformer/transformShapeToAstTermType.js +10 -8
  19. package/dist/_ShapesGraphToAstTransformer/transformShapeToAstType.js +3 -3
  20. package/dist/ast/ObjectType.d.ts +3 -3
  21. package/dist/enums/IdentifierMintingStrategy.d.ts +4 -0
  22. package/dist/enums/IdentifierMintingStrategy.js +17 -1
  23. package/dist/enums/TsObjectDeclarationType.d.ts +4 -0
  24. package/dist/enums/TsObjectDeclarationType.js +15 -1
  25. package/dist/enums/Visibility.d.ts +6 -0
  26. package/dist/enums/Visibility.js +18 -0
  27. package/dist/generators/ts/AbstractCollectionType.js +1 -7
  28. package/dist/generators/ts/AbstractTermType.d.ts +1 -0
  29. package/dist/generators/ts/AbstractTermType.js +6 -0
  30. package/dist/generators/ts/AbstractUnionType.d.ts +31 -9
  31. package/dist/generators/ts/AbstractUnionType.js +252 -126
  32. package/dist/generators/ts/SetType.d.ts +1 -0
  33. package/dist/generators/ts/SetType.js +12 -0
  34. package/dist/generators/ts/_NamedObjectType/AbstractProperty.d.ts +3 -3
  35. package/dist/input/ShapesGraph.d.ts +39 -22
  36. package/dist/input/ShapesGraph.js +56 -60
  37. package/dist/input/generated.d.ts +389 -191
  38. package/dist/input/generated.js +2501 -829
  39. package/dist/input/index.d.ts +1 -5
  40. package/dist/input/index.js +1 -5
  41. package/package.json +2 -2
  42. package/dist/enums/PropertyVisibility.d.ts +0 -2
  43. package/dist/enums/PropertyVisibility.js +0 -2
  44. package/dist/input/NodeShape.d.ts +0 -49
  45. package/dist/input/NodeShape.js +0 -154
  46. package/dist/input/Ontology.d.ts +0 -13
  47. package/dist/input/Ontology.js +0 -40
  48. package/dist/input/PropertyShape.d.ts +0 -20
  49. package/dist/input/PropertyShape.js +0 -78
  50. package/dist/input/Shape.d.ts +0 -4
  51. package/dist/input/Shape.js +0 -2
  52. package/dist/input/ancestorClassIris.d.ts +0 -4
  53. package/dist/input/ancestorClassIris.js +0 -24
  54. package/dist/input/descendantClassIris.d.ts +0 -4
  55. package/dist/input/descendantClassIris.js +0 -27
@@ -1,10 +1,13 @@
1
1
  import type { Either } from "purify-ts";
2
+ import type { TsFeature } from "./enums/TsFeature.js";
2
3
  import type { Generator } from "./generators/Generator.js";
3
4
  import type { ShapesGraph } from "./input/ShapesGraph.js";
4
5
  export declare class Compiler {
5
6
  private readonly generator;
6
- constructor({ generator }: {
7
+ private readonly tsFeaturesDefault?;
8
+ constructor({ generator, }: {
7
9
  generator: Generator;
10
+ tsFeaturesDefault?: ReadonlySet<TsFeature>;
8
11
  });
9
12
  compile(shapesGraph: ShapesGraph): Either<Error, string>;
10
13
  }
package/dist/Compiler.js CHANGED
@@ -1,12 +1,14 @@
1
1
  import { ShapesGraphToAstTransformer } from "./ShapesGraphToAstTransformer.js";
2
2
  export class Compiler {
3
3
  generator;
4
- constructor({ generator }) {
4
+ tsFeaturesDefault;
5
+ constructor({ generator, }) {
5
6
  this.generator = generator;
6
7
  }
7
8
  compile(shapesGraph) {
8
9
  return new ShapesGraphToAstTransformer({
9
10
  shapesGraph,
11
+ tsFeaturesDefault: this.tsFeaturesDefault,
10
12
  })
11
13
  .transform()
12
14
  .map((ast) => this.generator.generate(ast));
@@ -1,12 +1,19 @@
1
1
  import TermMap from "@rdfjs/term-map";
2
- import type * as rdfjs from "@rdfjs/types";
2
+ import type { BlankNode, NamedNode } from "@rdfjs/types";
3
3
  import { Either } from "purify-ts";
4
4
  import type * as ast from "./ast/index.js";
5
5
  import type { TsFeature } from "./enums/TsFeature.js";
6
6
  import type * as input from "./input/index.js";
7
+ interface RelatedNodeShapes {
8
+ readonly ancestors: input.NodeShape[];
9
+ readonly children: input.NodeShape[];
10
+ readonly parents: input.NodeShape[];
11
+ readonly descendants: input.NodeShape[];
12
+ }
7
13
  export declare class ShapesGraphToAstTransformer {
8
- protected readonly cachedAstTypesByShapeIdentifier: TermMap<rdfjs.BlankNode | rdfjs.NamedNode, ast.Type>;
14
+ protected readonly cachedAstTypesByShapeIdentifier: TermMap<BlankNode | NamedNode, ast.Type>;
9
15
  protected readonly shapesGraph: input.ShapesGraph;
16
+ protected readonly relatedNodeShapesByIdentifier: TermMap<BlankNode | NamedNode, RelatedNodeShapes>;
10
17
  protected tsFeaturesDefault: ReadonlySet<TsFeature>;
11
18
  constructor({ shapesGraph, tsFeaturesDefault, }: {
12
19
  shapesGraph: input.ShapesGraph;
@@ -14,4 +21,5 @@ export declare class ShapesGraphToAstTransformer {
14
21
  });
15
22
  transform(): Either<Error, ast.Ast>;
16
23
  }
24
+ export {};
17
25
  //# sourceMappingURL=ShapesGraphToAstTransformer.d.ts.map
@@ -1,15 +1,86 @@
1
1
  import TermMap from "@rdfjs/term-map";
2
2
  import { dash } from "@tpluscode/rdf-ns-builders";
3
3
  import { Either } from "purify-ts";
4
+ import { Resource } from "rdfjs-resource";
4
5
  import { invariant } from "ts-invariant";
5
6
  import { ShapeStack } from "./_ShapesGraphToAstTransformer/ShapeStack.js";
6
7
  import { transformShapeToAstType } from "./_ShapesGraphToAstTransformer/transformShapeToAstType.js";
8
+ import { logger } from "./logger.js";
9
+ function relatedNodeShapes(shapesGraph) {
10
+ const immediateRelatedNodeShapes = new TermMap();
11
+ for (const childNodeShape of shapesGraph.nodeShapes) {
12
+ let childRelatedNodeShapes = immediateRelatedNodeShapes.get(childNodeShape.$identifier);
13
+ if (!childRelatedNodeShapes) {
14
+ childRelatedNodeShapes = {
15
+ children: new TermMap(),
16
+ parents: new TermMap(),
17
+ };
18
+ immediateRelatedNodeShapes.set(childNodeShape.$identifier, childRelatedNodeShapes);
19
+ }
20
+ for (const parentClassIdentifier of childNodeShape.subClassOf) {
21
+ shapesGraph
22
+ .nodeShape(parentClassIdentifier)
23
+ .ifLeft((error) => {
24
+ logger.error("%s is rdfs:subClassOf %s which is either missing or not a node shape: %s", childNodeShape, Resource.Identifier.toString(parentClassIdentifier), error.message);
25
+ })
26
+ .ifRight((parentNodeShape) => {
27
+ childRelatedNodeShapes.parents.set(parentNodeShape.$identifier, parentNodeShape);
28
+ let parentRelatedNodeShapes = immediateRelatedNodeShapes.get(parentNodeShape.$identifier);
29
+ if (!parentRelatedNodeShapes) {
30
+ parentRelatedNodeShapes = {
31
+ children: new TermMap(),
32
+ parents: new TermMap(),
33
+ };
34
+ immediateRelatedNodeShapes.set(parentNodeShape.$identifier, parentRelatedNodeShapes);
35
+ }
36
+ parentRelatedNodeShapes.children.set(childNodeShape.$identifier, childNodeShape);
37
+ });
38
+ }
39
+ }
40
+ const result = new TermMap();
41
+ for (const nodeShape of shapesGraph.nodeShapes) {
42
+ const { children: childNodeShapes, parents: parentNodeShapes } = immediateRelatedNodeShapes.get(nodeShape.$identifier);
43
+ const ancestorNodeShapes = new TermMap();
44
+ function recurseAncestorNodeShapes(nodeShape) {
45
+ for (const parentNodeShape of immediateRelatedNodeShapes
46
+ .get(nodeShape.$identifier)
47
+ .parents.values()) {
48
+ if (!ancestorNodeShapes.has(parentNodeShape.$identifier)) {
49
+ ancestorNodeShapes.set(parentNodeShape.$identifier, parentNodeShape);
50
+ recurseAncestorNodeShapes(parentNodeShape);
51
+ }
52
+ }
53
+ }
54
+ recurseAncestorNodeShapes(nodeShape);
55
+ const descendantNodeShapes = new TermMap();
56
+ function recurseDescendantNodeShapes(nodeShape) {
57
+ for (const childNodeShape of immediateRelatedNodeShapes
58
+ .get(nodeShape.$identifier)
59
+ .children.values()) {
60
+ if (!descendantNodeShapes.has(childNodeShape.$identifier)) {
61
+ descendantNodeShapes.set(childNodeShape.$identifier, childNodeShape);
62
+ recurseDescendantNodeShapes(childNodeShape);
63
+ }
64
+ }
65
+ }
66
+ recurseDescendantNodeShapes(nodeShape);
67
+ result.set(nodeShape.$identifier, {
68
+ ancestors: [...ancestorNodeShapes.values()],
69
+ children: [...childNodeShapes.values()],
70
+ descendants: [...descendantNodeShapes.values()],
71
+ parents: [...parentNodeShapes.values()],
72
+ });
73
+ }
74
+ return result;
75
+ }
7
76
  export class ShapesGraphToAstTransformer {
8
77
  // Members are protected so they're accessible to functions in other files
9
78
  cachedAstTypesByShapeIdentifier = new TermMap();
10
79
  shapesGraph;
80
+ relatedNodeShapesByIdentifier = new TermMap();
11
81
  tsFeaturesDefault;
12
82
  constructor({ shapesGraph, tsFeaturesDefault, }) {
83
+ this.relatedNodeShapesByIdentifier = relatedNodeShapes(shapesGraph);
13
84
  this.shapesGraph = shapesGraph;
14
85
  this.tsFeaturesDefault =
15
86
  tsFeaturesDefault ??
@@ -21,10 +92,10 @@ export class ShapesGraphToAstTransformer {
21
92
  const syntheticAstObjectTypesByName = {};
22
93
  const astNamedUnionTypes = [];
23
94
  for (const nodeShape of this.shapesGraph.nodeShapes) {
24
- if (nodeShape.identifier.termType !== "NamedNode") {
95
+ if (nodeShape.$identifier.termType !== "NamedNode") {
25
96
  continue;
26
97
  }
27
- if (nodeShape.identifier.value.startsWith(dash[""].value)) {
98
+ if (nodeShape.$identifier.value.startsWith(dash[""].value)) {
28
99
  continue;
29
100
  }
30
101
  const nodeShapeAstTypeEither = transformShapeToAstType.call(this, nodeShape, new ShapeStack());
@@ -39,7 +110,7 @@ export class ShapesGraphToAstTransformer {
39
110
  }
40
111
  break;
41
112
  case "ObjectType": {
42
- invariant(nodeShapeAstType.name.isJust());
113
+ invariant(nodeShapeAstType.name.isJust(), `node shape missing name: ${nodeShapeAstType.shapeIdentifier}`);
43
114
  astObjectTypes.push(nodeShapeAstType);
44
115
  for (const property of nodeShapeAstType.properties) {
45
116
  switch (property.type.kind) {
@@ -7,16 +7,17 @@ export class ShapeStack {
7
7
  this.constraints = {
8
8
  get hasValues() {
9
9
  for (const shape of stack.toReversed()) {
10
- if (shape.constraints.hasValues.length > 0) {
11
- return shape.constraints.hasValues;
10
+ if (shape.hasValues.length > 0) {
11
+ return shape.hasValues;
12
12
  }
13
13
  }
14
14
  return [];
15
15
  },
16
16
  get in_() {
17
17
  for (const shape of stack.toReversed()) {
18
- if (shape.constraints.in_.length > 0) {
19
- return shape.constraints.in_;
18
+ const shapeIn = shape.in_.orDefault([]);
19
+ if (shapeIn.length > 0) {
20
+ return shapeIn;
20
21
  }
21
22
  }
22
23
  return [];
@@ -26,7 +27,7 @@ export class ShapeStack {
26
27
  constraints;
27
28
  get defaultValue() {
28
29
  for (const shape of this.stack.toReversed()) {
29
- if (shape.kind !== "PropertyShape") {
30
+ if (shape.$type !== "PropertyShape") {
30
31
  continue;
31
32
  }
32
33
  if (shape.defaultValue.isJust()) {
@@ -1,5 +1,6 @@
1
1
  import { Either, Maybe } from "purify-ts";
2
- import type { IdentifierMintingStrategy } from "../enums/IdentifierMintingStrategy.js";
2
+ import { IdentifierMintingStrategy } from "../enums/IdentifierMintingStrategy.js";
3
3
  import type * as input from "../input/index.js";
4
- export declare function nodeShapeIdentifierMintingStrategy(nodeShape: input.NodeShape): Either<Error, Maybe<IdentifierMintingStrategy>>;
4
+ import type { ShapesGraphToAstTransformer } from "../ShapesGraphToAstTransformer.js";
5
+ export declare function nodeShapeIdentifierMintingStrategy(this: ShapesGraphToAstTransformer, nodeShape: input.NodeShape): Either<Error, Maybe<IdentifierMintingStrategy>>;
5
6
  //# sourceMappingURL=nodeShapeIdentifierMintingStrategy.d.ts.map
@@ -1,4 +1,5 @@
1
1
  import { Either, Left, Maybe } from "purify-ts";
2
+ import { IdentifierMintingStrategy } from "../enums/IdentifierMintingStrategy.js";
2
3
  import { shapeNodeKinds } from "./shapeNodeKinds.js";
3
4
  const defaultNodeShapeNodeKinds = new Set([
4
5
  "BlankNode",
@@ -6,23 +7,26 @@ const defaultNodeShapeNodeKinds = new Set([
6
7
  ]);
7
8
  export function nodeShapeIdentifierMintingStrategy(nodeShape) {
8
9
  if (nodeShape.identifierMintingStrategy.isJust()) {
9
- if (nodeShape.identifierIn.length > 0) {
10
+ if (nodeShape.in_.filter((_) => _.length > 0).isJust()) {
10
11
  return Left(new Error(`${nodeShape} cannot have an identifier minting strategy and sh:in`));
11
12
  }
12
- return Either.of(nodeShape.identifierMintingStrategy);
13
+ return Either.of(nodeShape.identifierMintingStrategy.map(IdentifierMintingStrategy.fromIri));
13
14
  }
14
- return nodeShape.ancestorNodeShapes.chain((ancestorNodeShapes) => {
15
- for (const ancestorNodeShape of ancestorNodeShapes) {
16
- if (ancestorNodeShape.identifierMintingStrategy.isJust()) {
17
- return Either.of(ancestorNodeShape.identifierMintingStrategy);
18
- }
15
+ // Recurse into parents
16
+ for (const parentNodeShape of this.relatedNodeShapesByIdentifier.get(nodeShape.$identifier).parents) {
17
+ const parentNodeShapeIdentifierMintingStrategy = nodeShapeIdentifierMintingStrategy.call(this, parentNodeShape);
18
+ if (parentNodeShapeIdentifierMintingStrategy.isRight() &&
19
+ parentNodeShapeIdentifierMintingStrategy.extract().isJust()) {
20
+ return parentNodeShapeIdentifierMintingStrategy;
19
21
  }
20
- return shapeNodeKinds(nodeShape, { defaultNodeShapeNodeKinds }).map((nodeKinds) => {
21
- if (nodeKinds.has("BlankNode")) {
22
- return Maybe.of("blankNode");
23
- }
24
- return Maybe.empty();
25
- });
22
+ }
23
+ return shapeNodeKinds
24
+ .call(this, nodeShape, { defaultNodeShapeNodeKinds })
25
+ .map((nodeKinds) => {
26
+ if (nodeKinds.has("BlankNode")) {
27
+ return Maybe.of("blankNode");
28
+ }
29
+ return Maybe.empty();
26
30
  });
27
31
  }
28
32
  //# sourceMappingURL=nodeShapeIdentifierMintingStrategy.js.map
@@ -1,5 +1,6 @@
1
1
  import { Either } from "purify-ts";
2
2
  import { TS_FEATURES } from "../enums/TsFeature.js";
3
+ import { shapeOntology } from "./shapeOntology.js";
3
4
  export function nodeShapeTsFeatures(nodeShape) {
4
5
  const tsFeaturesDefault = this.tsFeaturesDefault;
5
6
  function iriToTsFeatures(iri) {
@@ -26,7 +27,7 @@ export function nodeShapeTsFeatures(nodeShape) {
26
27
  return ["sparql"];
27
28
  }
28
29
  }
29
- return nodeShape.isDefinedBy.chain((ontologyMaybe) => {
30
+ return shapeOntology.call(this, nodeShape).chain((ontologyMaybe) => {
30
31
  let tsFeatureExcludes = nodeShape.tsFeatureExcludes.flatMap(iriToTsFeatures);
31
32
  let tsFeatureIncludes = nodeShape.tsFeatureIncludes.flatMap(iriToTsFeatures);
32
33
  if (tsFeatureExcludes.length === 0 && tsFeatureIncludes.length === 0) {
@@ -1,10 +1,10 @@
1
1
  import { Curie } from "@shaclmate/shacl-ast";
2
2
  import { Maybe } from "purify-ts";
3
3
  export function shapeAstTypeName(shape) {
4
- if (shape.kind !== "NodeShape") {
4
+ if (shape.$type !== "NodeShape") {
5
5
  return Maybe.empty();
6
6
  }
7
- if (shape.identifier.termType !== "NamedNode") {
7
+ if (shape.$identifier.termType !== "NamedNode") {
8
8
  return Maybe.empty();
9
9
  }
10
10
  // Explicit shaclmate:name
@@ -16,11 +16,11 @@ export function shapeAstTypeName(shape) {
16
16
  return shape.label;
17
17
  }
18
18
  // CURIE shape identifier
19
- if (shape.identifier instanceof Curie) {
20
- if (shape.identifier.hasUniqueReference) {
21
- return Maybe.of(shape.identifier.reference);
19
+ if (shape.$identifier instanceof Curie) {
20
+ if (shape.$identifier.hasUniqueReference) {
21
+ return Maybe.of(shape.$identifier.reference);
22
22
  }
23
- return Maybe.of(`${shape.identifier.prefix}_${shape.identifier.reference}`);
23
+ return Maybe.of(`${shape.$identifier.prefix}_${shape.$identifier.reference}`);
24
24
  }
25
25
  return Maybe.empty();
26
26
  }
@@ -1,7 +1,8 @@
1
1
  import { NodeKind } from "@shaclmate/shacl-ast";
2
2
  import { Either } from "purify-ts";
3
3
  import type * as input from "../input/index.js";
4
- export declare function shapeNodeKinds(shape: input.Shape, options?: {
4
+ import type { ShapesGraphToAstTransformer } from "../ShapesGraphToAstTransformer.js";
5
+ export declare function shapeNodeKinds(this: ShapesGraphToAstTransformer, shape: input.Shape, options?: {
5
6
  defaultNodeShapeNodeKinds: ReadonlySet<NodeKind>;
6
7
  defaultPropertyShapeNodeKinds?: ReadonlySet<NodeKind>;
7
8
  }): Either<Error, ReadonlySet<NodeKind>>;
@@ -7,34 +7,39 @@ const defaultPropertyShapeNodeKinds = new Set([
7
7
  "Literal",
8
8
  ]);
9
9
  function nodeShapeNodeKinds(nodeShape) {
10
- const thisNodeKinds = nodeShape.constraints.nodeKinds;
11
- return nodeShape.parentNodeShapes.chain((parentNodeShapes) => {
12
- const parentNodeKinds = new Set();
13
- for (const parentNodeShape of parentNodeShapes) {
14
- for (const parentNodeKind of parentNodeShape.constraints.nodeKinds) {
10
+ const thisNodeKinds = nodeShape.nodeKind
11
+ .map(NodeKind.fromIri)
12
+ .orDefault(new Set());
13
+ // Recurse into parents
14
+ const parentNodeKinds = new Set();
15
+ for (const parentNodeShape of this.relatedNodeShapesByIdentifier.get(nodeShape.$identifier).parents) {
16
+ nodeShapeNodeKinds
17
+ .call(this, parentNodeShape)
18
+ .ifRight((parentNodeKinds_) => {
19
+ for (const parentNodeKind of parentNodeKinds_) {
15
20
  parentNodeKinds.add(parentNodeKind);
16
21
  }
22
+ });
23
+ }
24
+ if (parentNodeKinds.size > 0) {
25
+ if (thisNodeKinds.size === 0) {
26
+ return Either.of(parentNodeKinds);
17
27
  }
18
- if (parentNodeKinds.size > 0) {
19
- if (thisNodeKinds.size === 0) {
20
- return Either.of(parentNodeKinds);
21
- }
22
- // Check that thisNodeKinds doesn't conflict with parent node kinds
23
- for (const thisNodeKind of thisNodeKinds) {
24
- if (!parentNodeKinds.has(thisNodeKind)) {
25
- return Left(new Error(`${nodeShape} has a nodeKind ${thisNodeKind} that is not in its parent's node kinds`));
26
- }
28
+ // Check that thisNodeKinds doesn't conflict with parent node kinds
29
+ for (const thisNodeKind of thisNodeKinds) {
30
+ if (!parentNodeKinds.has(thisNodeKind)) {
31
+ return Left(new Error(`${nodeShape} has a nodeKind ${thisNodeKind} that is not in its parent's node kinds`));
27
32
  }
28
33
  }
29
- return Either.of(thisNodeKinds);
30
- });
34
+ }
35
+ return Either.of(thisNodeKinds);
31
36
  }
32
37
  function propertyShapeNodeKinds(propertyShape) {
33
- return Either.of(propertyShape.constraints.nodeKinds);
38
+ return Either.of(propertyShape.nodeKind.map(NodeKind.fromIri).orDefault(new Set()));
34
39
  }
35
40
  export function shapeNodeKinds(shape, options) {
36
- return (shape.kind === "NodeShape"
37
- ? nodeShapeNodeKinds(shape)
41
+ return (shape.$type === "NodeShape"
42
+ ? nodeShapeNodeKinds.call(this, shape)
38
43
  : propertyShapeNodeKinds(shape)).chain((explicitNodeKinds) => {
39
44
  // Consider constraints that dictate certain node kinds, like sh:datatype dictates a Literal nodeKind.
40
45
  const constraintExcludeNodeKinds = new Set();
@@ -42,14 +47,14 @@ export function shapeNodeKinds(shape, options) {
42
47
  for (const [constraint, { excludeNodeKinds, includeNodeKinds }] of [
43
48
  [
44
49
  "sh:class",
45
- shape.constraints.classes.length > 0
50
+ shape.classes.length > 0
46
51
  ? { excludeNodeKinds: ["Literal"] }
47
52
  : {},
48
53
  ],
49
54
  [
50
55
  "sh:datatype",
51
56
  {
52
- includeNodeKinds: shape.constraints.datatype
57
+ includeNodeKinds: shape.datatype
53
58
  .map(() => ["Literal"])
54
59
  .orDefault([]),
55
60
  },
@@ -57,7 +62,7 @@ export function shapeNodeKinds(shape, options) {
57
62
  [
58
63
  "sh:defaultValue",
59
64
  {
60
- includeNodeKinds: shape.kind === "PropertyShape"
65
+ includeNodeKinds: shape.$type === "PropertyShape"
61
66
  ? shape.defaultValue
62
67
  .map((value) => NodeKind.fromTermType(value.termType))
63
68
  .toList()
@@ -67,25 +72,27 @@ export function shapeNodeKinds(shape, options) {
67
72
  [
68
73
  "sh:hasValue",
69
74
  {
70
- includeNodeKinds: shape.constraints.hasValues.map((value) => NodeKind.fromTermType(value.termType)),
75
+ includeNodeKinds: shape.hasValues.map((value) => NodeKind.fromTermType(value.termType)),
71
76
  },
72
77
  ],
73
78
  [
74
79
  "sh:in",
75
80
  {
76
- includeNodeKinds: shape.constraints.in_.map((in_) => NodeKind.fromTermType(in_.termType)),
81
+ includeNodeKinds: shape.in_
82
+ .orDefault([])
83
+ .map((in_) => NodeKind.fromTermType(in_.termType)),
77
84
  },
78
85
  ],
79
86
  [
80
87
  "sh:languageIn",
81
- shape.constraints.languageIn.length > 0
88
+ shape.languageIn.orDefault([]).length > 0
82
89
  ? { includeNodeKinds: ["Literal"] }
83
90
  : {},
84
91
  ],
85
92
  [
86
93
  "sh:maxExclusive",
87
94
  {
88
- includeNodeKinds: shape.constraints.maxExclusive
95
+ includeNodeKinds: shape.maxExclusive
89
96
  .map(() => ["Literal"])
90
97
  .orDefault([]),
91
98
  },
@@ -93,7 +100,7 @@ export function shapeNodeKinds(shape, options) {
93
100
  [
94
101
  "sh:maxInclusive",
95
102
  {
96
- includeNodeKinds: shape.constraints.maxInclusive
103
+ includeNodeKinds: shape.maxInclusive
97
104
  .map(() => ["Literal"])
98
105
  .orDefault([]),
99
106
  },
@@ -101,7 +108,7 @@ export function shapeNodeKinds(shape, options) {
101
108
  [
102
109
  "sh:minExclusive",
103
110
  {
104
- includeNodeKinds: shape.constraints.minExclusive
111
+ includeNodeKinds: shape.minExclusive
105
112
  .map(() => ["Literal"])
106
113
  .orDefault([]),
107
114
  },
@@ -109,7 +116,7 @@ export function shapeNodeKinds(shape, options) {
109
116
  [
110
117
  "sh:minInclusive",
111
118
  {
112
- includeNodeKinds: shape.constraints.minInclusive
119
+ includeNodeKinds: shape.minInclusive
113
120
  .map(() => ["Literal"])
114
121
  .orDefault([]),
115
122
  },
@@ -162,7 +169,7 @@ export function shapeNodeKinds(shape, options) {
162
169
  if (constraintNodeKinds.size > 0) {
163
170
  return Either.of(constraintNodeKinds);
164
171
  }
165
- if (shape.kind === "NodeShape") {
172
+ if (shape.$type === "NodeShape") {
166
173
  return Either.of(options?.defaultNodeShapeNodeKinds ?? defaultNodeShapeNodeKinds);
167
174
  }
168
175
  if (shape.path.termType === "InversePath") {
@@ -0,0 +1,5 @@
1
+ import { Either, Maybe } from "purify-ts";
2
+ import type * as input from "../input/index.js";
3
+ import type { ShapesGraphToAstTransformer } from "../ShapesGraphToAstTransformer.js";
4
+ export declare function shapeOntology(this: ShapesGraphToAstTransformer, shape: input.Shape): Either<Error, Maybe<input.Ontology>>;
5
+ //# sourceMappingURL=shapeOntology.d.ts.map
@@ -0,0 +1,25 @@
1
+ import { Either, Maybe } from "purify-ts";
2
+ export function shapeOntology(shape) {
3
+ if (shape.isDefinedBy.isJust()) {
4
+ // If there's an rdfs:isDefinedBy statement on the shape then don't fall back to anything else
5
+ return this.shapesGraph
6
+ .ontology(shape.isDefinedBy.unsafeCoerce())
7
+ .map(Maybe.of);
8
+ }
9
+ // No rdfs:isDefinedBy statement on the shape
10
+ const ontologies = this.shapesGraph.ontologies;
11
+ if (ontologies.length === 1) {
12
+ // If there's a single ontology in the shapes graph, consider the shape a part of the ontology
13
+ return Either.of(Maybe.of(ontologies[0]));
14
+ }
15
+ if (shape.$identifier.termType === "NamedNode") {
16
+ const prefixOntologies = ontologies.filter((ontology) => ontology.$identifier.termType === "NamedNode" &&
17
+ shape.$identifier.value.startsWith(ontology.$identifier.value));
18
+ if (prefixOntologies.length === 1) {
19
+ // If there's a single ontology whose IRI is a prefix of this shape's IRI, consider the shape a part of the ontology
20
+ return Either.of(Maybe.of(prefixOntologies[0]));
21
+ }
22
+ }
23
+ return Either.of(Maybe.empty());
24
+ }
25
+ //# sourceMappingURL=shapeOntology.js.map
@@ -4,6 +4,7 @@ import { Either, Left, Maybe } from "purify-ts";
4
4
  import { invariant } from "ts-invariant";
5
5
  import * as ast from "../ast/index.js";
6
6
  import { Eithers } from "../Eithers.js";
7
+ import { Visibility } from "../enums/Visibility.js";
7
8
  import { ShapeStack } from "./ShapeStack.js";
8
9
  import { transformShapeToAstType } from "./transformShapeToAstType.js";
9
10
  function synthesizePartialAstObjectType({ identifierType, tsFeatures, }) {
@@ -48,13 +49,13 @@ function propertyName(objectType, propertyShape) {
48
49
  }
49
50
  // Pick up the common pattern of a property shape identifier being the node shape's identifier -localName,
50
51
  // like ex:NodeShape-property
51
- if (propertyShape.identifier.termType === "NamedNode" &&
52
+ if (propertyShape.$identifier.termType === "NamedNode" &&
52
53
  objectType.shapeIdentifier.termType === "NamedNode") {
53
54
  const propertyShapeIdentifierPrefix = `${objectType.shapeIdentifier.value}-`;
54
- if (propertyShape.identifier.value.startsWith(propertyShapeIdentifierPrefix) &&
55
- propertyShape.identifier.value.length >
55
+ if (propertyShape.$identifier.value.startsWith(propertyShapeIdentifierPrefix) &&
56
+ propertyShape.$identifier.value.length >
56
57
  propertyShapeIdentifierPrefix.length) {
57
- return propertyShape.identifier.value.substring(propertyShapeIdentifierPrefix.length);
58
+ return propertyShape.$identifier.value.substring(propertyShapeIdentifierPrefix.length);
58
59
  }
59
60
  }
60
61
  // sh:path CURIE reference
@@ -62,12 +63,12 @@ function propertyName(objectType, propertyShape) {
62
63
  return propertyShape.path.reference;
63
64
  }
64
65
  // Shape identifier CURIE reference
65
- if (propertyShape.identifier instanceof Curie) {
66
- return propertyShape.identifier.reference;
66
+ if (propertyShape.$identifier instanceof Curie) {
67
+ return propertyShape.$identifier.reference;
67
68
  }
68
69
  // Shape identifier IRI
69
- if (propertyShape.identifier.termType === "NamedNode") {
70
- return propertyShape.identifier.value;
70
+ if (propertyShape.$identifier.termType === "NamedNode") {
71
+ return propertyShape.$identifier.value;
71
72
  }
72
73
  // sh:path IRI
73
74
  if (propertyShape.path.termType === "NamedNode") {
@@ -84,13 +85,13 @@ function transformPropertyShapeToAstType(propertyShape, shapeStack) {
84
85
  return transformShapeToAstType
85
86
  .call(this, propertyShape, shapeStack)
86
87
  .chain((propertyShapeAstType) => {
87
- let maxCount = propertyShape.constraints.maxCount.orDefault(Number.MAX_SAFE_INTEGER);
88
- let minCount = propertyShape.constraints.minCount.orDefault(0);
88
+ let maxCount = propertyShape.maxCount.orDefault(Number.MAX_SAFE_INTEGER);
89
+ let minCount = propertyShape.minCount.orDefault(0);
89
90
  if (minCount < 0) {
90
91
  minCount = 0;
91
92
  }
92
- if (propertyShape.constraints.hasValues.length > minCount) {
93
- minCount = propertyShape.constraints.hasValues.length;
93
+ if (propertyShape.hasValues.length > minCount) {
94
+ minCount = propertyShape.hasValues.length;
94
95
  }
95
96
  if (maxCount < minCount) {
96
97
  maxCount = minCount;
@@ -127,7 +128,11 @@ function transformPropertyShapeToAstType(propertyShape, shapeStack) {
127
128
  }
128
129
  export function transformPropertyShapeToAstObjectTypeProperty({ objectType, propertyShape, }) {
129
130
  const shapeStack = new ShapeStack(); // Start a new ShapeStack per property shape
130
- return Eithers.chain2(propertyShape.resolve, transformPropertyShapeToAstType.call(this, propertyShape, shapeStack)).chain(([propertyShapeResolve, astType]) => {
131
+ return Eithers.chain2(propertyShape.resolve.isJust()
132
+ ? this.shapesGraph
133
+ .nodeShape(propertyShape.resolve.extract())
134
+ .map(Maybe.of)
135
+ : Either.of(Maybe.empty()), transformPropertyShapeToAstType.call(this, propertyShape, shapeStack)).chain(([propertyShapeResolve, astType]) => {
131
136
  let astResolveItemType;
132
137
  if (propertyShapeResolve.isJust()) {
133
138
  const astResolveTypeEither = transformShapeToAstType
@@ -196,7 +201,7 @@ export function transformPropertyShapeToAstObjectTypeProperty({ objectType, prop
196
201
  comment: Maybe.empty(),
197
202
  label: Maybe.empty(),
198
203
  name: Maybe.empty(),
199
- shapeIdentifier: propertyShape.identifier,
204
+ shapeIdentifier: propertyShape.$identifier,
200
205
  };
201
206
  switch (astType.kind) {
202
207
  case "BlankNodeType":
@@ -253,9 +258,11 @@ export function transformPropertyShapeToAstObjectTypeProperty({ objectType, prop
253
258
  objectType,
254
259
  order: propertyShape.order.orDefault(0),
255
260
  path: propertyShape.path,
256
- shapeIdentifier: propertyShape.identifier,
261
+ shapeIdentifier: propertyShape.$identifier,
257
262
  type: astType,
258
- visibility: propertyShape.visibility,
263
+ visibility: propertyShape.visibility
264
+ .map(Visibility.fromIri)
265
+ .orDefault("public"),
259
266
  }));
260
267
  });
261
268
  }
@@ -11,9 +11,13 @@ import { transformShapeToAstType } from "./transformShapeToAstType.js";
11
11
  export function transformShapeToAstCompoundType(shape, shapeStack) {
12
12
  shapeStack.push(shape);
13
13
  try {
14
- return Eithers.chain4(shape.constraints.and, shape.constraints.nodes, shape.kind === "NodeShape"
14
+ return Eithers.chain4(Either.sequence(shape.and
15
+ .orDefault([])
16
+ .map((shapeIdentifier) => this.shapesGraph.shape(shapeIdentifier))), Either.sequence(shape.nodes.map((nodeShapeIdentifier) => this.shapesGraph.nodeShape(nodeShapeIdentifier))), shape.$type === "NodeShape"
15
17
  ? nodeShapeTsFeatures.call(this, shape)
16
- : Either.of(new Set()), shape.constraints.xone).chain(([andConstraintShapes, nodeConstraintShapes, tsFeatures, xoneConstraintShapes,]) => {
18
+ : Either.of(new Set()), Either.sequence(shape.xone
19
+ .orDefault([])
20
+ .map((shapeIdentifier) => this.shapesGraph.shape(shapeIdentifier)))).chain(([andConstraintShapes, nodeConstraintShapes, tsFeatures, xoneConstraintShapes,]) => {
17
21
  let compoundTypeKind;
18
22
  // Distinguish constraints that take arbitrary shapes from those that only take node shapes
19
23
  // With the latter we'll do special transformations.
@@ -41,7 +45,7 @@ export function transformShapeToAstCompoundType(shape, shapeStack) {
41
45
  comment: shape.comment,
42
46
  label: shape.label,
43
47
  name: shapeAstTypeName(shape),
44
- shapeIdentifier: shape.identifier,
48
+ shapeIdentifier: shape.$identifier,
45
49
  tsFeatures,
46
50
  });
47
51
  if (memberShapes.length === 1) {
@@ -50,7 +54,7 @@ export function transformShapeToAstCompoundType(shape, shapeStack) {
50
54
  .map(Maybe.of);
51
55
  }
52
56
  // Put a placeholder in the cache to deal with cyclic references
53
- this.cachedAstTypesByShapeIdentifier.set(shape.identifier, compoundType);
57
+ this.cachedAstTypesByShapeIdentifier.set(shape.$identifier, compoundType);
54
58
  return Either.sequence(memberShapes.map((memberShape) => transformShapeToAstType.call(this, memberShape, shapeStack)))
55
59
  .chain((memberShapeTypes) => {
56
60
  for (let memberI = 0; memberI < memberShapes.length; memberI++) {
@@ -65,7 +69,7 @@ export function transformShapeToAstCompoundType(shape, shapeStack) {
65
69
  }
66
70
  let memberDiscriminantValue;
67
71
  if (compoundTypeKind === "UnionType") {
68
- if (memberShape.kind === "NodeShape") {
72
+ if (memberShape.$type === "NodeShape") {
69
73
  memberDiscriminantValue =
70
74
  memberShape.discriminantValue.extract();
71
75
  }
@@ -84,7 +88,7 @@ export function transformShapeToAstCompoundType(shape, shapeStack) {
84
88
  return Either.of(Maybe.of(compoundType));
85
89
  })
86
90
  .ifLeft(() => {
87
- this.cachedAstTypesByShapeIdentifier.delete(shape.identifier);
91
+ this.cachedAstTypesByShapeIdentifier.delete(shape.$identifier);
88
92
  });
89
93
  });
90
94
  }