@fibery/expression-utils 6.0.1 → 8.0.0

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.
@@ -262,7 +262,7 @@ const collectFieldExpressions = (memo, expression) => {
262
262
  }
263
263
  }
264
264
  }
265
- } else if (isFieldExpression(expression)) {
265
+ } else if (isFieldExpression(expression) || isMultiFieldExpression(expression)) {
266
266
  memo.push(expression);
267
267
  } else if (expression["q/from"] && isFieldExpression(expression["q/from"])) {
268
268
  const innerMemo = [];
@@ -275,6 +275,12 @@ const collectFieldExpressions = (memo, expression) => {
275
275
  throw new NotImplementedError(expression, "expression");
276
276
  }
277
277
  };
278
+
279
+ /** @deprecated
280
+ * This method checks few expression forms, that we do not generate on frontend anymore(field-access shortcut, direct value as parameter).
281
+ * I'm afraid to replace it with implementation based on visitor everywhere, as visitors don't allow such expression forms and I don't want to extend visitor with those forms.
282
+ * If you need this method in new places, consider implementing same logic on visitors and use it.
283
+ **/
278
284
  const extractFieldExpressions = expression => {
279
285
  const memo = [];
280
286
  collectFieldExpressions(memo, expression);
@@ -287,7 +293,6 @@ const createExpressionVisitor = visitor => {
287
293
  visitFunctionCallExpression: ([fnName, ...args]) => [fnName, ...args.map(x => visitorWithDefault.visitExpression(x))],
288
294
  visitFromRootFieldExpression: ([fromRootKeyword, ...rest]) => [fromRootKeyword, ...rest.map(x => visitorWithDefault.visitExpression(x))],
289
295
  visitFieldExpression: expression => expression,
290
- visitMultiFieldExpression: expression => expression,
291
296
  visitOrderByExpression: orderByExpression => orderByExpression.map(x => {
292
297
  const [fieldExpression, orderDir] = x;
293
298
  const fieldExpressionNew = visitorWithDefault.visitExpression(fieldExpression);
@@ -325,10 +330,8 @@ const createExpressionVisitor = visitor => {
325
330
  return visitorWithDefault.visitFromRootFieldExpression(expression, visitorDefault);
326
331
  } else if (isFunctionCallExpression(expression)) {
327
332
  return visitorWithDefault.visitFunctionCallExpression(expression, visitorDefault);
328
- } else if (isFieldExpression(expression)) {
333
+ } else if (isFieldExpression(expression) || isMultiFieldExpression(expression)) {
329
334
  return visitorWithDefault.visitFieldExpression(expression, visitorDefault);
330
- } else if (isMultiFieldExpression(expression)) {
331
- return visitorWithDefault.visitMultiFieldExpression(expression, visitorDefault);
332
335
  } else if (isQueryExpression(expression)) {
333
336
  return visitorWithDefault.visitQueryExpression(expression, visitorDefault);
334
337
  } else {
@@ -360,6 +363,7 @@ var utils = {
360
363
  isBinaryExpression: isBinaryExpression,
361
364
  isNaryExpression: isNaryExpression,
362
365
  isVariableExpression: isVariableExpression,
366
+ isMultiFieldAccess: isMultiFieldAccess,
363
367
  isMultiFieldExpression: isMultiFieldExpression,
364
368
  isFieldExpression: isFieldExpression,
365
369
  isQueryExpression: isQueryExpression,
@@ -384,7 +388,24 @@ const visitFieldExpressionForReplaceIdsWithNamesVisitor = ({
384
388
  currentTypeObject,
385
389
  fieldExpressionInNamesTerms
386
390
  }, fieldId) => {
387
- if (currentTypeObject && currentTypeObject.fieldObjectsById.hasOwnProperty(fieldId)) {
391
+ if (currentTypeObject && isMultiFieldAccess(fieldId) && currentTypeObject.fieldObjectsById.hasOwnProperty(fieldId[0])) {
392
+ var _fieldObject$multiRel;
393
+ const typeId = fieldId[1];
394
+ const fieldObject = currentTypeObject.fieldObjectsById[fieldId[0]];
395
+ const nextTypeObject = (_fieldObject$multiRel = fieldObject.multiRelatedFieldObjects.find(f => f.holderTypeObject.id === typeId)) == null ? void 0 : _fieldObject$multiRel.holderTypeObject;
396
+ if (!nextTypeObject) {
397
+ return onFieldNotFound({
398
+ currentTypeObject,
399
+ fieldExpressionInNamesTerms,
400
+ fieldId: fieldId,
401
+ expression
402
+ });
403
+ }
404
+ return {
405
+ currentTypeObject: nextTypeObject,
406
+ fieldExpressionInNamesTerms: [...fieldExpressionInNamesTerms, [fieldObject.name, nextTypeObject.name]]
407
+ };
408
+ } else if (currentTypeObject && currentTypeObject.fieldObjectsById.hasOwnProperty(fieldId)) {
388
409
  const fieldObject = currentTypeObject.fieldObjectsById[fieldId];
389
410
  return {
390
411
  currentTypeObject: fieldObject.typeObject,
@@ -459,7 +480,24 @@ const visitFieldExpressionForReplaceNamesWithIdsVisitor = ({
459
480
  currentTypeObject,
460
481
  fieldExpressionInIdsTerms
461
482
  }, field) => {
462
- if (currentTypeObject && currentTypeObject.fieldObjectsByName.hasOwnProperty(field)) {
483
+ if (currentTypeObject && isMultiFieldAccess(field) && currentTypeObject.fieldObjectsByName.hasOwnProperty(field[0])) {
484
+ var _fieldObject$multiRel2;
485
+ const type = field[1];
486
+ const fieldObject = currentTypeObject.fieldObjectsByName[field[0]];
487
+ const nextTypeObject = (_fieldObject$multiRel2 = fieldObject.multiRelatedFieldObjects.find(f => f.holderType === type)) == null ? void 0 : _fieldObject$multiRel2.holderTypeObject;
488
+ if (!nextTypeObject) {
489
+ return onFieldNotFound({
490
+ currentTypeObject,
491
+ fieldExpressionInIdsTerms,
492
+ field,
493
+ expression
494
+ });
495
+ }
496
+ return {
497
+ currentTypeObject: nextTypeObject,
498
+ fieldExpressionInIdsTerms: [...fieldExpressionInIdsTerms, [fieldObject.id, nextTypeObject.id]]
499
+ };
500
+ } else if (currentTypeObject && currentTypeObject.fieldObjectsByName.hasOwnProperty(field)) {
463
501
  const fieldObject = currentTypeObject.fieldObjectsByName[field];
464
502
  return {
465
503
  currentTypeObject: fieldObject.typeObject,
@@ -531,7 +569,22 @@ const deleteExpressionsWithNotFoundFieldsVisitor = typeObject => {
531
569
  }
532
570
  },
533
571
  visitFieldExpression: expression => {
534
- const fieldTypeObject = expression.reduce((holderTypeObject, field) => holderTypeObject && holderTypeObject.fieldObjectsByName.hasOwnProperty(field) ? holderTypeObject.fieldObjectsByName[field].typeObject : null, typeObject);
572
+ const fieldTypeObject = expression.reduce((holderTypeObject, field) => {
573
+ if (holderTypeObject && isMultiFieldAccess(field) && holderTypeObject.fieldObjectsByName.hasOwnProperty(field[0])) {
574
+ var _fieldObject$multiRel3;
575
+ const type = field[1];
576
+ const fieldObject = holderTypeObject.fieldObjectsByName[field[0]];
577
+ const nextTypeObject = (_fieldObject$multiRel3 = fieldObject.multiRelatedFieldObjects.find(f => f.holderType === type)) == null ? void 0 : _fieldObject$multiRel3.holderTypeObject;
578
+ if (!nextTypeObject) {
579
+ return null;
580
+ }
581
+ return nextTypeObject;
582
+ } else if (holderTypeObject && holderTypeObject.fieldObjectsByName.hasOwnProperty(field)) {
583
+ return holderTypeObject.fieldObjectsByName[field].typeObject;
584
+ } else {
585
+ return null;
586
+ }
587
+ }, typeObject);
535
588
  return fieldTypeObject && expression;
536
589
  },
537
590
  visitOrderByExpression: orderByExpression => {
@@ -611,8 +664,22 @@ const getFieldAccessExpressionTypeObject = ({
611
664
  const reduced = expression.reduce(({
612
665
  currentTypeObject
613
666
  }, fieldId, index) => {
614
- const fieldObject = currentTypeObject && currentTypeObject.fieldObjects.find(f => f.id === fieldId);
615
- if (fieldObject) {
667
+ if (currentTypeObject && isMultiFieldAccess(fieldId) && currentTypeObject.fieldObjectsById.hasOwnProperty(fieldId[0])) {
668
+ var _fieldObject$multiRel4;
669
+ const typeId = fieldId[1];
670
+ const fieldObject = currentTypeObject.fieldObjectsById[fieldId[0]];
671
+ const nextTypeObject = (_fieldObject$multiRel4 = fieldObject.multiRelatedFieldObjects.find(f => f.holderTypeObject.id === typeId)) == null ? void 0 : _fieldObject$multiRel4.holderTypeObject;
672
+ if (!nextTypeObject) {
673
+ return onFieldNotFound({
674
+ currentTypeObject,
675
+ fieldId
676
+ });
677
+ }
678
+ return {
679
+ currentTypeObject: nextTypeObject
680
+ };
681
+ } else if (currentTypeObject && currentTypeObject.fieldObjectsById.hasOwnProperty(fieldId)) {
682
+ const fieldObject = currentTypeObject.fieldObjectsById[fieldId];
616
683
  if (returnRefTypeInsteadOfId && index === expression.length - 1 && fieldObject.isId) {
617
684
  return {
618
685
  currentTypeObject
package/lib/utils.js CHANGED
@@ -74,7 +74,7 @@ const collectFieldExpressions = (memo, expression) => {
74
74
  }
75
75
  }
76
76
  }
77
- } else if (isFieldExpression(expression)) {
77
+ } else if (isFieldExpression(expression) || isMultiFieldExpression(expression)) {
78
78
  memo.push(expression);
79
79
  } else if (expression["q/from"] && isFieldExpression(expression["q/from"])) {
80
80
  const innerMemo = [];
@@ -87,6 +87,12 @@ const collectFieldExpressions = (memo, expression) => {
87
87
  throw new NotImplementedError(expression, "expression");
88
88
  }
89
89
  };
90
+
91
+ /** @deprecated
92
+ * This method checks few expression forms, that we do not generate on frontend anymore(field-access shortcut, direct value as parameter).
93
+ * I'm afraid to replace it with implementation based on visitor everywhere, as visitors don't allow such expression forms and I don't want to extend visitor with those forms.
94
+ * If you need this method in new places, consider implementing same logic on visitors and use it.
95
+ **/
90
96
  const extractFieldExpressions = expression => {
91
97
  const memo = [];
92
98
  collectFieldExpressions(memo, expression);
@@ -99,7 +105,6 @@ const createExpressionVisitor = visitor => {
99
105
  visitFunctionCallExpression: ([fnName, ...args]) => [fnName, ...args.map(x => visitorWithDefault.visitExpression(x))],
100
106
  visitFromRootFieldExpression: ([fromRootKeyword, ...rest]) => [fromRootKeyword, ...rest.map(x => visitorWithDefault.visitExpression(x))],
101
107
  visitFieldExpression: expression => expression,
102
- visitMultiFieldExpression: expression => expression,
103
108
  visitOrderByExpression: orderByExpression => orderByExpression.map(x => {
104
109
  const [fieldExpression, orderDir] = x;
105
110
  const fieldExpressionNew = visitorWithDefault.visitExpression(fieldExpression);
@@ -137,10 +142,8 @@ const createExpressionVisitor = visitor => {
137
142
  return visitorWithDefault.visitFromRootFieldExpression(expression, visitorDefault);
138
143
  } else if (isFunctionCallExpression(expression)) {
139
144
  return visitorWithDefault.visitFunctionCallExpression(expression, visitorDefault);
140
- } else if (isFieldExpression(expression)) {
145
+ } else if (isFieldExpression(expression) || isMultiFieldExpression(expression)) {
141
146
  return visitorWithDefault.visitFieldExpression(expression, visitorDefault);
142
- } else if (isMultiFieldExpression(expression)) {
143
- return visitorWithDefault.visitMultiFieldExpression(expression, visitorDefault);
144
147
  } else if (isQueryExpression(expression)) {
145
148
  return visitorWithDefault.visitQueryExpression(expression, visitorDefault);
146
149
  } else {
@@ -168,6 +171,7 @@ exports.isDateRangeFunctionExpression = isDateRangeFunctionExpression;
168
171
  exports.isFieldExpression = isFieldExpression;
169
172
  exports.isFromRootFieldExpression = isFromRootFieldExpression;
170
173
  exports.isFunctionCallExpression = isFunctionCallExpression;
174
+ exports.isMultiFieldAccess = isMultiFieldAccess;
171
175
  exports.isMultiFieldExpression = isMultiFieldExpression;
172
176
  exports.isNaryExpression = isNaryExpression;
173
177
  exports.isQueryExpression = isQueryExpression;
package/lib/visitors.js CHANGED
@@ -53,7 +53,6 @@ const createExpressionVisitor = visitor => {
53
53
  visitFunctionCallExpression: ([fnName, ...args]) => [fnName, ...args.map(x => visitorWithDefault.visitExpression(x))],
54
54
  visitFromRootFieldExpression: ([fromRootKeyword, ...rest]) => [fromRootKeyword, ...rest.map(x => visitorWithDefault.visitExpression(x))],
55
55
  visitFieldExpression: expression => expression,
56
- visitMultiFieldExpression: expression => expression,
57
56
  visitOrderByExpression: orderByExpression => orderByExpression.map(x => {
58
57
  const [fieldExpression, orderDir] = x;
59
58
  const fieldExpressionNew = visitorWithDefault.visitExpression(fieldExpression);
@@ -91,10 +90,8 @@ const createExpressionVisitor = visitor => {
91
90
  return visitorWithDefault.visitFromRootFieldExpression(expression, visitorDefault);
92
91
  } else if (isFunctionCallExpression(expression)) {
93
92
  return visitorWithDefault.visitFunctionCallExpression(expression, visitorDefault);
94
- } else if (isFieldExpression(expression)) {
93
+ } else if (isFieldExpression(expression) || isMultiFieldExpression(expression)) {
95
94
  return visitorWithDefault.visitFieldExpression(expression, visitorDefault);
96
- } else if (isMultiFieldExpression(expression)) {
97
- return visitorWithDefault.visitMultiFieldExpression(expression, visitorDefault);
98
95
  } else if (isQueryExpression(expression)) {
99
96
  return visitorWithDefault.visitQueryExpression(expression, visitorDefault);
100
97
  } else {
@@ -126,7 +123,24 @@ const visitFieldExpressionForReplaceIdsWithNamesVisitor = ({
126
123
  currentTypeObject,
127
124
  fieldExpressionInNamesTerms
128
125
  }, fieldId) => {
129
- if (currentTypeObject && currentTypeObject.fieldObjectsById.hasOwnProperty(fieldId)) {
126
+ if (currentTypeObject && isMultiFieldAccess(fieldId) && currentTypeObject.fieldObjectsById.hasOwnProperty(fieldId[0])) {
127
+ var _fieldObject$multiRel;
128
+ const typeId = fieldId[1];
129
+ const fieldObject = currentTypeObject.fieldObjectsById[fieldId[0]];
130
+ const nextTypeObject = (_fieldObject$multiRel = fieldObject.multiRelatedFieldObjects.find(f => f.holderTypeObject.id === typeId)) == null ? void 0 : _fieldObject$multiRel.holderTypeObject;
131
+ if (!nextTypeObject) {
132
+ return onFieldNotFound({
133
+ currentTypeObject,
134
+ fieldExpressionInNamesTerms,
135
+ fieldId: fieldId,
136
+ expression
137
+ });
138
+ }
139
+ return {
140
+ currentTypeObject: nextTypeObject,
141
+ fieldExpressionInNamesTerms: [...fieldExpressionInNamesTerms, [fieldObject.name, nextTypeObject.name]]
142
+ };
143
+ } else if (currentTypeObject && currentTypeObject.fieldObjectsById.hasOwnProperty(fieldId)) {
130
144
  const fieldObject = currentTypeObject.fieldObjectsById[fieldId];
131
145
  return {
132
146
  currentTypeObject: fieldObject.typeObject,
@@ -201,7 +215,24 @@ const visitFieldExpressionForReplaceNamesWithIdsVisitor = ({
201
215
  currentTypeObject,
202
216
  fieldExpressionInIdsTerms
203
217
  }, field) => {
204
- if (currentTypeObject && currentTypeObject.fieldObjectsByName.hasOwnProperty(field)) {
218
+ if (currentTypeObject && isMultiFieldAccess(field) && currentTypeObject.fieldObjectsByName.hasOwnProperty(field[0])) {
219
+ var _fieldObject$multiRel2;
220
+ const type = field[1];
221
+ const fieldObject = currentTypeObject.fieldObjectsByName[field[0]];
222
+ const nextTypeObject = (_fieldObject$multiRel2 = fieldObject.multiRelatedFieldObjects.find(f => f.holderType === type)) == null ? void 0 : _fieldObject$multiRel2.holderTypeObject;
223
+ if (!nextTypeObject) {
224
+ return onFieldNotFound({
225
+ currentTypeObject,
226
+ fieldExpressionInIdsTerms,
227
+ field,
228
+ expression
229
+ });
230
+ }
231
+ return {
232
+ currentTypeObject: nextTypeObject,
233
+ fieldExpressionInIdsTerms: [...fieldExpressionInIdsTerms, [fieldObject.id, nextTypeObject.id]]
234
+ };
235
+ } else if (currentTypeObject && currentTypeObject.fieldObjectsByName.hasOwnProperty(field)) {
205
236
  const fieldObject = currentTypeObject.fieldObjectsByName[field];
206
237
  return {
207
238
  currentTypeObject: fieldObject.typeObject,
@@ -273,7 +304,22 @@ const deleteExpressionsWithNotFoundFieldsVisitor = typeObject => {
273
304
  }
274
305
  },
275
306
  visitFieldExpression: expression => {
276
- const fieldTypeObject = expression.reduce((holderTypeObject, field) => holderTypeObject && holderTypeObject.fieldObjectsByName.hasOwnProperty(field) ? holderTypeObject.fieldObjectsByName[field].typeObject : null, typeObject);
307
+ const fieldTypeObject = expression.reduce((holderTypeObject, field) => {
308
+ if (holderTypeObject && isMultiFieldAccess(field) && holderTypeObject.fieldObjectsByName.hasOwnProperty(field[0])) {
309
+ var _fieldObject$multiRel3;
310
+ const type = field[1];
311
+ const fieldObject = holderTypeObject.fieldObjectsByName[field[0]];
312
+ const nextTypeObject = (_fieldObject$multiRel3 = fieldObject.multiRelatedFieldObjects.find(f => f.holderType === type)) == null ? void 0 : _fieldObject$multiRel3.holderTypeObject;
313
+ if (!nextTypeObject) {
314
+ return null;
315
+ }
316
+ return nextTypeObject;
317
+ } else if (holderTypeObject && holderTypeObject.fieldObjectsByName.hasOwnProperty(field)) {
318
+ return holderTypeObject.fieldObjectsByName[field].typeObject;
319
+ } else {
320
+ return null;
321
+ }
322
+ }, typeObject);
277
323
  return fieldTypeObject && expression;
278
324
  },
279
325
  visitOrderByExpression: orderByExpression => {
@@ -353,8 +399,22 @@ const getFieldAccessExpressionTypeObject = ({
353
399
  const reduced = expression.reduce(({
354
400
  currentTypeObject
355
401
  }, fieldId, index) => {
356
- const fieldObject = currentTypeObject && currentTypeObject.fieldObjects.find(f => f.id === fieldId);
357
- if (fieldObject) {
402
+ if (currentTypeObject && isMultiFieldAccess(fieldId) && currentTypeObject.fieldObjectsById.hasOwnProperty(fieldId[0])) {
403
+ var _fieldObject$multiRel4;
404
+ const typeId = fieldId[1];
405
+ const fieldObject = currentTypeObject.fieldObjectsById[fieldId[0]];
406
+ const nextTypeObject = (_fieldObject$multiRel4 = fieldObject.multiRelatedFieldObjects.find(f => f.holderTypeObject.id === typeId)) == null ? void 0 : _fieldObject$multiRel4.holderTypeObject;
407
+ if (!nextTypeObject) {
408
+ return onFieldNotFound({
409
+ currentTypeObject,
410
+ fieldId
411
+ });
412
+ }
413
+ return {
414
+ currentTypeObject: nextTypeObject
415
+ };
416
+ } else if (currentTypeObject && currentTypeObject.fieldObjectsById.hasOwnProperty(fieldId)) {
417
+ const fieldObject = currentTypeObject.fieldObjectsById[fieldId];
358
418
  if (returnRefTypeInsteadOfId && index === expression.length - 1 && fieldObject.isId) {
359
419
  return {
360
420
  currentTypeObject
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "@fibery/expression-utils",
3
- "version": "6.0.1",
3
+ "version": "8.0.0",
4
4
  "description": "utils for working with fibery api expressions",
5
5
  "exports": {
6
6
  ".": "./lib/expression-utils.js",
@@ -38,7 +38,7 @@
38
38
  "@fibery/eslint-config": "8.5.1"
39
39
  },
40
40
  "peerDependencies": {
41
- "@fibery/schema": "10.0.1"
41
+ "@fibery/schema": "10.1.0"
42
42
  },
43
43
  "jest": {
44
44
  "testEnvironment": "node",