remult 3.3.0-next.1 → 3.3.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 (38) hide show
  1. package/esm/graphql.js +1 -1
  2. package/esm/remult-knex/index.js +10 -3
  3. package/esm/remult-mongo.js +7 -3
  4. package/esm/server/get-remult-admin-html.js +125 -111
  5. package/esm/server/remult-admin.js +2 -0
  6. package/esm/server/remult-api-server.js +1 -1
  7. package/esm/src/data-api.js +30 -19
  8. package/esm/src/data-providers/rest-data-provider.js +48 -37
  9. package/esm/src/data-providers/sql-database.js +14 -3
  10. package/esm/src/live-query/SubscriptionChannel.js +52 -4
  11. package/esm/src/remult-proxy.js +4 -4
  12. package/esm/src/remult3/RepositoryImplementation.js +53 -25
  13. package/esm/src/server-action.js +2 -2
  14. package/esm/src/valueConverters.js +9 -5
  15. package/graphql.js +1 -1
  16. package/index.d.ts +1 -1
  17. package/package.json +1 -1
  18. package/remult-knex/index.js +18 -9
  19. package/remult-mongo.js +6 -2
  20. package/server/get-remult-admin-html.js +1 -1
  21. package/server/remult-admin.d.ts +2 -0
  22. package/server/remult-admin.js +2 -1
  23. package/server/remult-api-server.js +1 -0
  24. package/src/data-api.d.ts +4 -4
  25. package/src/data-api.js +50 -30
  26. package/src/data-interfaces.d.ts +6 -6
  27. package/src/data-providers/rest-data-provider.d.ts +4 -4
  28. package/src/data-providers/rest-data-provider.js +48 -37
  29. package/src/data-providers/sql-database.js +14 -3
  30. package/src/live-query/SubscriptionChannel.d.ts +52 -4
  31. package/src/live-query/SubscriptionChannel.js +52 -4
  32. package/src/remult-proxy.js +4 -4
  33. package/src/remult3/RepositoryImplementation.d.ts +11 -10
  34. package/src/remult3/RepositoryImplementation.js +237 -177
  35. package/src/remult3/remult3.d.ts +25 -23
  36. package/src/server-action.js +2 -2
  37. package/src/valueConverters.d.ts +3 -1
  38. package/src/valueConverters.js +9 -6
@@ -30,12 +30,14 @@ export interface FieldUIInfo {
30
30
  caption: string;
31
31
  type: FieldUIInfoType;
32
32
  inputType: string;
33
+ allowNull: boolean;
33
34
  relationToOne?: FieldRelationToOneInfo;
34
35
  }
35
36
  export interface FieldRelationToOneInfo extends RelationFields {
36
37
  entityKey: string;
37
38
  idField: string;
38
39
  captionField: string;
40
+ allowNull: boolean;
39
41
  where?: any;
40
42
  }
41
43
  export interface AdminEntitiesOptions {
@@ -65,7 +65,7 @@ function buildEntityInfo(options) {
65
65
  }
66
66
  }
