@aeriajs/compiler 0.0.27 → 0.0.29

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/dist/ast.d.ts CHANGED
@@ -34,6 +34,7 @@ export type FormLayoutNode = NodeBase<'formLayout'> & FormLayout<Description> &
34
34
  field: FormLayoutField<Description>;
35
35
  };
36
36
  };
37
+ terms?: [string, symbol][];
37
38
  };
38
39
  };
39
40
  export type PropertyNode = NodeBase<'property'> & {
@@ -58,6 +58,9 @@ const makeJSCollectionSchema = (collectionNode, collectionId) => {
58
58
  };
59
59
  collectionSchema.exposedFunctions = (0, utils_js_1.getExposedFunctions)(collectionNode[key]);
60
60
  break;
61
+ case 'required':
62
+ collectionSchema.description[key] = collectionNode[key];
63
+ break;
61
64
  case 'table':
62
65
  case 'filters':
63
66
  case 'indexes':
@@ -78,13 +81,10 @@ const makeJSCollectionSchema = (collectionNode, collectionId) => {
78
81
  collectionSchema.description[key] = collectionNode[key];
79
82
  break;
80
83
  case 'layout':
81
- collectionSchema.description[key] = collectionNode[key];
84
+ collectionSchema.description[key] = (0, utils_js_1.unwrapNode)(collectionNode[key]);
82
85
  break;
83
86
  case 'formLayout':
84
- collectionSchema.description[key] = collectionNode[key];
85
- break;
86
- case 'required':
87
- collectionSchema.description[key] = collectionNode[key];
87
+ collectionSchema.description[key] = (0, utils_js_1.unwrapNode)(collectionNode[key]);
88
88
  break;
89
89
  }
90
90
  }
@@ -1,5 +1,5 @@
1
1
  "use strict";
2
- import { makeASTImports, recursivelyUnwrapPropertyNodes, stringify, getExtendName, getCollectionId, UnquotedSymbol, getExposedFunctions, PACKAGE_NAME, DEFAULT_FUNCTIONS } from "./utils.mjs";
2
+ import { unwrapNode, recursivelyUnwrapPropertyNodes, stringify, makeASTImports, getCollectionId, UnquotedSymbol, getExposedFunctions, getExtendName, PACKAGE_NAME, DEFAULT_FUNCTIONS } from "./utils.mjs";
3
3
  const initialImportedFunctions = [
4
4
  "extendCollection",
5
5
  "defineCollection"
@@ -51,6 +51,9 @@ const makeJSCollectionSchema = (collectionNode, collectionId) => {
51
51
  };
52
52
  collectionSchema.exposedFunctions = getExposedFunctions(collectionNode[key]);
53
53
  break;
54
+ case "required":
55
+ collectionSchema.description[key] = collectionNode[key];
56
+ break;
54
57
  case "table":
55
58
  case "filters":
56
59
  case "indexes":
@@ -71,13 +74,10 @@ const makeJSCollectionSchema = (collectionNode, collectionId) => {
71
74
  collectionSchema.description[key] = collectionNode[key];
72
75
  break;
73
76
  case "layout":
74
- collectionSchema.description[key] = collectionNode[key];
77
+ collectionSchema.description[key] = unwrapNode(collectionNode[key]);
75
78
  break;
76
79
  case "formLayout":
77
- collectionSchema.description[key] = collectionNode[key];
78
- break;
79
- case "required":
80
- collectionSchema.description[key] = collectionNode[key];
80
+ collectionSchema.description[key] = unwrapNode(collectionNode[key]);
81
81
  break;
82
82
  }
83
83
  }
