@axiosleo/orm-mysql 0.7.0 → 0.8.0
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/README.md +33 -0
- package/index.d.ts +15 -3
- package/index.js +2 -0
- package/package.json +2 -2
- package/src/operator.js +52 -33
- package/src/query.js +2 -1
- package/src/transaction.js +13 -2
package/README.md
CHANGED
|
@@ -195,6 +195,39 @@ try {
|
|
|
195
195
|
}
|
|
196
196
|
```
|
|
197
197
|
|
|
198
|
+
### Custom query driver
|
|
199
|
+
|
|
200
|
+
```javascript
|
|
201
|
+
const {
|
|
202
|
+
createClient,
|
|
203
|
+
QueryHandler,
|
|
204
|
+
Query,
|
|
205
|
+
Builder
|
|
206
|
+
} = require("@axiosleo/orm-mysql");
|
|
207
|
+
|
|
208
|
+
const conn = createClient({
|
|
209
|
+
host: process.env.MYSQL_HOST,
|
|
210
|
+
port: process.env.MYSQL_PORT,
|
|
211
|
+
user: process.env.MYSQL_USER,
|
|
212
|
+
password: process.env.MYSQL_PASS,
|
|
213
|
+
database: process.env.MYSQL_DB,
|
|
214
|
+
});
|
|
215
|
+
|
|
216
|
+
const hanlder = new QueryHandler(conn, {
|
|
217
|
+
driver: 'custom',
|
|
218
|
+
query_handler: (con, options) => {
|
|
219
|
+
const builder = new Builder(options);
|
|
220
|
+
return new Promise((resolve, reject) => {
|
|
221
|
+
if (options.operator === 'select') {
|
|
222
|
+
resolve([{ a: 1, b: 2 }]);
|
|
223
|
+
} else {
|
|
224
|
+
reject(new Error('some error'));
|
|
225
|
+
}
|
|
226
|
+
});
|
|
227
|
+
}
|
|
228
|
+
});
|
|
229
|
+
```
|
|
230
|
+
|
|
198
231
|
## License
|
|
199
232
|
|
|
200
233
|
This project is open-sourced software licensed under the [MIT](LICENSE).
|
package/index.d.ts
CHANGED
|
@@ -48,7 +48,12 @@ export interface TableOption {
|
|
|
48
48
|
alias: string | null;
|
|
49
49
|
}
|
|
50
50
|
|
|
51
|
-
export type
|
|
51
|
+
export type QueryOperatorBaseOptions = {
|
|
52
|
+
driver?: string | 'mysql';
|
|
53
|
+
query_handler?: QueryHandler;
|
|
54
|
+
};
|
|
55
|
+
|
|
56
|
+
export type QueryOperatorOptions = QueryOperatorBaseOptions & {
|
|
52
57
|
conditions: WhereOptions[];
|
|
53
58
|
attrs?: string[] | null;
|
|
54
59
|
orders: OrderByOptions[];
|
|
@@ -106,7 +111,7 @@ export declare class QueryOperator extends Query {
|
|
|
106
111
|
conn: Connection;
|
|
107
112
|
options: QueryOperatorOptions
|
|
108
113
|
|
|
109
|
-
constructor(conn: Connection);
|
|
114
|
+
constructor(conn: Connection, opt?: QueryOperatorBaseOptions);
|
|
110
115
|
|
|
111
116
|
buildSql(operator: OperatorType): { sql: string, values: any[] };
|
|
112
117
|
|
|
@@ -132,8 +137,9 @@ export declare class QueryOperator extends Query {
|
|
|
132
137
|
|
|
133
138
|
export declare class QueryHandler {
|
|
134
139
|
conn: Connection;
|
|
140
|
+
options: QueryOperatorBaseOptions;
|
|
135
141
|
|
|
136
|
-
constructor(conn: Connection);
|
|
142
|
+
constructor(conn: Connection, options?: QueryOperatorBaseOptions);
|
|
137
143
|
|
|
138
144
|
/**
|
|
139
145
|
* select table
|
|
@@ -241,3 +247,9 @@ export declare class Hook {
|
|
|
241
247
|
...args: any[]
|
|
242
248
|
) => void
|
|
243
249
|
}
|
|
250
|
+
|
|
251
|
+
export declare class Builder {
|
|
252
|
+
sql: string;
|
|
253
|
+
values: any[];
|
|
254
|
+
constructor(options: QueryOperatorOptions);
|
|
255
|
+
}
|
package/index.js
CHANGED
package/package.json
CHANGED
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
{
|
|
2
2
|
"name": "@axiosleo/orm-mysql",
|
|
3
|
-
"version": "0.
|
|
3
|
+
"version": "0.8.0",
|
|
4
4
|
"description": "MySQL ORM tool",
|
|
5
5
|
"keywords": [
|
|
6
6
|
"mysql",
|
|
@@ -28,7 +28,7 @@
|
|
|
28
28
|
"url": "https://github.com/AxiosLeo/node-orm-mysql"
|
|
29
29
|
},
|
|
30
30
|
"devDependencies": {
|
|
31
|
-
"@types/node": "^
|
|
31
|
+
"@types/node": "^20.8.3",
|
|
32
32
|
"chai": "^4.2.0",
|
|
33
33
|
"chai-as-promised": "^7.1.1",
|
|
34
34
|
"eslint": "^7.0",
|
package/src/operator.js
CHANGED
|
@@ -4,31 +4,59 @@ const { Builder } = require('./builder');
|
|
|
4
4
|
const Query = require('./query');
|
|
5
5
|
const Hook = require('./hook');
|
|
6
6
|
|
|
7
|
-
const query = async (conn, options,
|
|
8
|
-
|
|
9
|
-
|
|
10
|
-
|
|
11
|
-
|
|
12
|
-
|
|
13
|
-
|
|
14
|
-
|
|
15
|
-
|
|
16
|
-
|
|
7
|
+
const query = async (conn, options, opt = null) => {
|
|
8
|
+
switch (options.driver) {
|
|
9
|
+
case 'mysql': {
|
|
10
|
+
if (opt === null) {
|
|
11
|
+
const builder = new Builder(options);
|
|
12
|
+
opt = {
|
|
13
|
+
sql: builder.sql,
|
|
14
|
+
values: builder.values || [],
|
|
15
|
+
};
|
|
16
|
+
}
|
|
17
|
+
return new Promise((resolve, reject) => {
|
|
18
|
+
if (options.transaction) {
|
|
19
|
+
conn.execute(opt)
|
|
20
|
+
.then((res) => resolve(res))
|
|
21
|
+
.catch((err) => reject(err));
|
|
17
22
|
} else {
|
|
18
|
-
|
|
23
|
+
conn.query(opt, (err, result) => {
|
|
24
|
+
if (err) {
|
|
25
|
+
reject(err);
|
|
26
|
+
} else {
|
|
27
|
+
resolve(result);
|
|
28
|
+
}
|
|
29
|
+
});
|
|
19
30
|
}
|
|
20
31
|
});
|
|
21
32
|
}
|
|
22
|
-
|
|
33
|
+
default: {
|
|
34
|
+
const promise = options.query_handler(conn, options, opt);
|
|
35
|
+
if (!(promise instanceof Promise)) {
|
|
36
|
+
throw new Error('query_handler must return a promise');
|
|
37
|
+
}
|
|
38
|
+
return promise;
|
|
39
|
+
}
|
|
40
|
+
}
|
|
23
41
|
};
|
|
24
42
|
|
|
25
43
|
class QueryOperator extends Query {
|
|
26
44
|
/**
|
|
27
45
|
* @param {*} conn
|
|
28
46
|
*/
|
|
29
|
-
constructor(conn = null) {
|
|
47
|
+
constructor(conn = null, options = {}) {
|
|
30
48
|
super(null);
|
|
31
49
|
this.conn = conn;
|
|
50
|
+
this.options.driver = options.driver || 'mysql';
|
|
51
|
+
this.options.query_handler = options.query_handler || null;
|
|
52
|
+
if (this.options.driver !== 'mysql') {
|
|
53
|
+
if (!this.options.query_handler) {
|
|
54
|
+
throw new Error('query_handler is required');
|
|
55
|
+
}
|
|
56
|
+
if (!(this.options.query_handler instanceof Function)) {
|
|
57
|
+
throw new Error('query_handler must be a function');
|
|
58
|
+
}
|
|
59
|
+
}
|
|
32
60
|
}
|
|
33
61
|
|
|
34
62
|
buildSql(operator) {
|
|
@@ -43,28 +71,23 @@ class QueryOperator extends Query {
|
|
|
43
71
|
if (this.conn === null) {
|
|
44
72
|
throw new Error('Connection is null');
|
|
45
73
|
}
|
|
46
|
-
const builder = this.buildSql(this.options.operator);
|
|
47
|
-
const { sql, values } = builder;
|
|
48
|
-
const options = {
|
|
49
|
-
sql, values
|
|
50
|
-
};
|
|
51
74
|
const from = this.options.tables.map(t => t.tableName).join(',');
|
|
52
75
|
Hook.listen({ label: 'pre', table: from, opt: this.options.operator }, this.options);
|
|
53
76
|
let res;
|
|
54
77
|
try {
|
|
55
78
|
switch (this.options.operator) {
|
|
56
79
|
case 'find': {
|
|
57
|
-
const tmp = await query(this.conn,
|
|
80
|
+
const tmp = await query(this.conn, this.options);
|
|
58
81
|
res = tmp[0];
|
|
59
82
|
break;
|
|
60
83
|
}
|
|
61
84
|
case 'count': {
|
|
62
|
-
const [tmp] = await query(this.conn,
|
|
85
|
+
const [tmp] = await query(this.conn, this.options);
|
|
63
86
|
res = tmp.count;
|
|
64
87
|
break;
|
|
65
88
|
}
|
|
66
89
|
default:
|
|
67
|
-
res = await query(this.conn,
|
|
90
|
+
res = await query(this.conn, this.options);
|
|
68
91
|
}
|
|
69
92
|
Hook.listen({ label: 'post', table: from, opt: this.options.operator }, this.options, res);
|
|
70
93
|
} catch (err) {
|
|
@@ -115,24 +138,20 @@ class QueryOperator extends Query {
|
|
|
115
138
|
}
|
|
116
139
|
|
|
117
140
|
class QueryHandler {
|
|
118
|
-
constructor(conn) {
|
|
141
|
+
constructor(conn, options = {}) {
|
|
119
142
|
this.conn = conn;
|
|
143
|
+
this.optinos = options;
|
|
120
144
|
}
|
|
121
145
|
|
|
122
|
-
async query(
|
|
123
|
-
|
|
124
|
-
|
|
125
|
-
|
|
126
|
-
|
|
127
|
-
} else {
|
|
128
|
-
resolve(result);
|
|
129
|
-
}
|
|
130
|
-
});
|
|
131
|
-
});
|
|
146
|
+
async query(opt) {
|
|
147
|
+
if (!opt) {
|
|
148
|
+
throw new Error('opt is required');
|
|
149
|
+
}
|
|
150
|
+
return await query(this.conn, this.options, opt);
|
|
132
151
|
}
|
|
133
152
|
|
|
134
153
|
table(table, alias = null) {
|
|
135
|
-
return (new QueryOperator(this.conn)).table(table, alias);
|
|
154
|
+
return (new QueryOperator(this.conn, this.optinos)).table(table, alias);
|
|
136
155
|
}
|
|
137
156
|
|
|
138
157
|
async upsert(tableName, data, condition = {}) {
|
package/src/query.js
CHANGED
|
@@ -3,6 +3,8 @@
|
|
|
3
3
|
class Query {
|
|
4
4
|
constructor(operator = 'select') {
|
|
5
5
|
this.options = {
|
|
6
|
+
driver: 'mysql',
|
|
7
|
+
query_handler: null,
|
|
6
8
|
conditions: [],
|
|
7
9
|
orders: [],
|
|
8
10
|
tables: [],
|
|
@@ -136,7 +138,6 @@ class Query {
|
|
|
136
138
|
let lastOpt = this.options.having[this.options.having.length - 1].opt.toUpperCase();
|
|
137
139
|
if (lastOpt !== 'AND' && lastOpt !== 'OR') {
|
|
138
140
|
this.options.having.push({ key: null, opt: 'AND', value: null });
|
|
139
|
-
return this;
|
|
140
141
|
}
|
|
141
142
|
}
|
|
142
143
|
this.options.having.push({ key, opt, value });
|
package/src/transaction.js
CHANGED
|
@@ -15,9 +15,19 @@ class TransactionOperator extends QueryOperator {
|
|
|
15
15
|
/**
|
|
16
16
|
* @param {*} conn
|
|
17
17
|
*/
|
|
18
|
-
constructor(conn) {
|
|
18
|
+
constructor(conn, options) {
|
|
19
19
|
super(conn);
|
|
20
20
|
this.options.transaction = true;
|
|
21
|
+
this.options.driver = options.driver || 'mysql';
|
|
22
|
+
this.options.query_handler = options.query_handler || null;
|
|
23
|
+
if (this.options.driver !== 'mysql') {
|
|
24
|
+
if (!this.options.query_handler) {
|
|
25
|
+
throw new Error('query_handler is required');
|
|
26
|
+
}
|
|
27
|
+
if (!(this.options.query_handler instanceof Function)) {
|
|
28
|
+
throw new Error('query_handler must be a function');
|
|
29
|
+
}
|
|
30
|
+
}
|
|
21
31
|
}
|
|
22
32
|
|
|
23
33
|
/**
|
|
@@ -42,6 +52,7 @@ class TransactionHandler {
|
|
|
42
52
|
if (levels[this.level]) {
|
|
43
53
|
this.level = levels[this.level];
|
|
44
54
|
}
|
|
55
|
+
this.options = options;
|
|
45
56
|
if (!Object.values(levels).includes(this.level)) {
|
|
46
57
|
throw new Error('Invalid transaction level: ' + this.level);
|
|
47
58
|
}
|
|
@@ -79,7 +90,7 @@ class TransactionHandler {
|
|
|
79
90
|
if (!this.isbegin) {
|
|
80
91
|
throw new Error('Transaction is not begin');
|
|
81
92
|
}
|
|
82
|
-
return (new TransactionOperator(this.conn)).table(table, alias);
|
|
93
|
+
return (new TransactionOperator(this.conn, this.options)).table(table, alias);
|
|
83
94
|
}
|
|
84
95
|
|
|
85
96
|
async upsert(tableName, data, condition = {}) {
|