67
67
  if (relRepo.metadata.apiReadAllowed) {
68
- relation = tslib_1.__assign(tslib_1.__assign({}, relInfo), { where: where, entityKey: relRepo.metadata.key, idField: idField_1, captionField: (_b = relRepo.metadata.fields
68
+ relation = tslib_1.__assign(tslib_1.__assign({}, relInfo), { allowNull: x.allowNull, where: where, entityKey: relRepo.metadata.key, idField: idField_1, captionField: (_b = relRepo.metadata.fields
69
69
  .toArray()
70
70
  .find(function (x) { return x.key != idField_1 && x.valueType == String; })) === null || _b === void 0 ? void 0 : _b.key });
71
71
  }
@@ -85,6 +85,7 @@ function buildEntityInfo(options) {
85
85
  caption: x.label,
86
86
  relationToOne: relation,
87
87
  inputType: x.inputType,
88
+ allowNull: x.allowNull,
88
89
  type: x.inputType === inputTypes_js_1.InputTypes.json
89
90
  ? 'json'
90
91
  : x.valueType === Number
@@ -579,6 +579,7 @@ var RemultServerImplementation = /** @class */ (function () {
579
579
  case 0:
580
580
  _b = (_a = dataApiFactory(c)).put;
581
581
  _c = [res,
582
+ req,
582
583
  reqInfo.params.id];
583
584
  return [4 /*yield*/, this.coreOptions.getRequestBody(orig)];
584
585
  case 1: return [2 /*return*/, _b.apply(_a, _c.concat([_d.sent()]))];
package/src/data-api.d.ts CHANGED
@@ -1,7 +1,6 @@
1
1
  import type { Remult } from './context.js';
2
2
  import { type ErrorInfo } from './data-interfaces.js';
3
3
  import { type EntityMetadata, type FindOptions, type Repository } from './remult3/remult3.js';
4
- import type { rowHelperImplementation } from './remult3/RepositoryImplementation.js';
5
4
  export declare class DataApi<T = unknown> {
6
5
  private repository;
7
6
  private remult;
@@ -17,6 +16,7 @@ export declare class DataApi<T = unknown> {
17
16
  get(response: DataApiResponse, id: any): Promise<void>;
18
17
  count(response: DataApiResponse, request: DataApiRequest, body?: any): Promise<void>;
19
18
  deleteMany(response: DataApiResponse, request: DataApiRequest, body?: any): Promise<void>;
19
+ private prepareWhereForManyOperation;
20
20
  groupBy(request: DataApiRequest, body: any): Promise<import("./remult3/remult3.js").GroupByResult<T, any[], any[], any[], any[], any[], any[]>[]>;
21
21
  getArrayImpl(request: DataApiRequest, body: any): Promise<{
22
22
  r: any[];
@@ -33,11 +33,11 @@ export declare class DataApi<T = unknown> {
33
33
  where?: any;
34
34
  set?: any;
35
35
  }): Promise<void>;
36
- actualUpdate(row: any, body: any): Promise<rowHelperImplementation<T>>;
37
- put(response: DataApiResponse, id: any, body: any): Promise<void>;
36
+ actualUpdate(row: any, body: any, req: DataApiRequest, doNotSelect?: boolean): Promise<any>;
37
+ put(response: DataApiResponse, req: DataApiRequest, id: any, body: any): Promise<void>;
38
38
  actualDelete(row: any): Promise<void>;
39
39
  delete(response: DataApiResponse, id: any): Promise<void>;
40
- post(body: any): Promise<any>;
40
+ post(body: any, req: DataApiRequest): Promise<any>;
41
41
  }
42
42
  export interface DataApiResponse {
43
43
  success(data: any): void;
package/src/data-api.js CHANGED
@@ -99,7 +99,7 @@ var DataApi = /** @class */ (function () {
99
99
  case 12: return [2 /*return*/, _e.apply(_d, [_h.sent()])];
100
100
  case 13:
101
101
  _g = (_f = res).created;
102
- return [4 /*yield*/, this.post(body)];
102
+ return [4 /*yield*/, this.post(body, req)];
103
103
  case 14: return [2 /*return*/, _g.apply(_f, [_h.sent()])];
104
104
  case 15: return [3 /*break*/, 17];
105
105
  case 16:
@@ -146,16 +146,16 @@ var DataApi = /** @class */ (function () {
146
146
  r = _f.sent();
147
147
  if (!(r.length == 0)) return [3 /*break*/, 6];
148
148
  _b = (_a = result).push;
149
- return [4 /*yield*/, this.post(tslib_1.__assign(tslib_1.__assign({}, item.where), item.set))];
149
+ return [4 /*yield*/, this.post(tslib_1.__assign(tslib_1.__assign({}, item.where), item.set), request)];
150
150
  case 5:
151
151
  _b.apply(_a, [_f.sent()]);
152
152
  return [3 /*break*/, 9];
153
153
  case 6:
154
154
  if (!(item.set !== undefined)) return [3 /*break*/, 8];
155
155
  _d = (_c = result).push;
156
- return [4 /*yield*/, this.actualUpdate(r[0], item.set)];
156
+ return [4 /*yield*/, this.actualUpdate(r[0], item.set, request)];
157
157
  case 7:
158
- _d.apply(_c, [(_f.sent()).toApiJson()]);
158
+ _d.apply(_c, [_f.sent()]);
159
159
  return [3 /*break*/, 9];
160
160
  case 8:
161
161
  result.push(this.repository.getEntityRef(r[0]).toApiJson());
@@ -282,10 +282,9 @@ var DataApi = /** @class */ (function () {
282
282
  case 0:
283
283
  _a.trys.push([0, 3, , 4]);
284
284
  deleted_1 = 0;
285
- return [4 /*yield*/, this.buildWhere(request, body)];
285
+ return [4 /*yield*/, this.prepareWhereForManyOperation(body, request)];
286
286
  case 1:
287
287
  where_1 = _a.sent();
288
- filter_interfaces_js_1.Filter.throwErrorIfFilterIsEmpty(where_1, 'deleteMany');
289
288
  return [4 /*yield*/, (0, context_js_1.doTransaction)(this.remult, function () { return tslib_1.__awaiter(_this, void 0, void 0, function () {
290
289
  var _a, _b, _c, x, e_2_1;
291
290
  var _d, e_2, _e, _f;
@@ -346,6 +345,24 @@ var DataApi = /** @class */ (function () {
346
345
  });
347
346
  });
348
347
  };
348
+ DataApi.prototype.prepareWhereForManyOperation = function (body, request) {
349
+ return tslib_1.__awaiter(this, void 0, void 0, function () {
350
+ var where;
351
+ return tslib_1.__generator(this, function (_a) {
352
+ switch (_a.label) {
353
+ case 0:
354
+ where = undefined;
355
+ if (!((body === null || body === void 0 ? void 0 : body.where) !== 'all')) return [3 /*break*/, 2];
356
+ return [4 /*yield*/, this.buildWhere(request, body)];
357
+ case 1:
358
+ where = _a.sent();
359
+ filter_interfaces_js_1.Filter.throwErrorIfFilterIsEmpty(where, 'deleteMany');
360
+ _a.label = 2;
361
+ case 2: return [2 /*return*/, where];
362
+ }
363
+ });
364
+ });
365
+ };
349
366
  DataApi.prototype.groupBy = function (request, body) {
350
367
  return tslib_1.__awaiter(this, void 0, void 0, function () {
351
368
  var findOptions, orderBy, _a, _b, element, direction, group, result;
@@ -762,7 +779,7 @@ var DataApi = /** @class */ (function () {
762
779
  return tslib_1.__generator(this, function (_a) {
763
780
  action = request === null || request === void 0 ? void 0 : request.get('__action');
764
781
  if (action == 'emptyId') {
765
- return [2 /*return*/, this.put(response, '', body)];
782
+ return [2 /*return*/, this.put(response, request, '', body)];
766
783
  }
767
784
  return [2 /*return*/, this.updateManyImplementation(response, request, {
768
785
  where: undefined,
@@ -779,10 +796,9 @@ var DataApi = /** @class */ (function () {
779
796
  switch (_a.label) {
780
797
  case 0:
781
798
  _a.trys.push([0, 3, , 4]);
782
- return [4 /*yield*/, this.buildWhere(request, body)];
799
+ return [4 /*yield*/, this.prepareWhereForManyOperation(body, request)];
783
800
  case 1:
784
801
  where_2 = _a.sent();
785
- filter_interfaces_js_1.Filter.throwErrorIfFilterIsEmpty(where_2, 'updateMany');
786
802
  return [4 /*yield*/, (0, context_js_1.doTransaction)(this.remult, function () { return tslib_1.__awaiter(_this, void 0, void 0, function () {
787
803
  var updated, _a, _b, _c, x, e_6_1;
788
804
  var _d, e_6, _e, _f;
@@ -805,7 +821,7 @@ var DataApi = /** @class */ (function () {
805
821
  _f = _c.value;
806
822
  _a = false;
807
823
  x = _f;
808
- return [4 /*yield*/, this.actualUpdate(x, body.set)];
824
+ return [4 /*yield*/, this.actualUpdate(x, body.set, request)];
809
825
  case 4:
810
826
  _g.sent();
811
827
  updated++;
@@ -846,9 +862,9 @@ var DataApi = /** @class */ (function () {
846
862
  });
847
863
  });
848
864
  };
849
- DataApi.prototype.actualUpdate = function (row, body) {
865
+ DataApi.prototype.actualUpdate = function (row, body, req, doNotSelect) {
850
866
  return tslib_1.__awaiter(this, void 0, void 0, function () {
851
- var ref;
867
+ var ref, options;
852
868
  return tslib_1.__generator(this, function (_a) {
853
869
  switch (_a.label) {
854
870
  case 0:
@@ -859,31 +875,32 @@ var DataApi = /** @class */ (function () {
859
875
  if (!ref.apiUpdateAllowed) {
860
876
  throw new server_action_js_1.ForbiddenError();
861
877
  }
862
- return [4 /*yield*/, ref.save()];
878
+ options = req.get('_select') === 'none' || doNotSelect
879
+ ? { select: 'none' }
880
+ : undefined;
881
+ return [4 /*yield*/, ref.save(options)];
863
882
  case 2:
864
883
  _a.sent();
865
- return [2 /*return*/, ref];
884
+ if ((options === null || options === void 0 ? void 0 : options.select) === 'none')
885
+ return [2 /*return*/, undefined];
886
+ return [2 /*return*/, ref.toApiJson()];
866
887
  }
867
888
  });
868
889
  });
869
890
  };
870
- DataApi.prototype.put = function (response, id, body) {
891
+ DataApi.prototype.put = function (response, req, id, body) {
871
892
  return tslib_1.__awaiter(this, void 0, void 0, function () {
872
893
  var _this = this;
873
894
  return tslib_1.__generator(this, function (_a) {
874
895
  switch (_a.label) {
875
- case 0: return [4 /*yield*/, this.doOnId(response, id, function (row) { return tslib_1.__awaiter(_this, void 0, void 0, function () {
876
- var ref;
877
- return tslib_1.__generator(this, function (_a) {
878
- switch (_a.label) {
879
- case 0: return [4 /*yield*/, this.actualUpdate(row, body)];
880
- case 1:
881
- ref = _a.sent();
882
- response.success(ref.toApiJson());
883
- return [2 /*return*/];
884
- }
885
- });
886
- }); })];
896
+ case 0: return [4 /*yield*/, this.doOnId(response, id, function (row) { return tslib_1.__awaiter(_this, void 0, void 0, function () { var _a, _b; return tslib_1.__generator(this, function (_c) {
897
+ switch (_c.label) {
898
+ case 0:
899
+ _b = (_a = response).success;
900
+ return [4 /*yield*/, this.actualUpdate(row, body, req)];
901
+ case 1: return [2 /*return*/, _b.apply(_a, [_c.sent()])];
902
+ }
903
+ }); }); })];
887
904
  case 1:
888
905
  _a.sent();
889
906
  return [2 /*return*/];
@@ -930,13 +947,14 @@ var DataApi = /** @class */ (function () {
930
947
  });
931
948
  });
932
949
  };
933
- DataApi.prototype.post = function (body) {
950
+ DataApi.prototype.post = function (body, req) {
934
951
  return tslib_1.__awaiter(this, void 0, void 0, function () {
935
- var insert, result_1;
952
+ var options, insert, result_1;
936
953
  var _this = this;
937
954
  return tslib_1.__generator(this, function (_a) {
938
955
  switch (_a.label) {
939
956
  case 0:
957
+ options = req.get('_select') === 'none' ? { select: 'none' } : undefined;
940
958
  insert = function (what) { return tslib_1.__awaiter(_this, void 0, void 0, function () {
941
959
  var newr;
942
960
  return tslib_1.__generator(this, function (_a) {
@@ -949,9 +967,11 @@ var DataApi = /** @class */ (function () {
949
967
  if (!this.repository.getEntityRef(newr).apiInsertAllowed) {
950
968
  throw new server_action_js_1.ForbiddenError();
951
969
  }
952
- return [4 /*yield*/, this.repository.getEntityRef(newr).save()];
970
+ return [4 /*yield*/, this.repository.getEntityRef(newr).save(options)];
953
971
  case 2:
954
972
  _a.sent();
973
+ if ((options === null || options === void 0 ? void 0 : options.select) === 'none')
974
+ return [2 /*return*/, undefined];
955
975
  return [2 /*return*/, this.repository.getEntityRef(newr).toApiJson()];
956
976
  }
957
977
  });
@@ -1,6 +1,6 @@
1
1
  import type { FieldMetadata } from '../index.js';
2
2
  import type { Filter } from './filter/filter-interfaces.js';
3
- import type { GroupByOperators, EntityMetadata, MembersOnly } from './remult3/remult3.js';
3
+ import type { GroupByOperators, EntityMetadata, MembersOnly, InsertOrUpdateOptions } from './remult3/remult3.js';
4
4
  import { Sort } from './sort.js';
5
5
  export interface DataProvider {
6
6
  getEntityDataProvider(entity: EntityMetadata): EntityDataProvider;
@@ -28,14 +28,14 @@ export interface EntityDataProvider {
28
28
  count(where: Filter): Promise<number>;
29
29
  find(options?: EntityDataProviderFindOptions): Promise<Array<any>>;
30
30
  groupBy(options?: EntityDataProviderGroupByOptions): Promise<any[]>;
31
- update(id: any, data: any): Promise<any>;
31
+ update(id: any, data: any, options?: InsertOrUpdateOptions): Promise<any>;
32
32
  delete(id: any): Promise<void>;
33
- insert(data: any): Promise<any>;
33
+ insert(data: any, options?: InsertOrUpdateOptions): Promise<any>;
34
34
  }
35
35
  export interface ProxyEntityDataProvider {
36
- insertMany(data: any[]): Promise<any[]>;
37
- deleteMany(where: Filter): Promise<number>;
38
- updateMany(where: Filter, data: any): Promise<number>;
36
+ insertMany(data: any[], options?: InsertOrUpdateOptions): Promise<any[]>;
37
+ deleteMany(where: Filter | 'all'): Promise<number>;
38
+ updateMany(where: Filter | 'all', data: any): Promise<number>;
39
39
  query(options: EntityDataProviderFindOptions, aggregateOptions: EntityDataProviderGroupByOptions): Promise<{
40
40
  items: any[];
41
41
  aggregates: any;
@@ -2,7 +2,7 @@ import type { DataProvider, EntityDataProvider, EntityDataProviderGroupByOptions
2
2
  import { UrlBuilder } from '../../urlBuilder.js';
3
3
  import type { ApiClient } from '../context.js';
4
4
  import { Filter } from '../filter/filter-interfaces.js';
5
- import type { EntityMetadata } from '../remult3/remult3.js';
5
+ import type { EntityMetadata, InsertOrUpdateOptions } from '../remult3/remult3.js';
6
6
  export declare class RestDataProvider implements DataProvider {
7
7
  private apiProvider;
8
8
  private entityRequested?;
@@ -33,11 +33,11 @@ export declare class RestEntityDataProvider implements EntityDataProvider, Proxy
33
33
  set: any;
34
34
  }[]): Promise<any[]>;
35
35
  find(options?: EntityDataProviderFindOptions): Promise<Array<any>>;
36
- update(id: any, data: any): Promise<any>;
36
+ update(id: any, data: any, options?: InsertOrUpdateOptions): Promise<any>;
37
37
  private toJsonOfIncludedKeys;
38
38
  delete(id: any): Promise<void>;
39
- insert(data: any): Promise<any>;
40
- insertMany(data: any[]): Promise<any[]>;
39
+ insert(data: any, options?: InsertOrUpdateOptions): Promise<any>;
40
+ insertMany(data: any[], options?: InsertOrUpdateOptions): Promise<any[]>;
41
41
  }
42
42
  export declare function addFilterToUrlAndReturnTrueIfSuccessful(filter: any, url: UrlBuilder): boolean;
43
43
  export declare const liveQueryAction = "liveQuery-";
@@ -287,37 +287,42 @@ var RestEntityDataProvider = /** @class */ (function () {
287
287
  var url = new urlBuilder_js_1.UrlBuilder(this.url());
288
288
  var filterObject;
289
289
  if (options) {
290
- if (options.where) {
291
- filterObject = options.where.toJson(); // options.where.__applyToConsumer(new FilterConsumnerBridgeToUrlBuilder(url));
292
- if (options.args === undefined)
293
- if (addFilterToUrlAndReturnTrueIfSuccessful(filterObject, url))
294
- filterObject = undefined;
290
+ if (options.where === 'all') {
291
+ filterObject = 'all';
295
292
  }
296
- if (options.orderBy && options.orderBy.Segments) {
297
- var sort_1 = '';
298
- var order_1 = '';
299
- var hasDescending_1 = false;
300
- options.orderBy.Segments.forEach(function (c) {
301
- if (sort_1.length > 0) {
302
- sort_1 += ',';
303
- order_1 += ',';
304
- }
305
- sort_1 += c.field.key;
306
- order_1 += c.isDescending ? 'desc' : 'asc';
307
- if (c.isDescending)
308
- hasDescending_1 = true;
309
- });
310
- if (sort_1)
311
- url.add('_sort', sort_1);
312
- if (hasDescending_1)
313
- url.add('_order', order_1);
314
- }
315
- if (options.limit)
316
- url.add('_limit', options.limit);
317
- if (options.page)
318
- url.add('_page', options.page);
319
- if (options.select) {
320
- url.add('_select', options.select.join(','));
293
+ else {
294
+ if (options.where) {
295
+ filterObject = options.where.toJson();
296
+ if (options.args === undefined)
297
+ if (addFilterToUrlAndReturnTrueIfSuccessful(filterObject, url))
298
+ filterObject = undefined;
299
+ }
300
+ if (options.orderBy && options.orderBy.Segments) {
301
+ var sort_1 = '';
302
+ var order_1 = '';
303
+ var hasDescending_1 = false;
304
+ options.orderBy.Segments.forEach(function (c) {
305
+ if (sort_1.length > 0) {
306
+ sort_1 += ',';
307
+ order_1 += ',';
308
+ }
309
+ sort_1 += c.field.key;
310
+ order_1 += c.isDescending ? 'desc' : 'asc';
311
+ if (c.isDescending)
312
+ hasDescending_1 = true;
313
+ });
314
+ if (sort_1)
315
+ url.add('_sort', sort_1);
316
+ if (hasDescending_1)
317
+ url.add('_order', order_1);
318
+ }
319
+ if (options.limit)
320
+ url.add('_limit', options.limit);
321
+ if (options.page)
322
+ url.add('_page', options.page);
323
+ if (options.select) {
324
+ url.add('_select', options.select.join(','));
325
+ }
321
326
  }
322
327
  }
323
328
  var run = function (action, body) {
@@ -334,7 +339,7 @@ var RestEntityDataProvider = /** @class */ (function () {
334
339
  else
335
340
  body = tslib_1.__assign(tslib_1.__assign({}, body), { where: filterObject });
336
341
  }
337
- if (options === null || options === void 0 ? void 0 : options.args)
342
+ if (options && 'args' in options)
338
343
  body.args = options.args;
339
344
  if (body && method != 'put')
340
345
  return _this.http().post(u.url, body);
@@ -370,11 +375,17 @@ var RestEntityDataProvider = /** @class */ (function () {
370
375
  }); },
371
376
  };
372
377
  };
373
- RestEntityDataProvider.prototype.update = function (id, data) {
378
+ RestEntityDataProvider.prototype.update = function (id, data, options) {
374
379
  var _this = this;
380
+ var urlArgs = [];
381
+ if (id == '')
382
+ urlArgs.push('__action=emptyId');
383
+ if ((options === null || options === void 0 ? void 0 : options.select) === 'none')
384
+ urlArgs.push('_select=$none');
375
385
  return this.http()
376
386
  .put(this.url() +
377
- (id != '' ? '/' + encodeURIComponent(id) : '?__action=emptyId'), this.toJsonOfIncludedKeys(data))
387
+ (id != '' ? '/' + encodeURIComponent(id) : '') +
388
+ (urlArgs.length > 0 ? '?' + urlArgs.join('&') : ''), this.toJsonOfIncludedKeys(data))
378
389
  .then(function (y) { return _this.translateFromJson(y); });
379
390
  };
380
391
  RestEntityDataProvider.prototype.toJsonOfIncludedKeys = function (data) {
@@ -413,16 +424,16 @@ var RestEntityDataProvider = /** @class */ (function () {
413
424
  });
414
425
  });
415
426
  };
416
- RestEntityDataProvider.prototype.insert = function (data) {
427
+ RestEntityDataProvider.prototype.insert = function (data, options) {
417
428
  var _this = this;
418
429
  return this.http()
419
- .post(this.url(), this.translateToJson(data))
430
+ .post(this.url() + ((options === null || options === void 0 ? void 0 : options.select) === 'none' ? '?_select=$none' : ''), this.translateToJson(data))
420
431
  .then(function (y) { return _this.translateFromJson(y); });
421
432
  };
422
- RestEntityDataProvider.prototype.insertMany = function (data) {
433
+ RestEntityDataProvider.prototype.insertMany = function (data, options) {
423
434
  var _this = this;
424
435
  return this.http()
425
- .post(this.url(), data.map(function (data) { return _this.translateToJson(data); }))
436
+ .post(this.url() + ((options === null || options === void 0 ? void 0 : options.select) === 'none' ? '?_select=$none' : ''), data.map(function (data) { return _this.translateToJson(data); }))
426
437
  .then(function (y) { return y.map(function (y) { return _this.translateFromJson(y); }); });
427
438
  };
428
439
  return RestEntityDataProvider;
@@ -601,7 +601,7 @@ var ActualSQLEntityDataProvider = /** @class */ (function () {
601
601
  });
602
602
  });
603
603
  };
604
- ActualSQLEntityDataProvider.prototype.update = function (id, data) {
604
+ ActualSQLEntityDataProvider.prototype.update = function (id, data, options) {
605
605
  return tslib_1.__awaiter(this, void 0, void 0, function () {
606
606
  var e, r, statement, added, _a, _b, x, v, idFilter, f, _c, _d, colKeys, select, returning;
607
607
  var e_5, _e;
@@ -651,6 +651,8 @@ var ActualSQLEntityDataProvider = /** @class */ (function () {
651
651
  returning = true;
652
652
  if (this.sql._getSourceSql().doesNotSupportReturningSyntax)
653
653
  returning = false;
654
+ if ((options === null || options === void 0 ? void 0 : options.select) === 'none')
655
+ returning = false;
654
656
  if (returning &&
655
657
  this.sql._getSourceSql().doesNotSupportReturningSyntaxOnlyForUpdate)
656
658
  returning = false;
@@ -660,6 +662,8 @@ var ActualSQLEntityDataProvider = /** @class */ (function () {
660
662
  var _a, _b;
661
663
  (_b = (_a = _this.sql._getSourceSql()).afterMutation) === null || _b === void 0 ? void 0 : _b.call(_a);
662
664
  if (!returning) {
665
+ if ((options === null || options === void 0 ? void 0 : options.select) === 'none')
666
+ return undefined;
663
667
  return getRowAfterUpdate(_this.entity, _this, data, id, 'update');
664
668
  }
665
669
  if (sqlResult.rows.length != 1)
@@ -698,7 +702,7 @@ var ActualSQLEntityDataProvider = /** @class */ (function () {
698
702
  });
699
703
  });
700
704
  };
701
- ActualSQLEntityDataProvider.prototype.insert = function (data) {
705
+ ActualSQLEntityDataProvider.prototype.insert = function (data, options) {
702
706
  return tslib_1.__awaiter(this, void 0, void 0, function () {
703
707
  var e, r, cols, vals, added, _a, _b, x, v, statement, _c, colKeys, select;
704
708
  var e_6, _d;
@@ -743,7 +747,8 @@ var ActualSQLEntityDataProvider = /** @class */ (function () {
743
747
  return [4 /*yield*/, this.buildSelect(e, r, undefined, undefined)];
744
748
  case 2:
745
749
  _c = _e.sent(), colKeys = _c.colKeys, select = _c.select;
746
- if (!this.sql._getSourceSql().doesNotSupportReturningSyntax)
750
+ if (!this.sql._getSourceSql().doesNotSupportReturningSyntax &&
751
+ !((options === null || options === void 0 ? void 0 : options.select) === 'none'))
747
752
  statement += ' returning ' + select;
748
753
  return [4 /*yield*/, r.execute(statement).then(function (sql) {
749
754
  var _a, _b;
@@ -754,6 +759,8 @@ var ActualSQLEntityDataProvider = /** @class */ (function () {
754
759
  if (typeof id_1 !== 'number')
755
760
  throw new Error('Auto increment, for a database that is does not support returning syntax, should return an array with the single last added id. Instead it returned: ' +
756
761
  JSON.stringify(id_1));
762
+ if ((options === null || options === void 0 ? void 0 : options.select) === 'none')
763
+ return undefined;
757
764
  return _this.find({
758
765
  where: new filter_interfaces_js_1.Filter(function (x) {
759
766
  return x.isEqualTo(_this.entity.idMetadata.field, id_1);
@@ -761,9 +768,13 @@ var ActualSQLEntityDataProvider = /** @class */ (function () {
761
768
  }).then(function (r) { return r[0]; });
762
769
  }
763
770
  else {
771
+ if ((options === null || options === void 0 ? void 0 : options.select) === 'none')
772
+ return undefined;
764
773
  return getRowAfterUpdate(_this.entity, _this, data, undefined, 'insert');
765
774
  }
766
775
  }
776
+ if ((options === null || options === void 0 ? void 0 : options.select) === 'none')
777
+ return undefined;
767
778
  return _this.buildResultRow(colKeys, sql.rows[0], sql);
768
779
  })];
769
780
  case 3: return [2 /*return*/, _e.sent()];
@@ -38,18 +38,66 @@ export declare type LiveQueryChange = {
38
38
  *
39
39
  * @template messageType The type of the message that the channel will handle.
40
40
  * @example
41
+ * ```ts
41
42
  * // Defined in code that is shared between the frontend and the backend
42
- * const statusChange = new SubscriptionChannel<{ oldStatus: number, newStatus: number }>("statusChange");
43
+ * export const notif = new SubscriptionChannel<{ coolInfo: string }>("notif");
43
44
  *
44
45
  * // Backend: Publishing a message
45
- * statusChange.publish({ oldStatus: 1, newStatus: 2 });
46
+ * notif.publish({ coolInfo: "Message coming from the backend" });
46
47
  *
47
48
  * // Frontend: Subscribing to messages
48
- * statusChange.subscribe((message) => {
49
- * console.log(`Status changed from ${message.oldStatus} to ${message.newStatus}`);
49
+ * notif.subscribe((message) => {
50
+ * console.log(`Something exciting happened: ${message.coolInfo}`);
50
51
  * });
51
52
  *
52
53
  * // Note: If you want to publish from the frontend, use a BackendMethod for that.
54
+ * ```
55
+ * ---
56
+ *
57
+ * ### Use cases:
58
+ *
59
+ * #### A user _(Paul)_ wants to notify everyone _(Eric & Simona)_
60
+ * ```ts
61
+ * // shared code between the frontend and the backend
62
+ * export const notif = new SubscriptionChannel<{ from: UserInfo, msg: string }>("notif");
63
+ *
64
+ * // Frontend, Paul can call a BackendMethod to send his message
65
+ * NotificationContoller.send("Hello everyone!")
66
+ *
67
+ * // Backend
68
+ * export class NotificationContoller {
69
+ * @BackendMethod({ allowed: true })
70
+ * static async send(message: string) {
71
+ * notif.publish({ from: remult.user, msg: message });
72
+ * }
73
+ * }
74
+ *
75
+ * // Frontend: Eric & Simona can subscribe to messages
76
+ * notif.subscribe((message) => {
77
+ * if (message.from === remult.user) return;
78
+ * console.log(`Message from ${message.from.name}: ${message.msg}`);
79
+ * });
80
+ * ```
81
+ *
82
+ * #### A complexe chart that needs to be updated on multiple changes
83
+ * ```ts
84
+ * // shared code between the frontend and the backend
85
+ * export const chart = new SubscriptionChannel<{ kind: "pie" | "bar" | "line", data: number[] }>("chart");
86
+ *
87
+ * // Entity
88
+ * @Entity<Task>("tasks", {
89
+ * saved: async (e) => {
90
+ * if (e.completed) chart.publish({ kind: "pie", data: [1, 2, 3] });
91
+ * }
92
+ * })
93
+ * export class Task { ... }
94
+ *
95
+ * // Frontend: in the chart component, we can subscribe to messages
96
+ * chart.subscribe((message) => {
97
+ * chartData = message.data;
98
+ * });
99
+ * ```
100
+ *
53
101
  */
54
102
  export declare class SubscriptionChannel<messageType> {
55
103
  channelKey: string;
@@ -167,18 +167,66 @@ exports.liveQueryKeepAliveRoute = '_liveQueryKeepAlive';
167
167
  *
168
168
  * @template messageType The type of the message that the channel will handle.
169
169
  * @example
170
+ * ```ts
170
171
  * // Defined in code that is shared between the frontend and the backend
171
- * const statusChange = new SubscriptionChannel<{ oldStatus: number, newStatus: number }>("statusChange");
172
+ * export const notif = new SubscriptionChannel<{ coolInfo: string }>("notif");
172
173
  *
173
174
  * // Backend: Publishing a message
174
- * statusChange.publish({ oldStatus: 1, newStatus: 2 });
175
+ * notif.publish({ coolInfo: "Message coming from the backend" });
175
176
  *
176
177
  * // Frontend: Subscribing to messages
177
- * statusChange.subscribe((message) => {
178
- * console.log(`Status changed from ${message.oldStatus} to ${message.newStatus}`);
178
+ * notif.subscribe((message) => {
179
+ * console.log(`Something exciting happened: ${message.coolInfo}`);
179
180
  * });
180
181
  *
181
182
  * // Note: If you want to publish from the frontend, use a BackendMethod for that.
183
+ * ```
184
+ * ---
185
+ *
186
+ * ### Use cases:
187
+ *
188
+ * #### A user _(Paul)_ wants to notify everyone _(Eric & Simona)_
189
+ * ```ts
190
+ * // shared code between the frontend and the backend
191
+ * export const notif = new SubscriptionChannel<{ from: UserInfo, msg: string }>("notif");
192
+ *
193
+ * // Frontend, Paul can call a BackendMethod to send his message
194
+ * NotificationContoller.send("Hello everyone!")
195
+ *
196
+ * // Backend
197
+ * export class NotificationContoller {
198
+ * @BackendMethod({ allowed: true })
199
+ * static async send(message: string) {
200
+ * notif.publish({ from: remult.user, msg: message });
201
+ * }
202
+ * }
203
+ *
204
+ * // Frontend: Eric & Simona can subscribe to messages
205
+ * notif.subscribe((message) => {
206
+ * if (message.from === remult.user) return;
207
+ * console.log(`Message from ${message.from.name}: ${message.msg}`);
208
+ * });
209
+ * ```
210
+ *
211
+ * #### A complexe chart that needs to be updated on multiple changes
212
+ * ```ts
213
+ * // shared code between the frontend and the backend
214
+ * export const chart = new SubscriptionChannel<{ kind: "pie" | "bar" | "line", data: number[] }>("chart");
215
+ *
216
+ * // Entity
217
+ * @Entity<Task>("tasks", {
218
+ * saved: async (e) => {
219
+ * if (e.completed) chart.publish({ kind: "pie", data: [1, 2, 3] });
220
+ * }
221
+ * })
222
+ * export class Task { ... }
223
+ *
224
+ * // Frontend: in the chart component, we can subscribe to messages
225
+ * chart.subscribe((message) => {
226
+ * chartData = message.data;
227
+ * });
228
+ * ```
229
+ *
182
230
  */
183
231
  var SubscriptionChannel = /** @class */ (function () {
184
232
  /**