oak-db 2.2.2 → 2.2.4

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.
@@ -1,856 +1,895 @@
1
- "use strict";
2
- Object.defineProperty(exports, "__esModule", { value: true });
3
- exports.SqlTranslator = void 0;
4
- var tslib_1 = require("tslib");
5
- var assert_1 = tslib_1.__importDefault(require("assert"));
6
- var lodash_1 = require("lodash");
7
- var types_1 = require("oak-domain/lib/types");
8
- var relation_1 = require("oak-domain/lib/store/relation");
9
- ;
10
- ;
11
- var SqlTranslator = /** @class */ (function () {
12
- function SqlTranslator(schema) {
13
- this.schema = this.makeFullSchema(schema);
14
- }
15
- SqlTranslator.prototype.makeFullSchema = function (schema2) {
16
- var schema = (0, lodash_1.cloneDeep)(schema2);
17
- for (var entity in schema) {
18
- var _a = schema[entity], attributes = _a.attributes, indexes = _a.indexes;
19
- // 增加默认的属性
20
- (0, lodash_1.assign)(attributes, {
21
- id: {
22
- type: 'char',
23
- params: {
24
- length: 36,
25
- },
26
- },
27
- $$seq$$: {
28
- type: 'sequence',
29
- sequenceStart: 10000,
30
- },
31
- $$createAt$$: {
32
- type: 'datetime',
33
- notNull: true,
34
- },
35
- $$updateAt$$: {
36
- type: 'datetime',
37
- notNull: true,
38
- },
39
- $$deleteAt$$: {
40
- type: 'datetime',
41
- },
42
- $$triggerData$$: {
43
- type: 'object',
44
- },
45
- $$triggerTimestamp$$: {
46
- type: 'datetime',
47
- },
48
- });
49
- // 增加默认的索引
50
- var intrinsticIndexes = [
51
- {
52
- name: "".concat(entity, "_create_at"),
53
- attributes: [{
54
- name: '$$createAt$$',
55
- }]
56
- }, {
57
- name: "".concat(entity, "_update_at"),
58
- attributes: [{
59
- name: '$$updateAt$$',
60
- }],
61
- }, {
62
- name: "".concat(entity, "_trigger_ts"),
63
- attributes: [{
64
- name: '$$triggerTimestamp$$',
65
- }],
66
- }
67
- ];
68
- var _loop_1 = function (attr) {
69
- if (attributes[attr].type === 'ref') {
70
- if (!(indexes === null || indexes === void 0 ? void 0 : indexes.find(function (ele) { return ele.attributes[0].name === attr; }))) {
71
- intrinsticIndexes.push({
72
- name: "".concat(entity, "_fk_").concat(attr),
73
- attributes: [{
74
- name: attr,
75
- }]
76
- });
77
- }
78
- }
79
- if (attr === 'entity' && attributes[attr].type === 'varchar') {
80
- var entityIdDef = attributes.entityId;
81
- if ((entityIdDef === null || entityIdDef === void 0 ? void 0 : entityIdDef.type) === 'varchar') {
82
- if (!(indexes === null || indexes === void 0 ? void 0 : indexes.find(function (ele) { var _a; return ele.attributes[0].name === 'entity' && ((_a = ele.attributes[1]) === null || _a === void 0 ? void 0 : _a.name) === 'entityId'; }))) {
83
- intrinsticIndexes.push({
84
- name: "".concat(entity, "_fk_entity_entityId"),
85
- attributes: [{
86
- name: 'entity',
87
- }, {
88
- name: 'entityId',
89
- }]
90
- });
91
- }
92
- }
93
- }
94
- };
95
- // 增加外键上的索引
96
- for (var attr in attributes) {
97
- _loop_1(attr);
98
- }
99
- if (indexes) {
100
- indexes.push.apply(indexes, intrinsticIndexes);
101
- }
102
- else {
103
- (0, lodash_1.assign)(schema[entity], {
104
- indexes: intrinsticIndexes,
105
- });
106
- }
107
- }
108
- return schema;
109
- };
110
- SqlTranslator.prototype.getStorageName = function (entity) {
111
- var storageName = this.schema[entity].storageName;
112
- return (storageName || entity);
113
- };
114
- SqlTranslator.prototype.translateInsert = function (entity, data) {
115
- var _this = this;
116
- var schema = this.schema;
117
- var _a = schema[entity], attributes = _a.attributes, _b = _a.storageName, storageName = _b === void 0 ? entity : _b;
118
- var sql = "insert into `".concat(storageName, "`(");
119
- /**
120
- * 这里的attrs要用所有行的union集合
121
- */
122
- var dataFull = data.reduce(function (prev, cur) { return Object.assign({}, cur, prev); }, {});
123
- var attrs = Object.keys(dataFull).filter(function (ele) { return attributes.hasOwnProperty(ele); });
124
- attrs.forEach(function (attr, idx) {
125
- sql += " `".concat(attr, "`");
126
- if (idx < attrs.length - 1) {
127
- sql += ',';
128
- }
129
- });
130
- sql += ') values ';
131
- data.forEach(function (d, dataIndex) {
132
- sql += '(';
133
- attrs.forEach(function (attr, attrIdx) {
134
- var attrDef = attributes[attr];
135
- var dataType = attrDef.type;
136
- var value = _this.translateAttrValue(dataType, d[attr]);
137
- sql += value;
138
- if (attrIdx < attrs.length - 1) {
139
- sql += ',';
140
- }
141
- });
142
- if (dataIndex < data.length - 1) {
143
- sql += '),';
144
- }
145
- else {
146
- sql += ')';
147
- }
148
- });
149
- return sql;
150
- };
151
- /**
152
- * analyze the join relations in projection/query/sort
153
- * 所有的层次关系都当成left join处理,如果有内表为空的情况,请手动处理
154
- * {
155
- * b: {
156
- * name: {
157
- * $exists: false,
158
- * }
159
- * }
160
- * }
161
- * 这样的query会把内表为空的行也返回
162
- * @param param0
163
- */
164
- SqlTranslator.prototype.analyzeJoin = function (entity, _a, initialNumber) {
165
- var _this = this;
166
- var projection = _a.projection, filter = _a.filter, sorter = _a.sorter, aggregation = _a.aggregation;
167
- var schema = this.schema;
168
- var number = initialNumber || 1;
169
- var projectionRefAlias = {};
170
- var filterRefAlias = {};
171
- var extraWhere = '';
172
- var alias = "".concat(entity, "_").concat(number++);
173
- var from = " `".concat(this.getStorageName(entity), "` `").concat(alias, "` ");
174
- var aliasDict = {
175
- './': alias,
176
- };
177
- var analyzeFilterNode = function (_a) {
178
- var _b;
179
- var node = _a.node, path = _a.path, entityName = _a.entityName, alias = _a.alias;
180
- Object.keys(node).forEach(function (op) {
181
- var _a, _b;
182
- if (['$and', '$or'].includes(op)) {
183
- node[op].forEach(function (subNode) { return analyzeFilterNode({
184
- node: subNode,
185
- path: path,
186
- entityName: entityName,
187
- alias: alias,
188
- }); });
189
- }
190
- else if (['$not'].includes(op)) {
191
- analyzeFilterNode({
192
- node: node[op],
193
- path: path,
194
- entityName: entityName,
195
- alias: alias,
196
- });
197
- }
198
- else if (['$text'].includes(op)) {
199
- }
200
- else {
201
- var rel = (0, relation_1.judgeRelation)(_this.schema, entityName, op);
202
- if (typeof rel === 'string') {
203
- var alias2 = void 0;
204
- var pathAttr = "".concat(path).concat(op, "/");
205
- if (!aliasDict.hasOwnProperty(pathAttr)) {
206
- alias2 = "".concat(rel, "_").concat(number++);
207
- (0, lodash_1.assign)(aliasDict, (_a = {},
208
- _a[pathAttr] = alias2,
209
- _a));
210
- from += " left join `".concat(_this.getStorageName(rel), "` `").concat(alias2, "` on `").concat(alias, "`.`").concat(op, "Id` = `").concat(alias2, "`.`id`");
211
- }
212
- else {
213
- alias2 = aliasDict[pathAttr];
214
- }
215
- analyzeFilterNode({
216
- node: node[op],
217
- path: pathAttr,
218
- entityName: rel,
219
- alias: alias2,
220
- });
221
- }
222
- else if (rel === 2) {
223
- var alias2 = void 0;
224
- var pathAttr = "".concat(path).concat(op, "/");
225
- if (!aliasDict.hasOwnProperty(pathAttr)) {
226
- alias2 = "".concat(op, "_").concat(number++);
227
- (0, lodash_1.assign)(aliasDict, (_b = {},
228
- _b[pathAttr] = alias2,
229
- _b));
230
- from += " left join `".concat(_this.getStorageName(op), "` `").concat(alias2, "` on `").concat(alias, "`.`entityId` = `").concat(alias2, "`.`id` and `").concat(alias, "`.`entity` = '").concat(op, "'");
231
- }
232
- else {
233
- alias2 = aliasDict[pathAttr];
234
- }
235
- analyzeFilterNode({
236
- node: node[op],
237
- path: pathAttr,
238
- entityName: op,
239
- alias: alias2,
240
- });
241
- }
242
- else {
243
- // 不支持一对多
244
- (0, assert_1.default)(rel === 0 || rel === 1);
245
- }
246
- }
247
- });
248
- if (node['#id']) {
249
- (0, assert_1.default)(!filterRefAlias[node['#id']]);
250
- (0, lodash_1.assign)(filterRefAlias, (_b = {},
251
- _b[node['#id']] = [alias, entityName],
252
- _b));
253
- }
254
- };
255
- if (filter) {
256
- analyzeFilterNode({
257
- node: filter,
258
- path: './',
259
- entityName: entity,
260
- alias: alias,
261
- });
262
- }
263
- var analyzeSortNode = function (_a) {
264
- var _b, _c;
265
- var node = _a.node, path = _a.path, entityName = _a.entityName, alias = _a.alias;
266
- var attr = (0, lodash_1.keys)(node)[0];
267
- var rel = (0, relation_1.judgeRelation)(_this.schema, entityName, attr);
268
- if (typeof rel === 'string') {
269
- var pathAttr = "".concat(path).concat(attr, "/");
270
- var alias2 = void 0;
271
- if (!aliasDict.hasOwnProperty(pathAttr)) {
272
- alias2 = "".concat(rel, "_").concat(number++);
273
- (0, lodash_1.assign)(aliasDict, (_b = {},
274
- _b[pathAttr] = alias2,
275
- _b));
276
- from += " left join `".concat(_this.getStorageName(rel), "` `").concat(alias2, "` on `").concat(alias, "`.`").concat(attr, "Id` = `").concat(alias2, "`.`id`");
277
- }
278
- else {
279
- alias2 = aliasDict[pathAttr];
280
- }
281
- analyzeSortNode({
282
- node: node[attr],
283
- path: pathAttr,
284
- entityName: rel,
285
- alias: alias2,
286
- });
287
- }
288
- else if (rel === 2) {
289
- var pathAttr = "".concat(path).concat(attr, "/");
290
- var alias2 = void 0;
291
- if (!aliasDict.hasOwnProperty(pathAttr)) {
292
- alias2 = "".concat(attr, "_").concat(number++);
293
- (0, lodash_1.assign)(aliasDict, (_c = {},
294
- _c[pathAttr] = alias2,
295
- _c));
296
- from += " left join `".concat(_this.getStorageName(attr), "` `").concat(alias2, "` on `").concat(alias, "`.`entityId` = `").concat(alias2, "`.`id` and `").concat(alias, "`.`entity` = '").concat(attr, "'");
297
- }
298
- else {
299
- alias2 = aliasDict[pathAttr];
300
- }
301
- analyzeSortNode({
302
- node: node[attr],
303
- path: pathAttr,
304
- entityName: attr,
305
- alias: alias2,
306
- });
307
- }
308
- else {
309
- (0, assert_1.default)(rel === 0 || rel === 1);
310
- }
311
- };
312
- if (sorter) {
313
- sorter.forEach(function (sortNode) {
314
- analyzeSortNode({
315
- node: sortNode.$attr,
316
- path: './',
317
- entityName: entity,
318
- alias: alias,
319
- });
320
- });
321
- }
322
- var analyzeProjectionNode = function (_a) {
323
- var _b;
324
- var node = _a.node, path = _a.path, entityName = _a.entityName, alias = _a.alias;
325
- var attributes = schema[entityName].attributes;
326
- Object.keys(node).forEach(function (attr) {
327
- var _a, _b;
328
- var rel = (0, relation_1.judgeRelation)(_this.schema, entityName, attr);
329
- if (typeof rel === 'string') {
330
- var pathAttr = "".concat(path).concat(attr, "/");
331
- var alias2 = void 0;
332
- if (!aliasDict.hasOwnProperty(pathAttr)) {
333
- alias2 = "".concat(rel, "_").concat(number++);
334
- (0, lodash_1.assign)(aliasDict, (_a = {},
335
- _a[pathAttr] = alias2,
336
- _a));
337
- from += " left join `".concat(_this.getStorageName(rel), "` `").concat(alias2, "` on `").concat(alias, "`.`").concat(attr, "Id` = `").concat(alias2, "`.`id`");
338
- }
339
- else {
340
- alias2 = aliasDict[pathAttr];
341
- }
342
- analyzeProjectionNode({
343
- node: node[attr],
344
- path: pathAttr,
345
- entityName: rel,
346
- alias: alias2,
347
- });
348
- }
349
- else if (rel === 2) {
350
- var pathAttr = "".concat(path).concat(attr, "/");
351
- var alias2 = void 0;
352
- if (!aliasDict.hasOwnProperty(pathAttr)) {
353
- alias2 = "".concat(attr, "_").concat(number++);
354
- (0, lodash_1.assign)(aliasDict, (_b = {},
355
- _b[pathAttr] = alias2,
356
- _b));
357
- from += " left join `".concat(_this.getStorageName(attr), "` `").concat(alias2, "` on `").concat(alias, "`.`entityId` = `").concat(alias2, "`.`id` and `").concat(alias, "`.`entity` = '").concat(attr, "'");
358
- }
359
- else {
360
- alias2 = aliasDict[pathAttr];
361
- }
362
- analyzeProjectionNode({
363
- node: node[attr],
364
- path: pathAttr,
365
- entityName: attr,
366
- alias: alias2,
367
- });
368
- }
369
- });
370
- if (node['#id']) {
371
- (0, assert_1.default)(!projectionRefAlias[node['#id']], "projection\u4E0A\u6709\u91CD\u590D\u7684#id\u5B9A\u4E49\u300C".concat(node['#id'], "\u300D"));
372
- (0, lodash_1.assign)(projectionRefAlias, (_b = {},
373
- _b[node['#id']] = [alias, entityName],
374
- _b));
375
- }
376
- };
377
- if (projection) {
378
- analyzeProjectionNode({ node: projection, path: './', entityName: entity, alias: alias });
379
- }
380
- else if (aggregation) {
381
- for (var k in aggregation) {
382
- analyzeProjectionNode({
383
- node: aggregation[k],
384
- path: './',
385
- entityName: entity,
386
- alias: alias,
387
- });
388
- }
389
- }
390
- return {
391
- aliasDict: aliasDict,
392
- from: from,
393
- projectionRefAlias: projectionRefAlias,
394
- filterRefAlias: filterRefAlias,
395
- extraWhere: extraWhere,
396
- currentNumber: number,
397
- };
398
- };
399
- SqlTranslator.prototype.translateComparison = function (attr, value, type) {
400
- var SQL_OP = {
401
- $gt: '>',
402
- $lt: '<',
403
- $gte: '>=',
404
- $lte: '<=',
405
- $eq: '=',
406
- $ne: '<>',
407
- };
408
- if (Object.keys(SQL_OP).includes(attr)) {
409
- return " ".concat(SQL_OP[attr], " ").concat(this.translateAttrValue(type, value));
410
- }
411
- switch (attr) {
412
- case '$startsWith': {
413
- return " like '".concat(value, "%'");
414
- }
415
- case '$endsWith': {
416
- return " like '%".concat(value, "'");
417
- }
418
- case '$includes': {
419
- return " like '%".concat(value, "%'");
420
- }
421
- default: {
422
- throw new Error("unrecoganized comparison operator ".concat(attr));
423
- }
424
- }
425
- };
426
- SqlTranslator.prototype.translateElement = function (attr, value) {
427
- (0, assert_1.default)(attr === '$exists'); // only support one operator now
428
- if (value) {
429
- return ' is not null';
430
- }
431
- return ' is null';
432
- };
433
- SqlTranslator.prototype.translateEvaluation = function (attr, value, entity, alias, type, initialNumber, refAlias) {
434
- switch (attr) {
435
- case '$text': {
436
- // fulltext search
437
- return {
438
- stmt: this.translateFullTextSearch(value, entity, alias),
439
- currentNumber: initialNumber,
440
- };
441
- }
442
- case '$in':
443
- case '$nin': {
444
- var IN_OP = {
445
- $in: 'in',
446
- $nin: 'not in',
447
- };
448
- if (value instanceof Array) {
449
- var values = value.map(function (v) {
450
- if (['varchar', 'char', 'text', 'nvarchar', 'ref'].includes(type)) {
451
- return "'".concat(v, "'");
452
- }
453
- else {
454
- return "".concat(v);
455
- }
456
- });
457
- if (values.length > 0) {
458
- return {
459
- stmt: " ".concat(IN_OP[attr], "(").concat(values.join(','), ")"),
460
- currentNumber: initialNumber,
461
- };
462
- }
463
- else {
464
- if (attr === '$in') {
465
- return {
466
- stmt: ' in (null)',
467
- currentNumber: initialNumber,
468
- };
469
- }
470
- else {
471
- return {
472
- stmt: ' is not null',
473
- currentNumber: initialNumber,
474
- };
475
- }
476
- }
477
- }
478
- else {
479
- // sub query
480
- var _a = this.translateSelectInner(value.entity, value, initialNumber, refAlias, undefined), subQueryStmt = _a.stmt, currentNumber = _a.currentNumber;
481
- return {
482
- stmt: " ".concat(IN_OP[attr], "(").concat(subQueryStmt, ")"),
483
- currentNumber: currentNumber,
484
- };
485
- }
486
- }
487
- default: {
488
- (0, assert_1.default)('$between' === attr);
489
- var values = value.map(function (v) {
490
- if (['varchar', 'char', 'text', 'nvarchar', 'ref'].includes(type)) {
491
- return "'".concat(v, "'");
492
- }
493
- else {
494
- return "".concat(v);
495
- }
496
- });
497
- return {
498
- stmt: " between ".concat(values[0], " and ").concat(values[1]),
499
- currentNumber: initialNumber,
500
- };
501
- }
502
- }
503
- };
504
- SqlTranslator.prototype.translateFilter = function (entity, selection, aliasDict, filterRefAlias, initialNumber, extraWhere, option) {
505
- var _this = this;
506
- var schema = this.schema;
507
- var filter = selection.filter;
508
- var currentNumber = initialNumber;
509
- var translateInner = function (entity2, path, filter2, type) {
510
- var alias = aliasDict[path];
511
- var attributes = schema[entity2].attributes;
512
- var whereText = type ? '' : _this.getDefaultSelectFilter(alias, option);
513
- if (filter2) {
514
- var attrs = Object.keys(filter2).filter(function (ele) { return !ele.startsWith('#'); });
515
- attrs.forEach(function (attr) {
516
- if (whereText) {
517
- whereText += ' and ';
518
- }
519
- if (['$and', '$or', '$xor', '$not'].includes(attr)) {
520
- var result = '';
521
- whereText += '(';
522
- switch (attr) {
523
- case '$and':
524
- case '$or':
525
- case '$xor': {
526
- var logicQueries_1 = filter2[attr];
527
- logicQueries_1.forEach(function (logicQuery, index) {
528
- var sql = translateInner(entity2, path, logicQuery);
529
- if (sql) {
530
- whereText += " (".concat(sql, ")");
531
- if (index < logicQueries_1.length - 1) {
532
- whereText += " ".concat(attr.slice(1));
533
- }
534
- }
535
- });
536
- break;
537
- }
538
- default: {
539
- (0, assert_1.default)(attr === '$not');
540
- var logicQuery = filter2[attr];
541
- var sql = translateInner(entity2, path, logicQuery);
542
- if (sql) {
543
- whereText += " not (".concat(translateInner(entity2, path, logicQuery), ")");
544
- break;
545
- }
546
- }
547
- }
548
- whereText += ')';
549
- }
550
- else if (attr.toLowerCase().startsWith(types_1.EXPRESSION_PREFIX)) {
551
- // expression
552
- whereText += " (".concat(_this.translateExpression(entity2, alias, filter2[attr], filterRefAlias), ")");
553
- }
554
- else if (['$gt', '$gte', '$lt', '$lte', '$eq', '$ne', '$startsWith', '$endsWith', '$includes'].includes(attr)) {
555
- whereText += _this.translateComparison(attr, filter2[attr], type);
556
- }
557
- else if (['$exists'].includes(attr)) {
558
- whereText += _this.translateElement(attr, filter2[attr]);
559
- }
560
- else if (['$text', '$in', '$nin', '$between'].includes(attr)) {
561
- var _a = _this.translateEvaluation(attr, filter2[attr], entity2, alias, type, initialNumber, filterRefAlias), stmt = _a.stmt, cn2 = _a.currentNumber;
562
- whereText += stmt;
563
- currentNumber = cn2;
564
- }
565
- else {
566
- var rel = (0, relation_1.judgeRelation)(_this.schema, entity2, attr);
567
- if (rel === 2) {
568
- whereText += " (".concat(translateInner(attr, "".concat(path).concat(attr, "/"), filter2[attr]), ")");
569
- }
570
- else if (typeof rel === 'string') {
571
- whereText += " (".concat(translateInner(rel, "".concat(path).concat(attr, "/"), filter2[attr]), ")");
572
- }
573
- else {
574
- (0, assert_1.default)(attributes.hasOwnProperty(attr), "\u975E\u6CD5\u7684\u5C5E\u6027".concat(attr));
575
- var type2 = attributes[attr].type;
576
- // assert (type2 !== 'ref');
577
- if (typeof filter2[attr] === 'object' && Object.keys(filter2[attr])[0] && Object.keys(filter2[attr])[0].startsWith('$')) {
578
- whereText += " (`".concat(alias, "`.`").concat(attr, "` ").concat(translateInner(entity2, path, filter2[attr], type2), ")");
579
- }
580
- else {
581
- whereText += " (`".concat(alias, "`.`").concat(attr, "` = ").concat(_this.translateAttrValue(type2, filter2[attr]), ")");
582
- }
583
- }
584
- }
585
- });
586
- }
587
- if (!whereText) {
588
- whereText = 'true'; // 如果为空就赋一个永真条件,以便处理and
589
- }
590
- return whereText;
591
- };
592
- var where = translateInner(entity, './', filter);
593
- if (extraWhere && where) {
594
- return {
595
- stmt: "".concat(extraWhere, " and ").concat(where),
596
- currentNumber: currentNumber,
597
- };
598
- }
599
- return {
600
- stmt: extraWhere || where,
601
- currentNumber: currentNumber,
602
- };
603
- };
604
- SqlTranslator.prototype.translateSorter = function (entity, sorter, aliasDict) {
605
- var _this = this;
606
- var translateInner = function (entity2, sortAttr, path) {
607
- (0, assert_1.default)(Object.keys(sortAttr).length === 1);
608
- var attr = Object.keys(sortAttr)[0];
609
- var alias = aliasDict[path];
610
- if (attr.toLocaleLowerCase().startsWith(types_1.EXPRESSION_PREFIX)) {
611
- return _this.translateExpression(entity2, alias, sortAttr[attr], {});
612
- }
613
- else if (sortAttr[attr] === 1) {
614
- return "`".concat(alias, "`.`").concat(attr, "`");
615
- }
616
- else {
617
- var rel = (0, relation_1.judgeRelation)(_this.schema, entity2, attr);
618
- if (typeof rel === 'string') {
619
- return translateInner(rel, sortAttr[attr], "".concat(path).concat(attr, "/"));
620
- }
621
- else {
622
- (0, assert_1.default)(rel === 2);
623
- return translateInner(attr, sortAttr[attr], "".concat(path).concat(attr, "/"));
624
- }
625
- }
626
- };
627
- var sortText = '';
628
- sorter.forEach(function (sortNode, index) {
629
- var $attr = sortNode.$attr, $direction = sortNode.$direction;
630
- sortText += translateInner(entity, $attr, './');
631
- if ($direction) {
632
- sortText += " ".concat($direction);
633
- }
634
- if (index < sorter.length - 1) {
635
- sortText += ',';
636
- }
637
- });
638
- return sortText;
639
- };
640
- SqlTranslator.prototype.translateProjection = function (entity, projection, aliasDict, projectionRefAlias, commonPrefix, disableAs) {
641
- var _this = this;
642
- var schema = this.schema;
643
- var as = '';
644
- var translateInner = function (entity2, projection2, path) {
645
- var alias = aliasDict[path];
646
- var attributes = schema[entity2].attributes;
647
- var projText = '';
648
- var prefix = path.slice(2).replace(/\//g, '.');
649
- var attrs = Object.keys(projection2).filter(function (attr) {
650
- if (attr.toLowerCase().startsWith(types_1.EXPRESSION_PREFIX)) {
651
- return true;
652
- }
653
- var rel = (0, relation_1.judgeRelation)(_this.schema, entity2, attr);
654
- return [1, 2].includes(rel) || typeof rel === 'string';
655
- });
656
- attrs.forEach(function (attr, idx) {
657
- var prefix2 = commonPrefix ? "".concat(commonPrefix, ".").concat(prefix) : prefix;
658
- if (attr.toLowerCase().startsWith(types_1.EXPRESSION_PREFIX)) {
659
- var exprText = _this.translateExpression(entity2, alias, projection2[attr], projectionRefAlias);
660
- if (disableAs) {
661
- projText += " ".concat(exprText);
662
- }
663
- else {
664
- projText += " ".concat(exprText, " as `").concat(prefix2).concat(attr, "`");
665
- if (!as) {
666
- as = "`".concat(prefix2).concat(attr, "`");
667
- }
668
- else {
669
- as += ", `".concat(prefix2).concat(attr, "`");
670
- }
671
- }
672
- }
673
- else {
674
- var rel = (0, relation_1.judgeRelation)(_this.schema, entity2, attr);
675
- if (typeof rel === 'string') {
676
- projText += translateInner(rel, projection2[attr], "".concat(path).concat(attr, "/"));
677
- }
678
- else if (rel === 2) {
679
- projText += translateInner(attr, projection2[attr], "".concat(path).concat(attr, "/"));
680
- }
681
- else if (rel === 1) {
682
- var type = attributes[attr].type;
683
- if (projection2[attr] === 1) {
684
- if (disableAs) {
685
- projText += " ".concat(_this.translateAttrProjection(type, alias, attr));
686
- }
687
- else {
688
- projText += " ".concat(_this.translateAttrProjection(type, alias, attr), " as `").concat(prefix2).concat(attr, "`");
689
- if (!as) {
690
- as = "`".concat(prefix2).concat(attr, "`");
691
- }
692
- else {
693
- as += ", `".concat(prefix2).concat(attr, "`");
694
- }
695
- }
696
- }
697
- else {
698
- (0, assert_1.default)(typeof projection2 === 'string');
699
- if (disableAs) {
700
- projText += " ".concat(_this.translateAttrProjection(type, alias, attr));
701
- }
702
- else {
703
- projText += " ".concat(_this.translateAttrProjection(type, alias, attr), " as `").concat(prefix2).concat(projection2[attr], "`");
704
- if (!as) {
705
- as = "`".concat(prefix2).concat(projection2[attr], "`");
706
- }
707
- else {
708
- as += "`".concat(prefix2).concat(projection2[attr], "`");
709
- }
710
- }
711
- }
712
- }
713
- }
714
- if (idx < attrs.length - 1) {
715
- projText += ',';
716
- }
717
- });
718
- return projText;
719
- };
720
- return {
721
- projText: translateInner(entity, projection, './'),
722
- as: as,
723
- };
724
- };
725
- SqlTranslator.prototype.translateSelectInner = function (entity, selection, initialNumber, refAlias, option) {
726
- var data = selection.data, filter = selection.filter, sorter = selection.sorter, indexFrom = selection.indexFrom, count = selection.count;
727
- var _a = this.analyzeJoin(entity, {
728
- projection: data,
729
- filter: filter,
730
- sorter: sorter,
731
- }, initialNumber), fromText = _a.from, aliasDict = _a.aliasDict, projectionRefAlias = _a.projectionRefAlias, extraWhere = _a.extraWhere, filterRefAlias = _a.filterRefAlias, currentNumber = _a.currentNumber;
732
- (0, assert_1.default)((0, lodash_1.intersection)((0, lodash_1.keys)(refAlias), (0, lodash_1.keys)(filterRefAlias)).length === 0, 'filter中的#node结点定义有重复');
733
- (0, lodash_1.assign)(refAlias, filterRefAlias);
734
- var projText = this.translateProjection(entity, data, aliasDict, projectionRefAlias).projText;
735
- var _b = this.translateFilter(entity, selection, aliasDict, refAlias, currentNumber, extraWhere, option), filterText = _b.stmt, currentNumber2 = _b.currentNumber;
736
- var sorterText = sorter && this.translateSorter(entity, sorter, aliasDict);
737
- return {
738
- stmt: this.populateSelectStmt(projText, fromText, aliasDict, filterText, sorterText, undefined, indexFrom, count, option, selection),
739
- currentNumber: currentNumber2,
740
- };
741
- };
742
- SqlTranslator.prototype.translateSelect = function (entity, selection, option) {
743
- var stmt = this.translateSelectInner(entity, selection, 1, {}, option).stmt;
744
- return stmt;
745
- };
746
- SqlTranslator.prototype.translateAggregate = function (entity, aggregation, option) {
747
- var data = aggregation.data, filter = aggregation.filter, sorter = aggregation.sorter, indexFrom = aggregation.indexFrom, count = aggregation.count;
748
- var _a = this.analyzeJoin(entity, {
749
- aggregation: data,
750
- filter: filter,
751
- sorter: sorter,
752
- }, 1), fromText = _a.from, aliasDict = _a.aliasDict, projectionRefAlias = _a.projectionRefAlias, extraWhere = _a.extraWhere, filterRefAlias = _a.filterRefAlias, currentNumber = _a.currentNumber;
753
- var projText = '';
754
- var groupByText = '';
755
- for (var k in data) {
756
- if (k === '#aggr') {
757
- var _b = this.translateProjection(entity, data[k], aliasDict, projectionRefAlias, '#data'), projSubText = _b.projText, as = _b.as;
758
- if (!projText) {
759
- projText = projSubText;
760
- }
761
- else {
762
- projText += ", ".concat(projSubText);
763
- }
764
- groupByText = as;
765
- }
766
- else {
767
- var projSubText = this.translateProjection(entity, data[k], aliasDict, projectionRefAlias, undefined, true).projText;
768
- var projSubText2 = '';
769
- if (k.startsWith('#max')) {
770
- projSubText2 = "max(".concat(projSubText, ") as `").concat(k, "`");
771
- }
772
- else if (k.startsWith('#min')) {
773
- projSubText2 = "min(".concat(projSubText, ") as `").concat(k, "`");
774
- }
775
- else if (k.startsWith('#count')) {
776
- projSubText2 = "count(".concat(projSubText, ") as `").concat(k, "`");
777
- }
778
- else if (k.startsWith('#sum')) {
779
- projSubText2 = "sum(".concat(projSubText, ") as `").concat(k, "`");
780
- }
781
- else {
782
- (0, assert_1.default)(k.startsWith('#avg'));
783
- projSubText2 = "avg(".concat(projSubText, ") as `").concat(k, "`");
784
- }
785
- if (!projText) {
786
- projText = projSubText2;
787
- }
788
- else {
789
- projText += ", ".concat(projSubText2);
790
- }
791
- }
792
- }
793
- var filterText = this.translateFilter(entity, aggregation, aliasDict, {}, currentNumber, extraWhere, option).stmt;
794
- var sorterText = sorter && this.translateSorter(entity, sorter, aliasDict);
795
- return this.populateSelectStmt(projText, fromText, aliasDict, filterText, sorterText, groupByText, indexFrom, count, option, undefined, aggregation);
796
- };
797
- SqlTranslator.prototype.translateCount = function (entity, selection, option) {
798
- var filter = selection.filter, count = selection.count;
799
- var _a = this.analyzeJoin(entity, {
800
- filter: filter,
801
- }), fromText = _a.from, aliasDict = _a.aliasDict, extraWhere = _a.extraWhere, filterRefAlias = _a.filterRefAlias, currentNumber = _a.currentNumber;
802
- var projText = 'count(1) cnt';
803
- var filterText = this.translateFilter(entity, selection, aliasDict, filterRefAlias, currentNumber, extraWhere, option).stmt;
804
- if (count) {
805
- var subQuerySql = this.populateSelectStmt('1', fromText, aliasDict, filterText, undefined, undefined, undefined, undefined, option, Object.assign({}, selection, { indexFrom: 0, count: count }));
806
- return "select count(1) cnt from (".concat(subQuerySql, ") __tmp");
807
- }
808
- return this.populateSelectStmt(projText, fromText, aliasDict, filterText, undefined, undefined, undefined, undefined, option, selection);
809
- };
810
- SqlTranslator.prototype.translateRemove = function (entity, operation, option) {
811
- var filter = operation.filter, sorter = operation.sorter, indexFrom = operation.indexFrom, count = operation.count;
812
- (0, assert_1.default)(!sorter, '当前remove不支持sorter行为');
813
- var _a = this.analyzeJoin(entity, { filter: filter, sorter: sorter }), aliasDict = _a.aliasDict, filterRefAlias = _a.filterRefAlias, extraWhere = _a.extraWhere, fromText = _a.from, currentNumber = _a.currentNumber;
814
- var alias = aliasDict['./'];
815
- var filterText = this.translateFilter(entity, operation, aliasDict, filterRefAlias, currentNumber, extraWhere, { includedDeleted: true }).stmt;
816
- // const sorterText = sorter && sorter.length > 0 ? this.translateSorter(entity, sorter, aliasDict) : undefined;
817
- return this.populateRemoveStmt(alias, fromText, aliasDict, filterText, /* sorterText */ undefined, indexFrom, count, option);
818
- };
819
- SqlTranslator.prototype.translateUpdate = function (entity, operation, option) {
820
- var attributes = this.schema[entity].attributes;
821
- var filter = operation.filter, sorter = operation.sorter, indexFrom = operation.indexFrom, count = operation.count, data = operation.data;
822
- (0, assert_1.default)(!sorter, '当前update不支持sorter行为');
823
- var _a = this.analyzeJoin(entity, { filter: filter, sorter: sorter }), aliasDict = _a.aliasDict, filterRefAlias = _a.filterRefAlias, extraWhere = _a.extraWhere, fromText = _a.from, currentNumber = _a.currentNumber;
824
- var alias = aliasDict['./'];
825
- var updateText = '';
826
- for (var attr in data) {
827
- if (updateText) {
828
- updateText += ',';
829
- }
830
- (0, assert_1.default)(attributes.hasOwnProperty(attr) && attributes[attr].type !== 'ref');
831
- var value = this.translateAttrValue(attributes[attr].type, data[attr]);
832
- updateText += "`".concat(alias, "`.`").concat(attr, "` = ").concat(value);
833
- }
834
- var filterText = this.translateFilter(entity, operation, aliasDict, filterRefAlias, currentNumber, extraWhere).stmt;
835
- // const sorterText = sorter && this.translateSorter(entity, sorter, aliasDict);
836
- return this.populateUpdateStmt(updateText, fromText, aliasDict, filterText, /* sorterText */ undefined, indexFrom, count, option);
837
- };
838
- SqlTranslator.prototype.translateDestroyEntity = function (entity, truncate) {
839
- var schema = this.schema;
840
- var _a = schema[entity], _b = _a.storageName, storageName = _b === void 0 ? entity : _b, view = _a.view;
841
- var sql;
842
- if (view) {
843
- sql = "drop view if exists `".concat(storageName, "`");
844
- }
845
- else {
846
- sql = truncate ? "truncate table `".concat(storageName, "`") : "drop table if exists `".concat(storageName, "`");
847
- }
848
- return sql;
849
- };
850
- SqlTranslator.prototype.escapeStringValue = function (value) {
851
- var result = "'".concat(value.replace(/'/g, '\\\''), "'");
852
- return result;
853
- };
854
- return SqlTranslator;
855
- }());
856
- exports.SqlTranslator = SqlTranslator;
1
+ "use strict";
2
+ Object.defineProperty(exports, "__esModule", { value: true });
3
+ exports.SqlTranslator = void 0;
4
+ var tslib_1 = require("tslib");
5
+ var assert_1 = tslib_1.__importDefault(require("assert"));
6
+ var lodash_1 = require("lodash");
7
+ var types_1 = require("oak-domain/lib/types");
8
+ var relation_1 = require("oak-domain/lib/store/relation");
9
+ ;
10
+ ;
11
+ var SqlTranslator = /** @class */ (function () {
12
+ function SqlTranslator(schema) {
13
+ this.schema = this.makeFullSchema(schema);
14
+ }
15
+ SqlTranslator.prototype.makeFullSchema = function (schema2) {
16
+ var schema = (0, lodash_1.cloneDeep)(schema2);
17
+ for (var entity in schema) {
18
+ var _a = schema[entity], attributes = _a.attributes, indexes = _a.indexes;
19
+ // 增加默认的属性
20
+ (0, lodash_1.assign)(attributes, {
21
+ id: {
22
+ type: 'char',
23
+ params: {
24
+ length: 36,
25
+ },
26
+ },
27
+ $$seq$$: {
28
+ type: 'sequence',
29
+ sequenceStart: 10000,
30
+ },
31
+ $$createAt$$: {
32
+ type: 'datetime',
33
+ notNull: true,
34
+ },
35
+ $$updateAt$$: {
36
+ type: 'datetime',
37
+ notNull: true,
38
+ },
39
+ $$deleteAt$$: {
40
+ type: 'datetime',
41
+ },
42
+ $$triggerData$$: {
43
+ type: 'object',
44
+ },
45
+ $$triggerTimestamp$$: {
46
+ type: 'datetime',
47
+ },
48
+ });
49
+ // 增加默认的索引
50
+ var intrinsticIndexes = [
51
+ {
52
+ name: "".concat(entity, "_create_at_auto_create"),
53
+ attributes: [{
54
+ name: '$$createAt$$',
55
+ }, {
56
+ name: '$$deleteAt$$',
57
+ }]
58
+ }, {
59
+ name: "".concat(entity, "_update_at_auto_create"),
60
+ attributes: [{
61
+ name: '$$updateAt$$',
62
+ }, {
63
+ name: '$$deleteAt$$',
64
+ }],
65
+ }, {
66
+ name: "".concat(entity, "_trigger_ts_auto_create"),
67
+ attributes: [{
68
+ name: '$$triggerTimestamp$$',
69
+ }, {
70
+ name: '$$deleteAt$$',
71
+ }],
72
+ }
73
+ ];
74
+ var _loop_1 = function (attr) {
75
+ if (attributes[attr].type === 'ref') {
76
+ if (!(indexes === null || indexes === void 0 ? void 0 : indexes.find(function (ele) { return ele.attributes[0].name === attr; }))) {
77
+ intrinsticIndexes.push({
78
+ name: "".concat(entity, "_fk_").concat(attr, "_auto_create"),
79
+ attributes: [{
80
+ name: attr,
81
+ }, {
82
+ name: '$$deleteAt$$',
83
+ }]
84
+ });
85
+ }
86
+ }
87
+ if (attr === 'entity' && attributes[attr].type === 'varchar') {
88
+ var entityIdDef = attributes.entityId;
89
+ if ((entityIdDef === null || entityIdDef === void 0 ? void 0 : entityIdDef.type) === 'varchar') {
90
+ if (!(indexes === null || indexes === void 0 ? void 0 : indexes.find(function (ele) { var _a; return ele.attributes[0].name === 'entity' && ((_a = ele.attributes[1]) === null || _a === void 0 ? void 0 : _a.name) === 'entityId'; }))) {
91
+ intrinsticIndexes.push({
92
+ name: "".concat(entity, "_fk_entity_entityId_auto_create"),
93
+ attributes: [{
94
+ name: 'entity',
95
+ }, {
96
+ name: 'entityId',
97
+ }, {
98
+ name: '$$deleteAt$$',
99
+ }]
100
+ });
101
+ }
102
+ }
103
+ }
104
+ if (attr.endsWith('State') && attributes[attr].type === 'varchar') {
105
+ if (!(indexes === null || indexes === void 0 ? void 0 : indexes.find(function (ele) { return ele.attributes[0].name === attr; }))) {
106
+ intrinsticIndexes.push({
107
+ name: "".concat(entity, "_attr_auto_create"),
108
+ attributes: [{
109
+ name: attr,
110
+ }, {
111
+ name: '$$deleteAt$$',
112
+ }]
113
+ });
114
+ }
115
+ }
116
+ if (attr === 'expired' && attributes[attr].type === 'boolean') {
117
+ var expiresAtDef = attributes.expiresAt;
118
+ if ((expiresAtDef === null || expiresAtDef === void 0 ? void 0 : expiresAtDef.type) === 'datetime') {
119
+ if (!(indexes === null || indexes === void 0 ? void 0 : indexes.find(function (ele) { var _a; return ele.attributes[0].name === 'expired' && ((_a = ele.attributes[1]) === null || _a === void 0 ? void 0 : _a.name) === 'expiresAt'; }))) {
120
+ intrinsticIndexes.push({
121
+ name: "".concat(entity, "_expires_expiredAt_auto_create"),
122
+ attributes: [{
123
+ name: 'expired',
124
+ }, {
125
+ name: 'expiresAt',
126
+ }, {
127
+ name: '$$deleteAt$$',
128
+ }]
129
+ });
130
+ }
131
+ }
132
+ }
133
+ };
134
+ // 增加外键等相关属性上的索引
135
+ for (var attr in attributes) {
136
+ _loop_1(attr);
137
+ }
138
+ if (indexes) {
139
+ indexes.push.apply(indexes, intrinsticIndexes);
140
+ }
141
+ else {
142
+ (0, lodash_1.assign)(schema[entity], {
143
+ indexes: intrinsticIndexes,
144
+ });
145
+ }
146
+ }
147
+ return schema;
148
+ };
149
+ SqlTranslator.prototype.getStorageName = function (entity) {
150
+ var storageName = this.schema[entity].storageName;
151
+ return (storageName || entity);
152
+ };
153
+ SqlTranslator.prototype.translateInsert = function (entity, data) {
154
+ var _this = this;
155
+ var schema = this.schema;
156
+ var _a = schema[entity], attributes = _a.attributes, _b = _a.storageName, storageName = _b === void 0 ? entity : _b;
157
+ var sql = "insert into `".concat(storageName, "`(");
158
+ /**
159
+ * 这里的attrs要用所有行的union集合
160
+ */
161
+ var dataFull = data.reduce(function (prev, cur) { return Object.assign({}, cur, prev); }, {});
162
+ var attrs = Object.keys(dataFull).filter(function (ele) { return attributes.hasOwnProperty(ele); });
163
+ attrs.forEach(function (attr, idx) {
164
+ sql += " `".concat(attr, "`");
165
+ if (idx < attrs.length - 1) {
166
+ sql += ',';
167
+ }
168
+ });
169
+ sql += ') values ';
170
+ data.forEach(function (d, dataIndex) {
171
+ sql += '(';
172
+ attrs.forEach(function (attr, attrIdx) {
173
+ var attrDef = attributes[attr];
174
+ var dataType = attrDef.type;
175
+ var value = _this.translateAttrValue(dataType, d[attr]);
176
+ sql += value;
177
+ if (attrIdx < attrs.length - 1) {
178
+ sql += ',';
179
+ }
180
+ });
181
+ if (dataIndex < data.length - 1) {
182
+ sql += '),';
183
+ }
184
+ else {
185
+ sql += ')';
186
+ }
187
+ });
188
+ return sql;
189
+ };
190
+ /**
191
+ * analyze the join relations in projection/query/sort
192
+ * 所有的层次关系都当成left join处理,如果有内表为空的情况,请手动处理
193
+ * {
194
+ * b: {
195
+ * name: {
196
+ * $exists: false,
197
+ * }
198
+ * }
199
+ * }
200
+ * 这样的query会把内表为空的行也返回
201
+ * @param param0
202
+ */
203
+ SqlTranslator.prototype.analyzeJoin = function (entity, _a, initialNumber) {
204
+ var _this = this;
205
+ var projection = _a.projection, filter = _a.filter, sorter = _a.sorter, aggregation = _a.aggregation;
206
+ var schema = this.schema;
207
+ var number = initialNumber || 1;
208
+ var projectionRefAlias = {};
209
+ var filterRefAlias = {};
210
+ var extraWhere = '';
211
+ var alias = "".concat(entity, "_").concat(number++);
212
+ var from = " `".concat(this.getStorageName(entity), "` `").concat(alias, "` ");
213
+ var aliasDict = {
214
+ './': alias,
215
+ };
216
+ var analyzeFilterNode = function (_a) {
217
+ var _b;
218
+ var node = _a.node, path = _a.path, entityName = _a.entityName, alias = _a.alias;
219
+ Object.keys(node).forEach(function (op) {
220
+ var _a, _b;
221
+ if (['$and', '$or'].includes(op)) {
222
+ node[op].forEach(function (subNode) { return analyzeFilterNode({
223
+ node: subNode,
224
+ path: path,
225
+ entityName: entityName,
226
+ alias: alias,
227
+ }); });
228
+ }
229
+ else if (['$not'].includes(op)) {
230
+ analyzeFilterNode({
231
+ node: node[op],
232
+ path: path,
233
+ entityName: entityName,
234
+ alias: alias,
235
+ });
236
+ }
237
+ else if (['$text'].includes(op)) {
238
+ }
239
+ else {
240
+ var rel = (0, relation_1.judgeRelation)(_this.schema, entityName, op);
241
+ if (typeof rel === 'string') {
242
+ var alias2 = void 0;
243
+ var pathAttr = "".concat(path).concat(op, "/");
244
+ if (!aliasDict.hasOwnProperty(pathAttr)) {
245
+ alias2 = "".concat(rel, "_").concat(number++);
246
+ (0, lodash_1.assign)(aliasDict, (_a = {},
247
+ _a[pathAttr] = alias2,
248
+ _a));
249
+ from += " left join `".concat(_this.getStorageName(rel), "` `").concat(alias2, "` on `").concat(alias, "`.`").concat(op, "Id` = `").concat(alias2, "`.`id`");
250
+ }
251
+ else {
252
+ alias2 = aliasDict[pathAttr];
253
+ }
254
+ analyzeFilterNode({
255
+ node: node[op],
256
+ path: pathAttr,
257
+ entityName: rel,
258
+ alias: alias2,
259
+ });
260
+ }
261
+ else if (rel === 2) {
262
+ var alias2 = void 0;
263
+ var pathAttr = "".concat(path).concat(op, "/");
264
+ if (!aliasDict.hasOwnProperty(pathAttr)) {
265
+ alias2 = "".concat(op, "_").concat(number++);
266
+ (0, lodash_1.assign)(aliasDict, (_b = {},
267
+ _b[pathAttr] = alias2,
268
+ _b));
269
+ from += " left join `".concat(_this.getStorageName(op), "` `").concat(alias2, "` on `").concat(alias, "`.`entityId` = `").concat(alias2, "`.`id` and `").concat(alias, "`.`entity` = '").concat(op, "'");
270
+ }
271
+ else {
272
+ alias2 = aliasDict[pathAttr];
273
+ }
274
+ analyzeFilterNode({
275
+ node: node[op],
276
+ path: pathAttr,
277
+ entityName: op,
278
+ alias: alias2,
279
+ });
280
+ }
281
+ else {
282
+ // 不支持一对多
283
+ (0, assert_1.default)(rel === 0 || rel === 1);
284
+ }
285
+ }
286
+ });
287
+ if (node['#id']) {
288
+ (0, assert_1.default)(!filterRefAlias[node['#id']]);
289
+ (0, lodash_1.assign)(filterRefAlias, (_b = {},
290
+ _b[node['#id']] = [alias, entityName],
291
+ _b));
292
+ }
293
+ };
294
+ if (filter) {
295
+ analyzeFilterNode({
296
+ node: filter,
297
+ path: './',
298
+ entityName: entity,
299
+ alias: alias,
300
+ });
301
+ }
302
+ var analyzeSortNode = function (_a) {
303
+ var _b, _c;
304
+ var node = _a.node, path = _a.path, entityName = _a.entityName, alias = _a.alias;
305
+ var attr = (0, lodash_1.keys)(node)[0];
306
+ var rel = (0, relation_1.judgeRelation)(_this.schema, entityName, attr);
307
+ if (typeof rel === 'string') {
308
+ var pathAttr = "".concat(path).concat(attr, "/");
309
+ var alias2 = void 0;
310
+ if (!aliasDict.hasOwnProperty(pathAttr)) {
311
+ alias2 = "".concat(rel, "_").concat(number++);
312
+ (0, lodash_1.assign)(aliasDict, (_b = {},
313
+ _b[pathAttr] = alias2,
314
+ _b));
315
+ from += " left join `".concat(_this.getStorageName(rel), "` `").concat(alias2, "` on `").concat(alias, "`.`").concat(attr, "Id` = `").concat(alias2, "`.`id`");
316
+ }
317
+ else {
318
+ alias2 = aliasDict[pathAttr];
319
+ }
320
+ analyzeSortNode({
321
+ node: node[attr],
322
+ path: pathAttr,
323
+ entityName: rel,
324
+ alias: alias2,
325
+ });
326
+ }
327
+ else if (rel === 2) {
328
+ var pathAttr = "".concat(path).concat(attr, "/");
329
+ var alias2 = void 0;
330
+ if (!aliasDict.hasOwnProperty(pathAttr)) {
331
+ alias2 = "".concat(attr, "_").concat(number++);
332
+ (0, lodash_1.assign)(aliasDict, (_c = {},
333
+ _c[pathAttr] = alias2,
334
+ _c));
335
+ from += " left join `".concat(_this.getStorageName(attr), "` `").concat(alias2, "` on `").concat(alias, "`.`entityId` = `").concat(alias2, "`.`id` and `").concat(alias, "`.`entity` = '").concat(attr, "'");
336
+ }
337
+ else {
338
+ alias2 = aliasDict[pathAttr];
339
+ }
340
+ analyzeSortNode({
341
+ node: node[attr],
342
+ path: pathAttr,
343
+ entityName: attr,
344
+ alias: alias2,
345
+ });
346
+ }
347
+ else {
348
+ (0, assert_1.default)(rel === 0 || rel === 1);
349
+ }
350
+ };
351
+ if (sorter) {
352
+ sorter.forEach(function (sortNode) {
353
+ analyzeSortNode({
354
+ node: sortNode.$attr,
355
+ path: './',
356
+ entityName: entity,
357
+ alias: alias,
358
+ });
359
+ });
360
+ }
361
+ var analyzeProjectionNode = function (_a) {
362
+ var _b;
363
+ var node = _a.node, path = _a.path, entityName = _a.entityName, alias = _a.alias;
364
+ var attributes = schema[entityName].attributes;
365
+ Object.keys(node).forEach(function (attr) {
366
+ var _a, _b;
367
+ var rel = (0, relation_1.judgeRelation)(_this.schema, entityName, attr);
368
+ if (typeof rel === 'string') {
369
+ var pathAttr = "".concat(path).concat(attr, "/");
370
+ var alias2 = void 0;
371
+ if (!aliasDict.hasOwnProperty(pathAttr)) {
372
+ alias2 = "".concat(rel, "_").concat(number++);
373
+ (0, lodash_1.assign)(aliasDict, (_a = {},
374
+ _a[pathAttr] = alias2,
375
+ _a));
376
+ from += " left join `".concat(_this.getStorageName(rel), "` `").concat(alias2, "` on `").concat(alias, "`.`").concat(attr, "Id` = `").concat(alias2, "`.`id`");
377
+ }
378
+ else {
379
+ alias2 = aliasDict[pathAttr];
380
+ }
381
+ analyzeProjectionNode({
382
+ node: node[attr],
383
+ path: pathAttr,
384
+ entityName: rel,
385
+ alias: alias2,
386
+ });
387
+ }
388
+ else if (rel === 2) {
389
+ var pathAttr = "".concat(path).concat(attr, "/");
390
+ var alias2 = void 0;
391
+ if (!aliasDict.hasOwnProperty(pathAttr)) {
392
+ alias2 = "".concat(attr, "_").concat(number++);
393
+ (0, lodash_1.assign)(aliasDict, (_b = {},
394
+ _b[pathAttr] = alias2,
395
+ _b));
396
+ from += " left join `".concat(_this.getStorageName(attr), "` `").concat(alias2, "` on `").concat(alias, "`.`entityId` = `").concat(alias2, "`.`id` and `").concat(alias, "`.`entity` = '").concat(attr, "'");
397
+ }
398
+ else {
399
+ alias2 = aliasDict[pathAttr];
400
+ }
401
+ analyzeProjectionNode({
402
+ node: node[attr],
403
+ path: pathAttr,
404
+ entityName: attr,
405
+ alias: alias2,
406
+ });
407
+ }
408
+ });
409
+ if (node['#id']) {
410
+ (0, assert_1.default)(!projectionRefAlias[node['#id']], "projection\u4E0A\u6709\u91CD\u590D\u7684#id\u5B9A\u4E49\u300C".concat(node['#id'], "\u300D"));
411
+ (0, lodash_1.assign)(projectionRefAlias, (_b = {},
412
+ _b[node['#id']] = [alias, entityName],
413
+ _b));
414
+ }
415
+ };
416
+ if (projection) {
417
+ analyzeProjectionNode({ node: projection, path: './', entityName: entity, alias: alias });
418
+ }
419
+ else if (aggregation) {
420
+ for (var k in aggregation) {
421
+ analyzeProjectionNode({
422
+ node: aggregation[k],
423
+ path: './',
424
+ entityName: entity,
425
+ alias: alias,
426
+ });
427
+ }
428
+ }
429
+ return {
430
+ aliasDict: aliasDict,
431
+ from: from,
432
+ projectionRefAlias: projectionRefAlias,
433
+ filterRefAlias: filterRefAlias,
434
+ extraWhere: extraWhere,
435
+ currentNumber: number,
436
+ };
437
+ };
438
+ SqlTranslator.prototype.translateComparison = function (attr, value, type) {
439
+ var SQL_OP = {
440
+ $gt: '>',
441
+ $lt: '<',
442
+ $gte: '>=',
443
+ $lte: '<=',
444
+ $eq: '=',
445
+ $ne: '<>',
446
+ };
447
+ if (Object.keys(SQL_OP).includes(attr)) {
448
+ return " ".concat(SQL_OP[attr], " ").concat(this.translateAttrValue(type, value));
449
+ }
450
+ switch (attr) {
451
+ case '$startsWith': {
452
+ return " like '".concat(value, "%'");
453
+ }
454
+ case '$endsWith': {
455
+ return " like '%".concat(value, "'");
456
+ }
457
+ case '$includes': {
458
+ return " like '%".concat(value, "%'");
459
+ }
460
+ default: {
461
+ throw new Error("unrecoganized comparison operator ".concat(attr));
462
+ }
463
+ }
464
+ };
465
+ SqlTranslator.prototype.translateElement = function (attr, value) {
466
+ (0, assert_1.default)(attr === '$exists'); // only support one operator now
467
+ if (value) {
468
+ return ' is not null';
469
+ }
470
+ return ' is null';
471
+ };
472
+ SqlTranslator.prototype.translateEvaluation = function (attr, value, entity, alias, type, initialNumber, refAlias) {
473
+ switch (attr) {
474
+ case '$text': {
475
+ // fulltext search
476
+ return {
477
+ stmt: this.translateFullTextSearch(value, entity, alias),
478
+ currentNumber: initialNumber,
479
+ };
480
+ }
481
+ case '$in':
482
+ case '$nin': {
483
+ var IN_OP = {
484
+ $in: 'in',
485
+ $nin: 'not in',
486
+ };
487
+ if (value instanceof Array) {
488
+ var values = value.map(function (v) {
489
+ if (['varchar', 'char', 'text', 'nvarchar', 'ref'].includes(type)) {
490
+ return "'".concat(v, "'");
491
+ }
492
+ else {
493
+ return "".concat(v);
494
+ }
495
+ });
496
+ if (values.length > 0) {
497
+ return {
498
+ stmt: " ".concat(IN_OP[attr], "(").concat(values.join(','), ")"),
499
+ currentNumber: initialNumber,
500
+ };
501
+ }
502
+ else {
503
+ if (attr === '$in') {
504
+ return {
505
+ stmt: ' in (null)',
506
+ currentNumber: initialNumber,
507
+ };
508
+ }
509
+ else {
510
+ return {
511
+ stmt: ' is not null',
512
+ currentNumber: initialNumber,
513
+ };
514
+ }
515
+ }
516
+ }
517
+ else {
518
+ // sub query
519
+ var _a = this.translateSelectInner(value.entity, value, initialNumber, refAlias, undefined), subQueryStmt = _a.stmt, currentNumber = _a.currentNumber;
520
+ return {
521
+ stmt: " ".concat(IN_OP[attr], "(").concat(subQueryStmt, ")"),
522
+ currentNumber: currentNumber,
523
+ };
524
+ }
525
+ }
526
+ default: {
527
+ (0, assert_1.default)('$between' === attr);
528
+ var values = value.map(function (v) {
529
+ if (['varchar', 'char', 'text', 'nvarchar', 'ref'].includes(type)) {
530
+ return "'".concat(v, "'");
531
+ }
532
+ else {
533
+ return "".concat(v);
534
+ }
535
+ });
536
+ return {
537
+ stmt: " between ".concat(values[0], " and ").concat(values[1]),
538
+ currentNumber: initialNumber,
539
+ };
540
+ }
541
+ }
542
+ };
543
+ SqlTranslator.prototype.translateFilter = function (entity, selection, aliasDict, filterRefAlias, initialNumber, extraWhere, option) {
544
+ var _this = this;
545
+ var schema = this.schema;
546
+ var filter = selection.filter;
547
+ var currentNumber = initialNumber;
548
+ var translateInner = function (entity2, path, filter2, type) {
549
+ var alias = aliasDict[path];
550
+ var attributes = schema[entity2].attributes;
551
+ var whereText = type ? '' : _this.getDefaultSelectFilter(alias, option);
552
+ if (filter2) {
553
+ var attrs = Object.keys(filter2).filter(function (ele) { return !ele.startsWith('#'); });
554
+ attrs.forEach(function (attr) {
555
+ if (whereText) {
556
+ whereText += ' and ';
557
+ }
558
+ if (['$and', '$or', '$xor', '$not'].includes(attr)) {
559
+ var result = '';
560
+ whereText += '(';
561
+ switch (attr) {
562
+ case '$and':
563
+ case '$or':
564
+ case '$xor': {
565
+ var logicQueries_1 = filter2[attr];
566
+ logicQueries_1.forEach(function (logicQuery, index) {
567
+ var sql = translateInner(entity2, path, logicQuery);
568
+ if (sql) {
569
+ whereText += " (".concat(sql, ")");
570
+ if (index < logicQueries_1.length - 1) {
571
+ whereText += " ".concat(attr.slice(1));
572
+ }
573
+ }
574
+ });
575
+ break;
576
+ }
577
+ default: {
578
+ (0, assert_1.default)(attr === '$not');
579
+ var logicQuery = filter2[attr];
580
+ var sql = translateInner(entity2, path, logicQuery);
581
+ if (sql) {
582
+ whereText += " not (".concat(translateInner(entity2, path, logicQuery), ")");
583
+ break;
584
+ }
585
+ }
586
+ }
587
+ whereText += ')';
588
+ }
589
+ else if (attr.toLowerCase().startsWith(types_1.EXPRESSION_PREFIX)) {
590
+ // expression
591
+ whereText += " (".concat(_this.translateExpression(entity2, alias, filter2[attr], filterRefAlias), ")");
592
+ }
593
+ else if (['$gt', '$gte', '$lt', '$lte', '$eq', '$ne', '$startsWith', '$endsWith', '$includes'].includes(attr)) {
594
+ whereText += _this.translateComparison(attr, filter2[attr], type);
595
+ }
596
+ else if (['$exists'].includes(attr)) {
597
+ whereText += _this.translateElement(attr, filter2[attr]);
598
+ }
599
+ else if (['$text', '$in', '$nin', '$between'].includes(attr)) {
600
+ var _a = _this.translateEvaluation(attr, filter2[attr], entity2, alias, type, initialNumber, filterRefAlias), stmt = _a.stmt, cn2 = _a.currentNumber;
601
+ whereText += stmt;
602
+ currentNumber = cn2;
603
+ }
604
+ else {
605
+ var rel = (0, relation_1.judgeRelation)(_this.schema, entity2, attr);
606
+ if (rel === 2) {
607
+ whereText += " (".concat(translateInner(attr, "".concat(path).concat(attr, "/"), filter2[attr]), ")");
608
+ }
609
+ else if (typeof rel === 'string') {
610
+ whereText += " (".concat(translateInner(rel, "".concat(path).concat(attr, "/"), filter2[attr]), ")");
611
+ }
612
+ else {
613
+ (0, assert_1.default)(attributes.hasOwnProperty(attr), "\u975E\u6CD5\u7684\u5C5E\u6027".concat(attr));
614
+ var type2 = attributes[attr].type;
615
+ // assert (type2 !== 'ref');
616
+ if (typeof filter2[attr] === 'object' && Object.keys(filter2[attr])[0] && Object.keys(filter2[attr])[0].startsWith('$')) {
617
+ whereText += " (`".concat(alias, "`.`").concat(attr, "` ").concat(translateInner(entity2, path, filter2[attr], type2), ")");
618
+ }
619
+ else {
620
+ whereText += " (`".concat(alias, "`.`").concat(attr, "` = ").concat(_this.translateAttrValue(type2, filter2[attr]), ")");
621
+ }
622
+ }
623
+ }
624
+ });
625
+ }
626
+ if (!whereText) {
627
+ whereText = 'true'; // 如果为空就赋一个永真条件,以便处理and
628
+ }
629
+ return whereText;
630
+ };
631
+ var where = translateInner(entity, './', filter);
632
+ if (extraWhere && where) {
633
+ return {
634
+ stmt: "".concat(extraWhere, " and ").concat(where),
635
+ currentNumber: currentNumber,
636
+ };
637
+ }
638
+ return {
639
+ stmt: extraWhere || where,
640
+ currentNumber: currentNumber,
641
+ };
642
+ };
643
+ SqlTranslator.prototype.translateSorter = function (entity, sorter, aliasDict) {
644
+ var _this = this;
645
+ var translateInner = function (entity2, sortAttr, path) {
646
+ (0, assert_1.default)(Object.keys(sortAttr).length === 1);
647
+ var attr = Object.keys(sortAttr)[0];
648
+ var alias = aliasDict[path];
649
+ if (attr.toLocaleLowerCase().startsWith(types_1.EXPRESSION_PREFIX)) {
650
+ return _this.translateExpression(entity2, alias, sortAttr[attr], {});
651
+ }
652
+ else if (sortAttr[attr] === 1) {
653
+ return "`".concat(alias, "`.`").concat(attr, "`");
654
+ }
655
+ else {
656
+ var rel = (0, relation_1.judgeRelation)(_this.schema, entity2, attr);
657
+ if (typeof rel === 'string') {
658
+ return translateInner(rel, sortAttr[attr], "".concat(path).concat(attr, "/"));
659
+ }
660
+ else {
661
+ (0, assert_1.default)(rel === 2);
662
+ return translateInner(attr, sortAttr[attr], "".concat(path).concat(attr, "/"));
663
+ }
664
+ }
665
+ };
666
+ var sortText = '';
667
+ sorter.forEach(function (sortNode, index) {
668
+ var $attr = sortNode.$attr, $direction = sortNode.$direction;
669
+ sortText += translateInner(entity, $attr, './');
670
+ if ($direction) {
671
+ sortText += " ".concat($direction);
672
+ }
673
+ if (index < sorter.length - 1) {
674
+ sortText += ',';
675
+ }
676
+ });
677
+ return sortText;
678
+ };
679
+ SqlTranslator.prototype.translateProjection = function (entity, projection, aliasDict, projectionRefAlias, commonPrefix, disableAs) {
680
+ var _this = this;
681
+ var schema = this.schema;
682
+ var as = '';
683
+ var translateInner = function (entity2, projection2, path) {
684
+ var alias = aliasDict[path];
685
+ var attributes = schema[entity2].attributes;
686
+ var projText = '';
687
+ var prefix = path.slice(2).replace(/\//g, '.');
688
+ var attrs = Object.keys(projection2).filter(function (attr) {
689
+ if (attr.toLowerCase().startsWith(types_1.EXPRESSION_PREFIX)) {
690
+ return true;
691
+ }
692
+ var rel = (0, relation_1.judgeRelation)(_this.schema, entity2, attr);
693
+ return [1, 2].includes(rel) || typeof rel === 'string';
694
+ });
695
+ attrs.forEach(function (attr, idx) {
696
+ var prefix2 = commonPrefix ? "".concat(commonPrefix, ".").concat(prefix) : prefix;
697
+ if (attr.toLowerCase().startsWith(types_1.EXPRESSION_PREFIX)) {
698
+ var exprText = _this.translateExpression(entity2, alias, projection2[attr], projectionRefAlias);
699
+ if (disableAs) {
700
+ projText += " ".concat(exprText);
701
+ }
702
+ else {
703
+ projText += " ".concat(exprText, " as `").concat(prefix2).concat(attr, "`");
704
+ if (!as) {
705
+ as = "`".concat(prefix2).concat(attr, "`");
706
+ }
707
+ else {
708
+ as += ", `".concat(prefix2).concat(attr, "`");
709
+ }
710
+ }
711
+ }
712
+ else {
713
+ var rel = (0, relation_1.judgeRelation)(_this.schema, entity2, attr);
714
+ if (typeof rel === 'string') {
715
+ projText += translateInner(rel, projection2[attr], "".concat(path).concat(attr, "/"));
716
+ }
717
+ else if (rel === 2) {
718
+ projText += translateInner(attr, projection2[attr], "".concat(path).concat(attr, "/"));
719
+ }
720
+ else if (rel === 1) {
721
+ var type = attributes[attr].type;
722
+ if (projection2[attr] === 1) {
723
+ if (disableAs) {
724
+ projText += " ".concat(_this.translateAttrProjection(type, alias, attr));
725
+ }
726
+ else {
727
+ projText += " ".concat(_this.translateAttrProjection(type, alias, attr), " as `").concat(prefix2).concat(attr, "`");
728
+ if (!as) {
729
+ as = "`".concat(prefix2).concat(attr, "`");
730
+ }
731
+ else {
732
+ as += ", `".concat(prefix2).concat(attr, "`");
733
+ }
734
+ }
735
+ }
736
+ else {
737
+ (0, assert_1.default)(typeof projection2 === 'string');
738
+ if (disableAs) {
739
+ projText += " ".concat(_this.translateAttrProjection(type, alias, attr));
740
+ }
741
+ else {
742
+ projText += " ".concat(_this.translateAttrProjection(type, alias, attr), " as `").concat(prefix2).concat(projection2[attr], "`");
743
+ if (!as) {
744
+ as = "`".concat(prefix2).concat(projection2[attr], "`");
745
+ }
746
+ else {
747
+ as += "`".concat(prefix2).concat(projection2[attr], "`");
748
+ }
749
+ }
750
+ }
751
+ }
752
+ }
753
+ if (idx < attrs.length - 1) {
754
+ projText += ',';
755
+ }
756
+ });
757
+ return projText;
758
+ };
759
+ return {
760
+ projText: translateInner(entity, projection, './'),
761
+ as: as,
762
+ };
763
+ };
764
+ SqlTranslator.prototype.translateSelectInner = function (entity, selection, initialNumber, refAlias, option) {
765
+ var data = selection.data, filter = selection.filter, sorter = selection.sorter, indexFrom = selection.indexFrom, count = selection.count;
766
+ var _a = this.analyzeJoin(entity, {
767
+ projection: data,
768
+ filter: filter,
769
+ sorter: sorter,
770
+ }, initialNumber), fromText = _a.from, aliasDict = _a.aliasDict, projectionRefAlias = _a.projectionRefAlias, extraWhere = _a.extraWhere, filterRefAlias = _a.filterRefAlias, currentNumber = _a.currentNumber;
771
+ (0, assert_1.default)((0, lodash_1.intersection)((0, lodash_1.keys)(refAlias), (0, lodash_1.keys)(filterRefAlias)).length === 0, 'filter中的#node结点定义有重复');
772
+ (0, lodash_1.assign)(refAlias, filterRefAlias);
773
+ var projText = this.translateProjection(entity, data, aliasDict, projectionRefAlias).projText;
774
+ var _b = this.translateFilter(entity, selection, aliasDict, refAlias, currentNumber, extraWhere, option), filterText = _b.stmt, currentNumber2 = _b.currentNumber;
775
+ var sorterText = sorter && this.translateSorter(entity, sorter, aliasDict);
776
+ return {
777
+ stmt: this.populateSelectStmt(projText, fromText, aliasDict, filterText, sorterText, undefined, indexFrom, count, option, selection),
778
+ currentNumber: currentNumber2,
779
+ };
780
+ };
781
+ SqlTranslator.prototype.translateSelect = function (entity, selection, option) {
782
+ var stmt = this.translateSelectInner(entity, selection, 1, {}, option).stmt;
783
+ return stmt;
784
+ };
785
+ SqlTranslator.prototype.translateAggregate = function (entity, aggregation, option) {
786
+ var data = aggregation.data, filter = aggregation.filter, sorter = aggregation.sorter, indexFrom = aggregation.indexFrom, count = aggregation.count;
787
+ var _a = this.analyzeJoin(entity, {
788
+ aggregation: data,
789
+ filter: filter,
790
+ sorter: sorter,
791
+ }, 1), fromText = _a.from, aliasDict = _a.aliasDict, projectionRefAlias = _a.projectionRefAlias, extraWhere = _a.extraWhere, filterRefAlias = _a.filterRefAlias, currentNumber = _a.currentNumber;
792
+ var projText = '';
793
+ var groupByText = '';
794
+ for (var k in data) {
795
+ if (k === '#aggr') {
796
+ var _b = this.translateProjection(entity, data[k], aliasDict, projectionRefAlias, '#data'), projSubText = _b.projText, as = _b.as;
797
+ if (!projText) {
798
+ projText = projSubText;
799
+ }
800
+ else {
801
+ projText += ", ".concat(projSubText);
802
+ }
803
+ groupByText = as;
804
+ }
805
+ else {
806
+ var projSubText = this.translateProjection(entity, data[k], aliasDict, projectionRefAlias, undefined, true).projText;
807
+ var projSubText2 = '';
808
+ if (k.startsWith('#max')) {
809
+ projSubText2 = "max(".concat(projSubText, ") as `").concat(k, "`");
810
+ }
811
+ else if (k.startsWith('#min')) {
812
+ projSubText2 = "min(".concat(projSubText, ") as `").concat(k, "`");
813
+ }
814
+ else if (k.startsWith('#count')) {
815
+ projSubText2 = "count(".concat(projSubText, ") as `").concat(k, "`");
816
+ }
817
+ else if (k.startsWith('#sum')) {
818
+ projSubText2 = "sum(".concat(projSubText, ") as `").concat(k, "`");
819
+ }
820
+ else {
821
+ (0, assert_1.default)(k.startsWith('#avg'));
822
+ projSubText2 = "avg(".concat(projSubText, ") as `").concat(k, "`");
823
+ }
824
+ if (!projText) {
825
+ projText = projSubText2;
826
+ }
827
+ else {
828
+ projText += ", ".concat(projSubText2);
829
+ }
830
+ }
831
+ }
832
+ var filterText = this.translateFilter(entity, aggregation, aliasDict, {}, currentNumber, extraWhere, option).stmt;
833
+ var sorterText = sorter && this.translateSorter(entity, sorter, aliasDict);
834
+ return this.populateSelectStmt(projText, fromText, aliasDict, filterText, sorterText, groupByText, indexFrom, count, option, undefined, aggregation);
835
+ };
836
+ SqlTranslator.prototype.translateCount = function (entity, selection, option) {
837
+ var filter = selection.filter, count = selection.count;
838
+ var _a = this.analyzeJoin(entity, {
839
+ filter: filter,
840
+ }), fromText = _a.from, aliasDict = _a.aliasDict, extraWhere = _a.extraWhere, filterRefAlias = _a.filterRefAlias, currentNumber = _a.currentNumber;
841
+ var projText = 'count(1) cnt';
842
+ var filterText = this.translateFilter(entity, selection, aliasDict, filterRefAlias, currentNumber, extraWhere, option).stmt;
843
+ if (count) {
844
+ var subQuerySql = this.populateSelectStmt('1', fromText, aliasDict, filterText, undefined, undefined, undefined, undefined, option, Object.assign({}, selection, { indexFrom: 0, count: count }));
845
+ return "select count(1) cnt from (".concat(subQuerySql, ") __tmp");
846
+ }
847
+ return this.populateSelectStmt(projText, fromText, aliasDict, filterText, undefined, undefined, undefined, undefined, option, selection);
848
+ };
849
+ SqlTranslator.prototype.translateRemove = function (entity, operation, option) {
850
+ var filter = operation.filter, sorter = operation.sorter, indexFrom = operation.indexFrom, count = operation.count;
851
+ (0, assert_1.default)(!sorter, '当前remove不支持sorter行为');
852
+ var _a = this.analyzeJoin(entity, { filter: filter, sorter: sorter }), aliasDict = _a.aliasDict, filterRefAlias = _a.filterRefAlias, extraWhere = _a.extraWhere, fromText = _a.from, currentNumber = _a.currentNumber;
853
+ var alias = aliasDict['./'];
854
+ var filterText = this.translateFilter(entity, operation, aliasDict, filterRefAlias, currentNumber, extraWhere, { includedDeleted: true }).stmt;
855
+ // const sorterText = sorter && sorter.length > 0 ? this.translateSorter(entity, sorter, aliasDict) : undefined;
856
+ return this.populateRemoveStmt(alias, fromText, aliasDict, filterText, /* sorterText */ undefined, indexFrom, count, option);
857
+ };
858
+ SqlTranslator.prototype.translateUpdate = function (entity, operation, option) {
859
+ var attributes = this.schema[entity].attributes;
860
+ var filter = operation.filter, sorter = operation.sorter, indexFrom = operation.indexFrom, count = operation.count, data = operation.data;
861
+ (0, assert_1.default)(!sorter, '当前update不支持sorter行为');
862
+ var _a = this.analyzeJoin(entity, { filter: filter, sorter: sorter }), aliasDict = _a.aliasDict, filterRefAlias = _a.filterRefAlias, extraWhere = _a.extraWhere, fromText = _a.from, currentNumber = _a.currentNumber;
863
+ var alias = aliasDict['./'];
864
+ var updateText = '';
865
+ for (var attr in data) {
866
+ if (updateText) {
867
+ updateText += ',';
868
+ }
869
+ (0, assert_1.default)(attributes.hasOwnProperty(attr));
870
+ var value = this.translateAttrValue(attributes[attr].type, data[attr]);
871
+ updateText += "`".concat(alias, "`.`").concat(attr, "` = ").concat(value);
872
+ }
873
+ var filterText = this.translateFilter(entity, operation, aliasDict, filterRefAlias, currentNumber, extraWhere).stmt;
874
+ // const sorterText = sorter && this.translateSorter(entity, sorter, aliasDict);
875
+ return this.populateUpdateStmt(updateText, fromText, aliasDict, filterText, /* sorterText */ undefined, indexFrom, count, option);
876
+ };
877
+ SqlTranslator.prototype.translateDestroyEntity = function (entity, truncate) {
878
+ var schema = this.schema;
879
+ var _a = schema[entity], _b = _a.storageName, storageName = _b === void 0 ? entity : _b, view = _a.view;
880
+ var sql;
881
+ if (view) {
882
+ sql = "drop view if exists `".concat(storageName, "`");
883
+ }
884
+ else {
885
+ sql = truncate ? "truncate table `".concat(storageName, "`") : "drop table if exists `".concat(storageName, "`");
886
+ }
887
+ return sql;
888
+ };
889
+ SqlTranslator.prototype.escapeStringValue = function (value) {
890
+ var result = "'".concat(value.replace(/'/g, '\\\''), "'");
891
+ return result;
892
+ };
893
+ return SqlTranslator;
894
+ }());
895
+ exports.SqlTranslator = SqlTranslator;