beech-api 3.7.23 → 3.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 +490 -168
- package/index.js +2 -2
- package/package.json +8 -1
- package/packages/cli/beech +2 -2
- package/packages/cli/bin/beech-app.js +10 -8
- package/packages/cli/bin/beech-service.js +1 -1
- package/packages/cli/core/auth/Credentials.js +139 -89
- package/packages/cli/core/auth/Passport.js +264 -164
- package/packages/cli/core/auth/_Request.js +1 -1
- package/packages/cli/core/configure/app.config-basic.js +2 -2
- package/packages/cli/core/configure/app.config-sequelize.js +2 -2
- package/packages/cli/core/configure/beech.config.js +1 -0
- package/packages/cli/core/configure/passport.config.js +33 -13
- package/packages/cli/core/databases/sequelize.js +3 -0
- package/packages/cli/core/databases/test.js +5 -3
- package/packages/cli/core/generator/_endpoints +5 -9
- package/packages/cli/core/generator/_endpoints_basic +11 -8
- package/packages/cli/core/generator/_help +1 -1
- package/packages/cli/core/generator/_models +5 -4
- package/packages/cli/core/generator/_models_basic +2 -2
- package/packages/cli/core/generator/_package +5 -1
- package/packages/cli/core/generator/{_add-on → _scheduler} +1 -1
- package/packages/cli/core/generator/_spec +15 -10
- package/packages/cli/core/generator/index.js +19 -44
- package/packages/cli/core/helpers/2fa.js +85 -0
- package/packages/cli/core/helpers/math.js +55 -7
- package/packages/cli/core/helpers/poolEntity.js +29 -1
- package/packages/cli/core/index.js +65 -34
- package/packages/cli/core/middleware/express/duplicateRequest.js +12 -0
- package/packages/cli/core/middleware/express/jwtCheckAllow.js +68 -0
- package/packages/cli/core/middleware/express/rateLimit.js +17 -0
- package/packages/cli/core/middleware/express/slowDown.js +2 -0
- package/packages/cli/core/middleware/index.js +6 -0
- package/packages/cli/core/middleware/origin/guard/advance.js +74 -0
- package/packages/cli/core/{origin → middleware/origin}/whitelist/cors.js +15 -12
- package/packages/cli/core/services/http.express.js +116 -72
- package/packages/lib/index.js +3 -1
- package/packages/lib/src/endpoint.js +523 -89
- package/packages/lib/src/guard.js +61 -0
- package/packages/lib/src/schema.js +57 -26
- package/packages/lib/src/specificExpress.js +7 -0
- package/packages/lib/src/user.js +94 -18
- package/packages/cli/core/origin/index.js +0 -2
|
@@ -1,33 +1,64 @@
|
|
|
1
|
+
const { Transaction } = require("sequelize");
|
|
2
|
+
let isolationLevel = { isolationLevel: Transaction.ISOLATION_LEVELS.SERIALIZABLE };
|
|
1
3
|
function Schema(Sequelize) {
|
|
2
4
|
return {
|
|
3
|
-
define: (table, schemaProps = {}) => {
|
|
4
|
-
|
|
5
|
-
|
|
6
|
-
|
|
7
|
-
|
|
8
|
-
|
|
9
|
-
|
|
10
|
-
|
|
11
|
-
|
|
12
|
-
|
|
13
|
-
|
|
14
|
-
|
|
15
|
-
|
|
16
|
-
|
|
17
|
-
|
|
18
|
-
|
|
19
|
-
|
|
20
|
-
|
|
21
|
-
|
|
22
|
-
|
|
23
|
-
|
|
5
|
+
define: (table, schemaProps = {}, elementProps = {}) => {
|
|
6
|
+
try {
|
|
7
|
+
let Project = Sequelize.define(table, schemaProps, elementProps);
|
|
8
|
+
return Object.assign(Project, {
|
|
9
|
+
query: (
|
|
10
|
+
rawSql,
|
|
11
|
+
props = {
|
|
12
|
+
model: Project,
|
|
13
|
+
mapToModel: false,
|
|
14
|
+
}
|
|
15
|
+
) => {
|
|
16
|
+
return new Promise((resolve) => {
|
|
17
|
+
if (props.mapToModel) {
|
|
18
|
+
let data = Sequelize.query(rawSql, props);
|
|
19
|
+
let results = [];
|
|
20
|
+
mapDataToModel(data, props.model, results, (err, r) => {
|
|
21
|
+
if (err) {
|
|
22
|
+
resolve([]);
|
|
23
|
+
} else {
|
|
24
|
+
resolve(r);
|
|
25
|
+
}
|
|
26
|
+
});
|
|
27
|
+
} else {
|
|
28
|
+
resolve(Sequelize.query(rawSql, props));
|
|
29
|
+
}
|
|
30
|
+
});
|
|
31
|
+
},
|
|
32
|
+
Sequelize,
|
|
33
|
+
/**
|
|
34
|
+
* Transaction
|
|
35
|
+
*
|
|
36
|
+
* @param object DEFAULT isolationLevel SERIALIZABLE
|
|
37
|
+
* @param cb Object
|
|
38
|
+
*
|
|
39
|
+
* @returns Object
|
|
40
|
+
*/
|
|
41
|
+
transaction: async (object, cb = null) => {
|
|
42
|
+
if(typeof object == "function") {
|
|
43
|
+
const t = await Sequelize.transaction(isolationLevel);
|
|
44
|
+
object(t);
|
|
45
|
+
} else if(cb) {
|
|
46
|
+
const t = await Sequelize.transaction(object = isolationLevel);
|
|
47
|
+
cb(t);
|
|
24
48
|
} else {
|
|
25
|
-
|
|
49
|
+
return await Sequelize.transaction(object = isolationLevel);
|
|
26
50
|
}
|
|
27
|
-
}
|
|
28
|
-
}
|
|
29
|
-
|
|
30
|
-
|
|
51
|
+
},
|
|
52
|
+
});
|
|
53
|
+
} catch (error) {
|
|
54
|
+
let errTurnOffDbDefine = JSON.stringify(error.toString()).match(/'define'/);
|
|
55
|
+
let errTurnOffDbOption = JSON.stringify(error.toString()).match(/'options'/);
|
|
56
|
+
if(errTurnOffDbDefine || errTurnOffDbOption) {
|
|
57
|
+
console.log(`\n[101m Failed [0m Database connection name is CLOSED.\n`, error);
|
|
58
|
+
} else {
|
|
59
|
+
console.log("\n[101m Failed [0m", error);
|
|
60
|
+
}
|
|
61
|
+
}
|
|
31
62
|
},
|
|
32
63
|
};
|
|
33
64
|
}
|
|
@@ -0,0 +1,7 @@
|
|
|
1
|
+
const { rateLimit } = require("../../cli/core/middleware/express/rateLimit");
|
|
2
|
+
const { slowDown } = require("../../cli/core/middleware/express/slowDown");
|
|
3
|
+
const { duplicateRequest } = require("../../cli/core/middleware/express/duplicateRequest");
|
|
4
|
+
let specificExpress = () => {
|
|
5
|
+
return { rateLimit, slowDown, duplicateRequest };
|
|
6
|
+
};
|
|
7
|
+
module.exports = { specificExpress };
|
package/packages/lib/src/user.js
CHANGED
|
@@ -1,4 +1,3 @@
|
|
|
1
|
-
const appRoot = require("app-root-path");
|
|
2
1
|
const md5 = require("md5");
|
|
3
2
|
const secret = require("./salt").salt;
|
|
4
3
|
const { findPassportPk } = require("../../cli/core/helpers/poolEntity");
|
|
@@ -7,7 +6,7 @@ async function FindOne(fields, fieldCondArr, cb) {
|
|
|
7
6
|
try {
|
|
8
7
|
const passport_config = require(appRoot + "/passport.config.js");
|
|
9
8
|
let stm = '';
|
|
10
|
-
let cond = '1';
|
|
9
|
+
let cond = '1=1';
|
|
11
10
|
let passportTable = await [passport_config.model.table || "users"];
|
|
12
11
|
const pool = await eval("sql." + passport_config.model.name);
|
|
13
12
|
let expectFields = await (fields[0]) ? fields : (passport_config.model.fields.length) ? passport_config.model.fields : [];
|
|
@@ -15,15 +14,17 @@ async function FindOne(fields, fieldCondArr, cb) {
|
|
|
15
14
|
if(err) {
|
|
16
15
|
cb(err, null);
|
|
17
16
|
} else {
|
|
17
|
+
let dynReplacement = [];
|
|
18
18
|
// Generate condition
|
|
19
|
-
|
|
20
|
-
cond +=
|
|
19
|
+
Object.keys(fieldCondArr).forEach(key => {
|
|
20
|
+
cond += ` AND ${key} = ?`;
|
|
21
|
+
dynReplacement.push(fieldCondArr[key]);
|
|
21
22
|
});
|
|
22
23
|
// check base pool
|
|
23
24
|
if (pool_base == "basic") {
|
|
24
25
|
// pool base is MySQL
|
|
25
|
-
stm += 'SELECT ?? FROM ?? WHERE ' + cond;
|
|
26
|
-
await pool.query(stm, [passportFields, passportTable], (err, row) => {
|
|
26
|
+
stm += 'SELECT ?? FROM ?? WHERE ' + cond + ' LIMIT 1;';
|
|
27
|
+
await pool.query(stm, [passportFields, passportTable, ...dynReplacement], (err, row) => {
|
|
27
28
|
if(err) {
|
|
28
29
|
cb(err, null);
|
|
29
30
|
} else {
|
|
@@ -35,11 +36,26 @@ async function FindOne(fields, fieldCondArr, cb) {
|
|
|
35
36
|
try {
|
|
36
37
|
stm += `SELECT ${passportFields} FROM ${passportTable} WHERE ` + cond;
|
|
37
38
|
let result = await pool.query(stm, {
|
|
39
|
+
replacements: [...dynReplacement],
|
|
38
40
|
type: QueryTypes.SELECT
|
|
39
41
|
});
|
|
40
42
|
return cb(null, result);
|
|
41
43
|
} catch (error) {
|
|
42
|
-
|
|
44
|
+
if(error.sql) {
|
|
45
|
+
delete error.sql;
|
|
46
|
+
if(error.parent) {
|
|
47
|
+
delete error.parent;
|
|
48
|
+
}
|
|
49
|
+
if(error.original) {
|
|
50
|
+
delete error.original.sql;
|
|
51
|
+
}
|
|
52
|
+
if(error.parameters) {
|
|
53
|
+
delete error.parameters;
|
|
54
|
+
}
|
|
55
|
+
return cb(error, null);
|
|
56
|
+
} else {
|
|
57
|
+
return cb(String(error), null);
|
|
58
|
+
}
|
|
43
59
|
}
|
|
44
60
|
} else {
|
|
45
61
|
return cb({ error: "The Base pool error. UNKNOWN pool_base = '"+ pool_base +"'" }, null);
|
|
@@ -71,14 +87,14 @@ async function Store(fields, cb) {
|
|
|
71
87
|
}
|
|
72
88
|
if(key == passwordField) {
|
|
73
89
|
haveUsernameAndPassword += 1;
|
|
90
|
+
// asign pwd hash
|
|
91
|
+
fields[passwordField] = md5(fields[passwordField] + secret);
|
|
74
92
|
}
|
|
75
93
|
keys.push(key);
|
|
76
94
|
values.push(fields[key]);
|
|
77
95
|
escaped.push('?');
|
|
78
96
|
});
|
|
79
97
|
if(haveUsernameAndPassword > 1) {
|
|
80
|
-
// asign password hash
|
|
81
|
-
fields[passwordField] = md5(fields[passwordField] + secret);
|
|
82
98
|
// check base pool
|
|
83
99
|
if (pool_base == "basic") {
|
|
84
100
|
// pool base is MySQL
|
|
@@ -108,7 +124,25 @@ async function Store(fields, cb) {
|
|
|
108
124
|
affectedRows: result[1]
|
|
109
125
|
});
|
|
110
126
|
} catch (error) {
|
|
111
|
-
|
|
127
|
+
if(pool.options.logging) {
|
|
128
|
+
return cb(error, null);
|
|
129
|
+
} else {
|
|
130
|
+
if(error.sql) {
|
|
131
|
+
delete error.sql;
|
|
132
|
+
if(error.parent) {
|
|
133
|
+
delete error.parent;
|
|
134
|
+
}
|
|
135
|
+
if(error.original) {
|
|
136
|
+
delete error.original.sql;
|
|
137
|
+
}
|
|
138
|
+
if(error.parameters) {
|
|
139
|
+
delete error.parameters;
|
|
140
|
+
}
|
|
141
|
+
return cb(error, null);
|
|
142
|
+
} else {
|
|
143
|
+
return cb(String(error), null);
|
|
144
|
+
}
|
|
145
|
+
}
|
|
112
146
|
}
|
|
113
147
|
} else {
|
|
114
148
|
return cb({ error: "The Base pool error. UNKNOWN pool_base = '"+ pool_base +"'" }, null);
|
|
@@ -155,7 +189,7 @@ async function Update(someFields, id, cb) {
|
|
|
155
189
|
cb(error, null);
|
|
156
190
|
} else {
|
|
157
191
|
cb(null, {
|
|
158
|
-
updateId: parseInt(id),
|
|
192
|
+
updateId: (result.changedRows) ? parseInt(id) : null,
|
|
159
193
|
affectedRows: result.changedRows
|
|
160
194
|
});
|
|
161
195
|
}
|
|
@@ -173,17 +207,59 @@ async function Update(someFields, id, cb) {
|
|
|
173
207
|
type: QueryTypes.UPDATE
|
|
174
208
|
}).then((result) => {
|
|
175
209
|
return cb(null, {
|
|
176
|
-
updateId: parseInt(id),
|
|
177
|
-
affectedRows: result[1]
|
|
210
|
+
updateId: (result[1]) ? parseInt(id) : null,
|
|
211
|
+
affectedRows: result[1],
|
|
178
212
|
});
|
|
179
|
-
}).catch((
|
|
180
|
-
|
|
213
|
+
}).catch((error) => {
|
|
214
|
+
if(pool.options.logging) {
|
|
215
|
+
return cb(error, null);
|
|
216
|
+
} else {
|
|
217
|
+
if(error.sql) {
|
|
218
|
+
delete error.sql;
|
|
219
|
+
if(error.errors) {
|
|
220
|
+
delete error.errors;
|
|
221
|
+
}
|
|
222
|
+
if(error.parent) {
|
|
223
|
+
delete error.parent;
|
|
224
|
+
}
|
|
225
|
+
if(error.original) {
|
|
226
|
+
delete error.original.sql;
|
|
227
|
+
}
|
|
228
|
+
if(error.parameters) {
|
|
229
|
+
delete error.parameters;
|
|
230
|
+
}
|
|
231
|
+
return cb(error, null);
|
|
232
|
+
} else {
|
|
233
|
+
return cb(String(error), null);
|
|
234
|
+
}
|
|
235
|
+
}
|
|
181
236
|
});
|
|
182
|
-
}).catch((
|
|
183
|
-
|
|
237
|
+
}).catch((error) => {
|
|
238
|
+
if(pool.options.logging) {
|
|
239
|
+
return cb(error, null);
|
|
240
|
+
} else {
|
|
241
|
+
if(error.sql) {
|
|
242
|
+
delete error.sql;
|
|
243
|
+
if(error.errors) {
|
|
244
|
+
delete error.errors;
|
|
245
|
+
}
|
|
246
|
+
if(error.parent) {
|
|
247
|
+
delete error.parent;
|
|
248
|
+
}
|
|
249
|
+
if(error.original) {
|
|
250
|
+
delete error.original.sql;
|
|
251
|
+
}
|
|
252
|
+
if(error.parameters) {
|
|
253
|
+
delete error.parameters;
|
|
254
|
+
}
|
|
255
|
+
return cb(error, null);
|
|
256
|
+
} else {
|
|
257
|
+
return cb(String(error), null);
|
|
258
|
+
}
|
|
259
|
+
}
|
|
184
260
|
});
|
|
185
261
|
} catch (error) {
|
|
186
|
-
return cb(error
|
|
262
|
+
return cb(error, null);
|
|
187
263
|
}
|
|
188
264
|
} else {
|
|
189
265
|
return cb({ error: "The Base pool error. UNKNOWN pool_base = '"+ pool_base +"'" }, null);
|