@@ -68,6 +68,9 @@ const makeTSCollectionSchema = (collectionNode, collectionId) => {
68
68
  collectionSchema.functions = makeTSFunctions(collectionNode[key]);
69
69
  collectionSchema.exposedFunctions = (0, utils_js_1.getExposedFunctions)(collectionNode[key]);
70
70
  break;
71
+ case 'required':
72
+ collectionSchema.description[key] = collectionNode[key];
73
+ break;
71
74
  case 'table':
72
75
  case 'filters':
73
76
  case 'indexes':
@@ -88,13 +91,10 @@ const makeTSCollectionSchema = (collectionNode, collectionId) => {
88
91
  collectionSchema.description[key] = collectionNode[key];
89
92
  break;
90
93
  case 'layout':
91
- collectionSchema.description[key] = collectionNode[key];
94
+ collectionSchema.description[key] = (0, utils_js_1.unwrapNode)(collectionNode[key]);
92
95
  break;
93
96
  case 'formLayout':
94
- collectionSchema.description[key] = collectionNode[key];
95
- break;
96
- case 'required':
97
- collectionSchema.description[key] = collectionNode[key];
97
+ collectionSchema.description[key] = (0, utils_js_1.unwrapNode)(collectionNode[key]);
98
98
  break;
99
99
  }
100
100
  }
@@ -1,5 +1,5 @@
1
1
  "use strict";
