angular-odata 0.99.2 → 0.100.1

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 (72) hide show
  1. package/esm2020/lib/api.mjs +65 -55
  2. package/esm2020/lib/cache/cache.mjs +2 -2
  3. package/esm2020/lib/client.mjs +3 -3
  4. package/esm2020/lib/helper.mjs +91 -86
  5. package/esm2020/lib/models/collection.mjs +35 -46
  6. package/esm2020/lib/models/model.mjs +36 -40
  7. package/esm2020/lib/models/options.mjs +53 -36
  8. package/esm2020/lib/module.mjs +4 -4
  9. package/esm2020/lib/options.mjs +4 -3
  10. package/esm2020/lib/resources/query/builder.mjs +5 -7
  11. package/esm2020/lib/resources/query/expressions/base.mjs +1 -1
  12. package/esm2020/lib/resources/query/expressions/compute.mjs +13 -6
  13. package/esm2020/lib/resources/query/expressions/expand.mjs +77 -13
  14. package/esm2020/lib/resources/query/expressions/filter.mjs +11 -5
  15. package/esm2020/lib/resources/query/expressions/orderby.mjs +11 -3
  16. package/esm2020/lib/resources/query/expressions/search.mjs +15 -3
  17. package/esm2020/lib/resources/query/expressions/select.mjs +10 -5
  18. package/esm2020/lib/resources/query/expressions/syntax.mjs +42 -9
  19. package/esm2020/lib/resources/query/handlers.mjs +41 -30
  20. package/esm2020/lib/resources/query/options.mjs +47 -44
  21. package/esm2020/lib/resources/resource.mjs +22 -61
  22. package/esm2020/lib/resources/responses/annotations.mjs +6 -6
  23. package/esm2020/lib/resources/responses/options.mjs +1 -2
  24. package/esm2020/lib/resources/responses/response.mjs +3 -3
  25. package/esm2020/lib/resources/types/entity-set.mjs +1 -1
  26. package/esm2020/lib/resources/types/entity.mjs +3 -3
  27. package/esm2020/lib/resources/types/function.mjs +9 -1
  28. package/esm2020/lib/schema/callable.mjs +6 -2
  29. package/esm2020/lib/schema/enum-type.mjs +10 -2
  30. package/esm2020/lib/schema/parsers/callable.mjs +3 -2
  31. package/esm2020/lib/schema/parsers/enum-type.mjs +6 -5
  32. package/esm2020/lib/schema/parsers/structured-type.mjs +5 -5
  33. package/esm2020/lib/schema/structured-type.mjs +4 -9
  34. package/esm2020/lib/services/entity-set.mjs +6 -6
  35. package/esm2020/lib/services/factory.mjs +3 -3
  36. package/esm2020/lib/types.mjs +2 -1
  37. package/esm2020/lib/utils/objects.mjs +5 -1
  38. package/esm2020/lib/utils/urls.mjs +2 -2
  39. package/fesm2015/angular-odata.mjs +642 -498
  40. package/fesm2015/angular-odata.mjs.map +1 -1
  41. package/fesm2020/angular-odata.mjs +642 -502
  42. package/fesm2020/angular-odata.mjs.map +1 -1
  43. package/lib/helper.d.ts +28 -57
  44. package/lib/models/collection.d.ts +4 -2
  45. package/lib/models/model.d.ts +3 -9
  46. package/lib/models/options.d.ts +13 -11
  47. package/lib/options.d.ts +4 -4
  48. package/lib/resources/query/builder.d.ts +2 -1
  49. package/lib/resources/query/expressions/base.d.ts +1 -0
  50. package/lib/resources/query/expressions/compute.d.ts +3 -2
  51. package/lib/resources/query/expressions/expand.d.ts +40 -12
  52. package/lib/resources/query/expressions/filter.d.ts +22 -21
  53. package/lib/resources/query/expressions/orderby.d.ts +4 -2
  54. package/lib/resources/query/expressions/search.d.ts +5 -2
  55. package/lib/resources/query/expressions/select.d.ts +3 -2
  56. package/lib/resources/query/expressions/syntax.d.ts +12 -2
  57. package/lib/resources/query/handlers.d.ts +19 -15
  58. package/lib/resources/query/options.d.ts +15 -15
  59. package/lib/resources/resource.d.ts +1 -0
  60. package/lib/resources/responses/annotations.d.ts +12 -18
  61. package/lib/resources/responses/options.d.ts +2 -3
  62. package/lib/resources/responses/response.d.ts +1 -3
  63. package/lib/resources/types/entity-set.d.ts +1 -1
  64. package/lib/resources/types/function.d.ts +3 -0
  65. package/lib/schema/callable.d.ts +4 -4
  66. package/lib/schema/enum-type.d.ts +10 -4
  67. package/lib/schema/parsers/callable.d.ts +9 -7
  68. package/lib/schema/parsers/enum-type.d.ts +7 -5
  69. package/lib/schema/parsers/structured-type.d.ts +7 -7
  70. package/lib/schema/structured-type.d.ts +4 -4
  71. package/lib/types.d.ts +6 -5
  72. package/package.json +3 -3
@@ -33,6 +33,7 @@ var QueryOptionNames;
33
33
  QueryOptionNames["skip"] = "skip";
34
34
  QueryOptionNames["skiptoken"] = "skiptoken";
35
35
  QueryOptionNames["format"] = "format";
36
+ QueryOptionNames["levels"] = "levels";
36
37
  QueryOptionNames["count"] = "count";
37
38
  })(QueryOptionNames || (QueryOptionNames = {}));
38
39
  const NONE_PARSER = {
@@ -213,7 +214,7 @@ class ODataCache {
213
214
  return of(cached);
214
215
  }
215
216
  else {
216
- return throwError('No Cached');
217
+ return throwError(() => new Error('No Cached'));
217
218
  }
218
219
  }
