query-core 0.1.21 → 0.1.24
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/lib/SearchBuilder.js +74 -6
- package/lib/index.js +0 -1
- package/lib/services.js +170 -7
- package/package.json +1 -1
- package/src/SearchBuilder.ts +77 -10
- package/src/index.ts +1 -1
- package/src/search.ts +6 -6
- package/src/services.ts +174 -6
package/lib/SearchBuilder.js
CHANGED
|
@@ -1,4 +1,17 @@
|
|
|
1
1
|
"use strict";
|
|
2
|
+
var __extends = (this && this.__extends) || (function () {
|
|
3
|
+
var extendStatics = function (d, b) {
|
|
4
|
+
extendStatics = Object.setPrototypeOf ||
|
|
5
|
+
({ __proto__: [] } instanceof Array && function (d, b) { d.__proto__ = b; }) ||
|
|
6
|
+
function (d, b) { for (var p in b) if (b.hasOwnProperty(p)) d[p] = b[p]; };
|
|
7
|
+
return extendStatics(d, b);
|
|
8
|
+
};
|
|
9
|
+
return function (d, b) {
|
|
10
|
+
extendStatics(d, b);
|
|
11
|
+
function __() { this.constructor = d; }
|
|
12
|
+
d.prototype = b === null ? Object.create(b) : (__.prototype = b.prototype, new __());
|
|
13
|
+
};
|
|
14
|
+
})();
|
|
2
15
|
Object.defineProperty(exports, "__esModule", { value: true });
|
|
3
16
|
var build_1 = require("./build");
|
|
4
17
|
var query_1 = require("./query");
|
|
@@ -27,20 +40,20 @@ var SearchBuilder = (function () {
|
|
|
27
40
|
this.excluding = (excluding && excluding.length > 0 ? excluding : 'excluding');
|
|
28
41
|
this.search = this.search.bind(this);
|
|
29
42
|
if (buildParam) {
|
|
30
|
-
this.
|
|
43
|
+
this.param = buildParam;
|
|
31
44
|
}
|
|
32
45
|
else {
|
|
33
46
|
if (provider === search_1.oracle) {
|
|
34
|
-
this.
|
|
47
|
+
this.param = query_1.buildOracleParam;
|
|
35
48
|
}
|
|
36
49
|
else if (provider === exports.postgres) {
|
|
37
|
-
this.
|
|
50
|
+
this.param = query_1.buildDollarParam;
|
|
38
51
|
}
|
|
39
52
|
else if (provider === exports.mssql) {
|
|
40
|
-
this.
|
|
53
|
+
this.param = query_1.buildMsSQLParam;
|
|
41
54
|
}
|
|
42
55
|
else {
|
|
43
|
-
this.
|
|
56
|
+
this.param = build_1.param;
|
|
44
57
|
}
|
|
45
58
|
}
|
|
46
59
|
this.total = (total && total.length > 0 ? total : 'total');
|
|
@@ -53,7 +66,7 @@ var SearchBuilder = (function () {
|
|
|
53
66
|
var st = (this.sort ? this.sort : 'sort');
|
|
54
67
|
var sn = s[st];
|
|
55
68
|
delete s[st];
|
|
56
|
-
var x = (this.provider === exports.postgres ? 'ilike' : this.
|
|
69
|
+
var x = (this.provider === exports.postgres ? 'ilike' : this.param);
|
|
57
70
|
var q2 = this.buildQuery(s, x, sn, this.buildSort, this.attributes, this.table, fields, this.q, this.excluding);
|
|
58
71
|
if (!q2) {
|
|
59
72
|
throw new Error('Cannot build query');
|
|
@@ -77,3 +90,58 @@ var SearchBuilder = (function () {
|
|
|
77
90
|
return SearchBuilder;
|
|
78
91
|
}());
|
|
79
92
|
exports.SearchBuilder = SearchBuilder;
|
|
93
|
+
var Query = (function (_super) {
|
|
94
|
+
__extends(Query, _super);
|
|
95
|
+
function Query(query, table, attributes, provider, buildQ, fromDB, sort, q, excluding, buildSort, buildParam, total) {
|
|
96
|
+
var _this = _super.call(this, query, table, attributes, provider, buildQ, fromDB, sort, q, excluding, buildSort, buildParam, total) || this;
|
|
97
|
+
var m = build_1.metadata(attributes);
|
|
98
|
+
_this.primaryKeys = m.keys;
|
|
99
|
+
_this.map = m.map;
|
|
100
|
+
_this.bools = m.bools;
|
|
101
|
+
if (_this.metadata) {
|
|
102
|
+
_this.metadata = _this.metadata.bind(_this);
|
|
103
|
+
}
|
|
104
|
+
_this.all = _this.all.bind(_this);
|
|
105
|
+
_this.load = _this.load.bind(_this);
|
|
106
|
+
_this.exist = _this.exist.bind(_this);
|
|
107
|
+
return _this;
|
|
108
|
+
}
|
|
109
|
+
Query.prototype.metadata = function () {
|
|
110
|
+
return this.attributes;
|
|
111
|
+
};
|
|
112
|
+
Query.prototype.all = function () {
|
|
113
|
+
var sql = "select * from " + this.table;
|
|
114
|
+
return this.query(sql, [], this.map);
|
|
115
|
+
};
|
|
116
|
+
Query.prototype.load = function (id, ctx) {
|
|
117
|
+
var stmt = build_1.select(id, this.table, this.primaryKeys, this.param);
|
|
118
|
+
if (!stmt) {
|
|
119
|
+
throw new Error('cannot build query by id');
|
|
120
|
+
}
|
|
121
|
+
var fn = this.fromDB;
|
|
122
|
+
if (fn) {
|
|
123
|
+
return this.query(stmt.query, stmt.params, this.map, ctx).then(function (res) {
|
|
124
|
+
if (!res || res.length === 0) {
|
|
125
|
+
return null;
|
|
126
|
+
}
|
|
127
|
+
else {
|
|
128
|
+
var obj = res[0];
|
|
129
|
+
return fn(obj);
|
|
130
|
+
}
|
|
131
|
+
});
|
|
132
|
+
}
|
|
133
|
+
else {
|
|
134
|
+
return this.query(stmt.query, stmt.params, this.map).then(function (res) { return (!res || res.length === 0) ? null : res[0]; });
|
|
135
|
+
}
|
|
136
|
+
};
|
|
137
|
+
Query.prototype.exist = function (id, ctx) {
|
|
138
|
+
var field = (this.primaryKeys[0].column ? this.primaryKeys[0].column : this.primaryKeys[0].name);
|
|
139
|
+
var stmt = build_1.exist(id, this.table, this.primaryKeys, this.param, field);
|
|
140
|
+
if (!stmt) {
|
|
141
|
+
throw new Error('cannot build query by id');
|
|
142
|
+
}
|
|
143
|
+
return this.query(stmt.query, stmt.params, this.map, undefined, ctx).then(function (res) { return (!res || res.length === 0) ? false : true; });
|
|
144
|
+
};
|
|
145
|
+
return Query;
|
|
146
|
+
}(SearchBuilder));
|
|
147
|
+
exports.Query = Query;
|
package/lib/index.js
CHANGED
|
@@ -6,7 +6,6 @@ Object.defineProperty(exports, "__esModule", { value: true });
|
|
|
6
6
|
var health_1 = require("./health");
|
|
7
7
|
exports.SqlChecker = health_1.Checker;
|
|
8
8
|
var services_1 = require("./services");
|
|
9
|
-
exports.SqlLoadRepository = services_1.SqlLoader;
|
|
10
9
|
exports.SqlViewRepository = services_1.SqlLoader;
|
|
11
10
|
exports.SqlLoadService = services_1.SqlLoader;
|
|
12
11
|
exports.SqlViewService = services_1.SqlLoader;
|
package/lib/services.js
CHANGED
|
@@ -14,16 +14,16 @@ var __extends = (this && this.__extends) || (function () {
|
|
|
14
14
|
})();
|
|
15
15
|
Object.defineProperty(exports, "__esModule", { value: true });
|
|
16
16
|
var build_1 = require("./build");
|
|
17
|
-
function useGet(
|
|
18
|
-
var l = new SqlLoader(
|
|
17
|
+
function useGet(q, table, attrs, param, fromDB) {
|
|
18
|
+
var l = new SqlLoader(q, table, attrs, param, fromDB);
|
|
19
19
|
return l.load;
|
|
20
20
|
}
|
|
21
21
|
exports.useGet = useGet;
|
|
22
22
|
exports.useLoad = useGet;
|
|
23
23
|
var SqlLoader = (function () {
|
|
24
|
-
function SqlLoader(
|
|
25
|
-
this.table = table;
|
|
24
|
+
function SqlLoader(query, table, attrs, param, fromDB) {
|
|
26
25
|
this.query = query;
|
|
26
|
+
this.table = table;
|
|
27
27
|
this.param = param;
|
|
28
28
|
this.fromDB = fromDB;
|
|
29
29
|
if (Array.isArray(attrs)) {
|
|
@@ -83,10 +83,173 @@ var SqlLoader = (function () {
|
|
|
83
83
|
return SqlLoader;
|
|
84
84
|
}());
|
|
85
85
|
exports.SqlLoader = SqlLoader;
|
|
86
|
+
var QueryRepository = (function () {
|
|
87
|
+
function QueryRepository(db, table, attrs, sort, id) {
|
|
88
|
+
this.db = db;
|
|
89
|
+
this.table = table;
|
|
90
|
+
this.attrs = attrs;
|
|
91
|
+
this.sort = sort;
|
|
92
|
+
this.id = (id && id.length > 0 ? id : 'id');
|
|
93
|
+
this.query = this.query.bind(this);
|
|
94
|
+
var m = build_1.metadata(attrs);
|
|
95
|
+
this.map = m.map;
|
|
96
|
+
this.bools = m.bools;
|
|
97
|
+
}
|
|
98
|
+
QueryRepository.prototype.query = function (ids) {
|
|
99
|
+
if (!ids || ids.length === 0) {
|
|
100
|
+
return Promise.resolve([]);
|
|
101
|
+
}
|
|
102
|
+
var ps = [];
|
|
103
|
+
for (var i = 1; i <= length; i++) {
|
|
104
|
+
ps.push(this.db.param(i));
|
|
105
|
+
}
|
|
106
|
+
var sql = "select * from " + this.table + " where " + this.id + " in (" + ps.join(',') + ")";
|
|
107
|
+
if (this.sort && this.sort.length > 0) {
|
|
108
|
+
sql = sql + ' order by ' + this.sort;
|
|
109
|
+
}
|
|
110
|
+
return this.db.query(sql, ids, this.map, this.bools);
|
|
111
|
+
};
|
|
112
|
+
return QueryRepository;
|
|
113
|
+
}());
|
|
114
|
+
exports.QueryRepository = QueryRepository;
|
|
115
|
+
var SqlLoadRepository = (function () {
|
|
116
|
+
function SqlLoadRepository(query, table, attrs, param, id1Field, id2Field, fromDB, id1Col, id2Col) {
|
|
117
|
+
this.query = query;
|
|
118
|
+
this.table = table;
|
|
119
|
+
this.param = param;
|
|
120
|
+
this.id1Field = id1Field;
|
|
121
|
+
this.id2Field = id2Field;
|
|
122
|
+
this.fromDB = fromDB;
|
|
123
|
+
var m = build_1.metadata(attrs);
|
|
124
|
+
this.attributes = attrs;
|
|
125
|
+
this.map = m.map;
|
|
126
|
+
this.bools = m.bools;
|
|
127
|
+
if (this.metadata) {
|
|
128
|
+
this.metadata = this.metadata.bind(this);
|
|
129
|
+
}
|
|
130
|
+
this.all = this.all.bind(this);
|
|
131
|
+
this.load = this.load.bind(this);
|
|
132
|
+
this.exist = this.exist.bind(this);
|
|
133
|
+
if (id1Col && id1Col.length > 0) {
|
|
134
|
+
this.id1Col = id1Col;
|
|
135
|
+
}
|
|
136
|
+
else {
|
|
137
|
+
var c = attrs[this.id1Field];
|
|
138
|
+
if (c) {
|
|
139
|
+
this.id1Col = (c.column && c.column.length > 0 ? c.column : this.id1Field);
|
|
140
|
+
}
|
|
141
|
+
else {
|
|
142
|
+
this.id1Col = this.id1Field;
|
|
143
|
+
}
|
|
144
|
+
}
|
|
145
|
+
if (id2Col && id2Col.length > 0) {
|
|
146
|
+
this.id2Col = id2Col;
|
|
147
|
+
}
|
|
148
|
+
else {
|
|
149
|
+
var c = attrs[this.id2Field];
|
|
150
|
+
if (c) {
|
|
151
|
+
this.id2Col = (c.column && c.column.length > 0 ? c.column : this.id2Field);
|
|
152
|
+
}
|
|
153
|
+
else {
|
|
154
|
+
this.id2Col = this.id2Field;
|
|
155
|
+
}
|
|
156
|
+
}
|
|
157
|
+
}
|
|
158
|
+
SqlLoadRepository.prototype.metadata = function () {
|
|
159
|
+
return this.attributes;
|
|
160
|
+
};
|
|
161
|
+
SqlLoadRepository.prototype.all = function () {
|
|
162
|
+
var sql = "select * from " + this.table;
|
|
163
|
+
return this.query(sql, [], this.map);
|
|
164
|
+
};
|
|
165
|
+
SqlLoadRepository.prototype.load = function (id1, id2, ctx) {
|
|
166
|
+
var _this = this;
|
|
167
|
+
return this.query("select * from " + this.table + " where " + this.id1Col + " = " + this.param(1) + " and " + this.id2Col + " = " + this.param(2), [id1, id2], this.map, undefined, ctx).then(function (objs) {
|
|
168
|
+
if (!objs || objs.length === 0) {
|
|
169
|
+
return null;
|
|
170
|
+
}
|
|
171
|
+
else {
|
|
172
|
+
var fn = _this.fromDB;
|
|
173
|
+
if (fn) {
|
|
174
|
+
return fn(objs[0]);
|
|
175
|
+
}
|
|
176
|
+
else {
|
|
177
|
+
return objs[0];
|
|
178
|
+
}
|
|
179
|
+
}
|
|
180
|
+
});
|
|
181
|
+
};
|
|
182
|
+
SqlLoadRepository.prototype.exist = function (id1, id2, ctx) {
|
|
183
|
+
return this.query("select " + this.id1Col + " from " + this.table + " where " + this.id1Col + " = " + this.param(1) + " and " + this.id2Col + " = " + this.param(2), [id1, id2], undefined, undefined, ctx).then(function (objs) {
|
|
184
|
+
return (objs && objs.length > 0 ? true : false);
|
|
185
|
+
});
|
|
186
|
+
};
|
|
187
|
+
return SqlLoadRepository;
|
|
188
|
+
}());
|
|
189
|
+
exports.SqlLoadRepository = SqlLoadRepository;
|
|
190
|
+
var GenericRepository = (function (_super) {
|
|
191
|
+
__extends(GenericRepository, _super);
|
|
192
|
+
function GenericRepository(manager, table, attrs, id1Field, id2Field, toDB, fromDB, id1Col, id2Col) {
|
|
193
|
+
var _this = _super.call(this, manager.query, table, attrs, manager.param, id1Field, id2Field, fromDB, id1Col, id2Col) || this;
|
|
194
|
+
_this.toDB = toDB;
|
|
195
|
+
var x = build_1.version(attrs);
|
|
196
|
+
_this.exec = manager.exec;
|
|
197
|
+
_this.execBatch = manager.execBatch;
|
|
198
|
+
if (x) {
|
|
199
|
+
_this.version = x.name;
|
|
200
|
+
}
|
|
201
|
+
_this.insert = _this.insert.bind(_this);
|
|
202
|
+
_this.update = _this.update.bind(_this);
|
|
203
|
+
_this.patch = _this.patch.bind(_this);
|
|
204
|
+
_this.delete = _this.delete.bind(_this);
|
|
205
|
+
return _this;
|
|
206
|
+
}
|
|
207
|
+
GenericRepository.prototype.insert = function (obj, ctx) {
|
|
208
|
+
var obj2 = obj;
|
|
209
|
+
if (this.toDB) {
|
|
210
|
+
obj2 = this.toDB(obj);
|
|
211
|
+
}
|
|
212
|
+
var stmt = build_1.buildToInsert(obj2, this.table, this.attributes, this.param, this.version);
|
|
213
|
+
if (stmt) {
|
|
214
|
+
return this.exec(stmt.query, stmt.params, ctx).catch(function (err) {
|
|
215
|
+
if (err && err.error === 'duplicate') {
|
|
216
|
+
return 0;
|
|
217
|
+
}
|
|
218
|
+
else {
|
|
219
|
+
throw err;
|
|
220
|
+
}
|
|
221
|
+
});
|
|
222
|
+
}
|
|
223
|
+
else {
|
|
224
|
+
return Promise.resolve(0);
|
|
225
|
+
}
|
|
226
|
+
};
|
|
227
|
+
GenericRepository.prototype.update = function (obj, ctx) {
|
|
228
|
+
var obj2 = obj;
|
|
229
|
+
if (this.toDB) {
|
|
230
|
+
obj2 = this.toDB(obj);
|
|
231
|
+
}
|
|
232
|
+
var stmt = build_1.buildToUpdate(obj2, this.table, this.attributes, this.param, this.version);
|
|
233
|
+
if (stmt) {
|
|
234
|
+
return this.exec(stmt.query, stmt.params, ctx);
|
|
235
|
+
}
|
|
236
|
+
else {
|
|
237
|
+
return Promise.resolve(0);
|
|
238
|
+
}
|
|
239
|
+
};
|
|
240
|
+
GenericRepository.prototype.patch = function (obj, ctx) {
|
|
241
|
+
return this.update(obj, ctx);
|
|
242
|
+
};
|
|
243
|
+
GenericRepository.prototype.delete = function (id1, id2, ctx) {
|
|
244
|
+
return this.exec("delete from " + this.table + " where " + this.id1Col + " = " + this.param(1) + " and " + this.id2Col + " = " + this.param(2), [id1, id2], ctx);
|
|
245
|
+
};
|
|
246
|
+
return GenericRepository;
|
|
247
|
+
}(SqlLoadRepository));
|
|
248
|
+
exports.GenericRepository = GenericRepository;
|
|
86
249
|
var SqlSearchLoader = (function (_super) {
|
|
87
250
|
__extends(SqlSearchLoader, _super);
|
|
88
|
-
function SqlSearchLoader(find,
|
|
89
|
-
var _this = _super.call(this,
|
|
251
|
+
function SqlSearchLoader(find, query, table, attrs, param, fromDB) {
|
|
252
|
+
var _this = _super.call(this, query, table, attrs, param, fromDB) || this;
|
|
90
253
|
_this.find = find;
|
|
91
254
|
_this.search = _this.search.bind(_this);
|
|
92
255
|
return _this;
|
|
@@ -374,7 +537,7 @@ exports.diff = diff;
|
|
|
374
537
|
var SqlWriter = (function (_super) {
|
|
375
538
|
__extends(SqlWriter, _super);
|
|
376
539
|
function SqlWriter(manager, table, attrs, toDB, fromDB) {
|
|
377
|
-
var _this = _super.call(this,
|
|
540
|
+
var _this = _super.call(this, manager.query, table, attrs, manager.param, fromDB) || this;
|
|
378
541
|
_this.toDB = toDB;
|
|
379
542
|
var x = build_1.version(attrs);
|
|
380
543
|
_this.exec = manager.exec;
|
package/package.json
CHANGED
package/src/SearchBuilder.ts
CHANGED
|
@@ -1,4 +1,4 @@
|
|
|
1
|
-
import {metadata, param} from './build';
|
|
1
|
+
import {exist, metadata, param, select} from './build';
|
|
2
2
|
import {Attribute, Attributes, Statement, StringMap} from './metadata';
|
|
3
3
|
import {buildDollarParam, buildMsSQLParam, buildOracleParam, buildQuery, buildSort as bs, LikeType} from './query';
|
|
4
4
|
import {buildFromQuery, oracle, SearchResult} from './search';
|
|
@@ -14,9 +14,10 @@ export class SearchBuilder<T, S> {
|
|
|
14
14
|
q?: string;
|
|
15
15
|
excluding?: string;
|
|
16
16
|
buildSort?: (sort?: string, map?: Attributes|StringMap) => string;
|
|
17
|
-
|
|
17
|
+
param: (i: number) => string;
|
|
18
18
|
total?: string;
|
|
19
|
-
constructor(public query: (sql: string, args?: any[], m?: StringMap, bools?: Attribute[]) => Promise<
|
|
19
|
+
constructor(public query: <K>(sql: string, args?: any[], m?: StringMap, bools?: Attribute[], ctx?: any) => Promise<K[]>,
|
|
20
|
+
public table: string,
|
|
20
21
|
public attributes?: Attributes,
|
|
21
22
|
public provider?: string,
|
|
22
23
|
buildQ?: (s: S, bparam: LikeType|((i: number ) => string), sort?: string, buildSort3?: (sort?: string, map?: Attributes|StringMap) => string, attrs?: Attributes, table?: string, fields?: string[], sq?: string, strExcluding?: string) => Statement|undefined,
|
|
@@ -39,16 +40,16 @@ export class SearchBuilder<T, S> {
|
|
|
39
40
|
this.excluding = (excluding && excluding.length > 0 ? excluding : 'excluding');
|
|
40
41
|
this.search = this.search.bind(this);
|
|
41
42
|
if (buildParam) {
|
|
42
|
-
this.
|
|
43
|
+
this.param = buildParam;
|
|
43
44
|
} else {
|
|
44
45
|
if (provider === oracle) {
|
|
45
|
-
this.
|
|
46
|
+
this.param = buildOracleParam;
|
|
46
47
|
} else if (provider === postgres) {
|
|
47
|
-
this.
|
|
48
|
+
this.param = buildDollarParam;
|
|
48
49
|
} else if (provider === mssql) {
|
|
49
|
-
this.
|
|
50
|
+
this.param = buildMsSQLParam;
|
|
50
51
|
} else {
|
|
51
|
-
this.
|
|
52
|
+
this.param = param;
|
|
52
53
|
}
|
|
53
54
|
}
|
|
54
55
|
this.total = (total && total.length > 0 ? total : 'total');
|
|
@@ -61,14 +62,14 @@ export class SearchBuilder<T, S> {
|
|
|
61
62
|
const st = (this.sort ? this.sort : 'sort');
|
|
62
63
|
const sn = (s as any)[st] as string;
|
|
63
64
|
delete (s as any)[st];
|
|
64
|
-
const x = (this.provider === postgres ? 'ilike' : this.
|
|
65
|
+
const x = (this.provider === postgres ? 'ilike' : this.param);
|
|
65
66
|
const q2 = this.buildQuery(s, x, sn, this.buildSort, this.attributes, this.table, fields, this.q, this.excluding);
|
|
66
67
|
if (!q2) {
|
|
67
68
|
throw new Error('Cannot build query');
|
|
68
69
|
}
|
|
69
70
|
const fn = this.fromDB;
|
|
70
71
|
if (fn) {
|
|
71
|
-
return buildFromQuery(this.query, q2.query, q2.params, limit, skip, this.map, this.bools, this.provider, this.total).then(r => {
|
|
72
|
+
return buildFromQuery<T>(this.query, q2.query, q2.params, limit, skip, this.map, this.bools, this.provider, this.total).then(r => {
|
|
72
73
|
if (r.list && r.list.length > 0) {
|
|
73
74
|
r.list = r.list.map(o => fn(o));
|
|
74
75
|
return r;
|
|
@@ -81,3 +82,69 @@ export class SearchBuilder<T, S> {
|
|
|
81
82
|
}
|
|
82
83
|
}
|
|
83
84
|
}
|
|
85
|
+
// tslint:disable-next-line:max-classes-per-file
|
|
86
|
+
export class Query<T, ID, S> extends SearchBuilder<T, S> {
|
|
87
|
+
primaryKeys: Attribute[];
|
|
88
|
+
map?: StringMap;
|
|
89
|
+
// attributes: Attributes;
|
|
90
|
+
bools?: Attribute[];
|
|
91
|
+
constructor(
|
|
92
|
+
query: <K>(sql: string, args?: any[], m?: StringMap, bools?: Attribute[], ctx?: any) => Promise<K[]>,
|
|
93
|
+
table: string,
|
|
94
|
+
attributes: Attributes,
|
|
95
|
+
provider?: string,
|
|
96
|
+
buildQ?: (s: S, bparam: LikeType|((i: number ) => string), sort?: string, buildSort3?: (sort?: string, map?: Attributes|StringMap) => string, attrs?: Attributes, table?: string, fields?: string[], sq?: string, strExcluding?: string) => Statement|undefined,
|
|
97
|
+
fromDB?: (v: T) => T,
|
|
98
|
+
sort?: string,
|
|
99
|
+
q?: string,
|
|
100
|
+
excluding?: string,
|
|
101
|
+
buildSort?: (sort?: string, map?: Attributes|StringMap) => string,
|
|
102
|
+
buildParam?: (i: number) => string,
|
|
103
|
+
total?: string) {
|
|
104
|
+
super(query, table, attributes, provider, buildQ, fromDB, sort, q, excluding, buildSort, buildParam, total);
|
|
105
|
+
const m = metadata(attributes);
|
|
106
|
+
this.primaryKeys = m.keys;
|
|
107
|
+
this.map = m.map;
|
|
108
|
+
this.bools = m.bools;
|
|
109
|
+
if (this.metadata) {
|
|
110
|
+
this.metadata = this.metadata.bind(this);
|
|
111
|
+
}
|
|
112
|
+
this.all = this.all.bind(this);
|
|
113
|
+
this.load = this.load.bind(this);
|
|
114
|
+
this.exist = this.exist.bind(this);
|
|
115
|
+
}
|
|
116
|
+
metadata?(): Attributes|undefined {
|
|
117
|
+
return this.attributes;
|
|
118
|
+
}
|
|
119
|
+
all(): Promise<T[]> {
|
|
120
|
+
const sql = `select * from ${this.table}`;
|
|
121
|
+
return this.query(sql, [], this.map);
|
|
122
|
+
}
|
|
123
|
+
load(id: ID, ctx?: any): Promise<T|null> {
|
|
124
|
+
const stmt = select<ID>(id, this.table, this.primaryKeys, this.param);
|
|
125
|
+
if (!stmt) {
|
|
126
|
+
throw new Error('cannot build query by id');
|
|
127
|
+
}
|
|
128
|
+
const fn = this.fromDB;
|
|
129
|
+
if (fn) {
|
|
130
|
+
return this.query<T>(stmt.query, stmt.params, this.map, ctx).then(res => {
|
|
131
|
+
if (!res || res.length === 0) {
|
|
132
|
+
return null;
|
|
133
|
+
} else {
|
|
134
|
+
const obj = res[0];
|
|
135
|
+
return fn(obj);
|
|
136
|
+
}
|
|
137
|
+
});
|
|
138
|
+
} else {
|
|
139
|
+
return this.query<T>(stmt.query, stmt.params, this.map).then(res => (!res || res.length === 0) ? null : res[0]);
|
|
140
|
+
}
|
|
141
|
+
}
|
|
142
|
+
exist(id: ID, ctx?: any): Promise<boolean> {
|
|
143
|
+
const field = (this.primaryKeys[0].column ? this.primaryKeys[0].column : this.primaryKeys[0].name);
|
|
144
|
+
const stmt = exist<ID>(id, this.table, this.primaryKeys, this.param, field);
|
|
145
|
+
if (!stmt) {
|
|
146
|
+
throw new Error('cannot build query by id');
|
|
147
|
+
}
|
|
148
|
+
return this.query(stmt.query, stmt.params, this.map, undefined, ctx).then(res => (!res || res.length === 0) ? false : true);
|
|
149
|
+
}
|
|
150
|
+
}
|
package/src/index.ts
CHANGED
|
@@ -3,7 +3,7 @@ export {Checker as SqlChecker};
|
|
|
3
3
|
|
|
4
4
|
import {Attribute, StringMap} from './metadata';
|
|
5
5
|
import {SqlLoader, SqlSearchLoader, SqlSearchWriter, SqlWriter} from './services';
|
|
6
|
-
export {SqlLoader as SqlLoadRepository};
|
|
6
|
+
// export {SqlLoader as SqlLoadRepository};
|
|
7
7
|
export {SqlLoader as SqlViewRepository};
|
|
8
8
|
export {SqlWriter as SqlGenericRepository};
|
|
9
9
|
export {SqlWriter as Repository};
|
package/src/search.ts
CHANGED
|
@@ -4,9 +4,9 @@ export interface SearchResult<T> {
|
|
|
4
4
|
list: T[];
|
|
5
5
|
total?: number;
|
|
6
6
|
}
|
|
7
|
-
export function buildFromQuery<T>(query: (sql: string, args?: any[], m?: StringMap, bools?: Attribute[]) => Promise<
|
|
7
|
+
export function buildFromQuery<T>(query: <K>(sql: string, args?: any[], m?: StringMap, bools?: Attribute[]) => Promise<K[]>, sql: string, params?: any[], limit?: number, offset?: number, mp?: StringMap, bools?: Attribute[], provider?: string, totalCol?: string): Promise<SearchResult<T>> {
|
|
8
8
|
if (!limit || limit <= 0) {
|
|
9
|
-
return query(sql, params, mp, bools).then(list => {
|
|
9
|
+
return query<T>(sql, params, mp, bools).then(list => {
|
|
10
10
|
const total = (list ? list.length : undefined);
|
|
11
11
|
return {list, total};
|
|
12
12
|
});
|
|
@@ -20,8 +20,8 @@ export function buildFromQuery<T>(query: (sql: string, args?: any[], m?: StringM
|
|
|
20
20
|
} else {
|
|
21
21
|
const sql2 = buildPagingQuery(sql, limit, offset);
|
|
22
22
|
const countQuery = buildCountQuery(sql);
|
|
23
|
-
const resultPromise = query(sql2, params, mp, bools);
|
|
24
|
-
const countPromise = query(countQuery, params).then(r => {
|
|
23
|
+
const resultPromise = query<T>(sql2, params, mp, bools);
|
|
24
|
+
const countPromise = query<T>(countQuery, params).then(r => {
|
|
25
25
|
if (!r || r.length === 0) {
|
|
26
26
|
return 0;
|
|
27
27
|
} else {
|
|
@@ -37,11 +37,11 @@ export function buildFromQuery<T>(query: (sql: string, args?: any[], m?: StringM
|
|
|
37
37
|
}
|
|
38
38
|
}
|
|
39
39
|
}
|
|
40
|
-
export function queryAndCount<T>(query: (sql: string, args?: any[], m?: StringMap, bools?: Attribute[]) => Promise<
|
|
40
|
+
export function queryAndCount<T>(query: <K>(sql: string, args?: any[], m?: StringMap, bools?: Attribute[]) => Promise<K[]>, sql: string, params: any[]|undefined, total: string, mp?: StringMap, bools?: Attribute[]): Promise<SearchResult<T>> {
|
|
41
41
|
if (!total || total.length === 0) {
|
|
42
42
|
total = 'total';
|
|
43
43
|
}
|
|
44
|
-
return query(sql, params, mp, bools).then(list => {
|
|
44
|
+
return query<T>(sql, params, mp, bools).then(list => {
|
|
45
45
|
if (!list || list.length === 0) {
|
|
46
46
|
return {list: [], total: 0};
|
|
47
47
|
}
|
package/src/services.ts
CHANGED
|
@@ -9,12 +9,13 @@ export interface Filter {
|
|
|
9
9
|
}
|
|
10
10
|
export type Load<T, ID> = (id: ID, ctx?: any) => Promise<T|null>;
|
|
11
11
|
export type Get<T, ID> = Load<T, ID>;
|
|
12
|
-
export function useGet<T, ID>(
|
|
12
|
+
export function useGet<T, ID>(
|
|
13
13
|
q: <K>(sql: string, args?: any[], m?: StringMap, bools?: Attribute[], ctx?: any) => Promise<K[]>,
|
|
14
|
+
table: string,
|
|
14
15
|
attrs: Attributes|string[],
|
|
15
16
|
param: (i: number) => string,
|
|
16
17
|
fromDB?: (v: T) => T): Load<T, ID> {
|
|
17
|
-
const l = new SqlLoader<T, ID>(
|
|
18
|
+
const l = new SqlLoader<T, ID>(q, table, attrs, param, fromDB);
|
|
18
19
|
return l.load;
|
|
19
20
|
}
|
|
20
21
|
export const useLoad = useGet;
|
|
@@ -23,8 +24,9 @@ export class SqlLoader<T, ID> {
|
|
|
23
24
|
map?: StringMap;
|
|
24
25
|
attributes: Attributes;
|
|
25
26
|
bools?: Attribute[];
|
|
26
|
-
constructor(
|
|
27
|
+
constructor(
|
|
27
28
|
public query: <K>(sql: string, args?: any[], m?: StringMap, bools?: Attribute[], ctx?: any) => Promise<K[]>,
|
|
29
|
+
public table: string,
|
|
28
30
|
attrs: Attributes|string[],
|
|
29
31
|
public param: (i: number) => string,
|
|
30
32
|
public fromDB?: (v: T) => T) {
|
|
@@ -81,15 +83,181 @@ export class SqlLoader<T, ID> {
|
|
|
81
83
|
}
|
|
82
84
|
}
|
|
83
85
|
// tslint:disable-next-line:max-classes-per-file
|
|
86
|
+
export class QueryRepository<T, ID> {
|
|
87
|
+
constructor(public db: DB, public table: string, public attrs: Attributes, public sort?: string, id?: string) {
|
|
88
|
+
this.id = (id && id.length > 0 ? id : 'id');
|
|
89
|
+
this.query = this.query.bind(this);
|
|
90
|
+
const m = metadata(attrs);
|
|
91
|
+
this.map = m.map;
|
|
92
|
+
this.bools = m.bools;
|
|
93
|
+
}
|
|
94
|
+
id: string;
|
|
95
|
+
map?: StringMap;
|
|
96
|
+
bools?: Attribute[];
|
|
97
|
+
query(ids: ID[]): Promise<T[]> {
|
|
98
|
+
if (!ids || ids.length === 0) {
|
|
99
|
+
return Promise.resolve([]);
|
|
100
|
+
}
|
|
101
|
+
const ps: string[] = [];
|
|
102
|
+
for (let i = 1; i <= length; i++) {
|
|
103
|
+
ps.push(this.db.param(i));
|
|
104
|
+
}
|
|
105
|
+
let sql = `select * from ${this.table} where ${this.id} in (${ps.join(',')})`;
|
|
106
|
+
if (this.sort && this.sort.length > 0) {
|
|
107
|
+
sql = sql + ' order by ' + this.sort;
|
|
108
|
+
}
|
|
109
|
+
return this.db.query<T>(sql, ids, this.map, this.bools);
|
|
110
|
+
}
|
|
111
|
+
}
|
|
112
|
+
// tslint:disable-next-line:max-classes-per-file
|
|
113
|
+
export class SqlLoadRepository<T, K1, K2> {
|
|
114
|
+
map?: StringMap;
|
|
115
|
+
attributes: Attributes;
|
|
116
|
+
bools?: Attribute[];
|
|
117
|
+
id1Col: string;
|
|
118
|
+
id2Col: string;
|
|
119
|
+
constructor(
|
|
120
|
+
public query: <K>(sql: string, args?: any[], m?: StringMap, bools?: Attribute[], ctx?: any) => Promise<K[]>,
|
|
121
|
+
public table: string,
|
|
122
|
+
attrs: Attributes,
|
|
123
|
+
public param: (i: number) => string,
|
|
124
|
+
public id1Field: string,
|
|
125
|
+
public id2Field: string,
|
|
126
|
+
public fromDB?: (v: T) => T,
|
|
127
|
+
id1Col?: string,
|
|
128
|
+
id2Col?: string) {
|
|
129
|
+
|
|
130
|
+
const m = metadata(attrs);
|
|
131
|
+
this.attributes = attrs;
|
|
132
|
+
this.map = m.map;
|
|
133
|
+
this.bools = m.bools;
|
|
134
|
+
|
|
135
|
+
if (this.metadata) {
|
|
136
|
+
this.metadata = this.metadata.bind(this);
|
|
137
|
+
}
|
|
138
|
+
this.all = this.all.bind(this);
|
|
139
|
+
this.load = this.load.bind(this);
|
|
140
|
+
this.exist = this.exist.bind(this);
|
|
141
|
+
if (id1Col && id1Col.length > 0) {
|
|
142
|
+
this.id1Col = id1Col;
|
|
143
|
+
} else {
|
|
144
|
+
const c = attrs[this.id1Field];
|
|
145
|
+
if (c) {
|
|
146
|
+
this.id1Col = (c.column && c.column.length > 0 ? c.column : this.id1Field);
|
|
147
|
+
} else {
|
|
148
|
+
this.id1Col = this.id1Field;
|
|
149
|
+
}
|
|
150
|
+
}
|
|
151
|
+
if (id2Col && id2Col.length > 0) {
|
|
152
|
+
this.id2Col = id2Col;
|
|
153
|
+
} else {
|
|
154
|
+
const c = attrs[this.id2Field];
|
|
155
|
+
if (c) {
|
|
156
|
+
this.id2Col = (c.column && c.column.length > 0 ? c.column : this.id2Field);
|
|
157
|
+
} else {
|
|
158
|
+
this.id2Col = this.id2Field;
|
|
159
|
+
}
|
|
160
|
+
}
|
|
161
|
+
}
|
|
162
|
+
metadata?(): Attributes|undefined {
|
|
163
|
+
return this.attributes;
|
|
164
|
+
}
|
|
165
|
+
all(): Promise<T[]> {
|
|
166
|
+
const sql = `select * from ${this.table}`;
|
|
167
|
+
return this.query(sql, [], this.map);
|
|
168
|
+
}
|
|
169
|
+
load(id1: K1, id2: K2, ctx?: any): Promise<T|null> {
|
|
170
|
+
return this.query<T>(`select * from ${this.table} where ${this.id1Col} = ${this.param(1)} and ${this.id2Col} = ${this.param(2)}`, [id1, id2], this.map, undefined, ctx).then(objs => {
|
|
171
|
+
if (!objs || objs.length === 0) {
|
|
172
|
+
return null;
|
|
173
|
+
} else {
|
|
174
|
+
const fn = this.fromDB;
|
|
175
|
+
if (fn) {
|
|
176
|
+
return fn(objs[0]);
|
|
177
|
+
} else {
|
|
178
|
+
return objs[0];
|
|
179
|
+
}
|
|
180
|
+
}
|
|
181
|
+
});
|
|
182
|
+
}
|
|
183
|
+
exist(id1: K1, id2: K2, ctx?: any): Promise<boolean> {
|
|
184
|
+
return this.query<T>(`select ${this.id1Col} from ${this.table} where ${this.id1Col} = ${this.param(1)} and ${this.id2Col} = ${this.param(2)}`, [id1, id2], undefined, undefined, ctx).then(objs => {
|
|
185
|
+
return (objs && objs.length > 0 ? true : false);
|
|
186
|
+
});
|
|
187
|
+
}
|
|
188
|
+
}
|
|
189
|
+
// tslint:disable-next-line:max-classes-per-file
|
|
190
|
+
export class GenericRepository<T, K1, K2> extends SqlLoadRepository<T, K1, K2> {
|
|
191
|
+
version?: string;
|
|
192
|
+
exec: (sql: string, args?: any[], ctx?: any) => Promise<number>;
|
|
193
|
+
execBatch: (statements: Statement[], firstSuccess?: boolean, ctx?: any) => Promise<number>;
|
|
194
|
+
constructor(manager: Manager, table: string,
|
|
195
|
+
attrs: Attributes,
|
|
196
|
+
id1Field: string,
|
|
197
|
+
id2Field: string,
|
|
198
|
+
public toDB?: (v: T) => T,
|
|
199
|
+
fromDB?: (v: T) => T,
|
|
200
|
+
id1Col?: string,
|
|
201
|
+
id2Col?: string) {
|
|
202
|
+
super(manager.query, table, attrs, manager.param, id1Field, id2Field, fromDB, id1Col, id2Col);
|
|
203
|
+
const x = version(attrs);
|
|
204
|
+
this.exec = manager.exec;
|
|
205
|
+
this.execBatch = manager.execBatch;
|
|
206
|
+
if (x) {
|
|
207
|
+
this.version = x.name;
|
|
208
|
+
}
|
|
209
|
+
this.insert = this.insert.bind(this);
|
|
210
|
+
this.update = this.update.bind(this);
|
|
211
|
+
this.patch = this.patch.bind(this);
|
|
212
|
+
this.delete = this.delete.bind(this);
|
|
213
|
+
}
|
|
214
|
+
insert(obj: T, ctx?: any): Promise<number> {
|
|
215
|
+
let obj2 = obj;
|
|
216
|
+
if (this.toDB) {
|
|
217
|
+
obj2 = this.toDB(obj);
|
|
218
|
+
}
|
|
219
|
+
const stmt = buildToInsert(obj2, this.table, this.attributes, this.param, this.version);
|
|
220
|
+
if (stmt) {
|
|
221
|
+
return this.exec(stmt.query, stmt.params, ctx).catch(err => {
|
|
222
|
+
if (err && err.error === 'duplicate') {
|
|
223
|
+
return 0;
|
|
224
|
+
} else {
|
|
225
|
+
throw err;
|
|
226
|
+
}
|
|
227
|
+
});
|
|
228
|
+
} else {
|
|
229
|
+
return Promise.resolve(0);
|
|
230
|
+
}
|
|
231
|
+
}
|
|
232
|
+
update(obj: T, ctx?: any): Promise<number> {
|
|
233
|
+
let obj2 = obj;
|
|
234
|
+
if (this.toDB) {
|
|
235
|
+
obj2 = this.toDB(obj);
|
|
236
|
+
}
|
|
237
|
+
const stmt = buildToUpdate(obj2, this.table, this.attributes, this.param, this.version);
|
|
238
|
+
if (stmt) {
|
|
239
|
+
return this.exec(stmt.query, stmt.params, ctx);
|
|
240
|
+
} else {
|
|
241
|
+
return Promise.resolve(0);
|
|
242
|
+
}
|
|
243
|
+
}
|
|
244
|
+
patch(obj: Partial<T>, ctx?: any): Promise<number> {
|
|
245
|
+
return this.update(obj as any, ctx);
|
|
246
|
+
}
|
|
247
|
+
delete(id1: K1, id2: K2, ctx?: any): Promise<number> {
|
|
248
|
+
return this.exec(`delete from ${this.table} where ${this.id1Col} = ${this.param(1)} and ${this.id2Col} = ${this.param(2)}`, [id1, id2], ctx);
|
|
249
|
+
}
|
|
250
|
+
}
|
|
251
|
+
// tslint:disable-next-line:max-classes-per-file
|
|
84
252
|
export class SqlSearchLoader<T, ID, S extends Filter> extends SqlLoader<T, ID> {
|
|
85
253
|
constructor(
|
|
86
254
|
protected find: (s: S, limit?: number, offset?: number|string, fields?: string[]) => Promise<SearchResult<T>>,
|
|
87
|
-
table: string,
|
|
88
255
|
query: <K>(sql: string, args?: any[], m?: StringMap, bools?: Attribute[], ctx?: any) => Promise<K[]>,
|
|
256
|
+
table: string,
|
|
89
257
|
attrs: Attributes|string[],
|
|
90
258
|
param: (i: number) => string,
|
|
91
259
|
fromDB?: (v: T) => T) {
|
|
92
|
-
super(
|
|
260
|
+
super(query, table, attrs, param, fromDB);
|
|
93
261
|
this.search = this.search.bind(this);
|
|
94
262
|
}
|
|
95
263
|
search(s: S, limit?: number, offset?: number|string, fields?: string[]): Promise<SearchResult<T>> {
|
|
@@ -412,7 +580,7 @@ export class SqlWriter<T, ID> extends SqlLoader<T, ID> {
|
|
|
412
580
|
attrs: Attributes,
|
|
413
581
|
public toDB?: (v: T) => T,
|
|
414
582
|
fromDB?: (v: T) => T) {
|
|
415
|
-
super(
|
|
583
|
+
super(manager.query, table, attrs, manager.param, fromDB);
|
|
416
584
|
const x = version(attrs);
|
|
417
585
|
this.exec = manager.exec;
|
|
418
586
|
this.execBatch = manager.execBatch;
|