2
- import { recursivelyUnwrapPropertyNodes, stringify, makeASTImports, resizeFirstChar, getCollectionId, UnquotedSymbol, getExposedFunctions, PACKAGE_NAME, DEFAULT_FUNCTIONS } from "./utils.mjs";
2
+ import { unwrapNode, recursivelyUnwrapPropertyNodes, stringify, makeASTImports, resizeFirstChar, getCollectionId, UnquotedSymbol, getExposedFunctions, PACKAGE_NAME, DEFAULT_FUNCTIONS } from "./utils.mjs";
3
3
  const initialImportedTypes = [
4
4
  "Collection",
5
5
  "SchemaWithId",
@@ -63,6 +63,9 @@ const makeTSCollectionSchema = (collectionNode, collectionId) => {
63
63
  collectionSchema.functions = makeTSFunctions(collectionNode[key]);
64
64
  collectionSchema.exposedFunctions = getExposedFunctions(collectionNode[key]);
65
65
  break;
66
+ case "required":
67
+ collectionSchema.description[key] = collectionNode[key];
68
+ break;
66
69
  case "table":
67
70
  case "filters":
68
71
  case "indexes":
@@ -83,13 +86,10 @@ const makeTSCollectionSchema = (collectionNode, collectionId) => {
83
86
  collectionSchema.description[key] = collectionNode[key];
84
87
  break;
85
88
  case "layout":
86
- collectionSchema.description[key] = collectionNode[key];
89
+ collectionSchema.description[key] = unwrapNode(collectionNode[key]);
87
90
  break;
88
91
  case "formLayout":
89
- collectionSchema.description[key] = collectionNode[key];
90
- break;
91
- case "required":
92
- collectionSchema.description[key] = collectionNode[key];
92
+ collectionSchema.description[key] = unwrapNode(collectionNode[key]);
93
93
  break;
94
94
  }
95
95
  }
@@ -13,6 +13,9 @@ export declare const makeASTImports: (ast: AST.Node[], initialImports?: Record<s
13
13
  code: string[];
14
14
  modifiedSymbols: Record<string, string>;
15
15
  };
16
+ export declare const unwrapNode: <TNode extends {
17
+ kind: string;
18
+ }>(node: TNode) => Omit<TNode, "kind" | symbol>;
16
19
  export declare const unwrapPropertyNode: ({ property, nestedProperties, nestedAdditionalProperties }: Pick<AST.PropertyNode, "property" | "nestedProperties" | "nestedAdditionalProperties">) => Property;
17
20
  /** Transforms the AST properties to the format of aeria schema properties */
18
21
  export declare const recursivelyUnwrapPropertyNodes: <TProperties extends Record<string, AST.PropertyNode | AST.PropertyNode[]>, TReturnType = TProperties[keyof TProperties] extends Array<unknown> ? Record<string, Property[]> : Record<string, Property>>(properties: TProperties) => TReturnType;
@@ -1,6 +1,6 @@
1
1
  "use strict";
2
2
  Object.defineProperty(exports, "__esModule", { value: true });
3
- exports.getExtendName = exports.getCollectionId = exports.resizeFirstChar = exports.stringify = exports.UnquotedSymbol = exports.recursivelyUnwrapPropertyNodes = exports.unwrapPropertyNode = exports.makeASTImports = exports.getExposedFunctions = exports.ArraySymbol = exports.DEFAULT_FUNCTIONS = exports.PACKAGE_NAME = void 0;
3
+ exports.getExtendName = exports.getCollectionId = exports.resizeFirstChar = exports.stringify = exports.UnquotedSymbol = exports.recursivelyUnwrapPropertyNodes = exports.unwrapPropertyNode = exports.unwrapNode = exports.makeASTImports = exports.getExposedFunctions = exports.ArraySymbol = exports.DEFAULT_FUNCTIONS = exports.PACKAGE_NAME = void 0;
4
4
  exports.PACKAGE_NAME = 'aeria';
5
5
  exports.DEFAULT_FUNCTIONS = [
6
6
  'count',
@@ -56,6 +56,11 @@ const makeASTImports = (ast, initialImports) => {
56
56
  };
57
57
  };
58
58
  exports.makeASTImports = makeASTImports;
59
+ const unwrapNode = (node) => {
60
+ const { kind, ...unwrappedNode } = Object.fromEntries(Object.entries(node).filter(([key]) => typeof key === 'string'));
61
+ return unwrappedNode;
62
+ };
63
+ exports.unwrapNode = unwrapNode;
59
64
  const unwrapPropertyNode = ({ property, nestedProperties, nestedAdditionalProperties }) => {
60
65
  const propertyOrPropertyItems = 'items' in property
61
66
  ? property.items
@@ -49,6 +49,10 @@ export const makeASTImports = (ast, initialImports) => {
49
49
  modifiedSymbols
50
50
  };
51
51
  };
52
+ export const unwrapNode = (node) => {
53
+ const { kind, ...unwrappedNode } = Object.fromEntries(Object.entries(node).filter(([key]) => typeof key === "string"));
54
+ return unwrappedNode;
55
+ };
52
56
  export const unwrapPropertyNode = ({ property, nestedProperties, nestedAdditionalProperties }) => {
53
57
  const propertyOrPropertyItems = "items" in property ? property.items : property;
54
58
  let unwrappedProperty = propertyOrPropertyItems;
package/dist/lexer.d.ts CHANGED
@@ -11,7 +11,8 @@ export declare const TOPLEVEL_KEYWORDS: readonly ["collection", "contract", "fun
11
11
  export declare const MISC_KEYWORDS: readonly ["extends"];
12
12
  export type Keyword = typeof COLLECTION_KEYWORDS[number] | typeof COLLECTION_ACTIONS_KEYWORDS[number] | typeof COLLECTION_SEARCH_KEYWORDS[number] | typeof COLLECTION_LAYOUT_KEYWORDS[number] | typeof COLLECTION_LAYOUT_OPTIONS_KEYWORDS[number] | typeof COLLECTION_FORM_LAYOUT_KEYWORDS[number] | typeof CONTRACT_KEYWORDS[number] | typeof TOPLEVEL_KEYWORDS[number] | typeof MISC_KEYWORDS[number];
13
13
  export declare const KEYWORDS: Keyword[];
14
- export declare const OPERATORS: readonly ["&&", "||", "==", "in", ">=", "<=", ">", "<"];
14
+ export declare const FINAL_OPERATORS: readonly ["==", "in", ">=", "<=", ">", "<", "!"];
15
+ export declare const LOGICAL_OPERATORS: readonly ["&&", "||"];
15
16
  export declare const tokenize: (rawInput: string) => {
16
17
  tokens: Token[];
17
18
  errors: Diagnostic[];
package/dist/lexer.js CHANGED
@@ -1,6 +1,6 @@
1
1
  "use strict";
2
2
  Object.defineProperty(exports, "__esModule", { value: true });
3
- exports.tokenize = exports.OPERATORS = exports.KEYWORDS = exports.MISC_KEYWORDS = exports.TOPLEVEL_KEYWORDS = exports.CONTRACT_KEYWORDS = exports.COLLECTION_FORM_LAYOUT_KEYWORDS = exports.COLLECTION_LAYOUT_OPTIONS_KEYWORDS = exports.COLLECTION_LAYOUT_KEYWORDS = exports.COLLECTION_SEARCH_KEYWORDS = exports.COLLECTION_ACTIONS_KEYWORDS = exports.COLLECTION_KEYWORDS = void 0;
3
+ exports.tokenize = exports.LOGICAL_OPERATORS = exports.FINAL_OPERATORS = exports.KEYWORDS = exports.MISC_KEYWORDS = exports.TOPLEVEL_KEYWORDS = exports.CONTRACT_KEYWORDS = exports.COLLECTION_FORM_LAYOUT_KEYWORDS = exports.COLLECTION_LAYOUT_OPTIONS_KEYWORDS = exports.COLLECTION_LAYOUT_KEYWORDS = exports.COLLECTION_SEARCH_KEYWORDS = exports.COLLECTION_ACTIONS_KEYWORDS = exports.COLLECTION_KEYWORDS = void 0;
4
4
  const token_js_1 = require("./token.js");
5
5
  const diagnostic_js_1 = require("./diagnostic.js");
6
6
  exports.COLLECTION_KEYWORDS = [
@@ -77,15 +77,18 @@ exports.TOPLEVEL_KEYWORDS = [
77
77
  ];
78
78
  exports.MISC_KEYWORDS = ['extends'];
79
79
  exports.KEYWORDS = [].concat(exports.COLLECTION_KEYWORDS, exports.COLLECTION_ACTIONS_KEYWORDS, exports.COLLECTION_SEARCH_KEYWORDS, exports.COLLECTION_LAYOUT_KEYWORDS, exports.COLLECTION_LAYOUT_OPTIONS_KEYWORDS, exports.COLLECTION_FORM_LAYOUT_KEYWORDS, exports.CONTRACT_KEYWORDS, exports.TOPLEVEL_KEYWORDS, exports.MISC_KEYWORDS);
80
- exports.OPERATORS = [
81
- '&&',
82
- '||',
80
+ exports.FINAL_OPERATORS = [
83
81
  '==',
84
82
  'in',
85
83
  '>=',
86
84
  '<=',
87
85
  '>',
88
86
  '<',
87
+ '!',
88
+ ];
89
+ exports.LOGICAL_OPERATORS = [
90
+ '&&',
91
+ '||',
89
92
  ];
90
93
  const keywordsSet = new Set();
91
94
  for (const keyword of exports.KEYWORDS) {
@@ -130,7 +133,7 @@ const TOKENS = [
130
133
  },
131
134
  {
132
135
  type: token_js_1.TokenType.Operator,
133
- matcher: exports.OPERATORS,
136
+ matcher: [].concat(exports.FINAL_OPERATORS, exports.LOGICAL_OPERATORS),
134
137
  },
135
138
  {
136
139
  type: token_js_1.TokenType.Pipe,
package/dist/lexer.mjs CHANGED
@@ -85,15 +85,18 @@ export const KEYWORDS = [].concat(
85
85
  TOPLEVEL_KEYWORDS,
86
86
  MISC_KEYWORDS
87
87
  );
88
- export const OPERATORS = [
89
- "&&",
90
- "||",
88
+ export const FINAL_OPERATORS = [
91
89
  "==",
92
90
  "in",
93
91
  ">=",
94
92
  "<=",
95
93
  ">",
96
- "<"
94
+ "<",
95
+ "!"
96
+ ];
97
+ export const LOGICAL_OPERATORS = [
98
+ "&&",
99
+ "||"
97
100
  ];
98
101
  const keywordsSet = /* @__PURE__ */ new Set();
99
102
  for (const keyword of KEYWORDS) {
@@ -138,7 +141,7 @@ const TOKENS = [
138
141
  },
139
142
  {
140
143
  type: TokenType.Operator,
141
- matcher: OPERATORS
144
+ matcher: [].concat(FINAL_OPERATORS, LOGICAL_OPERATORS)
142
145
  },
143
146
  {
144
147
  type: TokenType.Pipe,
package/dist/parser.js CHANGED
@@ -1088,7 +1088,9 @@ const parse = (tokens) => {
1088
1088
  const { value: keyword, location: keywordLocation } = consume(token_js_1.TokenType.Keyword, lexer.COLLECTION_FORM_LAYOUT_KEYWORDS);
1089
1089
  switch (keyword) {
1090
1090
  case 'if': {
1091
- fields[identifier].if = parseCondition();
1091
+ const ifTerms = [];
1092
+ fields[identifier].if = parseCondition(ifTerms);
1093
+ node[AST.LOCATION_SYMBOL].terms = ifTerms;
1092
1094
  break;
1093
1095
  }
1094
1096
  case 'span':
@@ -1123,13 +1125,13 @@ const parse = (tokens) => {
1123
1125
  consume(token_js_1.TokenType.RightBracket);
1124
1126
  return node;
1125
1127
  };
1126
- const parseCondition = () => {
1128
+ const parseCondition = (symbols = []) => {
1127
1129
  if (match(token_js_1.TokenType.LeftParens)) {
1128
1130
  consume(token_js_1.TokenType.LeftParens);
1129
1131
  let operatorType, newOp = operatorType;
1130
1132
  const conditions = [];
1131
1133
  while (!match(token_js_1.TokenType.RightParens)) {
1132
- conditions.push(parseCondition());
1134
+ conditions.push(parseCondition(symbols));
1133
1135
  if (match(token_js_1.TokenType.RightParens)) {
1134
1136
  break;
1135
1137
  }
@@ -1167,10 +1169,34 @@ const parse = (tokens) => {
1167
1169
  }
1168
1170
  }
1169
1171
  }
1170
- const { value: term1 } = consume(token_js_1.TokenType.Identifier);
1172
+ if (match(token_js_1.TokenType.Operator, '!')) {
1173
+ consume(token_js_1.TokenType.Operator);
1174
+ return {
1175
+ not: parseCondition(symbols),
1176
+ };
1177
+ }
1178
+ const { value: term1, location: term1Location } = consume(token_js_1.TokenType.Identifier);
1179
+ const term1Symbol = Symbol();
1180
+ exports.locationMap.set(term1Symbol, term1Location);
1181
+ symbols.push([
1182
+ term1,
1183
+ term1Symbol,
1184
+ ]);
1185
+ if (!match(token_js_1.TokenType.Operator, lexer.FINAL_OPERATORS)) {
1186
+ return {
1187
+ operator: 'truthy',
1188
+ term1,
1189
+ };
1190
+ }
1171
1191
  const { value: operatorSymbol, location } = consume(token_js_1.TokenType.Operator);
1172
- const { value: term2 } = current();
1173
- advance();
1192
+ let term2;
1193
+ if (match(token_js_1.TokenType.LeftParens)) {
1194
+ term2 = parseCondition(symbols);
1195
+ }
1196
+ else {
1197
+ term2 = current().value;
1198
+ advance();
1199
+ }
1174
1200
  let operator;
1175
1201
  switch (operatorSymbol) {
1176
1202
  case '==':
package/dist/parser.mjs CHANGED
@@ -1027,7 +1027,9 @@ export const parse = (tokens) => {
1027
1027
  const { value: keyword2, location: keywordLocation2 } = consume(TokenType.Keyword, lexer.COLLECTION_FORM_LAYOUT_KEYWORDS);
1028
1028
  switch (keyword2) {
1029
1029
  case "if": {
1030
- fields[identifier].if = parseCondition();
1030
+ const ifTerms = [];
1031
+ fields[identifier].if = parseCondition(ifTerms);
1032
+ node[AST.LOCATION_SYMBOL].terms = ifTerms;
1031
1033
  break;
1032
1034
  }
1033
1035
  case "span":
@@ -1060,13 +1062,13 @@ export const parse = (tokens) => {
1060
1062
  consume(TokenType.RightBracket);
1061
1063
  return node;
1062
1064
  };
1063
- const parseCondition = () => {
1065
+ const parseCondition = (symbols = []) => {
1064
1066
  if (match(TokenType.LeftParens)) {
1065
1067
  consume(TokenType.LeftParens);
1066
1068
  let operatorType, newOp = operatorType;
1067
1069
  const conditions = [];
1068
1070
  while (!match(TokenType.RightParens)) {
1069
- conditions.push(parseCondition());
1071
+ conditions.push(parseCondition(symbols));
1070
1072
  if (match(TokenType.RightParens)) {
1071
1073
  break;
1072
1074
  }
@@ -1104,10 +1106,33 @@ export const parse = (tokens) => {
1104
1106
  }
1105
1107
  }
1106
1108
  }
1107
- const { value: term1 } = consume(TokenType.Identifier);
1109
+ if (match(TokenType.Operator, "!")) {
1110
+ consume(TokenType.Operator);
1111
+ return {
1112
+ not: parseCondition(symbols)
1113
+ };
1114
+ }
1115
+ const { value: term1, location: term1Location } = consume(TokenType.Identifier);
1116
+ const term1Symbol = Symbol();
1117
+ locationMap.set(term1Symbol, term1Location);
1118
+ symbols.push([
1119
+ term1,
1120
+ term1Symbol
1121
+ ]);
1122
+ if (!match(TokenType.Operator, lexer.FINAL_OPERATORS)) {
1123
+ return {
1124
+ operator: "truthy",
1125
+ term1
1126
+ };
1127
+ }
1108
1128
  const { value: operatorSymbol, location } = consume(TokenType.Operator);
1109
- const { value: term2 } = current();
1110
- advance();
1129
+ let term2;
1130
+ if (match(TokenType.LeftParens)) {
1131
+ term2 = parseCondition(symbols);
1132
+ } else {
1133
+ term2 = current().value;
1134
+ advance();
1135
+ }
1111
1136
  let operator;
1112
1137
  switch (operatorSymbol) {
1113
1138
  case "==":
package/dist/semantic.js CHANGED
@@ -169,6 +169,14 @@ const analyze = async (ast, options, errors = []) => {
169
169
  }
170
170
  }
171
171
  }
172
+ if (node.formLayout[AST.LOCATION_SYMBOL].terms) {
173
+ for (const [name, symbol] of node.formLayout[AST.LOCATION_SYMBOL].terms) {
174
+ if (!(name in node.properties)) {
175
+ const location = parser_js_1.locationMap.get(symbol);
176
+ errors.push(new diagnostic_js_1.Diagnostic(`invalid left operand "${name}"`, location));
177
+ }
178
+ }
179
+ }
172
180
  }
173
181
  }
174
182
  for (const node of ast.contracts) {
package/dist/semantic.mjs CHANGED
@@ -131,6 +131,14 @@ export const analyze = async (ast, options, errors = []) => {
131
131
  }
132
132
  }
133
133
  }
134
+ if (node.formLayout[AST.LOCATION_SYMBOL].terms) {
135
+ for (const [name, symbol] of node.formLayout[AST.LOCATION_SYMBOL].terms) {
136
+ if (!(name in node.properties)) {
137
+ const location = locationMap.get(symbol);
138
+ errors.push(new Diagnostic(`invalid left operand "${name}"`, location));
139
+ }
140
+ }
141
+ }
134
142
  }
135
143
  }
136
144
  for (const node of ast.contracts) {
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "@aeriajs/compiler",
3
- "version": "0.0.27",
3
+ "version": "0.0.29",
4
4
  "description": "",
5
5
  "main": "dist/index.js",
6
6
  "module": "dist/index.mjs",