@asla/yoursql 0.2.0 → 0.3.1
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/dist/mod.d.ts +1 -0
- package/dist/mod.js +337 -92
- package/dist/select/TableQuery.d.ts +0 -1
- package/dist/select/select.d.ts +4 -2
- package/dist/sql_value/sql_value.d.ts +28 -8
- package/dist/your_table/checker.d.ts +13 -0
- package/dist/your_table/infer_db_type.d.ts +74 -0
- package/dist/your_table/mod.d.ts +4 -0
- package/dist/your_table/table.d.ts +16 -0
- package/package.json +2 -1
package/dist/mod.d.ts
CHANGED
package/dist/mod.js
CHANGED
|
@@ -55,7 +55,79 @@ function getObjectListKeys(objectList, keepUndefinedKey) {
|
|
|
55
55
|
return Array.from(keys);
|
|
56
56
|
}
|
|
57
57
|
|
|
58
|
-
|
|
58
|
+
/**
|
|
59
|
+
* 可选择项。可以是 table、查询结果等,它能被 select 语句选择
|
|
60
|
+
* @example
|
|
61
|
+
* ```ts
|
|
62
|
+
* declare const item: SqlSelectable<any>
|
|
63
|
+
* await query(`select * from ${item.toSelect()}`)
|
|
64
|
+
*
|
|
65
|
+
* ```
|
|
66
|
+
* @public
|
|
67
|
+
*/
|
|
68
|
+
class SqlSelectable {
|
|
69
|
+
constructor(columns) {
|
|
70
|
+
// Reflect.set(this, SQL_SELECTABLE, undefined);
|
|
71
|
+
let readonlyColumns;
|
|
72
|
+
if (typeof columns[Symbol.iterator] === "function") {
|
|
73
|
+
let iterable = columns;
|
|
74
|
+
readonlyColumns = [];
|
|
75
|
+
let iter = iterable[Symbol.iterator]();
|
|
76
|
+
let i = 0;
|
|
77
|
+
let item = iter.next();
|
|
78
|
+
while (!item.done) {
|
|
79
|
+
readonlyColumns[i++] = item.value;
|
|
80
|
+
item = iter.next();
|
|
81
|
+
}
|
|
82
|
+
// readonlyColumns.length = i;
|
|
83
|
+
}
|
|
84
|
+
else {
|
|
85
|
+
let arrayLike = columns;
|
|
86
|
+
readonlyColumns = new Array(arrayLike.length);
|
|
87
|
+
// readonlyColumns.length = arrayLike.length;
|
|
88
|
+
for (let i = 0; i < arrayLike.length; i++) {
|
|
89
|
+
readonlyColumns[i] = arrayLike[i];
|
|
90
|
+
}
|
|
91
|
+
}
|
|
92
|
+
this.columns = readonlyColumns;
|
|
93
|
+
}
|
|
94
|
+
}
|
|
95
|
+
/**
|
|
96
|
+
* 数据库表
|
|
97
|
+
* @public
|
|
98
|
+
*/
|
|
99
|
+
class DbTable extends SqlSelectable {
|
|
100
|
+
constructor(name, columns) {
|
|
101
|
+
if (!(columns instanceof Array))
|
|
102
|
+
columns = Object.keys(columns);
|
|
103
|
+
super(columns);
|
|
104
|
+
this.name = name;
|
|
105
|
+
}
|
|
106
|
+
toSelect() {
|
|
107
|
+
return this.name;
|
|
108
|
+
}
|
|
109
|
+
toString() {
|
|
110
|
+
return this.name;
|
|
111
|
+
}
|
|
112
|
+
}
|
|
113
|
+
/**
|
|
114
|
+
* SELECT 以及 UPDATE、DELETE、INSERT INTO 带结果的 SQL 语句
|
|
115
|
+
* @public
|
|
116
|
+
*/
|
|
117
|
+
class SqlQueryStatement extends SqlSelectable {
|
|
118
|
+
constructor(sql, columns) {
|
|
119
|
+
super(columns);
|
|
120
|
+
this.sql = sql;
|
|
121
|
+
}
|
|
122
|
+
toString() {
|
|
123
|
+
return this.sql;
|
|
124
|
+
}
|
|
125
|
+
toSelect() {
|
|
126
|
+
return "(" + this.toString() + ")";
|
|
127
|
+
}
|
|
128
|
+
}
|
|
129
|
+
|
|
130
|
+
var _SqlRaw_value, _YourValuesAs_asName, _YourValuesAs_valuesStr, _YourValuesAs_sql;
|
|
59
131
|
/**
|
|
60
132
|
* SQL 原始字符对象
|
|
61
133
|
* @public
|
|
@@ -106,7 +178,10 @@ class SqlValuesCreator {
|
|
|
106
178
|
let basicType;
|
|
107
179
|
if (expectType) {
|
|
108
180
|
if (typeof expectType === "function") {
|
|
109
|
-
|
|
181
|
+
let type = this.map.get(expectType);
|
|
182
|
+
if (!type)
|
|
183
|
+
throw new Error("类型不存在");
|
|
184
|
+
return type.call(this, value);
|
|
110
185
|
}
|
|
111
186
|
else {
|
|
112
187
|
basicType = expectType;
|
|
@@ -123,8 +198,13 @@ class SqlValuesCreator {
|
|
|
123
198
|
return SqlValuesCreator.string(value);
|
|
124
199
|
case "boolean":
|
|
125
200
|
return value.toString();
|
|
126
|
-
case "object":
|
|
127
|
-
|
|
201
|
+
case "object": {
|
|
202
|
+
if (value === null)
|
|
203
|
+
return "NULL";
|
|
204
|
+
if (value instanceof SqlRaw)
|
|
205
|
+
return value.toString();
|
|
206
|
+
return this.getObjectType(value).call(this, value);
|
|
207
|
+
}
|
|
128
208
|
case "undefined":
|
|
129
209
|
return "DEFAULT";
|
|
130
210
|
default:
|
|
@@ -133,16 +213,13 @@ class SqlValuesCreator {
|
|
|
133
213
|
throw new Error("不支持转换 " + type + " 类型");
|
|
134
214
|
}
|
|
135
215
|
}
|
|
136
|
-
|
|
137
|
-
|
|
138
|
-
return "NULL";
|
|
139
|
-
if (value instanceof SqlRaw)
|
|
140
|
-
return value.toString();
|
|
216
|
+
/** 获取值对应的 SqlValueEncoder */
|
|
217
|
+
getObjectType(value) {
|
|
141
218
|
for (const Class of this.map.keys()) {
|
|
142
219
|
if (value instanceof Class)
|
|
143
|
-
return this.map.get(Class)
|
|
220
|
+
return this.map.get(Class);
|
|
144
221
|
}
|
|
145
|
-
return this.defaultObject
|
|
222
|
+
return this.defaultObject;
|
|
146
223
|
}
|
|
147
224
|
defaultObject(value) {
|
|
148
225
|
return SqlValuesCreator.string(JSON.stringify(value));
|
|
@@ -212,7 +289,70 @@ class SqlValuesCreator {
|
|
|
212
289
|
toValues(values) {
|
|
213
290
|
return values.map((v) => this.toSqlStr(v)).join(",");
|
|
214
291
|
}
|
|
292
|
+
createValues(asName, values, valuesTypes) {
|
|
293
|
+
if (values.length === 0)
|
|
294
|
+
throw new Error("values 不能为空");
|
|
295
|
+
const insertKeys = Object.keys(valuesTypes);
|
|
296
|
+
const defaultValues = [];
|
|
297
|
+
const valuesStr = new Array(values.length);
|
|
298
|
+
{
|
|
299
|
+
const column0 = new Array(insertKeys.length);
|
|
300
|
+
let columnName;
|
|
301
|
+
let item;
|
|
302
|
+
let type;
|
|
303
|
+
let value;
|
|
304
|
+
for (let i = 0; i < insertKeys.length; i++) {
|
|
305
|
+
columnName = insertKeys[i];
|
|
306
|
+
item = valuesTypes[columnName];
|
|
307
|
+
if (typeof item === "string") {
|
|
308
|
+
type = item;
|
|
309
|
+
defaultValues[i] = "NULL";
|
|
310
|
+
}
|
|
311
|
+
else {
|
|
312
|
+
type = item.sqlType;
|
|
313
|
+
defaultValues[i] = item.sqlDefault ?? "NULL";
|
|
314
|
+
}
|
|
315
|
+
value = values[0][columnName];
|
|
316
|
+
if (value === undefined)
|
|
317
|
+
column0[i] = defaultValues[i] + "::" + type;
|
|
318
|
+
else
|
|
319
|
+
column0[i] = this.toSqlStr(value) + "::" + type;
|
|
320
|
+
}
|
|
321
|
+
valuesStr[0] = "(" + column0.join(",") + ")";
|
|
322
|
+
}
|
|
323
|
+
let items = new Array(insertKeys.length);
|
|
324
|
+
let value;
|
|
325
|
+
for (let i = 1; i < values.length; i++) {
|
|
326
|
+
for (let j = 0; j < insertKeys.length; j++) {
|
|
327
|
+
value = values[i][insertKeys[j]];
|
|
328
|
+
if (value === undefined)
|
|
329
|
+
items[j] = defaultValues[j];
|
|
330
|
+
else
|
|
331
|
+
items[j] = this.toSqlStr(value);
|
|
332
|
+
}
|
|
333
|
+
valuesStr[i] = "(" + items.join(",") + ")";
|
|
334
|
+
}
|
|
335
|
+
return new YourValuesAs(insertKeys, asName, valuesStr.join(",\n"));
|
|
336
|
+
}
|
|
215
337
|
}
|
|
338
|
+
class YourValuesAs extends SqlSelectable {
|
|
339
|
+
constructor(columns, asName, valuesStr) {
|
|
340
|
+
super(columns);
|
|
341
|
+
_YourValuesAs_asName.set(this, void 0);
|
|
342
|
+
_YourValuesAs_valuesStr.set(this, void 0);
|
|
343
|
+
_YourValuesAs_sql.set(this, void 0);
|
|
344
|
+
__classPrivateFieldSet(this, _YourValuesAs_asName, asName, "f");
|
|
345
|
+
__classPrivateFieldSet(this, _YourValuesAs_valuesStr, valuesStr, "f");
|
|
346
|
+
__classPrivateFieldSet(this, _YourValuesAs_sql, `(VALUES\n${__classPrivateFieldGet(this, _YourValuesAs_valuesStr, "f")})\nAS ${__classPrivateFieldGet(this, _YourValuesAs_asName, "f")}(${this.columns.join(",")})`, "f");
|
|
347
|
+
}
|
|
348
|
+
toSelect() {
|
|
349
|
+
return __classPrivateFieldGet(this, _YourValuesAs_sql, "f");
|
|
350
|
+
}
|
|
351
|
+
toString() {
|
|
352
|
+
return __classPrivateFieldGet(this, _YourValuesAs_sql, "f");
|
|
353
|
+
}
|
|
354
|
+
}
|
|
355
|
+
_YourValuesAs_asName = new WeakMap(), _YourValuesAs_valuesStr = new WeakMap(), _YourValuesAs_sql = new WeakMap();
|
|
216
356
|
function toKeyType(object, keys_types) {
|
|
217
357
|
let type = {};
|
|
218
358
|
let keys;
|
|
@@ -235,90 +375,25 @@ const pgSqlTransformer = new Map([
|
|
|
235
375
|
[
|
|
236
376
|
Array,
|
|
237
377
|
function encodePgArray(value) {
|
|
238
|
-
|
|
239
|
-
|
|
240
|
-
|
|
241
|
-
|
|
242
|
-
|
|
243
|
-
|
|
244
|
-
|
|
378
|
+
if (value.length === 0)
|
|
379
|
+
return "NULL";
|
|
380
|
+
const valueStr = [];
|
|
381
|
+
let type;
|
|
382
|
+
let basicType;
|
|
383
|
+
for (let i = 0; i < value.length; i++) {
|
|
384
|
+
{
|
|
385
|
+
basicType = typeof value[i];
|
|
386
|
+
if (value[i] === null || basicType === "undefined")
|
|
387
|
+
basicType = undefined;
|
|
388
|
+
valueStr[i] = this.toSqlStr(value[i], type);
|
|
389
|
+
}
|
|
390
|
+
}
|
|
391
|
+
return "ARRAY[" + valueStr.join(",") + "]";
|
|
245
392
|
},
|
|
246
393
|
],
|
|
247
394
|
[Date, (value) => SqlValuesCreator.string(value.toISOString())],
|
|
248
395
|
]);
|
|
249
396
|
|
|
250
|
-
/**
|
|
251
|
-
* 可选择项。可以是 table、查询结果等,它能被 select 语句选择
|
|
252
|
-
* @example
|
|
253
|
-
* ```ts
|
|
254
|
-
* declare const item: SqlSelectable<any>
|
|
255
|
-
* await query(`select * from ${item.toSelect()}`)
|
|
256
|
-
*
|
|
257
|
-
* ```
|
|
258
|
-
* @public
|
|
259
|
-
*/
|
|
260
|
-
class SqlSelectable {
|
|
261
|
-
constructor(columns) {
|
|
262
|
-
// Reflect.set(this, SQL_SELECTABLE, undefined);
|
|
263
|
-
let readonlyColumns;
|
|
264
|
-
if (typeof columns[Symbol.iterator] === "function") {
|
|
265
|
-
let iterable = columns;
|
|
266
|
-
readonlyColumns = [];
|
|
267
|
-
let iter = iterable[Symbol.iterator]();
|
|
268
|
-
let i = 0;
|
|
269
|
-
let item = iter.next();
|
|
270
|
-
while (!item.done) {
|
|
271
|
-
readonlyColumns[i++] = item.value;
|
|
272
|
-
item = iter.next();
|
|
273
|
-
}
|
|
274
|
-
// readonlyColumns.length = i;
|
|
275
|
-
}
|
|
276
|
-
else {
|
|
277
|
-
let arrayLike = columns;
|
|
278
|
-
readonlyColumns = new Array(arrayLike.length);
|
|
279
|
-
// readonlyColumns.length = arrayLike.length;
|
|
280
|
-
for (let i = 0; i < arrayLike.length; i++) {
|
|
281
|
-
readonlyColumns[i] = arrayLike[i];
|
|
282
|
-
}
|
|
283
|
-
}
|
|
284
|
-
this.columns = readonlyColumns;
|
|
285
|
-
}
|
|
286
|
-
}
|
|
287
|
-
/**
|
|
288
|
-
* 数据库表
|
|
289
|
-
* @public
|
|
290
|
-
*/
|
|
291
|
-
class DbTable extends SqlSelectable {
|
|
292
|
-
constructor(name, columns) {
|
|
293
|
-
if (!(columns instanceof Array))
|
|
294
|
-
columns = Object.keys(columns);
|
|
295
|
-
super(columns);
|
|
296
|
-
this.name = name;
|
|
297
|
-
}
|
|
298
|
-
toSelect() {
|
|
299
|
-
return this.name;
|
|
300
|
-
}
|
|
301
|
-
toString() {
|
|
302
|
-
return this.name;
|
|
303
|
-
}
|
|
304
|
-
}
|
|
305
|
-
/**
|
|
306
|
-
* SELECT 以及 UPDATE、DELETE、INSERT INTO 带结果的 SQL 语句
|
|
307
|
-
* @public
|
|
308
|
-
*/
|
|
309
|
-
class SqlQueryStatement extends SqlSelectable {
|
|
310
|
-
constructor(sql, columns) {
|
|
311
|
-
super(columns);
|
|
312
|
-
this.sql = sql;
|
|
313
|
-
}
|
|
314
|
-
toString() {
|
|
315
|
-
return this.sql;
|
|
316
|
-
}
|
|
317
|
-
toSelect() {
|
|
318
|
-
return "(" + this.toString() + ")";
|
|
319
|
-
}
|
|
320
|
-
}
|
|
321
|
-
|
|
322
397
|
function genOderBy(orderBy, orderNullRule) {
|
|
323
398
|
let select = [];
|
|
324
399
|
let v;
|
|
@@ -600,7 +675,6 @@ class TableRepeatError extends Error {
|
|
|
600
675
|
class DbTableQuery extends DbTable {
|
|
601
676
|
constructor(name, columns, statement) {
|
|
602
677
|
super(name, columns);
|
|
603
|
-
this.name = name;
|
|
604
678
|
this.statement = statement;
|
|
605
679
|
}
|
|
606
680
|
select(columns, option) {
|
|
@@ -695,4 +769,175 @@ function genWhere(where) {
|
|
|
695
769
|
return "\nWHERE " + where;
|
|
696
770
|
}
|
|
697
771
|
|
|
698
|
-
|
|
772
|
+
/**
|
|
773
|
+
* 表格列的信息
|
|
774
|
+
* @public
|
|
775
|
+
*/
|
|
776
|
+
class ColumnMeta {
|
|
777
|
+
constructor(type,
|
|
778
|
+
/** 数据库原始数据类型 */
|
|
779
|
+
sqlType,
|
|
780
|
+
/** 是否非空 */
|
|
781
|
+
notNull = false,
|
|
782
|
+
/** 是否是数组类型 */
|
|
783
|
+
isArray = false,
|
|
784
|
+
/** 数据库原始默认值 */
|
|
785
|
+
sqlDefault) {
|
|
786
|
+
this.type = type;
|
|
787
|
+
this.sqlType = sqlType;
|
|
788
|
+
this.notNull = notNull;
|
|
789
|
+
this.isArray = isArray;
|
|
790
|
+
this.sqlDefault = sqlDefault;
|
|
791
|
+
}
|
|
792
|
+
/** 校验 value 的类型 */
|
|
793
|
+
checkValue(value) {
|
|
794
|
+
if (typeof this.type === "function")
|
|
795
|
+
return value instanceof this.type;
|
|
796
|
+
return this.type.is(value);
|
|
797
|
+
}
|
|
798
|
+
}
|
|
799
|
+
/**
|
|
800
|
+
* 数据库类型到JS类型的映射
|
|
801
|
+
* @public
|
|
802
|
+
*/
|
|
803
|
+
class YourTypeMap {
|
|
804
|
+
static create(rawTypeMap) {
|
|
805
|
+
return new this(rawTypeMap);
|
|
806
|
+
}
|
|
807
|
+
constructor(typeMap = {}) {
|
|
808
|
+
this.typeMap = typeMap;
|
|
809
|
+
}
|
|
810
|
+
genColumn(type, notNull, defaultValue) {
|
|
811
|
+
const constructor = Reflect.get(this.typeMap, type);
|
|
812
|
+
const column = new ColumnMeta(constructor, type, notNull, false, defaultValue);
|
|
813
|
+
return column;
|
|
814
|
+
}
|
|
815
|
+
genArrColumn(type, notNull, defaultValue) {
|
|
816
|
+
const constructor = Reflect.get(this.typeMap, type);
|
|
817
|
+
const column = new ColumnMeta(constructor, type + "[]", notNull, true, defaultValue);
|
|
818
|
+
return column;
|
|
819
|
+
}
|
|
820
|
+
}
|
|
821
|
+
function baseType(v) {
|
|
822
|
+
return typeof v === this.name;
|
|
823
|
+
}
|
|
824
|
+
/**
|
|
825
|
+
* 自定义数据类型
|
|
826
|
+
* @public
|
|
827
|
+
*/
|
|
828
|
+
class CustomDbType {
|
|
829
|
+
constructor(is, name) {
|
|
830
|
+
this.is = is;
|
|
831
|
+
this.name = name;
|
|
832
|
+
}
|
|
833
|
+
}
|
|
834
|
+
CustomDbType.bigint = new CustomDbType(baseType, "bigint");
|
|
835
|
+
CustomDbType.number = new CustomDbType(baseType, "number");
|
|
836
|
+
CustomDbType.string = new CustomDbType(baseType, "string");
|
|
837
|
+
CustomDbType.boolean = new CustomDbType(baseType, "boolean");
|
|
838
|
+
|
|
839
|
+
/** @public */
|
|
840
|
+
class TypeChecker {
|
|
841
|
+
constructor(map) {
|
|
842
|
+
this.map = map;
|
|
843
|
+
}
|
|
844
|
+
check(value) {
|
|
845
|
+
const map = this.map;
|
|
846
|
+
let v;
|
|
847
|
+
for (const [k, expect] of map) {
|
|
848
|
+
v = value[k];
|
|
849
|
+
let err;
|
|
850
|
+
if (v === null) {
|
|
851
|
+
if (expect.notNull)
|
|
852
|
+
throw new Error(`${k} 不能为空`);
|
|
853
|
+
continue;
|
|
854
|
+
}
|
|
855
|
+
else if (v === undefined) {
|
|
856
|
+
if (expect.sqlDefault === undefined && expect.notNull)
|
|
857
|
+
throw new Error(`${k} 不能为 undefined`);
|
|
858
|
+
continue;
|
|
859
|
+
}
|
|
860
|
+
else if (expect.isArray) {
|
|
861
|
+
if (v instanceof Array)
|
|
862
|
+
err = this.checkArray(v, expect.type);
|
|
863
|
+
else
|
|
864
|
+
err = getErrStr(`Array<${expect.type.name}>`, typeof v);
|
|
865
|
+
}
|
|
866
|
+
else {
|
|
867
|
+
err = this.checkItem(v, expect.type);
|
|
868
|
+
}
|
|
869
|
+
if (err)
|
|
870
|
+
throw new Error(`Key ${k} error: ${err}`);
|
|
871
|
+
}
|
|
872
|
+
return value;
|
|
873
|
+
}
|
|
874
|
+
checkList(value) {
|
|
875
|
+
let i = 0;
|
|
876
|
+
try {
|
|
877
|
+
for (let i = 0; i < value.length; i++) {
|
|
878
|
+
this.check(value[i]);
|
|
879
|
+
}
|
|
880
|
+
return value;
|
|
881
|
+
}
|
|
882
|
+
catch (error) {
|
|
883
|
+
throw new Error(`Item ${i}, ${error.message}`);
|
|
884
|
+
}
|
|
885
|
+
}
|
|
886
|
+
checkArray(v, expect) {
|
|
887
|
+
let err;
|
|
888
|
+
for (let i = 0; i < v.length; i++) {
|
|
889
|
+
err = this.checkItem(v[i], expect);
|
|
890
|
+
if (err)
|
|
891
|
+
return `Item[${i}] ${err}`;
|
|
892
|
+
}
|
|
893
|
+
}
|
|
894
|
+
checkItem(v, expect) {
|
|
895
|
+
if (expect instanceof CustomDbType) {
|
|
896
|
+
if (expect.is(v))
|
|
897
|
+
return;
|
|
898
|
+
}
|
|
899
|
+
else {
|
|
900
|
+
if (v instanceof expect)
|
|
901
|
+
return;
|
|
902
|
+
}
|
|
903
|
+
let actName = typeof v;
|
|
904
|
+
if (actName === "object") {
|
|
905
|
+
if (v === null)
|
|
906
|
+
actName = "null";
|
|
907
|
+
else
|
|
908
|
+
actName = v.constructor?.name ?? "object";
|
|
909
|
+
}
|
|
910
|
+
return getErrStr(expect.name, typeof v);
|
|
911
|
+
}
|
|
912
|
+
}
|
|
913
|
+
function getErrStr(expect, actual) {
|
|
914
|
+
return `Expect ${expect}, Actual ${actual}`;
|
|
915
|
+
}
|
|
916
|
+
|
|
917
|
+
/**
|
|
918
|
+
* 完整数据库表数据
|
|
919
|
+
* @public
|
|
920
|
+
*/
|
|
921
|
+
class YourTable extends DbTableQuery {
|
|
922
|
+
constructor(name, define, sqlValue) {
|
|
923
|
+
super(name, Object.keys(define), sqlValue);
|
|
924
|
+
this.define = define;
|
|
925
|
+
}
|
|
926
|
+
getColumnMeta(name) {
|
|
927
|
+
return Reflect.get(this.define, name);
|
|
928
|
+
}
|
|
929
|
+
createTypeChecker(keys) {
|
|
930
|
+
let map = new Map();
|
|
931
|
+
let defined = this.define;
|
|
932
|
+
let k;
|
|
933
|
+
for (let i = 0; i < keys.length; i++) {
|
|
934
|
+
k = keys[i];
|
|
935
|
+
if (defined[k] === undefined)
|
|
936
|
+
throw new Error(`key ${k} 未定义`);
|
|
937
|
+
map.set(k, defined[k]);
|
|
938
|
+
}
|
|
939
|
+
return new TypeChecker(map);
|
|
940
|
+
}
|
|
941
|
+
}
|
|
942
|
+
|
|
943
|
+
export { ColumnMeta, CustomDbType, DbTable, DbTableQuery, SqlQueryStatement, SqlRaw, SqlSelectable, SqlValuesCreator, TypeChecker, YourTable, YourTypeMap, createSelect, getObjectListKeys, pgSqlTransformer };
|
|
@@ -4,7 +4,6 @@ import { Select, SelectTableOption } from "./select.ts";
|
|
|
4
4
|
import { DbTable, SqlQueryStatement } from "./selectable.ts";
|
|
5
5
|
/** @public */
|
|
6
6
|
export declare class DbTableQuery<T extends TableType = Record<string, any>, C extends TableType = Partial<T>> extends DbTable<T> {
|
|
7
|
-
readonly name: string;
|
|
8
7
|
private statement;
|
|
9
8
|
constructor(name: string, columns: readonly string[], statement: SqlValuesCreator);
|
|
10
9
|
/** 选择全部列 */
|
package/dist/select/select.d.ts
CHANGED
|
@@ -1,5 +1,5 @@
|
|
|
1
1
|
import { SqlSelectable, InferQueryResult, SqlQueryStatement } from "./selectable.ts";
|
|
2
|
-
import type { ColumnsSelected, RowsOrder, SelectColumns, TableType } from "./type.ts";
|
|
2
|
+
import type { ColumnsSelected, OrderValue, RowsOrder, SelectColumns, TableType } from "./type.ts";
|
|
3
3
|
interface AddTableFn<T extends TableType> {
|
|
4
4
|
<Q extends SqlSelectable<any>, A extends InferQueryResult<Q>>(tb: Q, columns?: undefined, option?: SelectTableOption): Select<T>;
|
|
5
5
|
<Q extends SqlSelectable<any>, A extends InferQueryResult<Q>, C extends ColumnsSelected<A>>(tb: Q, columns: C, option?: SelectTableOption): Select<T & SelectColumns<A, C>>;
|
|
@@ -18,7 +18,9 @@ export interface SelectFilterOption<T extends object> {
|
|
|
18
18
|
}
|
|
19
19
|
/** @public */
|
|
20
20
|
export interface FinalSelect<T extends TableType> extends SqlSelectable<T> {
|
|
21
|
-
toQuery(option?: SelectFilterOption<T
|
|
21
|
+
toQuery(option?: SelectFilterOption<T & {
|
|
22
|
+
[key: string]: OrderValue;
|
|
23
|
+
}>): SqlQueryStatement<T>;
|
|
22
24
|
}
|
|
23
25
|
/** @public */
|
|
24
26
|
export interface JoinSelect<T extends TableType> extends FinalSelect<T> {
|
|
@@ -1,3 +1,4 @@
|
|
|
1
|
+
import { SqlSelectable } from "../select/selectable.ts";
|
|
1
2
|
declare const SQL_RAW: unique symbol;
|
|
2
3
|
/**
|
|
3
4
|
* SQL 原始字符对象
|
|
@@ -13,18 +14,20 @@ export declare class SqlRaw<T = any> {
|
|
|
13
14
|
/** @public */
|
|
14
15
|
export type JsObjectMapSql = Map<new (...args: any[]) => any, SqlValueEncoder>;
|
|
15
16
|
/** @public */
|
|
16
|
-
export type SqlValueEncoder<T = any> = (this: SqlValuesCreator, value: T
|
|
17
|
+
export type SqlValueEncoder<T = any> = (this: SqlValuesCreator, value: T) => string;
|
|
17
18
|
/** @public */
|
|
18
|
-
export type ManualType = "bigint" | "number" | "string" | "boolean" | (new (...args: any[]) => any);
|
|
19
|
+
export type ManualType = "bigint" | "number" | "string" | "boolean" | "object" | (new (...args: any[]) => any);
|
|
20
|
+
/** @public */
|
|
21
|
+
export interface SqlValueFn {
|
|
22
|
+
/** 将 JS 对象转为 SQL 的字符值的形式 。 undefined 将被转换为 DEFAULT */
|
|
23
|
+
(value: any, expectType?: ManualType): string;
|
|
24
|
+
}
|
|
19
25
|
/**
|
|
20
26
|
* SQL value 生成器
|
|
21
27
|
* @public
|
|
22
28
|
*/
|
|
23
29
|
export declare class SqlValuesCreator {
|
|
24
|
-
static create(map?: JsObjectMapSql): SqlValuesCreator &
|
|
25
|
-
/** 将 JS 对象转为 SQL 的字符值的形式 。 undefined 将被转换为 DEFAULT */
|
|
26
|
-
(value: any, expectType?: ManualType): string;
|
|
27
|
-
};
|
|
30
|
+
static create(map?: JsObjectMapSql): SqlValuesCreator & SqlValueFn;
|
|
28
31
|
/**
|
|
29
32
|
* 将字符串转为 SQL 的字符串值的形式(单引号会被转义)。
|
|
30
33
|
* @example 输入 a'b'c , 返回 a''b''c.
|
|
@@ -38,8 +41,9 @@ export declare class SqlValuesCreator {
|
|
|
38
41
|
setTransformer<T>(type: new (...args: any[]) => T, transformer?: SqlValueEncoder): void;
|
|
39
42
|
private readonly map;
|
|
40
43
|
/** 将 JS 对象转为 SQL 的字符值的形式 。 undefined 将被转换为 DEFAULT */
|
|
41
|
-
toSqlStr(value: any, expectType?:
|
|
42
|
-
|
|
44
|
+
toSqlStr(value: any, expectType?: ManualType): string;
|
|
45
|
+
/** 获取值对应的 SqlValueEncoder */
|
|
46
|
+
getObjectType(value: object): SqlValueEncoder;
|
|
43
47
|
protected defaultObject(value: object): string;
|
|
44
48
|
/**
|
|
45
49
|
* 将对象列表转为 SQL 的 VALUES
|
|
@@ -62,6 +66,22 @@ export declare class SqlValuesCreator {
|
|
|
62
66
|
* @example 返回示例: " 'abc', '6', 'now()' "
|
|
63
67
|
*/
|
|
64
68
|
toValues(values: readonly any[]): string;
|
|
69
|
+
/**
|
|
70
|
+
* @public 创建 VALUES AS 语句
|
|
71
|
+
* @example
|
|
72
|
+
* ```ts
|
|
73
|
+
* sqlValue.createValues(
|
|
74
|
+
* "customName",
|
|
75
|
+
* [{age:8, name:"hhh"}, {age:9, name:"row2"}],
|
|
76
|
+
* {age:"INT", name:"TEXT"}
|
|
77
|
+
* )
|
|
78
|
+
* // (VALUES (8:INT,'hhh':TEXT),(9,'row2')) AS customName(age, name)
|
|
79
|
+
* ```
|
|
80
|
+
*/
|
|
81
|
+
createValues<T extends {}>(asName: string, values: T[], valuesTypes: Record<string, string | {
|
|
82
|
+
sqlType: string;
|
|
83
|
+
sqlDefault?: string;
|
|
84
|
+
}>): SqlSelectable<T>;
|
|
65
85
|
}
|
|
66
86
|
export {};
|
|
67
87
|
//# sourceMappingURL=sql_value.d.ts.map
|
|
@@ -0,0 +1,13 @@
|
|
|
1
|
+
import { ColumnMeta } from "./infer_db_type.ts";
|
|
2
|
+
/** @public */
|
|
3
|
+
export declare class TypeChecker<T> {
|
|
4
|
+
private map;
|
|
5
|
+
constructor(map: Map<string, ColumnMeta<any>>);
|
|
6
|
+
check(value: {
|
|
7
|
+
[key: string]: any;
|
|
8
|
+
}): T;
|
|
9
|
+
checkList(value: any[]): T[];
|
|
10
|
+
private checkArray;
|
|
11
|
+
private checkItem;
|
|
12
|
+
}
|
|
13
|
+
//# sourceMappingURL=checker.d.ts.map
|
|
@@ -0,0 +1,74 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* 表格列的信息
|
|
3
|
+
* @public
|
|
4
|
+
*/
|
|
5
|
+
export declare class ColumnMeta<T> {
|
|
6
|
+
readonly type: CustomDbType<T> | (new (...args: any[]) => T);
|
|
7
|
+
/** 数据库原始数据类型 */
|
|
8
|
+
readonly sqlType: string;
|
|
9
|
+
/** 是否非空 */
|
|
10
|
+
readonly notNull: boolean;
|
|
11
|
+
/** 是否是数组类型 */
|
|
12
|
+
readonly isArray: boolean;
|
|
13
|
+
/** 数据库原始默认值 */
|
|
14
|
+
readonly sqlDefault?: string | undefined;
|
|
15
|
+
constructor(type: CustomDbType<T> | (new (...args: any[]) => T),
|
|
16
|
+
/** 数据库原始数据类型 */
|
|
17
|
+
sqlType: string,
|
|
18
|
+
/** 是否非空 */
|
|
19
|
+
notNull?: boolean,
|
|
20
|
+
/** 是否是数组类型 */
|
|
21
|
+
isArray?: boolean,
|
|
22
|
+
/** 数据库原始默认值 */
|
|
23
|
+
sqlDefault?: string | undefined);
|
|
24
|
+
/** 校验 value 的类型 */
|
|
25
|
+
checkValue(value: any): boolean;
|
|
26
|
+
}
|
|
27
|
+
/**
|
|
28
|
+
* 数据库类型到JS类型的映射
|
|
29
|
+
* @public
|
|
30
|
+
*/
|
|
31
|
+
export declare class YourTypeMap<M extends TypeMapDefined> {
|
|
32
|
+
private readonly typeMap;
|
|
33
|
+
static create<T extends TypeMapDefined>(rawTypeMap?: T): YourTypeMap<{
|
|
34
|
+
[key in keyof T]: InferTypeMapDefined<T[key]>;
|
|
35
|
+
}>;
|
|
36
|
+
constructor(typeMap?: M);
|
|
37
|
+
genColumn<T extends keyof M>(type: T, noNull: true, defaultValue?: string): ColumnMeta<M[T]>;
|
|
38
|
+
genColumn<T extends keyof M>(type: T, noNull?: boolean, defaultValue?: string): ColumnMeta<M[T] | null>;
|
|
39
|
+
genColumn<T>(type: keyof M, noNull: true, defaultValue?: string): ColumnMeta<T>;
|
|
40
|
+
genColumn<T>(type: keyof M, noNull?: boolean, defaultValue?: string): ColumnMeta<T | null>;
|
|
41
|
+
genArrColumn<T extends keyof M>(type: T, noNull: true, defaultValue?: string): ColumnMeta<M[T][]>;
|
|
42
|
+
genArrColumn<T extends keyof M>(type: T, noNull?: boolean, defaultValue?: string): ColumnMeta<M[T][] | null>;
|
|
43
|
+
genArrColumn<T>(type: keyof M, notNull: true, defaultValue?: string): ColumnMeta<T[]>;
|
|
44
|
+
genArrColumn<T>(type: keyof M, notNull?: boolean, defaultValue?: string): ColumnMeta<T[] | null>;
|
|
45
|
+
}
|
|
46
|
+
type Constructor<T = any> = new (...args: any[]) => T;
|
|
47
|
+
/**
|
|
48
|
+
* 自定义数据类型
|
|
49
|
+
* @public
|
|
50
|
+
*/
|
|
51
|
+
export declare class CustomDbType<T> {
|
|
52
|
+
readonly is: (this: CustomDbType<T>, value: any) => boolean;
|
|
53
|
+
readonly name: string;
|
|
54
|
+
static readonly bigint: CustomDbType<bigint>;
|
|
55
|
+
static readonly number: CustomDbType<number>;
|
|
56
|
+
static readonly string: CustomDbType<string>;
|
|
57
|
+
static readonly boolean: CustomDbType<boolean>;
|
|
58
|
+
constructor(is: (this: CustomDbType<T>, value: any) => boolean, name: string);
|
|
59
|
+
}
|
|
60
|
+
type TypeMapDefined = {
|
|
61
|
+
[key: string]: Constructor | CustomDbType<any>;
|
|
62
|
+
};
|
|
63
|
+
type InferTypeMapDefined<T> = T extends Constructor<infer P> ? TRaw<P> : T extends CustomDbType<infer Q> ? Q : never;
|
|
64
|
+
type TRaw<T> = T extends Number ? number : T extends BigInt ? bigint : T extends String ? string : T extends Boolean ? boolean : T;
|
|
65
|
+
/** @public */
|
|
66
|
+
export type TableDefined = {
|
|
67
|
+
[key: string]: ColumnMeta<any>;
|
|
68
|
+
};
|
|
69
|
+
/** @public */
|
|
70
|
+
export type InferTableDefined<T extends TableDefined> = {
|
|
71
|
+
[key in keyof T]: T[key] extends ColumnMeta<infer P> ? P : unknown;
|
|
72
|
+
};
|
|
73
|
+
export {};
|
|
74
|
+
//# sourceMappingURL=infer_db_type.d.ts.map
|
|
@@ -0,0 +1,16 @@
|
|
|
1
|
+
import { DbTableQuery } from "../select/TableQuery.ts";
|
|
2
|
+
import type { TableType } from "../select/type.ts";
|
|
3
|
+
import type { SqlValuesCreator } from "../sql_value/sql_value.ts";
|
|
4
|
+
import type { ColumnMeta, TableDefined } from "./infer_db_type.ts";
|
|
5
|
+
import { TypeChecker } from "./checker.ts";
|
|
6
|
+
/**
|
|
7
|
+
* 完整数据库表数据
|
|
8
|
+
* @public
|
|
9
|
+
*/
|
|
10
|
+
export declare class YourTable<T extends TableType = TableType, C extends TableType = T> extends DbTableQuery<T, C> {
|
|
11
|
+
private define;
|
|
12
|
+
constructor(name: string, define: TableDefined, sqlValue: SqlValuesCreator);
|
|
13
|
+
getColumnMeta(name: keyof T): ColumnMeta<unknown>;
|
|
14
|
+
createTypeChecker<T>(keys: readonly string[]): TypeChecker<T>;
|
|
15
|
+
}
|
|
16
|
+
//# sourceMappingURL=table.d.ts.map
|
package/package.json
CHANGED
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
{
|
|
2
2
|
"name": "@asla/yoursql",
|
|
3
|
-
"version": "0.
|
|
3
|
+
"version": "0.3.1",
|
|
4
4
|
"description": "",
|
|
5
5
|
"type": "module",
|
|
6
6
|
"types": "./dist/mod.d.ts",
|
|
@@ -10,6 +10,7 @@
|
|
|
10
10
|
"build": "pnpm rollup -c build/rollup.config.js && pnpm run ci:check-api -l",
|
|
11
11
|
"test": "vitest",
|
|
12
12
|
"type:check": "tsc",
|
|
13
|
+
"publish-check": "deno publish --dry-run --allow-dirty",
|
|
13
14
|
"ci:check-api": "api-extractor run -c api-extractor.jsonc -v"
|
|
14
15
|
},
|
|
15
16
|
"devDependencies": {
|