219
220
  if (policy === 'cache-first' ||
@@ -390,7 +391,7 @@ function buildPathAndQuery({ select, search, skiptoken, format, top, skip, filte
390
391
  }
391
392
  if (func) {
392
393
  if (typeof func === 'string') {
393
- path += `/${func}`;
394
+ path += `/${func}()`;
394
395
  }
395
396
  else if (typeof func === 'object') {
396
397
  const [funcName] = Object.keys(func);
@@ -398,10 +399,7 @@ function buildPathAndQuery({ select, search, skiptoken, format, top, skip, filte
398
399
  aliases,
399
400
  escape,
400
401
  });
401
- path += `/${funcName}`;
402
- if (funcArgs !== '') {
403
- path += `(${funcArgs})`;
404
- }
402
+ path += `/${funcName}(${funcArgs})`;
405
403
  }
406
404
  }
407
405
  if (aliases.length > 0) {
@@ -650,7 +648,7 @@ function escapeIllegalChars(string) {
650
648
  string = string.replace(/'/g, "''");
651
649
  return string;
652
650
  }
653
- function normalizeValue(value, { aliases, escape = false }) {
651
+ function normalizeValue(value, { aliases, escape = false, } = {}) {
654
652
  if (typeof value === 'string') {
655
653
  return escape ? `'${escapeIllegalChars(value)}'` : `'${value}'`;
656
654
  }
@@ -745,6 +743,7 @@ function buildExpand(expands, { aliases, escape = false }) {
745
743
  case 'levels':
746
744
  case 'count':
747
745
  case 'top':
746
+ case 'skip':
748
747
  value = `${expands[key]}`;
749
748
  break;
750
749
  default:
@@ -1331,6 +1330,10 @@ const Objects = {
1331
1330
  if (typeof target != 'object' || target == null) {
1332
1331
  return target;
1333
1332
  }
1333
+ if (Types.isObject(target) && 'clone' in target) {
1334
+ // target is a cloneable object
1335
+ return target.clone();
1336
+ }
1334
1337
  const type = Types.rawType(target);
1335
1338
  let cloneTarget = null;
1336
1339
  if (map.get(target)) {
@@ -1420,7 +1423,7 @@ const Urls = {
1420
1423
  let index = param.indexOf(VALUE_SEPARATOR);
1421
1424
  if (index !== -1)
1422
1425
  Object.assign(acc, {
1423
- [param.substr(0, index)]: param.substr(index + 1),
1426
+ [param.substring(0, index)]: param.substring(index + 1),
1424
1427
  });
1425
1428
  return acc;
1426
1429
  }, {});
@@ -1461,17 +1464,33 @@ class Field$1 {
1461
1464
  constructor(name = '') {
1462
1465
  this.name = name;
1463
1466
  }
1464
- static factory() {
1465
- const h = new Field$1();
1466
- return new Proxy({ _name: '' }, h);
1467
+ static factory(name = '') {
1468
+ return new Proxy({ _name: name }, new Field$1());
1467
1469
  }
1468
- get(target, p) {
1470
+ get(target, key) {
1469
1471
  let name = target['_name'];
1470
- if (p === 'render') {
1472
+ if (key === 'render') {
1471
1473
  return ({ prefix }) => prefix ? `${prefix}/${name}` : name;
1472
1474
  }
1473
- name = name ? `${name}/${p}` : p;
1474
- return new Proxy({ _name: name }, this);
1475
+ else if (key === 'clone') {
1476
+ return () => Field$1.factory(name);
1477
+ }
1478
+ else if (key === Symbol.toStringTag) {
1479
+ return () => 'Field';
1480
+ }
1481
+ else if (key === 'toJSON') {
1482
+ return () => ({
1483
+ $type: Types.rawType(this),
1484
+ name: name,
1485
+ });
1486
+ }
1487
+ else {
1488
+ name = name ? `${name}/${key}` : key;
1489
+ return new Proxy({ _name: name }, this);
1490
+ }
1491
+ }
1492
+ has(target, key) {
1493
+ return ['toJSON', 'clone', 'render'].includes(key) || key in target;
1475
1494
  }
1476
1495
  }
1477
1496
  function applyMixins(derivedCtor, constructors) {
@@ -1510,6 +1529,7 @@ class Function {
1510
1529
  }
1511
1530
  toJSON() {
1512
1531
  return {
1532
+ $type: Types.rawType(this),
1513
1533
  name: this.name,
1514
1534
  values: this.values,
1515
1535
  normalize: this.normalize,
@@ -1518,12 +1538,15 @@ class Function {
1518
1538
  render({ aliases, escape, prefix, }) {
1519
1539
  let [field, ...values] = this.values;
1520
1540
  field = render(field, { aliases, escape, prefix });
1521
- let params = [
1541
+ const params = [
1522
1542
  field,
1523
1543
  ...values.map((v) => render(v, { aliases, escape, prefix, normalize: this.normalize })),
1524
1544
  ];
1525
1545
  return `${this.name}(${params.join(', ')})`;
1526
1546
  }
1547
+ clone() {
1548
+ return new Function(this.name, this.values.map((v) => Objects.clone(v)), this.normalize, this.escape);
1549
+ }
1527
1550
  }
1528
1551
  class StringAndCollectionFunctions {
1529
1552
  concat(field, value, normalize) {
@@ -1664,6 +1687,7 @@ class Operator {
1664
1687
  }
1665
1688
  toJSON() {
1666
1689
  return {
1690
+ $type: Types.rawType(this),
1667
1691
  op: this.op,
1668
1692
  values: this.values,
1669
1693
  normalize: this.normalize,
@@ -1692,6 +1716,9 @@ class Operator {
1692
1716
  }
1693
1717
  return `${this.op}(${left})`;
1694
1718
  }
1719
+ clone() {
1720
+ return new Operator(this.op, this.values.map((v) => Objects.clone(v)), this.normalize);
1721
+ }
1695
1722
  }
1696
1723
  class LogicalOperators {
1697
1724
  eq(left, right, normalize) {
@@ -1759,12 +1786,16 @@ class Grouping {
1759
1786
  }
1760
1787
  toJSON() {
1761
1788
  return {
1789
+ $type: Types.rawType(this),
1762
1790
  group: this.group.toJSON(),
1763
1791
  };
1764
1792
  }
1765
1793
  render({ aliases, escape, prefix, }) {
1766
1794
  return `(${render(this.group, { aliases, escape, prefix })})`;
1767
1795
  }
1796
+ clone() {
1797
+ return new Grouping(Objects.clone(this.group));
1798
+ }
1768
1799
  }
1769
1800
  class Lambda {
1770
1801
  constructor(op, values, alias) {
@@ -1777,6 +1808,7 @@ class Lambda {
1777
1808
  }
1778
1809
  toJSON() {
1779
1810
  return {
1811
+ $type: Types.rawType(this),
1780
1812
  op: this.op,
1781
1813
  values: this.values,
1782
1814
  alias: this.alias,
@@ -1792,6 +1824,9 @@ class Lambda {
1792
1824
  prefix: alias,
1793
1825
  })})`;
1794
1826
  }
1827
+ clone() {
1828
+ return new Lambda(this.op, this.values.map((v) => Objects.clone(v)), this.alias);
1829
+ }
1795
1830
  }
1796
1831
  class LambdaOperators {
1797
1832
  any(field, value, alias) {
@@ -1838,16 +1873,23 @@ class ComputeExpression extends Expression {
1838
1873
  static s() {
1839
1874
  return Field$1.factory();
1840
1875
  }
1841
- static compute(opts) {
1876
+ static compute(opts, current) {
1842
1877
  return opts({
1843
1878
  s: ComputeExpression.s(),
1844
1879
  e: ComputeExpression.e,
1845
- });
1880
+ }, current);
1846
1881
  }
1847
1882
  render({ aliases, escape, prefix, } = {}) {
1848
- let children = this._children
1849
- .map((n) => n.render({ aliases, escape, prefix }));
1850
- return this.names.map((name, index) => `${children[index]} as ${name}`).join(',');
1883
+ let children = this._children.map((n) => n.render({ aliases, escape, prefix }));
1884
+ return this.names
1885
+ .map((name, index) => `${children[index]} as ${name}`)
1886
+ .join(',');
1887
+ }
1888
+ clone() {
1889
+ return new ComputeExpression({
1890
+ children: this._children.map((c) => c.clone()),
1891
+ names: [...this.names],
1892
+ });
1851
1893
  }
1852
1894
  _add(name, node) {
1853
1895
  this.names.push(name);
@@ -1875,13 +1917,13 @@ class FilterExpression extends Expression {
1875
1917
  static e(connector = 'and') {
1876
1918
  return new FilterExpression({ connector });
1877
1919
  }
1878
- static filter(opts) {
1920
+ static filter(opts, current) {
1879
1921
  return opts({
1880
1922
  s: FilterExpression.s(),
1881
1923
  e: FilterExpression.e,
1882
1924
  o: operators,
1883
1925
  f: functions,
1884
- });
1926
+ }, current);
1885
1927
  }
1886
1928
  toJSON() {
1887
1929
  return {
@@ -1905,6 +1947,13 @@ class FilterExpression extends Expression {
1905
1947
  }
1906
1948
  return content;
1907
1949
  }
1950
+ clone() {
1951
+ return new FilterExpression({
1952
+ children: this._children.map((c) => c.clone()),
1953
+ connector: this._connector,
1954
+ negated: this._negated,
1955
+ });
1956
+ }
1908
1957
  _add(node, connector) {
1909
1958
  if (connector !== undefined && this._connector !== connector) {
1910
1959
  let children = [];
@@ -2031,6 +2080,9 @@ class OrderByField {
2031
2080
  render({ aliases, escape, prefix, }) {
2032
2081
  return `${render(this.field, { aliases, escape, prefix })} ${this.order}`;
2033
2082
  }
2083
+ clone() {
2084
+ return new OrderByField(this.field.clone(), this.order);
2085
+ }
2034
2086
  }
2035
2087
  class OrderByExpression extends Expression {
2036
2088
  constructor({ children, } = {}) {
@@ -2042,11 +2094,11 @@ class OrderByExpression extends Expression {
2042
2094
  static s() {
2043
2095
  return Field$1.factory();
2044
2096
  }
2045
- static orderBy(opts) {
2097
+ static orderBy(opts, current) {
2046
2098
  return opts({
2047
2099
  s: OrderByExpression.s(),
2048
2100
  e: OrderByExpression.e,
2049
- });
2101
+ }, current);
2050
2102
  }
2051
2103
  _add(node) {
2052
2104
  this._children.push(node);
@@ -2058,6 +2110,11 @@ class OrderByExpression extends Expression {
2058
2110
  .join(`,`);
2059
2111
  return content;
2060
2112
  }
2113
+ clone() {
2114
+ return new OrderByExpression({
2115
+ children: this._children.map((c) => c.clone()),
2116
+ });
2117
+ }
2061
2118
  ascending(field) {
2062
2119
  return this._add(new OrderByField(field, 'asc'));
2063
2120
  }
@@ -2075,12 +2132,16 @@ class SearchTerm {
2075
2132
  }
2076
2133
  toJSON() {
2077
2134
  return {
2135
+ $type: Types.rawType(this),
2078
2136
  value: this.value,
2079
2137
  };
2080
2138
  }
2081
2139
  render({ aliases, escape, prefix, }) {
2082
2140
  return `${render(this.value, { aliases, escape, prefix })}`;
2083
2141
  }
2142
+ clone() {
2143
+ return new SearchTerm(this.value);
2144
+ }
2084
2145
  }
2085
2146
  class SearchExpression extends Expression {
2086
2147
  constructor({ children, connector, negated, } = {}) {
@@ -2091,10 +2152,10 @@ class SearchExpression extends Expression {
2091
2152
  static e(connector = 'AND') {
2092
2153
  return new SearchExpression({ connector });
2093
2154
  }
2094
- static search(opts) {
2155
+ static search(opts, current) {
2095
2156
  return opts({
2096
2157
  e: SearchExpression.e,
2097
- });
2158
+ }, current);
2098
2159
  }
2099
2160
  _add(node, connector) {
2100
2161
  if (connector !== undefined && this._connector !== connector) {
@@ -2145,6 +2206,13 @@ class SearchExpression extends Expression {
2145
2206
  .join(` ${this._connector} `);
2146
2207
  return content;
2147
2208
  }
2209
+ clone() {
2210
+ return new SearchExpression({
2211
+ children: this._children.map((c) => c.clone()),
2212
+ connector: this._connector,
2213
+ negated: this._negated,
2214
+ });
2215
+ }
2148
2216
  toJSON() {
2149
2217
  return {
2150
2218
  children: this._children.map((c) => c.toJSON()),
@@ -2177,9 +2245,45 @@ class SearchExpression extends Expression {
2177
2245
  }
2178
2246
  }
2179
2247
 
2248
+ class SelectExpression extends Expression {
2249
+ constructor({ children, } = {}) {
2250
+ super({ children });
2251
+ }
2252
+ static e() {
2253
+ return new SelectExpression();
2254
+ }
2255
+ static s() {
2256
+ return Field$1.factory();
2257
+ }
2258
+ static select(builder, current) {
2259
+ return builder({
2260
+ s: SelectExpression.s(),
2261
+ e: SelectExpression.e,
2262
+ }, current);
2263
+ }
2264
+ render({ aliases, escape, prefix, } = {}) {
2265
+ return this._children
2266
+ .map((n) => n.render({ aliases, escape, prefix }))
2267
+ .join(',');
2268
+ }
2269
+ clone() {
2270
+ return new SelectExpression({
2271
+ children: this._children.map((c) => c.clone()),
2272
+ });
2273
+ }
2274
+ _add(node) {
2275
+ this._children.push(node);
2276
+ return this;
2277
+ }
2278
+ field(field) {
2279
+ return this._add(field);
2280
+ }
2281
+ }
2282
+
2180
2283
  class ExpandField {
2181
- constructor(field) {
2284
+ constructor(field, values = {}) {
2182
2285
  this.field = field;
2286
+ this.values = values;
2183
2287
  }
2184
2288
  get [Symbol.toStringTag]() {
2185
2289
  return 'ExpandField';
@@ -2190,14 +2294,66 @@ class ExpandField {
2190
2294
  };
2191
2295
  }
2192
2296
  render({ aliases, escape, prefix, }) {
2193
- return `${render(this.field, { aliases, escape, prefix })}`;
2297
+ const params = [
2298
+ QueryOptionNames.select,
2299
+ QueryOptionNames.expand,
2300
+ QueryOptionNames.filter,
2301
+ QueryOptionNames.search,
2302
+ QueryOptionNames.orderBy,
2303
+ QueryOptionNames.skip,
2304
+ QueryOptionNames.top,
2305
+ QueryOptionNames.levels,
2306
+ ]
2307
+ .filter((key) => !Types.isEmpty(this.values[key]))
2308
+ .reduce((acc, key) => {
2309
+ let value = this.values[key];
2310
+ if (Types.rawType(value).endsWith('Expression')) {
2311
+ value = value.render({ aliases, prefix, escape });
2312
+ }
2313
+ return Object.assign(acc, { [key]: value });
2314
+ }, {});
2315
+ let expand = `${render(this.field, { aliases, escape, prefix })}`;
2316
+ if (!Types.isEmpty(params)) {
2317
+ expand = `${expand}(${Object.keys(params)
2318
+ .map((key) => `$${key}=${params[key]}`)
2319
+ .join(';')})`;
2320
+ }
2321
+ return expand;
2322
+ }
2323
+ clone() {
2324
+ const values = Object.keys(this.values).reduce((acc, key) => Object.assign(acc, { [key]: Objects.clone(this.values[key]) }), {});
2325
+ return new ExpandField(this.field.clone(), values);
2326
+ }
2327
+ select(opts) {
2328
+ return this.option(QueryOptionNames.select, SelectExpression.select(opts, this.values[QueryOptionNames.select]));
2329
+ }
2330
+ expand(opts) {
2331
+ return this.option(QueryOptionNames.expand, ExpandExpression.expand(opts, this.values[QueryOptionNames.expand]));
2332
+ }
2333
+ filter(opts) {
2334
+ return this.option(QueryOptionNames.filter, FilterExpression.filter(opts, this.values[QueryOptionNames.filter]));
2335
+ }
2336
+ search(opts) {
2337
+ return this.option(QueryOptionNames.search, SearchExpression.search(opts, this.values[QueryOptionNames.search]));
2338
+ }
2339
+ orderBy(opts) {
2340
+ return this.option(QueryOptionNames.orderBy, OrderByExpression.orderBy(opts, this.values[QueryOptionNames.orderBy]));
2341
+ }
2342
+ skip(n) {
2343
+ return this.option(QueryOptionNames.skip, n);
2344
+ }
2345
+ top(n) {
2346
+ return this.option(QueryOptionNames.top, n);
2347
+ }
2348
+ levels(n) {
2349
+ return this.option(QueryOptionNames.levels, n);
2350
+ }
2351
+ // Option Handler
2352
+ option(name, opts) {
2353
+ if (opts !== undefined)
2354
+ this.values[name] = opts;
2355
+ return this.values[name];
2194
2356
  }
2195
- select() { }
2196
- filter() { }
2197
- levels() { }
2198
- orderBy() { }
2199
- top() { }
2200
- skip() { }
2201
2357
  }
2202
2358
  class ExpandExpression extends Expression {
2203
2359
  constructor({ children, } = {}) {
@@ -2209,17 +2365,22 @@ class ExpandExpression extends Expression {
2209
2365
  static s() {
2210
2366
  return Field$1.factory();
2211
2367
  }
2212
- static expand(opts) {
2368
+ static expand(opts, current) {
2213
2369
  return opts({
2214
2370
  s: ExpandExpression.s(),
2215
2371
  e: ExpandExpression.e,
2216
- });
2372
+ }, current);
2217
2373
  }
2218
2374
  render({ aliases, escape, prefix, } = {}) {
2219
2375
  return this._children
2220
2376
  .map((n) => n.render({ aliases, escape, prefix }))
2221
2377
  .join(',');
2222
2378
  }
2379
+ clone() {
2380
+ return new ExpandExpression({
2381
+ children: this._children.map((c) => c.clone()),
2382
+ });
2383
+ }
2223
2384
  _add(node) {
2224
2385
  this._children.push(node);
2225
2386
  return this;
@@ -2232,36 +2393,6 @@ class ExpandExpression extends Expression {
2232
2393
  }
2233
2394
  }
2234
2395
 
2235
- class SelectExpression extends Expression {
2236
- constructor({ children, } = {}) {
2237
- super({ children });
2238
- }
2239
- static e() {
2240
- return new SelectExpression();
2241
- }
2242
- static s() {
2243
- return Field$1.factory();
2244
- }
2245
- static select(opts) {
2246
- return opts({
2247
- s: SelectExpression.s(),
2248
- e: SelectExpression.e,
2249
- });
2250
- }
2251
- render({ aliases, escape, prefix, } = {}) {
2252
- return this._children
2253
- .map((n) => n.render({ aliases, escape, prefix }))
2254
- .join(',');
2255
- }
2256
- _add(node) {
2257
- this._children.push(node);
2258
- return this;
2259
- }
2260
- field(field) {
2261
- return this._add(field);
2262
- }
2263
- }
2264
-
2265
2396
  class ODataQueryOptionHandler {
2266
2397
  constructor(o, n) {
2267
2398
  this.o = o;
@@ -2271,30 +2402,32 @@ class ODataQueryOptionHandler {
2271
2402
  return this.n;
2272
2403
  }
2273
2404
  toJSON() {
2274
- return this.o[this.n];
2405
+ return this.o.get(this.n);
2275
2406
  }
2276
2407
  empty() {
2277
- return Types.isEmpty(this.o[this.n]);
2408
+ return Types.isEmpty(this.o.get(this.n));
2278
2409
  }
2279
2410
  //#region Primitive Value
2280
2411
  value(v) {
2281
- return (v !== undefined && (this.o[this.n] = v)) || this.o[this.n];
2412
+ if (v !== undefined)
2413
+ this.o.set(this.n, v);
2414
+ return this.o.get(this.n);
2282
2415
  }
2283
2416
  //#endregion
2284
2417
  //#region Array Value
2285
2418
  assertArray() {
2286
- if (!Types.isArray(this.o[this.n]))
2287
- this.o[this.n] = this.o[this.n] !== undefined ? [this.o[this.n]] : [];
2288
- return this.o[this.n];
2419
+ if (!Types.isArray(this.o.get(this.n)))
2420
+ this.o.set(this.n, this.o.has(this.n) ? [this.o.get(this.n)] : []);
2421
+ return this.o.get(this.n);
2289
2422
  }
2290
2423
  push(value) {
2291
2424
  this.assertArray().push(value);
2292
2425
  }
2293
2426
  remove(value) {
2294
- this.o[this.n] = this.assertArray().filter((v) => v !== value);
2427
+ this.o.set(this.n, this.assertArray().filter((v) => v !== value));
2295
2428
  // If only one... down to value
2296
- if (this.o[this.n].length === 1)
2297
- this.o[this.n] = this.o[this.n][0];
2429
+ if (this.o.get(this.n).length === 1)
2430
+ this.o.set(this.n, this.o.get(this.n)[0]);
2298
2431
  }
2299
2432
  at(index) {
2300
2433
  return this.assertArray()[index];
@@ -2302,8 +2435,9 @@ class ODataQueryOptionHandler {
2302
2435
  //#endregion
2303
2436
  //#region HashMap Value
2304
2437
  assertObject(create) {
2305
- if (!Types.isArray(this.o[this.n]) && Types.isPlainObject(this.o[this.n])) {
2306
- return this.o[this.n];
2438
+ if (!Types.isArray(this.o.get(this.n)) &&
2439
+ Types.isPlainObject(this.o.get(this.n))) {
2440
+ return this.o.get(this.n);
2307
2441
  }
2308
2442
  let arr = this.assertArray();
2309
2443
  let obj = arr.find((v) => Types.isPlainObject(v));
@@ -2324,10 +2458,10 @@ class ODataQueryOptionHandler {
2324
2458
  unset(path) {
2325
2459
  let obj = this.assertObject(true);
2326
2460
  Objects.unset(obj, path);
2327
- if (Types.isArray(this.o[this.n])) {
2328
- this.o[this.n] = this.o[this.n].filter((v) => !Types.isEmpty(v));
2329
- if (this.o[this.n].length === 1)
2330
- this.o[this.n] = this.o[this.n][0];
2461
+ if (Types.isArray(this.o.get(this.n))) {
2462
+ this.o.set(this.n, this.o.get(this.n).filter((v) => !Types.isEmpty(v)));
2463
+ if (this.o.get(this.n).length === 1)
2464
+ this.o.set(this.n, this.o.get(this.n)[0]);
2331
2465
  }
2332
2466
  }
2333
2467
  has(path) {
@@ -2340,7 +2474,7 @@ class ODataQueryOptionHandler {
2340
2474
  }
2341
2475
  //#endregion
2342
2476
  clear() {
2343
- delete this.o[this.n];
2477
+ this.o.delete(this.n);
2344
2478
  }
2345
2479
  }
2346
2480
  class ODataQueryOptionsHandler {
@@ -2357,21 +2491,29 @@ class ODataQueryOptionsHandler {
2357
2491
  alias(value, name) {
2358
2492
  return alias(value, name);
2359
2493
  }
2494
+ /**
2495
+ * Normalize the given value to a valid odata value
2496
+ * @param value The value to normalize
2497
+ * @returns The normalized value
2498
+ */
2499
+ normalize(value) {
2500
+ return normalizeValue(value);
2501
+ }
2360
2502
  select(opts) {
2361
2503
  if (Types.isFunction(opts)) {
2362
- return this.options.expression(QueryOptionNames.select, SelectExpression.select(opts));
2504
+ return this.options.expression(QueryOptionNames.select, SelectExpression.select(opts, this.options.expression(QueryOptionNames.select)));
2363
2505
  }
2364
2506
  return this.options.option(QueryOptionNames.select, opts);
2365
2507
  }
2366
2508
  expand(opts) {
2367
2509
  if (Types.isFunction(opts)) {
2368
- return this.options.expression(QueryOptionNames.expand, ExpandExpression.expand(opts));
2510
+ return this.options.expression(QueryOptionNames.expand, ExpandExpression.expand(opts, this.options.expression(QueryOptionNames.expand)));
2369
2511
  }
2370
2512
  return this.options.option(QueryOptionNames.expand, opts);
2371
2513
  }
2372
2514
  compute(opts) {
2373
2515
  if (Types.isFunction(opts)) {
2374
- return this.options.expression(QueryOptionNames.compute, ComputeExpression.compute(opts));
2516
+ return this.options.expression(QueryOptionNames.compute, ComputeExpression.compute(opts, this.options.expression(QueryOptionNames.compute)));
2375
2517
  }
2376
2518
  return this.options.option(QueryOptionNames.compute, opts);
2377
2519
  }
@@ -2383,19 +2525,19 @@ class ODataQueryOptionsHandler {
2383
2525
  }
2384
2526
  search(opts) {
2385
2527
  if (Types.isFunction(opts)) {
2386
- return this.options.expression(QueryOptionNames.search, SearchExpression.search(opts));
2528
+ return this.options.expression(QueryOptionNames.search, SearchExpression.search(opts, this.options.expression(QueryOptionNames.search)));
2387
2529
  }
2388
2530
  return this.options.option(QueryOptionNames.search, opts);
2389
2531
  }
2390
2532
  filter(opts) {
2391
2533
  if (Types.isFunction(opts)) {
2392
- return this.options.expression(QueryOptionNames.filter, FilterExpression.filter(opts));
2534
+ return this.options.expression(QueryOptionNames.filter, FilterExpression.filter(opts, this.options.expression(QueryOptionNames.filter)));
2393
2535
  }
2394
2536
  return this.options.option(QueryOptionNames.filter, opts);
2395
2537
  }
2396
2538
  orderBy(opts) {
2397
2539
  if (Types.isFunction(opts)) {
2398
- return this.options.expression(QueryOptionNames.orderBy, OrderByExpression.orderBy(opts));
2540
+ return this.options.option(QueryOptionNames.orderBy, OrderByExpression.orderBy(opts, this.options.expression(QueryOptionNames.orderBy)));
2399
2541
  }
2400
2542
  return this.options.option(QueryOptionNames.orderBy, opts);
2401
2543
  }
@@ -2423,30 +2565,33 @@ class ODataQueryOptionsHandler {
2423
2565
  }
2424
2566
  apply(query) {
2425
2567
  if (query.select !== undefined) {
2426
- this.select(query.select);
2568
+ this.options.option(QueryOptionNames.select, query.select);
2427
2569
  }
2428
2570
  if (query.expand !== undefined) {
2429
- this.expand(query.expand);
2571
+ this.options.option(QueryOptionNames.expand, query.expand);
2430
2572
  }
2431
2573
  if (query.transform !== undefined) {
2432
- this.transform(query.transform);
2574
+ this.options.option(QueryOptionNames.transform, query.transform);
2433
2575
  }
2434
2576
  if (query.search !== undefined) {
2435
- this.search(query.search);
2577
+ this.options.option(QueryOptionNames.search, query.search);
2436
2578
  }
2437
2579
  if (query.filter !== undefined) {
2438
- this.filter(query.filter);
2580
+ this.options.option(QueryOptionNames.filter, query.filter);
2439
2581
  }
2440
2582
  if (query.orderBy !== undefined) {
2441
- this.orderBy(query.orderBy);
2583
+ this.options.option(QueryOptionNames.orderBy, query.orderBy);
2442
2584
  }
2443
2585
  this.paging(query);
2444
2586
  }
2445
2587
  }
2446
2588
 
2447
2589
  class ODataQueryOptions {
2448
- constructor(options) {
2449
- this.options = options || {};
2590
+ constructor(values) {
2591
+ this.values =
2592
+ values instanceof Map
2593
+ ? values
2594
+ : new Map(Object.entries(values || {}));
2450
2595
  }
2451
2596
  // Params
2452
2597
  pathAndParams(escape = false) {
@@ -2464,11 +2609,11 @@ class ODataQueryOptions {
2464
2609
  QueryOptionNames.expand,
2465
2610
  QueryOptionNames.format,
2466
2611
  ]
2467
- .filter((key) => !Types.isEmpty(this.options[key]))
2612
+ .filter((key) => !Types.isEmpty(this.values.get(key)))
2468
2613
  .reduce((acc, key) => {
2469
- let value = this.options[key];
2470
- if (Types.rawType(value) === 'Expression') {
2471
- value = value.render(aliases);
2614
+ let value = this.values.get(key);
2615
+ if (Types.rawType(value).endsWith('Expression')) {
2616
+ value = value.render({ aliases });
2472
2617
  }
2473
2618
  return Object.assign(acc, { [key]: value });
2474
2619
  }, {});
@@ -2483,63 +2628,63 @@ class ODataQueryOptions {
2483
2628
  .join('&'));
2484
2629
  }
2485
2630
  toJSON() {
2486
- return Object.keys(this.options).reduce((acc, key) => {
2487
- let value = this.options[key];
2488
- if (Types.rawType(value) === 'Expression') {
2489
- value = value.toJSON();
2490
- }
2631
+ return [...this.values.keys()].reduce((acc, key) => {
2632
+ let value = this.values.get(key);
2633
+ value =
2634
+ Types.isObject(value) && 'toJSON' in value ? value.toJSON() : value;
2491
2635
  return Object.assign(acc, { [key]: value });
2492
2636
  }, {});
2493
2637
  }
2494
2638
  toQueryArguments() {
2495
2639
  return {
2496
- select: this.options[QueryOptionNames.select],
2497
- expand: this.options[QueryOptionNames.expand],
2498
- transform: this.options[QueryOptionNames.transform],
2499
- compute: this.options[QueryOptionNames.compute],
2500
- search: this.options[QueryOptionNames.search],
2501
- filter: this.options[QueryOptionNames.filter],
2502
- orderBy: this.options[QueryOptionNames.orderBy],
2503
- top: this.options[QueryOptionNames.top],
2504
- skip: this.options[QueryOptionNames.skip],
2505
- skiptoken: this.options[QueryOptionNames.skiptoken],
2640
+ select: this.values.get(QueryOptionNames.select),
2641
+ expand: this.values.get(QueryOptionNames.expand),
2642
+ transform: this.values.get(QueryOptionNames.transform),
2643
+ compute: this.values.get(QueryOptionNames.compute),
2644
+ search: this.values.get(QueryOptionNames.search),
2645
+ filter: this.values.get(QueryOptionNames.filter),
2646
+ orderBy: this.values.get(QueryOptionNames.orderBy),
2647
+ top: this.values.get(QueryOptionNames.top),
2648
+ skip: this.values.get(QueryOptionNames.skip),
2649
+ skiptoken: this.values.get(QueryOptionNames.skiptoken),
2506
2650
  };
2507
2651
  }
2508
2652
  clone() {
2509
- const options = Object.keys(this.options).reduce((acc, key) => {
2510
- let value = this.options[key];
2511
- if (Types.rawType(value) !== 'Expression') {
2512
- value = Objects.clone(value);
2513
- }
2514
- return Object.assign(acc, { [key]: value });
2515
- }, {});
2516
- return new ODataQueryOptions(options);
2653
+ return new ODataQueryOptions(Objects.clone(this.values));
2517
2654
  }
2518
2655
  // Set Renderable
2519
- expression(name, exp) {
2520
- return (this.options[name] = exp);
2656
+ expression(key, exp) {
2657
+ if (exp !== undefined)
2658
+ this.values.set(key, exp);
2659
+ return this.values.get(key);
2521
2660
  }
2522
2661
  // Option Handler
2523
- option(name, opts) {
2662
+ option(key, opts) {
2524
2663
  if (opts !== undefined)
2525
- this.options[name] = opts;
2526
- return new ODataQueryOptionHandler(this.options, name);
2664
+ this.values.set(key, opts);
2665
+ return new ODataQueryOptionHandler(this.values, key);
2527
2666
  }
2528
2667
  // Query Options tools
2529
- has(name) {
2530
- return this.options[name] !== undefined;
2531
- }
2532
- remove(...names) {
2533
- names.forEach((name) => this.option(name).clear());
2668
+ has(key) {
2669
+ return this.values.has(key);
2670
+ }
2671
+ remove(...keys) {
2672
+ [...this.values.keys()]
2673
+ .filter((k) => keys.indexOf(k) !== -1)
2674
+ .forEach((key) => {
2675
+ this.values.delete(key);
2676
+ });
2534
2677
  }
2535
- keep(...names) {
2536
- this.options = Object.keys(this.options)
2537
- .filter((k) => names.indexOf(k) !== -1)
2538
- .reduce((acc, k) => Object.assign(acc, { [k]: this.options[k] }), {});
2678
+ keep(...keys) {
2679
+ [...this.values.keys()]
2680
+ .filter((k) => keys.indexOf(k) === -1)
2681
+ .forEach((key) => {
2682
+ this.values.delete(key);
2683
+ });
2539
2684
  }
2540
2685
  // Clear
2541
2686
  clear() {
2542
- this.options = {};
2687
+ this.values.clear();
2543
2688
  }
2544
2689
  }
2545
2690
 
@@ -3141,70 +3286,69 @@ const ODataVersionBaseHelper = {
3141
3286
  property(data) {
3142
3287
  return this.VALUE in data ? data[this.VALUE] : data;
3143
3288
  },
3144
- functions(value) {
3145
- return Object.keys(value)
3146
- .filter((k) => k.startsWith(this.ODATA_FUNCTION_PREFIX))
3147
- .reduce((acc, key) => Object.assign(acc, { [key.substr(1)]: value[key] }), {});
3289
+ functions(annots) {
3290
+ const funcs = new Map();
3291
+ [...annots.keys()]
3292
+ .filter((key) => key.startsWith(this.ODATA_FUNCTION_PREFIX))
3293
+ .forEach((key) => funcs.set(key.substring(this.ODATA_FUNCTION_PREFIX.length), annots.get(key)));
3294
+ return funcs;
3148
3295
  },
3149
- properties(value) {
3150
- return Object.keys(value)
3151
- .filter((k) => k.indexOf(this.ODATA_ANNOTATION_PREFIX) > 0)
3152
- .reduce((acc, key) => {
3153
- let name = key.substr(0, key.indexOf(this.ODATA_ANNOTATION_PREFIX));
3154
- if (!(name in acc)) {
3155
- acc[name] = {};
3156
- }
3157
- Object.assign(acc[name], {
3158
- [key.substr(key.indexOf(this.ODATA_ANNOTATION_PREFIX))]: value[key],
3159
- });
3160
- return acc;
3161
- }, {});
3296
+ properties(annots) {
3297
+ const props = new Map();
3298
+ [...annots.keys()]
3299
+ .filter((key) => key.indexOf(this.ODATA_ANNOTATION_PREFIX) > 0)
3300
+ .forEach((key) => {
3301
+ let name = key.substring(0, key.indexOf(this.ODATA_ANNOTATION_PREFIX));
3302
+ let prop = props.has(name) ? props.get(name) : new Map();
3303
+ prop.set(key.substring(key.indexOf(this.ODATA_ANNOTATION_PREFIX)), annots.get(key));
3304
+ props.set(name, prop);
3305
+ });
3306
+ return props;
3162
3307
  },
3163
- id(value, id) {
3164
- if (id !== undefined)
3165
- value[this.ODATA_ID] = id;
3166
- return this.ODATA_ID in value
3167
- ? value[this.ODATA_ID]
3168
- : undefined;
3308
+ id(annots) {
3309
+ return annots instanceof Map
3310
+ ? annots.get(this.ODATA_ID)
3311
+ : annots[this.ODATA_ID];
3169
3312
  },
3170
- etag(value, etag) {
3171
- if (etag !== undefined)
3172
- value[this.ODATA_ETAG] = etag;
3173
- return this.ODATA_ETAG in value
3174
- ? value[this.ODATA_ETAG]
3175
- : undefined;
3313
+ etag(annots) {
3314
+ return annots instanceof Map
3315
+ ? annots.get(this.ODATA_ETAG)
3316
+ : annots[this.ODATA_ETAG];
3176
3317
  },
3177
- type(value, type) {
3178
- if (type !== undefined)
3179
- value[this.ODATA_TYPE] = `#${type}`;
3180
- if (!(this.ODATA_TYPE in value))
3318
+ type(annots) {
3319
+ let type = annots instanceof Map
3320
+ ? annots.get(this.ODATA_TYPE)
3321
+ : annots[this.ODATA_TYPE];
3322
+ if (!type)
3181
3323
  return undefined;
3182
- const t = value[this.ODATA_TYPE].substr(1);
3183
- const matches = COLLECTION.exec(t);
3324
+ type = type.substring(1);
3325
+ const matches = COLLECTION.exec(type);
3184
3326
  if (matches)
3185
3327
  return matches[1].indexOf('.') === -1 ? `Edm.${matches[1]}` : matches[1];
3186
- return t;
3328
+ return type;
3187
3329
  },
3188
- mediaEtag(value) {
3189
- return this.ODATA_MEDIA_ETAG in value
3190
- ? decodeURIComponent(value[this.ODATA_MEDIA_ETAG])
3330
+ mediaEtag(annots) {
3331
+ return annots.has(this.ODATA_MEDIA_ETAG)
3332
+ ? decodeURIComponent(annots.get(this.ODATA_MEDIA_ETAG))
3191
3333
  : undefined;
3192
3334
  },
3193
- metadataEtag(value) {
3194
- return this.ODATA_METADATA_ETAG in value
3195
- ? decodeURIComponent(value[this.ODATA_METADATA_ETAG])
3335
+ metadataEtag(annots) {
3336
+ return annots.has(this.ODATA_METADATA_ETAG)
3337
+ ? decodeURIComponent(annots.get(this.ODATA_METADATA_ETAG))
3196
3338
  : undefined;
3197
3339
  },
3198
- count(value) {
3199
- return this.ODATA_COUNT in value
3200
- ? Number(value[this.ODATA_COUNT])
3340
+ count(annots) {
3341
+ return annots.has(this.ODATA_COUNT)
3342
+ ? Number(annots.get(this.ODATA_COUNT))
3201
3343
  : undefined;
3202
3344
  },
3203
3345
  annotations(value) {
3204
- return Object.keys(value)
3205
- .filter((key) => key.indexOf(this.ODATA_ANNOTATION_PREFIX) !== -1 ||
3346
+ const annots = new Map();
3347
+ Object.entries(value)
3348
+ .filter(([key]) => key.indexOf(this.ODATA_ANNOTATION_PREFIX) !== -1 ||
3206
3349
  key.startsWith(this.ODATA_FUNCTION_PREFIX))
3207
- .reduce((acc, key) => Object.assign(acc, { [key]: value[key] }), {});
3350
+ .forEach(([key, value]) => annots.set(key, value));
3351
+ return annots;
3208
3352
  },
3209
3353
  attributes(value, metadata) {
3210
3354
  return Object.entries(value)
@@ -3218,39 +3362,39 @@ const ODataVersionBaseHelper = {
3218
3362
  !k.startsWith(this.ODATA_FUNCTION_PREFIX)))
3219
3363
  .reduce((acc, e) => ({ ...acc, [e[0]]: e[1] }), {});
3220
3364
  },
3221
- nextLink(value) {
3222
- return this.ODATA_NEXTLINK in value
3223
- ? decodeURIComponent(value[this.ODATA_NEXTLINK])
3365
+ nextLink(annots) {
3366
+ return annots.has(this.ODATA_NEXTLINK)
3367
+ ? decodeURIComponent(annots.get(this.ODATA_NEXTLINK))
3224
3368
  : undefined;
3225
3369
  },
3226
- readLink(value) {
3227
- return this.ODATA_READLINK in value
3228
- ? decodeURIComponent(value[this.ODATA_READLINK])
3370
+ readLink(annots) {
3371
+ return annots.has(this.ODATA_READLINK)
3372
+ ? decodeURIComponent(annots.get(this.ODATA_READLINK))
3229
3373
  : undefined;
3230
3374
  },
3231
- mediaReadLink(value) {
3232
- return this.ODATA_MEDIA_READLINK in value
3233
- ? decodeURIComponent(value[this.ODATA_MEDIA_READLINK])
3375
+ mediaReadLink(annots) {
3376
+ return annots.has(this.ODATA_MEDIA_READLINK)
3377
+ ? decodeURIComponent(annots.get(this.ODATA_MEDIA_READLINK))
3234
3378
  : undefined;
3235
3379
  },
3236
- editLink(value) {
3237
- return this.ODATA_EDITLINK in value
3238
- ? decodeURIComponent(value[this.ODATA_EDITLINK])
3380
+ editLink(annots) {
3381
+ return annots.has(this.ODATA_EDITLINK)
3382
+ ? decodeURIComponent(annots.get(this.ODATA_EDITLINK))
3239
3383
  : undefined;
3240
3384
  },
3241
- mediaEditLink(value) {
3242
- return this.ODATA_MEDIA_EDITLINK in value
3243
- ? decodeURIComponent(value[this.ODATA_MEDIA_EDITLINK])
3385
+ mediaEditLink(annots) {
3386
+ return annots.has(this.ODATA_MEDIA_EDITLINK)
3387
+ ? decodeURIComponent(annots.get(this.ODATA_MEDIA_EDITLINK))
3244
3388
  : undefined;
3245
3389
  },
3246
- deltaLink(value) {
3247
- return this.ODATA_DELTALINK in value
3248
- ? decodeURIComponent(value[this.ODATA_DELTALINK])
3390
+ deltaLink(annots) {
3391
+ return annots.has(this.ODATA_DELTALINK)
3392
+ ? decodeURIComponent(annots.get(this.ODATA_DELTALINK))
3249
3393
  : undefined;
3250
3394
  },
3251
- mediaContentType(value) {
3252
- return this.ODATA_MEDIA_CONTENTTYPE in value
3253
- ? decodeURIComponent(value[this.ODATA_MEDIA_CONTENTTYPE])
3395
+ mediaContentType(annots) {
3396
+ return annots.has(this.ODATA_MEDIA_CONTENTTYPE)
3397
+ ? decodeURIComponent(annots.get(this.ODATA_MEDIA_CONTENTTYPE))
3254
3398
  : undefined;
3255
3399
  },
3256
3400
  };
@@ -3269,7 +3413,7 @@ const ODataHelper = {
3269
3413
  //odata.etag: the ETag of the entity
3270
3414
  ODATA_ETAG: '@odata.etag',
3271
3415
  ODATA_METADATA_ETAG: '@odata.metadataEtag',
3272
- //odata.type: the type of the containing {[name: string]: any} or targeted property if the type of the {[name: string]: any} or targeted property cannot be heuristically determined
3416
+ //odata.type: the type of the containing {[key: string]: any} or targeted property if the type of the {[key: string]: any} or targeted property cannot be heuristically determined
3273
3417
  ODATA_TYPE: '@odata.type',
3274
3418
  //odata.nextLink: the next link of a collection with partial results
3275
3419
  ODATA_NEXTLINK: '@odata.nextLink',
@@ -3300,15 +3444,17 @@ const ODataHelper = {
3300
3444
  //http://nb-mdp-dev01:57970/$metadata#categorias(children(children(children(children(children(children(children(children(children(children()))))))))))/$entity
3301
3445
  //http://nb-mdp-dev01:57970/$metadata#recursos/SIU.Documentos.Documento/$entity
3302
3446
  //http://nb-mdp-dev01:57970/$metadata#SIU.Api.Infrastructure.Storage.Backend.SiuUrls
3303
- context(value) {
3447
+ context(annots) {
3304
3448
  let ctx = {};
3305
- if (this.ODATA_CONTEXT in value) {
3306
- const str = value[this.ODATA_CONTEXT];
3449
+ const str = annots instanceof Map
3450
+ ? annots.get(this.ODATA_CONTEXT)
3451
+ : annots[this.ODATA_CONTEXT];
3452
+ if (typeof str === 'string') {
3307
3453
  let index = str.indexOf('$metadata');
3308
- ctx.serviceRootUrl = str.substr(0, index);
3454
+ ctx.serviceRootUrl = str.substring(0, index);
3309
3455
  index = str.indexOf('#');
3310
- ctx.metadataUrl = str.substr(0, index);
3311
- const parts = str.substr(index + 1).split('/');
3456
+ ctx.metadataUrl = str.substring(0, index);
3457
+ const parts = str.substring(index + 1).split('/');
3312
3458
  const col = COLLECTION.exec(parts[0]);
3313
3459
  if (col) {
3314
3460
  ctx.type = col[1];
@@ -3352,15 +3498,17 @@ const ODataHelper = {
3352
3498
  ODATA_TYPE: 'odata.type',
3353
3499
  ODATA_COUNT: 'odata.count',
3354
3500
  VALUE: 'value',
3355
- context(value) {
3501
+ context(annots) {
3356
3502
  let ctx = {};
3357
- if (this.ODATA_CONTEXT in value) {
3358
- const str = value[this.ODATA_CONTEXT];
3503
+ const str = annots instanceof Map
3504
+ ? annots.get(this.ODATA_CONTEXT)
3505
+ : annots[this.ODATA_CONTEXT];
3506
+ if (typeof str === 'string') {
3359
3507
  let index = str.indexOf('$metadata');
3360
- ctx.serviceRootUrl = str.substr(0, index);
3508
+ ctx.serviceRootUrl = str.substring(0, index);
3361
3509
  index = str.indexOf('#');
3362
- ctx.metadataUrl = str.substr(0, index);
3363
- const parts = str.substr(index + 1).split('/');
3510
+ ctx.metadataUrl = str.substring(0, index);
3511
+ const parts = str.substring(index + 1).split('/');
3364
3512
  ctx.entitySet = parts[0];
3365
3513
  }
3366
3514
  return ctx;
@@ -3381,9 +3529,11 @@ const ODataHelper = {
3381
3529
  ODATA_TYPE: 'type',
3382
3530
  VALUE: 'results',
3383
3531
  annotations(value) {
3384
- if (this.ODATA_ANNOTATION in value)
3385
- return value[this.ODATA_ANNOTATION];
3386
- return value;
3532
+ const annots = new Map();
3533
+ if (this.ODATA_ANNOTATION in value) {
3534
+ Object.entries(value[this.ODATA_ANNOTATION]).forEach(([key, value]) => annots.set(key, value));
3535
+ }
3536
+ return annots;
3387
3537
  },
3388
3538
  attributes(value, metadata) {
3389
3539
  return value;
@@ -3399,7 +3549,7 @@ class ODataApiOptions {
3399
3549
  constructor(config) {
3400
3550
  this.etag = { ifMatch: true, ifNoneMatch: false };
3401
3551
  this.version = config.version || DEFAULT_VERSION;
3402
- this.stringAsEnum = config.stringAsEnum;
3552
+ this.stringAsEnum = config.stringAsEnum || false;
3403
3553
  this.params = config.params || {};
3404
3554
  this.headers = config.headers || {};
3405
3555
  this.withCredentials = config.withCredentials;
@@ -3410,6 +3560,8 @@ class ODataApiOptions {
3410
3560
  Object.assign(this.etag, config.etag || {});
3411
3561
  this.prefer = config.prefer;
3412
3562
  this.deleteRefBy = config.deleteRefBy || 'path';
3563
+ this.nonParenthesisForEmptyParameterFunction =
3564
+ config.nonParenthesisForEmptyParameterFunction || false;
3413
3565
  }
3414
3566
  get helper() {
3415
3567
  return ODataHelper[this.version];
@@ -3418,7 +3570,6 @@ class ODataApiOptions {
3418
3570
  class ODataParserOptions {
3419
3571
  constructor(config) {
3420
3572
  this.version = config.version || DEFAULT_VERSION;
3421
- this.stringAsEnum = config.stringAsEnum;
3422
3573
  }
3423
3574
  get helper() {
3424
3575
  return ODataHelper[this.version];
@@ -3454,7 +3605,8 @@ class ODataEnumTypeParser extends ODataAnnotatable {
3454
3605
  ttitelize(term) {
3455
3606
  return (term && this.annotatedValue(term)) || Strings.titleCase(this.name);
3456
3607
  }
3457
- configure({ options }) {
3608
+ configure({ stringAsEnum, options }) {
3609
+ this.stringAsEnum = stringAsEnum;
3458
3610
  this.optionsHelper = options;
3459
3611
  }
3460
3612
  isTypeOf(type) {
@@ -3485,13 +3637,13 @@ class ODataEnumTypeParser extends ODataAnnotatable {
3485
3637
  : this.optionsHelper;
3486
3638
  if (this.flags) {
3487
3639
  const names = Enums.toNames(this.members, value);
3488
- return !parserOptions?.stringAsEnum
3640
+ return !this.stringAsEnum
3489
3641
  ? `${this.namespace}.${this.name}'${names.join(', ')}'`
3490
3642
  : names.join(', ');
3491
3643
  }
3492
3644
  else {
3493
3645
  const name = Enums.toName(this.members, value);
3494
- return !parserOptions?.stringAsEnum
3646
+ return !this.stringAsEnum
3495
3647
  ? `${this.namespace}.${this.name}'${name}'`
3496
3648
  : name;
3497
3649
  }
@@ -3502,7 +3654,7 @@ class ODataEnumTypeParser extends ODataAnnotatable {
3502
3654
  ? new ODataParserOptions(options)
3503
3655
  : this.optionsHelper;
3504
3656
  const serialized = this.serialize(value, parserOptions);
3505
- return parserOptions?.stringAsEnum
3657
+ return this.stringAsEnum
3506
3658
  ? raw(`'${serialized}'`)
3507
3659
  : raw(serialized);
3508
3660
  }
@@ -3593,8 +3745,8 @@ class ODataStructuredTypeFieldParser extends ODataAnnotatable {
3593
3745
  }
3594
3746
  //#region Deserialize
3595
3747
  parse(parser, value, options) {
3596
- const type = Types.isPlainObject(value)
3597
- ? options?.helper.type(value)
3748
+ const type = options !== undefined && Types.isPlainObject(value)
3749
+ ? options.helper.type(value)
3598
3750
  : undefined;
3599
3751
  if (type !== undefined) {
3600
3752
  return parser
@@ -3621,8 +3773,8 @@ class ODataStructuredTypeFieldParser extends ODataAnnotatable {
3621
3773
  //#endregion
3622
3774
  //#region Serialize
3623
3775
  toJson(parser, value, options) {
3624
- const type = Types.isPlainObject(value)
3625
- ? options?.helper.type(value)
3776
+ const type = options !== undefined && Types.isPlainObject(value)
3777
+ ? options.helper.type(value)
3626
3778
  : undefined;
3627
3779
  if (type !== undefined) {
3628
3780
  return parser
@@ -4030,7 +4182,8 @@ class ODataCallableParser {
4030
4182
  [p.name]: p.encode(params[p.name], parserOptions),
4031
4183
  }), {});
4032
4184
  }
4033
- configure({ parserForType, options, }) {
4185
+ configure({ nonParenthesisForEmptyParameterFunction, parserForType, options, }) {
4186
+ this.nonParenthesisForEmptyParameterFunction = nonParenthesisForEmptyParameterFunction;
4034
4187
  this.optionsHelper = options;
4035
4188
  if (this.return)
4036
4189
  this.parser = parserForType(this.return.type) || NONE_PARSER;
@@ -4063,7 +4216,11 @@ class ODataCallable extends ODataSchemaElement {
4063
4216
  return path;
4064
4217
  }
4065
4218
  configure({ parserForType, }) {
4066
- this.parser.configure({ options: this.api.options, parserForType });
4219
+ this.parser.configure({
4220
+ nonParenthesisForEmptyParameterFunction: this.api.options.nonParenthesisForEmptyParameterFunction,
4221
+ options: this.api.options,
4222
+ parserForType
4223
+ });
4067
4224
  }
4068
4225
  /**
4069
4226
  * Deseialize the given value from the callable.
@@ -4123,7 +4280,7 @@ class ODataEnumType extends ODataSchemaElement {
4123
4280
  this.parser = new ODataEnumTypeParser(config, schema.namespace, schema.alias);
4124
4281
  }
4125
4282
  configure() {
4126
- this.parser.configure({ options: this.api.options });
4283
+ this.parser.configure({ stringAsEnum: this.api.options.stringAsEnum, options: this.api.options });
4127
4284
  }
4128
4285
  /**
4129
4286
  * Returns the fields of the enum type.
@@ -4148,6 +4305,14 @@ class ODataEnumType extends ODataSchemaElement {
4148
4305
  findFieldByValue(value) {
4149
4306
  return this.fields().find((f) => f.value === value);
4150
4307
  }
4308
+ /**
4309
+ * Find a fields by flag.
4310
+ * @param value The value of the field
4311
+ * @returns The fields with the given flag
4312
+ */
4313
+ findFieldsByValue(value) {
4314
+ return this.fields().filter((f) => Boolean(f.value & value));
4315
+ }
4151
4316
  /**
4152
4317
  * Map the fields of the enum type.
4153
4318
  * @param mapper Function that maps the value to the new value
@@ -4320,14 +4485,9 @@ class ODataStructuredType extends ODataSchemaElement {
4320
4485
  */
4321
4486
  pick(attrs, { include_parents = true, include_navigation = false, include_etag = true, } = {}) {
4322
4487
  const names = this.fields({ include_parents, include_navigation }).map((f) => f.name);
4323
- let values = Object.keys(attrs)
4324
- .filter((k) => names.indexOf(k) !== -1)
4325
- .reduce((acc, k) => Object.assign(acc, { [k]: attrs[k] }), {});
4326
- if (include_etag) {
4327
- const etag = this.api.options.helper.etag(attrs);
4328
- this.api.options.helper.etag(attrs, etag);
4329
- }
4330
- return values;
4488
+ return Object.keys(attrs)
4489
+ .filter((key) => names.indexOf(key) !== -1 || (key == this.api.options.helper.ODATA_ETAG && include_etag))
4490
+ .reduce((acc, key) => Object.assign(acc, { [key]: attrs[key] }), {});
4331
4491
  }
4332
4492
  /**
4333
4493
  * Deseialize the given value from the structured type.
@@ -4555,29 +4715,28 @@ class ODataResource {
4555
4715
  query: this.cloneQuery(),
4556
4716
  });
4557
4717
  }
4718
+ __parser(value, options, type) {
4719
+ const dataType = options !== undefined && Types.isPlainObject(value)
4720
+ ? options.helper.type(value)
4721
+ : undefined;
4722
+ if (dataType !== undefined) {
4723
+ // Parser from data type
4724
+ return this.api.parserForType(dataType);
4725
+ }
4726
+ else if (this.schema !== undefined && 'parser' in this.schema) {
4727
+ // Parser from resource schema
4728
+ return this.schema.parser;
4729
+ }
4730
+ else if (type !== undefined) {
4731
+ // Parser from resource type
4732
+ return this.api.parserForType(type);
4733
+ }
4734
+ return undefined;
4735
+ }
4558
4736
  deserialize(value, options) {
4559
4737
  const resourceType = this.returnType();
4560
- const resourceSchema = this.schema;
4561
- const _p = (value, options) => {
4562
- const dataType = Types.isPlainObject(value)
4563
- ? options.helper.type(value)
4564
- : undefined;
4565
- if (dataType !== undefined) {
4566
- // Parser from data type
4567
- return this.api.parserForType(dataType);
4568
- }
4569
- else if (resourceSchema !== undefined && 'parser' in resourceSchema) {
4570
- // Parser from resource schema
4571
- return resourceSchema.parser;
4572
- }
4573
- else if (resourceType !== undefined) {
4574
- // Parser from resource type
4575
- return this.api.parserForType(resourceType);
4576
- }
4577
- return undefined;
4578
- };
4579
4738
  const _d = (value, options) => {
4580
- const parser = _p(value, options);
4739
+ const parser = this.__parser(value, options, resourceType);
4581
4740
  return parser !== undefined && 'deserialize' in parser
4582
4741
  ? parser.deserialize(value, options)
4583
4742
  : value;
@@ -4588,27 +4747,8 @@ class ODataResource {
4588
4747
  }
4589
4748
  serialize(value, options) {
4590
4749
  const resourceType = this.type();
4591
- const resourceSchema = this.schema;
4592
- const _p = (value, options) => {
4593
- const dataType = Types.isPlainObject(value)
4594
- ? options.helper.type(value)
4595
- : undefined;
4596
- if (dataType !== undefined) {
4597
- // Parser from data type
4598
- return this.api.parserForType(dataType);
4599
- }
4600
- else if (resourceSchema !== undefined && 'parser' in resourceSchema) {
4601
- // Parser from resource schema
4602
- return resourceSchema.parser;
4603
- }
4604
- else if (resourceType !== undefined) {
4605
- // Parser from resource type
4606
- return this.api.parserForType(resourceType);
4607
- }
4608
- return undefined;
4609
- };
4610
4750
  const _s = (value, options) => {
4611
- const parser = _p(value, options);
4751
+ const parser = this.__parser(value, options, resourceType);
4612
4752
  return parser !== undefined && 'serialize' in parser
4613
4753
  ? parser.serialize(value, options)
4614
4754
  : value;
@@ -4619,27 +4759,8 @@ class ODataResource {
4619
4759
  }
4620
4760
  encode(value, options) {
4621
4761
  const resourceType = this.type();
4622
- const resourceSchema = this.schema;
4623
- const _p = (value, options) => {
4624
- const dataType = Types.isPlainObject(value)
4625
- ? options.helper.type(value)
4626
- : undefined;
4627
- if (dataType !== undefined) {
4628
- // Parser from data type
4629
- return this.api.parserForType(dataType);
4630
- }
4631
- else if (resourceSchema !== undefined && 'parser' in resourceSchema) {
4632
- // Parser from resource schema
4633
- return resourceSchema.parser;
4634
- }
4635
- else if (resourceType !== undefined) {
4636
- // Parser from resource type
4637
- return this.api.parserForType(resourceType);
4638
- }
4639
- return undefined;
4640
- };
4641
4762
  const _e = (value, options) => {
4642
- const parser = _p(value, options);
4763
+ const parser = this.__parser(value, options, resourceType);
4643
4764
  return parser !== undefined && 'encode' in parser
4644
4765
  ? parser.encode(value, options)
4645
4766
  : value;
@@ -4856,7 +4977,7 @@ class ODataActionResource extends ODataResource {
4856
4977
  }
4857
4978
 
4858
4979
  class ODataAnnotations {
4859
- constructor(helper, annotations = {}, context) {
4980
+ constructor(helper, annotations = new Map(), context) {
4860
4981
  this.helper = helper;
4861
4982
  this.annotations = annotations;
4862
4983
  this.context = context;
@@ -4873,7 +4994,7 @@ class ODataAnnotations {
4873
4994
  }
4874
4995
  class ODataPropertyAnnotations extends ODataAnnotations {
4875
4996
  clone() {
4876
- return new ODataPropertyAnnotations(this.helper, { ...this.annotations }, this.context);
4997
+ return new ODataPropertyAnnotations(this.helper, new Map(this.annotations), this.context);
4877
4998
  }
4878
4999
  data(data) {
4879
5000
  return this.helper.property(data);
@@ -4881,7 +5002,7 @@ class ODataPropertyAnnotations extends ODataAnnotations {
4881
5002
  }
4882
5003
  class ODataEntityAnnotations extends ODataAnnotations {
4883
5004
  clone() {
4884
- return new ODataEntityAnnotations(this.helper, { ...this.annotations }, this.context);
5005
+ return new ODataEntityAnnotations(this.helper, new Map(this.annotations), this.context);
4885
5006
  }
4886
5007
  data(data) {
4887
5008
  return this.helper.entity(data);
@@ -4920,7 +5041,7 @@ class ODataEntityAnnotations extends ODataAnnotations {
4920
5041
  return this._properties;
4921
5042
  }
4922
5043
  property(name) {
4923
- return this.properties[name];
5044
+ return this.properties.get(name);
4924
5045
  }
4925
5046
  get functions() {
4926
5047
  if (this._functions === undefined) {
@@ -4934,7 +5055,7 @@ class ODataEntityAnnotations extends ODataAnnotations {
4934
5055
  }
4935
5056
  class ODataEntitiesAnnotations extends ODataAnnotations {
4936
5057
  clone() {
4937
- return new ODataEntitiesAnnotations(this.helper, { ...this.annotations }, this.context);
5058
+ return new ODataEntitiesAnnotations(this.helper, new Map(this.annotations), this.context);
4938
5059
  }
4939
5060
  data(data) {
4940
5061
  return this.helper.entities(data);
@@ -4977,7 +5098,6 @@ class ODataEntitiesAnnotations extends ODataAnnotations {
4977
5098
  class ODataResponseOptions {
4978
5099
  constructor(config) {
4979
5100
  this.version = config.version || DEFAULT_VERSION;
4980
- this.stringAsEnum = config.stringAsEnum;
4981
5101
  }
4982
5102
  get helper() {
4983
5103
  return ODataHelper[this.version];
@@ -5116,13 +5236,13 @@ class ODataResponse extends HttpResponse {
5116
5236
  if (key) {
5117
5237
  const etag = this.headers.get(key);
5118
5238
  if (etag)
5119
- options.helper.etag(this._annotations, etag);
5239
+ this._annotations.set(options.helper.ODATA_ETAG, etag);
5120
5240
  }
5121
5241
  key = Http.resolveHeaderKey(this.headers, ODATA_ENTITYID_HEADERS);
5122
5242
  if (key) {
5123
5243
  const entityId = this.headers.get(key);
5124
5244
  if (entityId)
5125
- options.helper.id(this._annotations, entityId);
5245
+ this._annotations.set(options.helper.ODATA_ID, entityId);
5126
5246
  }
5127
5247
  }
5128
5248
  return this._annotations;
@@ -6360,6 +6480,14 @@ class ODataFunctionResource extends ODataResource {
6360
6480
  ? this.schema.parser.return?.type
6361
6481
  : undefined;
6362
6482
  }
6483
+ pathAndParams(escape = false) {
6484
+ let [path, params] = super.pathAndParams(escape);
6485
+ if (path.endsWith('()') &&
6486
+ this.api.options.nonParenthesisForEmptyParameterFunction) {
6487
+ path = path.substring(0, path.length - 2);
6488
+ }
6489
+ return [path, params];
6490
+ }
6363
6491
  parameters(params, { alias } = {}) {
6364
6492
  let parameters = params !== null ? this.encode(params) : null;
6365
6493
  if (alias && parameters !== null) {
@@ -7065,7 +7193,7 @@ class ODataEntityResource extends ODataResource {
7065
7193
  if (castSchema !== undefined &&
7066
7194
  baseSchema !== undefined &&
7067
7195
  !castSchema.isSubtypeOf(baseSchema))
7068
- throw new Error(`Cannot cast to ${type}`);
7196
+ throw new Error(`cast: Cannot cast to ${type}`);
7069
7197
  const segments = this.cloneSegments();
7070
7198
  segments.add(PathSegmentNames.type, type).type(type);
7071
7199
  return new ODataEntityResource(this.api, {
@@ -7106,7 +7234,7 @@ class ODataEntityResource extends ODataResource {
7106
7234
  }
7107
7235
  fetch(options) {
7108
7236
  if (!this.hasKey())
7109
- return throwError('Entity resource without key');
7237
+ return throwError(() => new Error('fetch: Entity resource without key'));
7110
7238
  return this.get(options);
7111
7239
  }
7112
7240
  fetchEntity(options) {
@@ -7424,6 +7552,18 @@ class ODataModelEvent {
7424
7552
  : '')
7425
7553
  .join('');
7426
7554
  }
7555
+ //Identifies the current model for the event
7556
+ get currentModel() {
7557
+ const link = this.chain.find((c) => ODataModelOptions.isModel(c[0]));
7558
+ return link !== undefined ? link[0] : undefined;
7559
+ }
7560
+ //Identifies the current collection for the event
7561
+ get currentCollection() {
7562
+ const link = this.chain.find((c) => ODataModelOptions.isCollection(c[0]));
7563
+ return link !== undefined
7564
+ ? link[0]
7565
+ : undefined;
7566
+ }
7427
7567
  }
7428
7568
  const BUBBLING = [
7429
7569
  'change',
@@ -7621,8 +7761,8 @@ class ODataModelField {
7621
7761
  }
7622
7762
  annotationsFactory(base) {
7623
7763
  return this.parser.collection
7624
- ? new ODataEntitiesAnnotations(base.helper, base.property(this.parser.name) || {})
7625
- : new ODataEntityAnnotations(base.helper, base.property(this.parser.name) || {});
7764
+ ? new ODataEntitiesAnnotations(base.helper, base.property(this.parser.name))
7765
+ : new ODataEntityAnnotations(base.helper, base.property(this.parser.name));
7626
7766
  }
7627
7767
  schemaFactory(base) {
7628
7768
  return this.api.findStructuredTypeForType(this.parser.type);
@@ -7752,30 +7892,35 @@ class ODataModelOptions {
7752
7892
  return chain;
7753
7893
  }
7754
7894
  static resource(child) {
7755
- let resource = undefined;
7895
+ let resource = null;
7896
+ let prevField = null;
7756
7897
  for (let [model, field] of ODataModelOptions.chain(child)) {
7757
7898
  resource = resource || model._resource;
7758
- if (resource === undefined)
7899
+ if (resource === null)
7759
7900
  break;
7760
- if (ODataModelOptions.isModel(model)) {
7761
- let key = model.key({
7901
+ if (ODataModelOptions.isModel(model) &&
7902
+ (prevField === null || prevField.collection)) {
7903
+ // Resolve key
7904
+ let modelKey = model.key({
7762
7905
  field_mapping: true,
7763
7906
  });
7764
- if (key !== undefined)
7907
+ if (modelKey !== undefined)
7765
7908
  resource =
7766
7909
  resource instanceof ODataEntitySetResource
7767
- ? resource.entity(key)
7768
- : resource.key(key);
7910
+ ? resource.entity(modelKey)
7911
+ : resource.key(modelKey);
7769
7912
  }
7913
+ prevField = field;
7770
7914
  if (field === null) {
7915
+ // Apply the query from model to new resource
7771
7916
  const query = model._resource?.cloneQuery().toQueryArguments();
7772
- if (query !== undefined && resource !== undefined)
7917
+ if (query !== undefined)
7773
7918
  resource.query((q) => q.apply(query));
7774
7919
  continue;
7775
7920
  }
7776
7921
  resource = field.resourceFactory(resource);
7777
7922
  }
7778
- if (resource === undefined)
7923
+ if (resource === null)
7779
7924
  throw new Error(`resource: Can't build resource for ${child}`);
7780
7925
  return resource;
7781
7926
  }
@@ -7926,8 +8071,8 @@ class ODataModelOptions {
7926
8071
  return !Types.isEmpty(defs) ? defs : undefined;
7927
8072
  }
7928
8073
  hasChanged(self, { include_navigation = false } = {}) {
7929
- return (!Types.isEmpty(self._changes) ||
7930
- Object.values(self._relations)
8074
+ return (self._changes.size != 0 ||
8075
+ [...self._relations.values()]
7931
8076
  .filter(({ field }) => !field.navigation || include_navigation)
7932
8077
  .some(({ field, state, model }) => (!include_navigation || field.navigation) &&
7933
8078
  (state === ODataModelState.Changed ||
@@ -7968,7 +8113,7 @@ class ODataModelOptions {
7968
8113
  include_computed,
7969
8114
  include_non_field,
7970
8115
  });
7971
- let relations = Object.entries(self._relations)
8116
+ let relations = [...self._relations.entries()]
7972
8117
  .filter(
7973
8118
  // Chain
7974
8119
  ([, { model }]) => chain.every((c) => c !== model))
@@ -8045,19 +8190,19 @@ class ODataModelOptions {
8045
8190
  (ODataModelOptions.isCollection(self._parent[0]) &&
8046
8191
  self._parent[0]._model
8047
8192
  .meta !== self._meta))) {
8048
- this.api.options.helper.type(entity, this.schema.type());
8193
+ entity[this.api.options.helper.ODATA_TYPE] = `#${this.schema.type()}`;
8049
8194
  }
8050
8195
  return entity;
8051
8196
  }
8052
8197
  attributes(self, { changes_only = false, include_concurrency = false, include_computed = false, include_non_field = false, field_mapping = false, } = {}) {
8053
8198
  // Attributes by fields (attributes for the model type)
8054
8199
  const fieldAttrs = this.fields().reduce((acc, f) => {
8055
- const isChanged = f.name in self._changes;
8200
+ const isChanged = self._changes.has(f.name);
8056
8201
  const name = field_mapping ? f.field : f.name;
8057
8202
  const computed = f.annotatedValue(COMPUTED);
8058
8203
  const value = isChanged
8059
- ? self._changes[f.name]
8060
- : self._attributes[f.name];
8204
+ ? self._changes.get(f.name)
8205
+ : self._attributes.get(f.name);
8061
8206
  if (f.concurrency && include_concurrency) {
8062
8207
  return Object.assign(acc, { [name]: value });
8063
8208
  }
@@ -8084,10 +8229,10 @@ class ODataModelOptions {
8084
8229
  return { ...fieldAttrs, ...nonFieldAttrs };
8085
8230
  }
8086
8231
  reset(self, { name, silent = false } = {}) {
8087
- if (!Types.isEmpty(name) && name in self._changes) {
8088
- const value = self._attributes[name];
8089
- const previous = self._changes[name];
8090
- delete self._changes[name];
8232
+ if (!Types.isEmpty(name) && self._changes.has(name)) {
8233
+ const value = self._attributes.get(name);
8234
+ const previous = self._changes.get(name);
8235
+ self._changes.delete(name);
8091
8236
  if (!silent) {
8092
8237
  self.events$.emit(new ODataModelEvent('change', {
8093
8238
  model: self,
@@ -8098,14 +8243,14 @@ class ODataModelOptions {
8098
8243
  }
8099
8244
  }
8100
8245
  else if (Types.isEmpty(name)) {
8101
- const entries = Object.entries(self._changes);
8102
- self._changes = {};
8246
+ const entries = [...self._changes.entries()];
8247
+ self._changes.clear();
8103
8248
  if (!silent) {
8104
8249
  entries.forEach((entry) => {
8105
8250
  self.events$.emit(new ODataModelEvent('change', {
8106
8251
  track: entry[0],
8107
8252
  model: self,
8108
- value: self._attributes[entry[0]],
8253
+ value: self._attributes.get(entry[0]),
8109
8254
  previous: entry[1],
8110
8255
  }));
8111
8256
  });
@@ -8176,7 +8321,7 @@ class ODataModelOptions {
8176
8321
  }
8177
8322
  _get(self, field) {
8178
8323
  if (field.isStructuredType()) {
8179
- return self._relations[field.name]?.model;
8324
+ return self._relations.get(field.name)?.model;
8180
8325
  }
8181
8326
  else {
8182
8327
  return this.attributes(self, {
@@ -8188,13 +8333,13 @@ class ODataModelOptions {
8188
8333
  _setStructured(self, field, value) {
8189
8334
  let changed = false;
8190
8335
  // Ensures that the relation exists
8191
- if (!(field.name in self._relations)) {
8192
- self._relations[field.name] = {
8336
+ if (!self._relations.has(field.name)) {
8337
+ self._relations.set(field.name, {
8193
8338
  state: ODataModelState.Unchanged,
8194
8339
  field: field,
8195
- };
8340
+ });
8196
8341
  }
8197
- const relation = self._relations[field.name];
8342
+ const relation = self._relations.get(field.name);
8198
8343
  const currentModel = relation.model;
8199
8344
  if (value === null) {
8200
8345
  relation.model = value;
@@ -8277,14 +8422,14 @@ class ODataModelOptions {
8277
8422
  const currentValue = attrs[field];
8278
8423
  changed = !Types.isEqual(currentValue, value);
8279
8424
  if (self._reset) {
8280
- delete self._changes[field];
8281
- self._attributes[field] = value;
8425
+ self._changes.delete(field);
8426
+ self._attributes.set(field, value);
8282
8427
  }
8283
- else if (Types.isEqual(value, self._attributes[field])) {
8284
- delete self._changes[field];
8428
+ else if (Types.isEqual(value, self._attributes.get(field))) {
8429
+ self._changes.delete(field);
8285
8430
  }
8286
8431
  else if (changed) {
8287
- self._changes[field] = value;
8432
+ self._changes.set(field, value);
8288
8433
  }
8289
8434
  if (!self._silent && changed) {
8290
8435
  self.events$.emit(new ODataModelEvent('change', {
@@ -8348,7 +8493,7 @@ class ODataCollection {
8348
8493
  if (model === undefined && Klass.model !== null)
8349
8494
  model = Klass.model;
8350
8495
  if (model === undefined)
8351
- throw new Error('Collection need model');
8496
+ throw new Error('Collection: Collection need model');
8352
8497
  this._model = model;
8353
8498
  // Parent
8354
8499
  if (parent !== undefined) {
@@ -8386,7 +8531,7 @@ class ODataCollection {
8386
8531
  if (this._resource !== null &&
8387
8532
  this._resource.type() !== resource.type() &&
8388
8533
  !this._resource.isSubtypeOf(resource))
8389
- throw new Error(`Can't reattach ${this._resource.type()} to ${resource.type()}`);
8534
+ throw new Error(`attach: Can't reattach ${this._resource.type()} to ${resource.type()}`);
8390
8535
  this._entries.forEach(({ model }) => {
8391
8536
  const mr = this._model.meta.modelResourceFactory(resource.cloneQuery());
8392
8537
  model.attach(mr);
@@ -8406,7 +8551,7 @@ class ODataCollection {
8406
8551
  const query = this.resource().cloneQuery();
8407
8552
  let resource = this._model.meta.collectionResourceFactory(query);
8408
8553
  if (resource === undefined)
8409
- throw new Error('Collection does not have associated EntitySet endpoint');
8554
+ throw new Error('asEntitySet: Collection does not have associated EntitySet endpoint');
8410
8555
  // Store parent and resource
8411
8556
  const store = { parent: this._parent, resource: this._resource };
8412
8557
  // Replace parent and resource
@@ -8434,7 +8579,7 @@ class ODataCollection {
8434
8579
  modelFactory(data, { reset = false } = {}) {
8435
8580
  let Model = this._model;
8436
8581
  const helper = this._annotations.helper;
8437
- const annots = new ODataEntityAnnotations(helper, helper.annotations(data) || {});
8582
+ const annots = new ODataEntityAnnotations(helper, helper.annotations(data));
8438
8583
  if (annots?.type !== undefined && Model.meta !== null) {
8439
8584
  let schema = Model.meta.findChildOptions((o) => o.isTypeOf(annots.type))?.schema;
8440
8585
  if (schema !== undefined && schema.model !== undefined)
@@ -8481,26 +8626,13 @@ class ODataCollection {
8481
8626
  }
8482
8627
  fetch({ withCount, ...options } = {}) {
8483
8628
  const resource = this.resource();
8484
- if (resource === undefined)
8485
- return throwError('fetch: Resource is undefined');
8486
- let obs$;
8487
- if (resource instanceof ODataEntitySetResource) {
8488
- obs$ = resource.fetch({ withCount, ...options });
8489
- }
8490
- else if (resource instanceof ODataNavigationPropertyResource) {
8491
- obs$ = resource.fetch({
8629
+ const obs$ = resource instanceof ODataEntitySetResource
8630
+ ? resource.fetch({ withCount, ...options })
8631
+ : resource.fetch({
8492
8632
  responseType: 'entities',
8493
8633
  withCount,
8494
8634
  ...options,
8495
8635
  });
8496
- }
8497
- else {
8498
- obs$ = resource.fetch({
8499
- responseType: 'entities',
8500
- withCount,
8501
- ...options,
8502
- });
8503
- }
8504
8636
  this.events$.emit(new ODataModelEvent('request', { collection: this, value: obs$ }));
8505
8637
  return obs$.pipe(map(({ entities, annots }) => {
8506
8638
  this._annotations = annots;
@@ -8511,10 +8643,8 @@ class ODataCollection {
8511
8643
  }
8512
8644
  fetchAll(options) {
8513
8645
  const resource = this.resource();
8514
- if (resource === undefined)
8515
- return throwError('fetchAll: Resource is undefined');
8516
8646
  if (resource instanceof ODataPropertyResource)
8517
- return throwError('fetchAll: Resource is ODataPropertyResource');
8647
+ return throwError(() => new Error('fetchAll: Resource is ODataPropertyResource'));
8518
8648
  const obs$ = resource.fetchAll(options);
8519
8649
  this.events$.emit(new ODataModelEvent('request', {
8520
8650
  collection: this,
@@ -8538,10 +8668,8 @@ class ODataCollection {
8538
8668
  */
8539
8669
  save({ relModel = false, method, ...options } = {}) {
8540
8670
  const resource = this.resource();
8541
- if (resource === undefined)
8542
- return throwError('saveAll: Resource is undefined');
8543
8671
  if (resource instanceof ODataPropertyResource)
8544
- return throwError('fetchAll: Resource is ODataPropertyResource');
8672
+ return throwError(() => new Error('save: Resource is ODataPropertyResource'));
8545
8673
  let toDestroyEntity = [];
8546
8674
  let toRemoveReference = [];
8547
8675
  let toDestroyContained = [];
@@ -8831,7 +8959,7 @@ class ODataCollection {
8831
8959
  }
8832
8960
  else {
8833
8961
  const helper = this._annotations.helper;
8834
- const annots = new ODataEntityAnnotations(helper, helper.annotations(obj) || {});
8962
+ const annots = new ODataEntityAnnotations(helper, helper.annotations(obj));
8835
8963
  const entity = annots.attributes(obj, 'full');
8836
8964
  model._annotations = annots;
8837
8965
  model.assign(entity, { reset, silent });
@@ -8911,25 +9039,25 @@ class ODataCollection {
8911
9039
  return func.call(params, { responseType, ...options });
8912
9040
  }
8913
9041
  }
8914
- return throwError(`Can't function without ODataEntitySetResource`);
9042
+ return throwError(() => new Error(`callFunction: Can't function without ODataEntitySetResource`));
8915
9043
  }
8916
9044
  callAction(name, params, responseType, { ...options } = {}) {
8917
9045
  const resource = this.resource();
8918
- if (resource instanceof ODataEntitySetResource) {
8919
- const action = resource.action(name);
8920
- action.query((q) => q.apply(options));
8921
- switch (responseType) {
8922
- case 'property':
8923
- return action.callProperty(params, options);
8924
- case 'model':
8925
- return action.callModel(params, options);
8926
- case 'collection':
8927
- return action.callCollection(params, options);
8928
- default:
8929
- return action.call(params, { responseType, ...options });
8930
- }
9046
+ if (!(resource instanceof ODataEntitySetResource)) {
9047
+ return throwError(() => new Error(`callAction: Can't action without ODataEntitySetResource`));
9048
+ }
9049
+ const action = resource.action(name);
9050
+ action.query((q) => q.apply(options));
9051
+ switch (responseType) {
9052
+ case 'property':
9053
+ return action.callProperty(params, options);
9054
+ case 'model':
9055
+ return action.callModel(params, options);
9056
+ case 'collection':
9057
+ return action.callCollection(params, options);
9058
+ default:
9059
+ return action.call(params, { responseType, ...options });
8931
9060
  }
8932
- return throwError(`Can't action without ODataEntitySetResource`);
8933
9061
  }
8934
9062
  _unsubscribe(entry) {
8935
9063
  if (entry.subscription) {
@@ -8939,7 +9067,7 @@ class ODataCollection {
8939
9067
  }
8940
9068
  _subscribe(entry) {
8941
9069
  if (entry.subscription) {
8942
- throw new Error('Subscription already exists');
9070
+ throw new Error('Collection: Subscription already exists');
8943
9071
  }
8944
9072
  entry.subscription = entry.model.events$.subscribe((event) => {
8945
9073
  if (BUBBLING.indexOf(event.name) !== -1 &&
@@ -8988,12 +9116,18 @@ class ODataCollection {
8988
9116
  },
8989
9117
  };
8990
9118
  }
8991
- filter(predicate) {
9119
+ filter(predicate, thisArg) {
8992
9120
  return this.models().filter(predicate);
8993
9121
  }
8994
- find(predicate) {
9122
+ map(callbackfn, thisArg) {
9123
+ return this.models().map(callbackfn, thisArg);
9124
+ }
9125
+ find(predicate, thisArg) {
8995
9126
  return this.models().find(predicate);
8996
9127
  }
9128
+ reduce(callbackfn, initialValue) {
9129
+ return this.models().reduce(callbackfn, initialValue);
9130
+ }
8997
9131
  first() {
8998
9132
  return this.models()[0];
8999
9133
  }
@@ -9090,9 +9224,9 @@ class ODataModel {
9090
9224
  constructor(data = {}, { parent, resource, annots, reset = false, } = {}) {
9091
9225
  // Parent
9092
9226
  this._parent = null;
9093
- this._attributes = {};
9094
- this._changes = {};
9095
- this._relations = {};
9227
+ this._attributes = new Map();
9228
+ this._changes = new Map();
9229
+ this._relations = new Map();
9096
9230
  this._resource = null;
9097
9231
  this._reset = false;
9098
9232
  this._reparent = false;
@@ -9101,7 +9235,7 @@ class ODataModel {
9101
9235
  this.events$ = new EventEmitter();
9102
9236
  const Klass = this.constructor;
9103
9237
  if (Klass.meta === undefined)
9104
- throw new Error(`Can't create model without metadata`);
9238
+ throw new Error(`ODataModel: Can't create model without metadata`);
9105
9239
  this._meta = Klass.meta;
9106
9240
  this._meta.bind(this, { parent, resource, annots });
9107
9241
  // Client Id
@@ -9141,19 +9275,19 @@ class ODataModel {
9141
9275
  navigationProperty(name) {
9142
9276
  const field = this._meta.field(name);
9143
9277
  if (field === undefined || !field.navigation)
9144
- throw Error(`Can't find navigation property ${name}`);
9278
+ throw Error(`navigationProperty: Can't find navigation property ${name}`);
9145
9279
  const resource = this.resource();
9146
9280
  if (!(resource instanceof ODataEntityResource) || !resource.hasKey())
9147
- throw Error("Can't get navigation without ODataEntityResource with key");
9281
+ throw Error("navigationProperty: Can't get navigation without ODataEntityResource with key");
9148
9282
  return field.resourceFactory(resource);
9149
9283
  }
9150
9284
  property(name) {
9151
9285
  const field = this._meta.field(name);
9152
9286
  if (field === undefined || field.navigation)
9153
- throw Error(`Can't find property ${name}`);
9287
+ throw Error(`property: Can't find property ${name}`);
9154
9288
  const resource = this.resource();
9155
9289
  if (!(resource instanceof ODataEntityResource) || !resource.hasKey())
9156
- throw Error("Can't get property without ODataEntityResource with key");
9290
+ throw Error("property: Can't get property without ODataEntityResource with key");
9157
9291
  return field.resourceFactory(resource);
9158
9292
  }
9159
9293
  attach(resource) {
@@ -9298,11 +9432,11 @@ class ODataModel {
9298
9432
  fetch({ ...options } = {}) {
9299
9433
  let resource = this.resource();
9300
9434
  if (resource === undefined)
9301
- return throwError('fetch: Resource is undefined');
9435
+ return throwError(() => new Error('fetch: Resource is undefined'));
9302
9436
  let obs$;
9303
9437
  if (resource instanceof ODataEntityResource) {
9304
9438
  if (!resource.hasKey())
9305
- return throwError("fetch: Can't fetch model without key");
9439
+ return throwError(() => new Error("fetch: Can't fetch model without key"));
9306
9440
  obs$ = resource.fetch(options);
9307
9441
  }
9308
9442
  else if (resource instanceof ODataNavigationPropertyResource) {
@@ -9319,49 +9453,45 @@ class ODataModel {
9319
9453
  save({ method, navigation = false, validate = true, ...options } = {}) {
9320
9454
  let resource = this.resource();
9321
9455
  if (resource === undefined)
9322
- return throwError('save: Resource is undefined');
9456
+ return throwError(() => new Error('save: Resource is undefined'));
9323
9457
  if (!(resource instanceof ODataEntityResource ||
9324
9458
  resource instanceof ODataNavigationPropertyResource))
9325
- return throwError('save: Resource type ODataEntityResource/ODataNavigationPropertyResource needed');
9459
+ return throwError(() => new Error('save: Resource type ODataEntityResource/ODataNavigationPropertyResource needed'));
9326
9460
  // Resolve method and resource key
9327
9461
  if (method === undefined && this.schema().isCompoundKey())
9328
- return throwError('save: Composite key require a specific method, use create/update/modify');
9462
+ return throwError(() => new Error('save: Composite key require a specific method, use create/update/modify'));
9329
9463
  method = method || (!resource.hasKey() ? 'create' : 'update');
9330
9464
  if (resource instanceof ODataEntityResource &&
9331
9465
  (method === 'update' || method === 'modify') &&
9332
9466
  !resource.hasKey())
9333
- return throwError('save: Update/Patch require entity key');
9467
+ return throwError(() => new Error('save: Update/Patch require entity key'));
9334
9468
  if (resource instanceof ODataNavigationPropertyResource ||
9335
9469
  method === 'create')
9336
9470
  resource.clearKey();
9337
- let obs$;
9338
- if (!validate || this.isValid({ method, navigation })) {
9339
- const _entity = this.toEntity({
9340
- changes_only: method === 'modify',
9341
- field_mapping: true,
9342
- include_concurrency: true,
9343
- include_navigation: navigation,
9344
- });
9345
- obs$ = (method === 'create'
9346
- ? resource.create(_entity, options)
9347
- : method === 'modify'
9348
- ? resource.modify(_entity, { etag: this.annots().etag, ...options })
9349
- : resource.update(_entity, { etag: this.annots().etag, ...options })).pipe(map(({ entity, annots }) => ({ entity: entity || _entity, annots })));
9350
- }
9351
- else {
9352
- obs$ = throwError(this._errors);
9471
+ if (validate && !this.isValid({ method, navigation })) {
9472
+ return throwError(() => new Error('save: Validation errors'));
9353
9473
  }
9354
- return this._request(obs$);
9474
+ const _entity = this.toEntity({
9475
+ changes_only: method === 'modify',
9476
+ field_mapping: true,
9477
+ include_concurrency: true,
9478
+ include_navigation: navigation,
9479
+ });
9480
+ return this._request((method === 'create'
9481
+ ? resource.create(_entity, options)
9482
+ : method === 'modify'
9483
+ ? resource.modify(_entity, { etag: this.annots().etag, ...options })
9484
+ : resource.update(_entity, { etag: this.annots().etag, ...options })).pipe(map(({ entity, annots }) => ({ entity: entity || _entity, annots }))));
9355
9485
  }
9356
9486
  destroy({ ...options } = {}) {
9357
9487
  let resource = this.resource();
9358
9488
  if (resource === undefined)
9359
- return throwError('destroy: Resource is undefined');
9489
+ return throwError(() => new Error('destroy: Resource is undefined'));
9360
9490
  if (!(resource instanceof ODataEntityResource ||
9361
9491
  resource instanceof ODataNavigationPropertyResource))
9362
- return throwError('destroy: Resource type ODataEntityResource/ODataNavigationPropertyResource needed');
9492
+ return throwError(() => new Error('destroy: Resource type ODataEntityResource/ODataNavigationPropertyResource needed'));
9363
9493
  if (!resource.hasKey())
9364
- return throwError("destroy: Can't destroy model without key");
9494
+ return throwError(() => new Error("destroy: Can't destroy model without key"));
9365
9495
  const _entity = this.toEntity({ field_mapping: true });
9366
9496
  const obs$ = resource
9367
9497
  .destroy({ etag: this.annots().etag, ...options })
@@ -9394,7 +9524,7 @@ class ODataModel {
9394
9524
  callFunction(name, params, responseType, { ...options } = {}) {
9395
9525
  const resource = this.resource();
9396
9526
  if (!(resource instanceof ODataEntityResource) || !resource.hasKey())
9397
- return throwError("Can't call function without ODataEntityResource with key");
9527
+ return throwError(() => new Error("callFunction: Can't call function without ODataEntityResource with key"));
9398
9528
  const func = resource.function(name).query((q) => q.apply(options));
9399
9529
  switch (responseType) {
9400
9530
  case 'property':
@@ -9410,7 +9540,7 @@ class ODataModel {
9410
9540
  callAction(name, params, responseType, { ...options } = {}) {
9411
9541
  const resource = this.resource();
9412
9542
  if (!(resource instanceof ODataEntityResource) || !resource.hasKey())
9413
- return throwError("Can't call action without ODataEntityResource with key");
9543
+ return throwError(() => new Error("callAction: Can't call action without ODataEntityResource with key"));
9414
9544
  const action = resource.action(name).query((q) => q.apply(options));
9415
9545
  switch (responseType) {
9416
9546
  case 'property':
@@ -9427,7 +9557,7 @@ class ODataModel {
9427
9557
  cast(type) {
9428
9558
  const resource = this.resource();
9429
9559
  if (!(resource instanceof ODataEntityResource))
9430
- throw new Error(`Can't cast to derived model without ODataEntityResource`);
9560
+ throw new Error(`cast: Can't cast to derived model without ODataEntityResource`);
9431
9561
  return resource
9432
9562
  .cast(type)
9433
9563
  .asModel(this.toEntity(INCLUDE_DEEP), { annots: this.annots() });
@@ -9446,7 +9576,7 @@ class ODataModel {
9446
9576
  getValue(name, options) {
9447
9577
  const field = this._meta.field(name);
9448
9578
  if (field === undefined || field.navigation)
9449
- throw Error(`Can't find property ${name}`);
9579
+ throw Error(`getValue: Can't find property ${name}`);
9450
9580
  let value = this[name];
9451
9581
  if (value === undefined) {
9452
9582
  const prop = field.resourceFactory(this.resource());
@@ -9493,7 +9623,7 @@ class ODataModel {
9493
9623
  getReference(name) {
9494
9624
  const field = this._meta.field(name);
9495
9625
  if (field === undefined || !field.navigation)
9496
- throw Error(`Can't find navigation property ${name}`);
9626
+ throw Error(`getReference: Can't find navigation property ${name}`);
9497
9627
  let model = this[name];
9498
9628
  if (model === undefined) {
9499
9629
  const value = field.collection ? [] : this.referenced(field);
@@ -9540,14 +9670,19 @@ class ODataApi {
9540
9670
  // Memoize
9541
9671
  this.memo = {
9542
9672
  forType: {
9543
- enum: {},
9544
- structured: {},
9545
- callable: {},
9546
- entitySet: {},
9547
- parser: {},
9548
- options: {},
9673
+ enum: new Map(),
9674
+ structured: new Map(),
9675
+ callable: new Map(),
9676
+ entitySet: new Map(),
9677
+ parser: new Map(),
9678
+ options: new Map(),
9679
+ },
9680
+ byName: {
9681
+ enum: new Map(),
9682
+ structured: new Map(),
9683
+ callable: new Map(),
9684
+ entitySet: new Map(),
9549
9685
  },
9550
- byName: { enum: {}, structured: {}, callable: {}, entitySet: {} },
9551
9686
  };
9552
9687
  this.serviceRootUrl = config.serviceRootUrl;
9553
9688
  if (this.serviceRootUrl.indexOf('?') != -1)
@@ -9674,28 +9809,29 @@ class ODataApi {
9674
9809
  .pop();
9675
9810
  }
9676
9811
  findEnumTypeForType(type) {
9677
- if (!(type in this.memo.forType.enum))
9678
- this.memo.forType.enum[type] =
9679
- this.findSchemaForType(type)?.findEnumTypeForType(type);
9680
- return this.memo.forType.enum[type];
9812
+ if (!this.memo.forType.enum.has(type)) {
9813
+ this.memo.forType.enum.set(type, this.findSchemaForType(type)?.findEnumTypeForType(type));
9814
+ }
9815
+ return this.memo.forType.enum.get(type);
9681
9816
  }
9682
9817
  findStructuredTypeForType(type) {
9683
- if (!(type in this.memo.forType.structured))
9684
- this.memo.forType.structured[type] =
9685
- this.findSchemaForType(type)?.findStructuredTypeForType(type);
9686
- return this.memo.forType.structured[type];
9818
+ if (!this.memo.forType.structured.has(type)) {
9819
+ this.memo.forType.structured.set(type, this.findSchemaForType(type)?.findStructuredTypeForType(type));
9820
+ }
9821
+ return this.memo.forType.structured.get(type);
9687
9822
  }
9688
9823
  findCallableForType(type, bindingType) {
9689
9824
  const key = bindingType !== undefined ? `${bindingType}/${type}` : type;
9690
- if (!(key in this.memo.forType.callable))
9691
- this.memo.forType.callable[key] = this.findSchemaForType(type)?.findCallableForType(type, bindingType);
9692
- return this.memo.forType.callable[key];
9825
+ if (!this.memo.forType.callable.has(key)) {
9826
+ this.memo.forType.callable.set(key, this.findSchemaForType(type)?.findCallableForType(type, bindingType));
9827
+ }
9828
+ return this.memo.forType.callable.get(key);
9693
9829
  }
9694
9830
  findEntitySetForType(type) {
9695
- if (!(type in this.memo.forType.entitySet))
9696
- this.memo.forType.entitySet[type] =
9697
- this.findSchemaForType(type)?.findEntitySetForType(type);
9698
- return this.memo.forType.entitySet[type];
9831
+ if (!this.memo.forType.entitySet.has(type)) {
9832
+ this.memo.forType.entitySet.set(type, this.findSchemaForType(type)?.findEntitySetForType(type));
9833
+ }
9834
+ return this.memo.forType.entitySet.get(type);
9699
9835
  }
9700
9836
  findModelForType(type) {
9701
9837
  return this.findStructuredTypeForType(type)?.model;
@@ -9742,44 +9878,49 @@ class ODataApi {
9742
9878
  return this.findEntitySetForType(type)?.service;
9743
9879
  }
9744
9880
  findEntitySetForEntityType(entityType) {
9745
- if (!(entityType in this.memo.forType.entitySet))
9746
- this.memo.forType.entitySet[entityType] = this.schemas
9881
+ if (!this.memo.forType.entitySet.has(entityType)) {
9882
+ this.memo.forType.entitySet.set(entityType, this.schemas
9747
9883
  .reduce((acc, schema) => [...acc, ...schema.entitySets], [])
9748
- .find((e) => e.entityType === entityType);
9749
- return this.memo.forType.entitySet[entityType];
9884
+ .find((e) => e.entityType === entityType));
9885
+ }
9886
+ return this.memo.forType.entitySet.get(entityType);
9750
9887
  }
9751
9888
  findServiceForEntityType(entityType) {
9752
9889
  return this.findEntitySetForEntityType(entityType)?.service;
9753
9890
  }
9754
9891
  findEnumTypeByName(name) {
9755
- if (!(name in this.memo.byName.enum))
9756
- this.memo.byName.enum[name] = this.schemas
9892
+ if (!this.memo.byName.enum.has(name)) {
9893
+ this.memo.byName.enum.set(name, this.schemas
9757
9894
  .reduce((acc, schema) => [...acc, ...schema.enums], [])
9758
- .find((e) => e.name === name);
9759
- return this.memo.byName.enum[name];
9895
+ .find((e) => e.name === name));
9896
+ }
9897
+ return this.memo.byName.enum.get(name);
9760
9898
  }
9761
9899
  findStructuredTypeByName(name) {
9762
- if (!(name in this.memo.byName.structured))
9763
- this.memo.byName.structured[name] = this.schemas
9900
+ if (!this.memo.byName.structured.has(name)) {
9901
+ this.memo.byName.structured.set(name, this.schemas
9764
9902
  .reduce((acc, schema) => [...acc, ...schema.entities], [])
9765
- .find((e) => e.name === name);
9766
- return this.memo.byName.structured[name];
9903
+ .find((e) => e.name === name));
9904
+ }
9905
+ return this.memo.byName.structured.get(name);
9767
9906
  }
9768
9907
  findCallableByName(name, bindingType) {
9769
9908
  const key = bindingType !== undefined ? `${bindingType}/${name}` : name;
9770
- if (!(key in this.memo.byName.callable))
9771
- this.memo.byName.callable[key] = this.schemas
9909
+ if (!this.memo.byName.callable.has(key)) {
9910
+ this.memo.byName.callable.set(key, this.schemas
9772
9911
  .reduce((acc, schema) => [...acc, ...schema.callables], [])
9773
9912
  .find((c) => c.name === name &&
9774
- (bindingType === undefined || c.binding()?.type === bindingType));
9775
- return this.memo.byName.callable[key];
9913
+ (bindingType === undefined || c.binding()?.type === bindingType)));
9914
+ }
9915
+ return this.memo.byName.callable.get(key);
9776
9916
  }
9777
9917
  findEntitySetByName(name) {
9778
- if (!(name in this.memo.byName.entitySet))
9779
- this.memo.byName.entitySet[name] = this.schemas
9918
+ if (!this.memo.byName.entitySet.has(name)) {
9919
+ this.memo.byName.entitySet.set(name, this.schemas
9780
9920
  .reduce((acc, schema) => [...acc, ...schema.entitySets], [])
9781
- .find((e) => e.name === name);
9782
- return this.memo.byName.entitySet[name];
9921
+ .find((e) => e.name === name));
9922
+ }
9923
+ return this.memo.byName.entitySet.get(name);
9783
9924
  }
9784
9925
  findModelByName(name) {
9785
9926
  return this.findStructuredTypeByName(name)?.model;
@@ -9792,35 +9933,34 @@ class ODataApi {
9792
9933
  }
9793
9934
  parserForType(type, bindingType) {
9794
9935
  const key = bindingType !== undefined ? `${bindingType}/${type}` : type;
9795
- if (!(key in this.memo.forType.parser)) {
9936
+ if (!this.memo.forType.parser.has(key)) {
9796
9937
  if (type in this.parsers) {
9797
9938
  // Edm, Base Parsers
9798
- this.memo.forType.parser[key] = this.parsers[type];
9939
+ this.memo.forType.parser.set(key, this.parsers[type]);
9799
9940
  }
9800
9941
  else if (!type.startsWith('Edm.')) {
9801
9942
  // EnumType, ComplexType and EntityType Parsers
9802
9943
  let value = this.findCallableForType(type, bindingType) ||
9803
9944
  this.findEnumTypeForType(type) ||
9804
9945
  this.findStructuredTypeForType(type);
9805
- this.memo.forType.parser[key] = value?.parser;
9946
+ this.memo.forType.parser.set(key, value?.parser);
9806
9947
  }
9807
9948
  else {
9808
9949
  // None Parser
9809
- this.memo.forType.parser[key] = NONE_PARSER;
9950
+ this.memo.forType.parser.set(key, NONE_PARSER);
9810
9951
  }
9811
9952
  }
9812
- return this.memo.forType.parser[key];
9953
+ return this.memo.forType.parser.get(key);
9813
9954
  }
9814
9955
  findOptionsForType(type) {
9815
9956
  // Strucutred Options
9816
- if (!(type in this.memo.forType.options)) {
9957
+ if (!this.memo.forType.options.has(type)) {
9817
9958
  let st = this.findStructuredTypeForType(type);
9818
- this.memo.forType.options[type] =
9819
- st !== undefined && st.model !== undefined && st.model?.meta !== null
9820
- ? st.model.meta
9821
- : undefined;
9959
+ this.memo.forType.options.set(type, st !== undefined && st.model !== undefined && st.model?.meta !== null
9960
+ ? st.model.meta
9961
+ : undefined);
9822
9962
  }
9823
- return this.memo.forType.options[type];
9963
+ return this.memo.forType.options.get(type);
9824
9964
  }
9825
9965
  }
9826
9966
 
@@ -10282,9 +10422,9 @@ class ODataClient {
10282
10422
  return this.request('PUT', resource, addBody(options, body));
10283
10423
  }
10284
10424
  }
10285
- ODataClient.ɵfac = i0.ɵɵngDeclareFactory({ minVersion: "12.0.0", version: "13.2.2", ngImport: i0, type: ODataClient, deps: [{ token: i1.HttpClient }, { token: ODataSettings }, { token: i0.Injector }], target: i0.ɵɵFactoryTarget.Injectable });
10286
- ODataClient.ɵprov = i0.ɵɵngDeclareInjectable({ minVersion: "12.0.0", version: "13.2.2", ngImport: i0, type: ODataClient, providedIn: 'root' });
10287
- i0.ɵɵngDeclareClassMetadata({ minVersion: "12.0.0", version: "13.2.2", ngImport: i0, type: ODataClient, decorators: [{
10425
+ ODataClient.ɵfac = i0.ɵɵngDeclareFactory({ minVersion: "12.0.0", version: "13.3.0", ngImport: i0, type: ODataClient, deps: [{ token: i1.HttpClient }, { token: ODataSettings }, { token: i0.Injector }], target: i0.ɵɵFactoryTarget.Injectable });
10426
+ ODataClient.ɵprov = i0.ɵɵngDeclareInjectable({ minVersion: "12.0.0", version: "13.3.0", ngImport: i0, type: ODataClient, providedIn: 'root' });
10427
+ i0.ɵɵngDeclareClassMetadata({ minVersion: "12.0.0", version: "13.3.0", ngImport: i0, type: ODataClient, decorators: [{
10288
10428
  type: Injectable,
10289
10429
  args: [{
10290
10430
  providedIn: 'root',
@@ -10403,7 +10543,7 @@ class ODataEntitySetService extends ODataEntityService {
10403
10543
  update(key, attrs, options) {
10404
10544
  const res = this.entity(key);
10405
10545
  if (!res.hasKey())
10406
- return throwError('Resource without key');
10546
+ return throwError(() => new Error('update: Resource without key'));
10407
10547
  return res.update(attrs, options);
10408
10548
  }
10409
10549
  /**
@@ -10416,7 +10556,7 @@ class ODataEntitySetService extends ODataEntityService {
10416
10556
  modify(key, attrs, options) {
10417
10557
  const res = this.entity(key);
10418
10558
  if (!res.hasKey())
10419
- return throwError('Resource without key');
10559
+ return throwError(() => new Error('modify: Resource without key'));
10420
10560
  return res.modify(attrs, options);
10421
10561
  }
10422
10562
  /**
@@ -10428,7 +10568,7 @@ class ODataEntitySetService extends ODataEntityService {
10428
10568
  destroy(key, options) {
10429
10569
  const res = this.entity(key);
10430
10570
  if (!res.hasKey())
10431
- return throwError('Resource without key');
10571
+ return throwError(() => new Error('destroy: Resource without key'));
10432
10572
  return res.destroy(options);
10433
10573
  }
10434
10574
  //#region Shortcuts
@@ -10457,12 +10597,12 @@ class ODataEntitySetService extends ODataEntityService {
10457
10597
  save(attrs, { etag, method, ...options } = {}) {
10458
10598
  let schema = this.structuredTypeSchema;
10459
10599
  if (method === undefined && schema !== undefined && schema.isCompoundKey())
10460
- return throwError('Composite key require a specific method, use create/update/patch');
10600
+ return throwError(() => new Error('save: Composite key require a specific method, use create/update/patch'));
10461
10601
  let key = schema && schema.resolveKey(attrs);
10462
10602
  if (method === undefined)
10463
10603
  method = key !== undefined ? 'update' : 'create';
10464
10604
  if ((method === 'update' || method === 'modify') && key === undefined)
10465
- return throwError("Can't update/patch entity without key");
10605
+ return throwError(() => new Error("save: Can't update/patch entity without key"));
10466
10606
  return method === 'create'
10467
10607
  ? this.create(attrs, options)
10468
10608
  : method === 'modify'
@@ -10540,9 +10680,9 @@ class ODataServiceFactory {
10540
10680
  })(this.client, singletonName, apiNameOrEntityType);
10541
10681
  }
10542
10682
  }
10543
- ODataServiceFactory.ɵfac = i0.ɵɵngDeclareFactory({ minVersion: "12.0.0", version: "13.2.2", ngImport: i0, type: ODataServiceFactory, deps: [{ token: ODataClient }], target: i0.ɵɵFactoryTarget.Injectable });
10544
- ODataServiceFactory.ɵprov = i0.ɵɵngDeclareInjectable({ minVersion: "12.0.0", version: "13.2.2", ngImport: i0, type: ODataServiceFactory });
10545
- i0.ɵɵngDeclareClassMetadata({ minVersion: "12.0.0", version: "13.2.2", ngImport: i0, type: ODataServiceFactory, decorators: [{
10683
+ ODataServiceFactory.ɵfac = i0.ɵɵngDeclareFactory({ minVersion: "12.0.0", version: "13.3.0", ngImport: i0, type: ODataServiceFactory, deps: [{ token: ODataClient }], target: i0.ɵɵFactoryTarget.Injectable });
10684
+ ODataServiceFactory.ɵprov = i0.ɵɵngDeclareInjectable({ minVersion: "12.0.0", version: "13.3.0", ngImport: i0, type: ODataServiceFactory });
10685
+ i0.ɵɵngDeclareClassMetadata({ minVersion: "12.0.0", version: "13.3.0", ngImport: i0, type: ODataServiceFactory, decorators: [{
10546
10686
  type: Injectable
10547
10687
  }], ctorParameters: function () { return [{ type: ODataClient }]; } });
10548
10688
 
@@ -10566,10 +10706,10 @@ class ODataModule {
10566
10706
  };
10567
10707
  }
10568
10708
  }
10569
- ODataModule.ɵfac = i0.ɵɵngDeclareFactory({ minVersion: "12.0.0", version: "13.2.2", ngImport: i0, type: ODataModule, deps: [], target: i0.ɵɵFactoryTarget.NgModule });
10570
- ODataModule.ɵmod = i0.ɵɵngDeclareNgModule({ minVersion: "12.0.0", version: "13.2.2", ngImport: i0, type: ODataModule, imports: [HttpClientModule] });
10571
- ODataModule.ɵinj = i0.ɵɵngDeclareInjector({ minVersion: "12.0.0", version: "13.2.2", ngImport: i0, type: ODataModule, providers: [ODataClient, ODataServiceFactory], imports: [[HttpClientModule]] });
10572
- i0.ɵɵngDeclareClassMetadata({ minVersion: "12.0.0", version: "13.2.2", ngImport: i0, type: ODataModule, decorators: [{
10709
+ ODataModule.ɵfac = i0.ɵɵngDeclareFactory({ minVersion: "12.0.0", version: "13.3.0", ngImport: i0, type: ODataModule, deps: [], target: i0.ɵɵFactoryTarget.NgModule });
10710
+ ODataModule.ɵmod = i0.ɵɵngDeclareNgModule({ minVersion: "12.0.0", version: "13.3.0", ngImport: i0, type: ODataModule, imports: [HttpClientModule] });
10711
+ ODataModule.ɵinj = i0.ɵɵngDeclareInjector({ minVersion: "12.0.0", version: "13.3.0", ngImport: i0, type: ODataModule, providers: [ODataClient, ODataServiceFactory], imports: [[HttpClientModule]] });
10712
+ i0.ɵɵngDeclareClassMetadata({ minVersion: "12.0.0", version: "13.3.0", ngImport: i0, type: ODataModule, decorators: [{
10573
10713
  type: NgModule,
10574
10714
  args: [{
10575
10715
  imports: [HttpClientModule],