evaengine 1.0.14 → 3.0.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 +15 -7
- package/bin/engine +2 -31
- package/dist/bin.d.ts +1 -0
- package/dist/bin.js +32 -0
- package/dist/bin.js.map +1 -0
- package/{src/commands/index.js → dist/commands/index.d.ts} +1 -8
- package/dist/commands/index.js +6 -0
- package/dist/commands/index.js.map +1 -0
- package/dist/commands/interface.d.ts +18 -0
- package/dist/commands/interface.js +40 -0
- package/dist/commands/interface.js.map +1 -0
- package/dist/commands/make_entity.d.ts +47 -0
- package/dist/commands/make_entity.js +410 -0
- package/dist/commands/make_entity.js.map +1 -0
- package/dist/commands/tramp.d.ts +7 -0
- package/dist/commands/tramp.js +29 -0
- package/dist/commands/tramp.js.map +1 -0
- package/dist/config/index.d.ts +92 -0
- package/dist/config/index.js +96 -0
- package/dist/config/index.js.map +1 -0
- package/dist/di.d.ts +131 -0
- package/dist/di.js +197 -0
- package/dist/di.js.map +1 -0
- package/dist/engine.d.ts +85 -0
- package/dist/engine.js +404 -0
- package/dist/engine.js.map +1 -0
- package/dist/entities/index.d.ts +54 -0
- package/dist/entities/index.js +228 -0
- package/dist/entities/index.js.map +1 -0
- package/dist/exceptions/index.d.ts +153 -0
- package/dist/exceptions/index.js +466 -0
- package/dist/exceptions/index.js.map +1 -0
- package/dist/index.d.ts +41 -0
- package/dist/index.js +43 -0
- package/dist/index.js.map +1 -0
- package/dist/middlewares/auth.d.ts +5 -0
- package/dist/middlewares/auth.js +63 -0
- package/dist/middlewares/auth.js.map +1 -0
- package/dist/middlewares/auth_kong.d.ts +2 -0
- package/dist/middlewares/auth_kong.js +24 -0
- package/dist/middlewares/auth_kong.js.map +1 -0
- package/dist/middlewares/debug.d.ts +3 -0
- package/dist/middlewares/debug.js +50 -0
- package/dist/middlewares/debug.js.map +1 -0
- package/{src/middlewares/index.js → dist/middlewares/index.d.ts} +1 -11
- package/dist/middlewares/index.js +9 -0
- package/dist/middlewares/index.js.map +1 -0
- package/dist/middlewares/providers.d.ts +25 -0
- package/dist/middlewares/providers.js +63 -0
- package/dist/middlewares/providers.js.map +1 -0
- package/dist/middlewares/session.d.ts +5 -0
- package/dist/middlewares/session.js +46 -0
- package/dist/middlewares/session.js.map +1 -0
- package/dist/middlewares/trace.d.ts +52 -0
- package/dist/middlewares/trace.js +225 -0
- package/dist/middlewares/trace.js.map +1 -0
- package/dist/middlewares/validator.d.ts +10 -0
- package/dist/middlewares/validator.js +43 -0
- package/dist/middlewares/validator.js.map +1 -0
- package/dist/middlewares/view_cache.d.ts +14 -0
- package/dist/middlewares/view_cache.js +102 -0
- package/dist/middlewares/view_cache.js.map +1 -0
- package/dist/services/cache.d.ts +68 -0
- package/dist/services/cache.js +206 -0
- package/dist/services/cache.js.map +1 -0
- package/dist/services/config.d.ts +17 -0
- package/dist/services/config.js +67 -0
- package/dist/services/config.js.map +1 -0
- package/dist/services/env.d.ts +12 -0
- package/dist/services/env.js +24 -0
- package/dist/services/env.js.map +1 -0
- package/dist/services/event_manager.d.ts +30 -0
- package/dist/services/event_manager.js +74 -0
- package/dist/services/event_manager.js.map +1 -0
- package/dist/services/http_client.d.ts +67 -0
- package/dist/services/http_client.js +61 -0
- package/dist/services/http_client.js.map +1 -0
- package/{src/services/index.js → dist/services/index.d.ts} +1 -15
- package/dist/services/index.js +14 -0
- package/dist/services/index.js.map +1 -0
- package/{src/services/interface.js → dist/services/interface.d.ts} +1 -3
- package/dist/services/interface.js +6 -0
- package/dist/services/interface.js.map +1 -0
- package/{src/services/joi.js → dist/services/joi.d.ts} +2 -9
- package/dist/services/joi.js +11 -0
- package/dist/services/joi.js.map +1 -0
- package/dist/services/jwt_token.d.ts +25 -0
- package/dist/services/jwt_token.js +76 -0
- package/dist/services/jwt_token.js.map +1 -0
- package/dist/services/jwt_token_kong.d.ts +26 -0
- package/dist/services/jwt_token_kong.js +64 -0
- package/dist/services/jwt_token_kong.js.map +1 -0
- package/dist/services/logger.d.ts +31 -0
- package/dist/services/logger.js +125 -0
- package/dist/services/logger.js.map +1 -0
- package/dist/services/namespace.d.ts +62 -0
- package/dist/services/namespace.js +171 -0
- package/dist/services/namespace.js.map +1 -0
- package/dist/services/now.d.ts +15 -0
- package/dist/services/now.js +42 -0
- package/dist/services/now.js.map +1 -0
- package/dist/services/providers.d.ts +55 -0
- package/dist/services/providers.js +134 -0
- package/dist/services/providers.js.map +1 -0
- package/dist/services/redis.d.ts +19 -0
- package/dist/services/redis.js +52 -0
- package/dist/services/redis.js.map +1 -0
- package/dist/services/rest_client.d.ts +49 -0
- package/dist/services/rest_client.js +95 -0
- package/dist/services/rest_client.js.map +1 -0
- package/dist/swagger/index.d.ts +223 -0
- package/dist/swagger/index.js +564 -0
- package/dist/swagger/index.js.map +1 -0
- package/dist/types/express.d.ts +14 -0
- package/dist/types/vendor.d.ts +30 -0
- package/dist/utils/api_scaffold.d.ts +74 -0
- package/dist/utils/api_scaffold.js +220 -0
- package/dist/utils/api_scaffold.js.map +1 -0
- package/dist/utils/case_converter.d.ts +7 -0
- package/dist/utils/case_converter.js +29 -0
- package/dist/utils/case_converter.js.map +1 -0
- package/dist/utils/crc32.d.ts +2 -0
- package/dist/utils/crc32.js +43 -0
- package/dist/utils/crc32.js.map +1 -0
- package/dist/utils/cron.d.ts +27 -0
- package/dist/utils/cron.js +186 -0
- package/dist/utils/cron.js.map +1 -0
- package/dist/utils/datetime.d.ts +4 -0
- package/dist/utils/datetime.js +6 -0
- package/dist/utils/datetime.js.map +1 -0
- package/dist/utils/host.d.ts +18 -0
- package/dist/utils/host.js +33 -0
- package/dist/utils/host.js.map +1 -0
- package/{src/utils/index.js → dist/utils/index.d.ts} +2 -26
- package/dist/utils/index.js +12 -0
- package/dist/utils/index.js.map +1 -0
- package/dist/utils/jwt.d.ts +16 -0
- package/dist/utils/jwt.js +93 -0
- package/dist/utils/jwt.js.map +1 -0
- package/dist/utils/pagination.d.ts +150 -0
- package/dist/utils/pagination.js +242 -0
- package/dist/utils/pagination.js.map +1 -0
- package/dist/utils/random.d.ts +3 -0
- package/dist/utils/random.js +18 -0
- package/dist/utils/random.js.map +1 -0
- package/dist/utils/request_client.d.ts +33 -0
- package/dist/utils/request_client.js +153 -0
- package/dist/utils/request_client.js.map +1 -0
- package/dist/utils/smart_query.d.ts +144 -0
- package/dist/utils/smart_query.js +310 -0
- package/dist/utils/smart_query.js.map +1 -0
- package/dist/utils/test.d.ts +14 -0
- package/dist/utils/test.js +37 -0
- package/dist/utils/test.js.map +1 -0
- package/dist/utils/wrapper.d.ts +3 -0
- package/dist/utils/wrapper.js +5 -0
- package/dist/utils/wrapper.js.map +1 -0
- package/package.json +22 -15
- package/index.js +0 -2
- package/src/commands/interface.js +0 -45
- package/src/commands/make_entity.js +0 -490
- package/src/commands/tramp.js +0 -34
- package/src/config/index.js +0 -95
- package/src/di.js +0 -96
- package/src/engine.js +0 -556
- package/src/entities/index.js +0 -272
- package/src/exceptions/index.js +0 -501
- package/src/index.js +0 -55
- package/src/middlewares/auth.js +0 -67
- package/src/middlewares/auth_kong.js +0 -28
- package/src/middlewares/debug.js +0 -88
- package/src/middlewares/providers.js +0 -73
- package/src/middlewares/session.js +0 -63
- package/src/middlewares/trace.js +0 -254
- package/src/middlewares/validator.js +0 -50
- package/src/middlewares/view_cache.js +0 -127
- package/src/services/cache.js +0 -223
- package/src/services/config.js +0 -115
- package/src/services/env.js +0 -28
- package/src/services/event_manager.js +0 -84
- package/src/services/http_client.js +0 -69
- package/src/services/jwt_token.js +0 -89
- package/src/services/jwt_token_kong.js +0 -75
- package/src/services/logger.js +0 -150
- package/src/services/namespace.js +0 -176
- package/src/services/now.js +0 -49
- package/src/services/providers.js +0 -158
- package/src/services/redis.js +0 -63
- package/src/services/rest_client.js +0 -112
- package/src/swagger/index.js +0 -665
- package/src/utils/api_scaffold.js +0 -240
- package/src/utils/case_converter.js +0 -33
- package/src/utils/crc32.js +0 -44
- package/src/utils/cron.js +0 -208
- package/src/utils/datetime.js +0 -13
- package/src/utils/host.js +0 -39
- package/src/utils/pagination.js +0 -260
- package/src/utils/random.js +0 -23
- package/src/utils/request_client.js +0 -179
- package/src/utils/smart_query.js +0 -352
- package/src/utils/test.js +0 -48
- package/src/utils/wrapper.js +0 -8
|
@@ -1,490 +0,0 @@
|
|
|
1
|
-
import groupBy from 'lodash/groupBy.js';
|
|
2
|
-
import template from 'lodash/template.js';
|
|
3
|
-
import Sequelize from 'sequelize';
|
|
4
|
-
import fs from 'fs';
|
|
5
|
-
import Command from './interface.js';
|
|
6
|
-
import DI from '../di.js';
|
|
7
|
-
import Entities from '../entities/index.js';
|
|
8
|
-
|
|
9
|
-
|
|
10
|
-
export class MakeDbView extends Command {
|
|
11
|
-
static getName() {
|
|
12
|
-
return 'make:dbview';
|
|
13
|
-
}
|
|
14
|
-
|
|
15
|
-
static getDescription() {
|
|
16
|
-
return 'Generate db views';
|
|
17
|
-
}
|
|
18
|
-
|
|
19
|
-
static getSpec() {
|
|
20
|
-
return {
|
|
21
|
-
entity_path: {
|
|
22
|
-
required: false,
|
|
23
|
-
description: 'Entity path'
|
|
24
|
-
},
|
|
25
|
-
dir: {
|
|
26
|
-
required: false,
|
|
27
|
-
description: 'Where view.sql to be generated'
|
|
28
|
-
}
|
|
29
|
-
};
|
|
30
|
-
}
|
|
31
|
-
|
|
32
|
-
getSql(tableName, attributes) {
|
|
33
|
-
const attrs = attributes.map((attr) => {
|
|
34
|
-
const { fieldName } = attr;
|
|
35
|
-
if (fieldName.endsWith('At')) {
|
|
36
|
-
return ` FROM_UNIXTIME(IF(${fieldName} > 0, ${fieldName}, NULL)) AS ${fieldName}`;
|
|
37
|
-
}
|
|
38
|
-
return ` \`${fieldName}\` AS \`${fieldName}\``;
|
|
39
|
-
});
|
|
40
|
-
return `DROP VIEW IF EXISTS view_${tableName};
|
|
41
|
-
CREATE ALGORITHM=UNDEFINED SQL SECURITY DEFINER VIEW view_${tableName}
|
|
42
|
-
AS SELECT
|
|
43
|
-
${attrs.join(',\n ')}
|
|
44
|
-
FROM ${tableName};
|
|
45
|
-
|
|
46
|
-
`;
|
|
47
|
-
}
|
|
48
|
-
|
|
49
|
-
async run() {
|
|
50
|
-
const logger = DI.get('logger');
|
|
51
|
-
const { dir, entity_path: entityPath = `${process.cwd()}/build/entities` } = this.getArgv();
|
|
52
|
-
const path = dir ? `${process.cwd()}/${dir}` : `${process.cwd()}/sql`;
|
|
53
|
-
const file = [path, 'views.sql'].join('/');
|
|
54
|
-
logger.info('Scan entity files under %s', entityPath);
|
|
55
|
-
const entities = new Entities(entityPath);
|
|
56
|
-
|
|
57
|
-
logger.info('Start generate db views to %s', file);
|
|
58
|
-
fs.mkdirSync(path, { recursive: true });
|
|
59
|
-
const models = Object.values(entities.getInstance().models);
|
|
60
|
-
const sql = [];
|
|
61
|
-
models.forEach((model) => {
|
|
62
|
-
logger.info(`Creating ${model.getTableName()} view`);
|
|
63
|
-
sql.push(this.getSql(model.getTableName(), Object.values(model.attributes)));
|
|
64
|
-
});
|
|
65
|
-
|
|
66
|
-
fs.writeFileSync(file, sql.join(''));
|
|
67
|
-
logger.info('Views created');
|
|
68
|
-
}
|
|
69
|
-
}
|
|
70
|
-
|
|
71
|
-
export class MakeEntity extends Command {
|
|
72
|
-
static getName() {
|
|
73
|
-
return 'make:entity';
|
|
74
|
-
}
|
|
75
|
-
|
|
76
|
-
static getDescription() {
|
|
77
|
-
return 'Generate entities';
|
|
78
|
-
}
|
|
79
|
-
|
|
80
|
-
static getSpec() {
|
|
81
|
-
return {
|
|
82
|
-
timestamp: {
|
|
83
|
-
required: false,
|
|
84
|
-
description: 'Sequelize timestamp enabled'
|
|
85
|
-
},
|
|
86
|
-
dir: {
|
|
87
|
-
required: false,
|
|
88
|
-
description: 'Where entity files to be generated'
|
|
89
|
-
},
|
|
90
|
-
prefix: {
|
|
91
|
-
required: false,
|
|
92
|
-
description: 'Table prefix'
|
|
93
|
-
}
|
|
94
|
-
};
|
|
95
|
-
}
|
|
96
|
-
|
|
97
|
-
static typeMapping(_type) {
|
|
98
|
-
const type = _type.toLowerCase();
|
|
99
|
-
if (type === 'tinyint(1)' || type === 'boolean' || type === 'bit(1)') {
|
|
100
|
-
return 'DataTypes.BOOLEAN';
|
|
101
|
-
}
|
|
102
|
-
|
|
103
|
-
if (type.match(/^(smallint|mediumint|tinyint|int)/)) {
|
|
104
|
-
const length = type.match(/\(\d+\)/) || '';
|
|
105
|
-
return `DataTypes.INTEGER${length}`;
|
|
106
|
-
}
|
|
107
|
-
|
|
108
|
-
if (type.startsWith('bigint')) {
|
|
109
|
-
return 'DataTypes.BIGINT';
|
|
110
|
-
}
|
|
111
|
-
if (type.startsWith('enum')) {
|
|
112
|
-
return type.replace('enum', 'DataTypes.ENUM').replace(/,/g, ', ');
|
|
113
|
-
}
|
|
114
|
-
|
|
115
|
-
if (type.match(/^string|varchar|varying|nvarchar/)) {
|
|
116
|
-
const length = type.match(/\(\d+\)/) || '';
|
|
117
|
-
return length ? `DataTypes.STRING${length}` : 'DataTypes.STRING';
|
|
118
|
-
}
|
|
119
|
-
|
|
120
|
-
if (type.startsWith('char')) {
|
|
121
|
-
const length = type.match(/\(\d+\)/) || '';
|
|
122
|
-
return `DataTypes.CHAR${length}`;
|
|
123
|
-
}
|
|
124
|
-
|
|
125
|
-
if (type.match(/text|ntext$/)) {
|
|
126
|
-
return 'DataTypes.TEXT';
|
|
127
|
-
}
|
|
128
|
-
|
|
129
|
-
if (type.startsWith('year')) {
|
|
130
|
-
return 'DataTypes.INTEGER(4)';
|
|
131
|
-
}
|
|
132
|
-
|
|
133
|
-
if (type.startsWith('datetime')) {
|
|
134
|
-
return 'DataTypes.DATE';
|
|
135
|
-
}
|
|
136
|
-
|
|
137
|
-
if (type.startsWith('date')) {
|
|
138
|
-
return 'DataTypes.DATEONLY';
|
|
139
|
-
}
|
|
140
|
-
|
|
141
|
-
if (type.startsWith('time')) {
|
|
142
|
-
return 'DataTypes.TIME';
|
|
143
|
-
}
|
|
144
|
-
|
|
145
|
-
if (type.match(/^(float8|double precision)/)) {
|
|
146
|
-
return 'DataTypes.DOUBLE';
|
|
147
|
-
}
|
|
148
|
-
|
|
149
|
-
if (type.match(/^(float|float4)/)) {
|
|
150
|
-
return 'DataTypes.FLOAT';
|
|
151
|
-
}
|
|
152
|
-
|
|
153
|
-
if (type.startsWith('decimal')) {
|
|
154
|
-
const [, length, bits] = /\((\d+),(\d+)\)/g.exec(type) || [];
|
|
155
|
-
return length ? `DataTypes.DECIMAL(${length}, ${bits})` : 'DataTypes.DECIMAL';
|
|
156
|
-
}
|
|
157
|
-
|
|
158
|
-
if (type.match(/^uuid|uniqueidentifier/)) {
|
|
159
|
-
return 'DataTypes.UUIDV4';
|
|
160
|
-
}
|
|
161
|
-
|
|
162
|
-
if (type.startsWith('jsonb')) {
|
|
163
|
-
return 'DataTypes.JSONB';
|
|
164
|
-
}
|
|
165
|
-
if (type.startsWith('json')) {
|
|
166
|
-
return 'DataTypes.JSON';
|
|
167
|
-
}
|
|
168
|
-
|
|
169
|
-
if (type.startsWith('geometry')) {
|
|
170
|
-
return 'DataTypes.GEOMETRY';
|
|
171
|
-
}
|
|
172
|
-
|
|
173
|
-
return type;
|
|
174
|
-
}
|
|
175
|
-
|
|
176
|
-
static typeAdditional(_type, sequlizeType, rawColumn) {
|
|
177
|
-
const type = _type.toLowerCase();
|
|
178
|
-
let finalType = sequlizeType;
|
|
179
|
-
|
|
180
|
-
if (type.match(/unsigned/)) {
|
|
181
|
-
finalType += '.UNSIGNED';
|
|
182
|
-
}
|
|
183
|
-
|
|
184
|
-
if (type.match(/zerofill/)) {
|
|
185
|
-
finalType += '.ZEROFILL';
|
|
186
|
-
}
|
|
187
|
-
|
|
188
|
-
if (rawColumn.Collation === 'utf8_bin') {
|
|
189
|
-
finalType += '.BINARY';
|
|
190
|
-
}
|
|
191
|
-
return finalType;
|
|
192
|
-
}
|
|
193
|
-
|
|
194
|
-
static async getIndexes(tableName, sequelize) {
|
|
195
|
-
let rawIndexes = await sequelize.query(
|
|
196
|
-
`SHOW INDEX FROM ${tableName}`,
|
|
197
|
-
{
|
|
198
|
-
type: sequelize.QueryTypes.SELECT,
|
|
199
|
-
raw: true
|
|
200
|
-
}
|
|
201
|
-
);
|
|
202
|
-
if (!rawIndexes) {
|
|
203
|
-
return [];
|
|
204
|
-
}
|
|
205
|
-
rawIndexes = groupBy(rawIndexes, 'Key_name');
|
|
206
|
-
return Object.entries(rawIndexes).filter(([key]) => key !== 'PRIMARY').map(([name, columns]) => {
|
|
207
|
-
const index = columns[0].Non_unique !== 1 ? { name, unique: true } : { name };
|
|
208
|
-
index.fields = columns.map(c => c.Column_name);
|
|
209
|
-
return index;
|
|
210
|
-
});
|
|
211
|
-
}
|
|
212
|
-
|
|
213
|
-
async run() {
|
|
214
|
-
const config = DI.get('config').get();
|
|
215
|
-
const logger = DI.get('logger');
|
|
216
|
-
const sequelize = new Sequelize(
|
|
217
|
-
config.db.database,
|
|
218
|
-
null,
|
|
219
|
-
null,
|
|
220
|
-
Object.assign({}, config.sequelize, config.db, { logging: logger.getInstance().verbose })
|
|
221
|
-
);
|
|
222
|
-
const query = sequelize.getQueryInterface();
|
|
223
|
-
|
|
224
|
-
let tables = await query.showAllTables();
|
|
225
|
-
const views = await sequelize.query(`SHOW FULL TABLES IN ${config.db.database} WHERE TABLE_TYPE LIKE 'VIEW'`, {
|
|
226
|
-
type: sequelize.QueryTypes.SELECT,
|
|
227
|
-
raw: true
|
|
228
|
-
});
|
|
229
|
-
if (views) {
|
|
230
|
-
const viewNames = views.map(v => Object.values(v)[0]);
|
|
231
|
-
tables = tables.filter(t => !viewNames.includes(t));
|
|
232
|
-
}
|
|
233
|
-
const { dir, timestamp = true, prefix } = this.getArgv();
|
|
234
|
-
if (prefix) {
|
|
235
|
-
tables = tables.filter(t => t.startsWith(prefix));
|
|
236
|
-
}
|
|
237
|
-
|
|
238
|
-
const path = dir ? `${process.cwd()}/${dir}` : `${process.cwd()}/src/entities`;
|
|
239
|
-
const schemaPath = `${path}/schemas`;
|
|
240
|
-
const entityTemplate = fs.readFileSync(`${import.meta.dirname}/../../template/entity.ejs`, 'utf8');
|
|
241
|
-
const schemaTemplate = fs.readFileSync(`${import.meta.dirname}/../../template/schema.ejs`, 'utf8');
|
|
242
|
-
fs.mkdirSync(path, { recursive: true });
|
|
243
|
-
fs.mkdirSync(schemaPath, { recursive: true });
|
|
244
|
-
|
|
245
|
-
logger.info('Start generate DB schemas to dir %s', path);
|
|
246
|
-
|
|
247
|
-
const tableHandler = async (table) => {
|
|
248
|
-
const columns = await query.describeTable(table);
|
|
249
|
-
const rawColumns = await sequelize.query(`SHOW FULL COLUMNS FROM ${table}`, {
|
|
250
|
-
type: sequelize.QueryTypes.SELECT,
|
|
251
|
-
raw: true
|
|
252
|
-
});
|
|
253
|
-
Object.values(rawColumns).forEach((rawColumn) => {
|
|
254
|
-
const columnName = rawColumn.Field;
|
|
255
|
-
columns[columnName].type = MakeEntity.typeAdditional(
|
|
256
|
-
columns[columnName].type,
|
|
257
|
-
MakeEntity.typeMapping(columns[columnName].type),
|
|
258
|
-
rawColumn
|
|
259
|
-
);
|
|
260
|
-
columns[columnName].unique = rawColumn.Key === 'UNI';
|
|
261
|
-
columns[columnName].comment = rawColumn.Comment;
|
|
262
|
-
columns[columnName].autoIncrement = rawColumn.Extra.startsWith('auto_increment') === true;
|
|
263
|
-
});
|
|
264
|
-
|
|
265
|
-
const indexes = await MakeEntity.getIndexes(table, sequelize);
|
|
266
|
-
const entityFile = `${path}/${table}.js`;
|
|
267
|
-
const schemaFile = `${schemaPath}/${table}.js`;
|
|
268
|
-
try {
|
|
269
|
-
fs.accessSync(entityFile);
|
|
270
|
-
logger.info('Entity file %s generate skipped, already exists by %s', table, entityFile);
|
|
271
|
-
} catch {
|
|
272
|
-
fs.writeFileSync(entityFile, template(entityTemplate)({ table }));
|
|
273
|
-
logger.info('Entity file %s generated as %s', table, entityFile);
|
|
274
|
-
}
|
|
275
|
-
|
|
276
|
-
try {
|
|
277
|
-
fs.accessSync(schemaFile);
|
|
278
|
-
logger.info('Schema file %s generate override, already exists by %s', table, schemaFile);
|
|
279
|
-
} catch {
|
|
280
|
-
logger.info('Schema file %s generated as %s', table, schemaFile);
|
|
281
|
-
}
|
|
282
|
-
fs.writeFileSync(schemaFile, template(schemaTemplate)({
|
|
283
|
-
columns,
|
|
284
|
-
table,
|
|
285
|
-
indexes,
|
|
286
|
-
timestamp: parseInt(timestamp, 10) > 0
|
|
287
|
-
}));
|
|
288
|
-
};
|
|
289
|
-
|
|
290
|
-
//Skip sequelize migrate table
|
|
291
|
-
await Promise.all(Object.values(tables).filter(t => !['sequelizemeta', 'tramp_migrations'].includes(t)).map(tableHandler));
|
|
292
|
-
logger.info('All DB schemas generated');
|
|
293
|
-
}
|
|
294
|
-
}
|
|
295
|
-
|
|
296
|
-
export class MakeGraphql extends Command {
|
|
297
|
-
static getName() {
|
|
298
|
-
return 'make:graphql';
|
|
299
|
-
}
|
|
300
|
-
|
|
301
|
-
static getDescription() {
|
|
302
|
-
return 'Generate graphql schema';
|
|
303
|
-
}
|
|
304
|
-
|
|
305
|
-
static getSpec() {
|
|
306
|
-
return {
|
|
307
|
-
dir: {
|
|
308
|
-
required: false,
|
|
309
|
-
description: 'Where entity files to be generated'
|
|
310
|
-
},
|
|
311
|
-
prefix: {
|
|
312
|
-
required: false,
|
|
313
|
-
description: 'Table prefix'
|
|
314
|
-
},
|
|
315
|
-
mapping: {
|
|
316
|
-
required: false,
|
|
317
|
-
description: 'Mapping file path'
|
|
318
|
-
}
|
|
319
|
-
};
|
|
320
|
-
}
|
|
321
|
-
|
|
322
|
-
static typeMapping(_type) {
|
|
323
|
-
const type = _type.toLowerCase();
|
|
324
|
-
if (type === 'tinyint(1)' || type === 'boolean' || type === 'bit(1)') {
|
|
325
|
-
return 'Boolean';
|
|
326
|
-
}
|
|
327
|
-
|
|
328
|
-
if (type.match(/^(smallint|mediumint|tinyint|int)/)) {
|
|
329
|
-
return 'Int';
|
|
330
|
-
}
|
|
331
|
-
|
|
332
|
-
if (type.startsWith('bigint')) {
|
|
333
|
-
return 'Int';
|
|
334
|
-
}
|
|
335
|
-
|
|
336
|
-
if (type.startsWith('enum')) {
|
|
337
|
-
return 'Enum';
|
|
338
|
-
}
|
|
339
|
-
|
|
340
|
-
if (type.match(/^string|varchar|varying|nvarchar/)) {
|
|
341
|
-
return 'String';
|
|
342
|
-
}
|
|
343
|
-
|
|
344
|
-
if (type.startsWith('char')) {
|
|
345
|
-
return 'String';
|
|
346
|
-
}
|
|
347
|
-
|
|
348
|
-
if (type.match(/text|ntext$/)) {
|
|
349
|
-
return 'String';
|
|
350
|
-
}
|
|
351
|
-
|
|
352
|
-
if (type.startsWith('year')) {
|
|
353
|
-
return 'Int';
|
|
354
|
-
}
|
|
355
|
-
|
|
356
|
-
if (type.startsWith('datetime')) {
|
|
357
|
-
return 'String';
|
|
358
|
-
}
|
|
359
|
-
|
|
360
|
-
if (type.startsWith('date')) {
|
|
361
|
-
return 'String';
|
|
362
|
-
}
|
|
363
|
-
|
|
364
|
-
if (type.startsWith('time')) {
|
|
365
|
-
return 'String';
|
|
366
|
-
}
|
|
367
|
-
|
|
368
|
-
if (type.match(/^(float8|double precision)/)) {
|
|
369
|
-
return 'Float';
|
|
370
|
-
}
|
|
371
|
-
|
|
372
|
-
if (type.match(/^(float|float4)/)) {
|
|
373
|
-
return 'Float';
|
|
374
|
-
}
|
|
375
|
-
|
|
376
|
-
if (type.startsWith('decimal')) {
|
|
377
|
-
return 'Float';
|
|
378
|
-
}
|
|
379
|
-
|
|
380
|
-
if (type.match(/^uuid|uniqueidentifier/)) {
|
|
381
|
-
return 'String';
|
|
382
|
-
}
|
|
383
|
-
|
|
384
|
-
if (type.startsWith('jsonb')) {
|
|
385
|
-
return 'JSON';
|
|
386
|
-
}
|
|
387
|
-
if (type.startsWith('json')) {
|
|
388
|
-
return 'JSON';
|
|
389
|
-
}
|
|
390
|
-
|
|
391
|
-
if (type.startsWith('geometry')) {
|
|
392
|
-
return 'String';
|
|
393
|
-
}
|
|
394
|
-
|
|
395
|
-
return type;
|
|
396
|
-
}
|
|
397
|
-
|
|
398
|
-
getEnums(_type, columnName, tableName) {
|
|
399
|
-
const type = _type.toLowerCase();
|
|
400
|
-
const values = type.slice(5, -1).split(',').map(v => v.slice(1, -1));
|
|
401
|
-
return {
|
|
402
|
-
name: `ENUM_${tableName}_${columnName}`,
|
|
403
|
-
values
|
|
404
|
-
};
|
|
405
|
-
}
|
|
406
|
-
|
|
407
|
-
async run() {
|
|
408
|
-
const config = DI.get('config').get();
|
|
409
|
-
const logger = DI.get('logger');
|
|
410
|
-
const sequelize = new Sequelize(
|
|
411
|
-
config.db.database,
|
|
412
|
-
null,
|
|
413
|
-
null,
|
|
414
|
-
Object.assign({}, config.sequelize, config.db, { logging: logger.getInstance().verbose })
|
|
415
|
-
);
|
|
416
|
-
const query = sequelize.getQueryInterface();
|
|
417
|
-
|
|
418
|
-
let tables = await query.showAllTables();
|
|
419
|
-
const views = await sequelize.query(`SHOW FULL TABLES IN ${config.db.database} WHERE TABLE_TYPE LIKE 'VIEW'`, {
|
|
420
|
-
type: sequelize.QueryTypes.SELECT,
|
|
421
|
-
raw: true
|
|
422
|
-
});
|
|
423
|
-
if (views) {
|
|
424
|
-
const viewNames = views.map(v => Object.values(v)[0]);
|
|
425
|
-
tables = tables.filter(t => !viewNames.includes(t));
|
|
426
|
-
}
|
|
427
|
-
const {
|
|
428
|
-
dir, prefix, mapping
|
|
429
|
-
} = this.getArgv();
|
|
430
|
-
if (prefix) {
|
|
431
|
-
tables = tables.filter(t => t.startsWith(prefix));
|
|
432
|
-
}
|
|
433
|
-
|
|
434
|
-
const path = dir ? `${process.cwd()}/${dir}` : `${process.cwd()}/src/graphql`;
|
|
435
|
-
const schemaPath = `${path}/entities`;
|
|
436
|
-
const schemaTemplate = fs.readFileSync(`${import.meta.dirname}/../../template/graphql.ejs`, 'utf8');
|
|
437
|
-
const mappingFile = mapping ? `${process.cwd()}/${mapping}` : `${process.cwd()}/src/graphql/mapping.json`;
|
|
438
|
-
const mappingContent = JSON.parse(fs.readFileSync(mappingFile, 'utf8'));
|
|
439
|
-
const getMappedTableName = tableName =>
|
|
440
|
-
(mappingContent[tableName] ? mappingContent[tableName] : tableName);
|
|
441
|
-
fs.mkdirSync(path, { recursive: true });
|
|
442
|
-
fs.mkdirSync(schemaPath, { recursive: true });
|
|
443
|
-
|
|
444
|
-
logger.info('Start generate GraphQL schemas to dir %s', path);
|
|
445
|
-
|
|
446
|
-
const tableHandler = async (tableName) => {
|
|
447
|
-
const enums = [];
|
|
448
|
-
const columns = await query.describeTable(tableName);
|
|
449
|
-
const rawColumns = await sequelize.query(`SHOW FULL COLUMNS FROM ${tableName}`, {
|
|
450
|
-
type: sequelize.QueryTypes.SELECT,
|
|
451
|
-
raw: true
|
|
452
|
-
});
|
|
453
|
-
const mappedTableName = getMappedTableName(tableName);
|
|
454
|
-
Object.values(rawColumns).forEach((rawColumn) => {
|
|
455
|
-
const columnName = rawColumn.Field;
|
|
456
|
-
let type = MakeGraphql.typeMapping(columns[columnName].type, mappedTableName);
|
|
457
|
-
if (type === 'Enum') {
|
|
458
|
-
const enumObj = this.getEnums(columns[columnName].type, columnName, mappedTableName);
|
|
459
|
-
type = enumObj.name;
|
|
460
|
-
enums.push(enumObj);
|
|
461
|
-
}
|
|
462
|
-
|
|
463
|
-
columns[columnName].type = type;
|
|
464
|
-
columns[columnName].unique = rawColumn.Key === 'UNI';
|
|
465
|
-
columns[columnName].comment = rawColumn.Comment;
|
|
466
|
-
columns[columnName].autoIncrement = rawColumn.Extra.startsWith('auto_increment') === true;
|
|
467
|
-
});
|
|
468
|
-
|
|
469
|
-
const indexes = await MakeEntity.getIndexes(tableName, sequelize);
|
|
470
|
-
const schemaFile = `${schemaPath}/${tableName}.graphqls`;
|
|
471
|
-
try {
|
|
472
|
-
fs.accessSync(schemaFile);
|
|
473
|
-
logger.info('Graphql schema file %s generate override, already exists by %s', tableName, schemaFile);
|
|
474
|
-
} catch {
|
|
475
|
-
logger.info('Graphql schema file %s generated as %s', tableName, schemaFile);
|
|
476
|
-
}
|
|
477
|
-
fs.writeFileSync(schemaFile, template(schemaTemplate)({
|
|
478
|
-
tableName,
|
|
479
|
-
mappedTableName,
|
|
480
|
-
columns,
|
|
481
|
-
indexes,
|
|
482
|
-
enums
|
|
483
|
-
}));
|
|
484
|
-
};
|
|
485
|
-
|
|
486
|
-
//Skip sequelize migrate table
|
|
487
|
-
await Promise.all(Object.values(tables).filter(t => !['sequelizemeta', 'tramp_migrations'].includes(t)).map(tableHandler));
|
|
488
|
-
logger.info('All DB schemas generated');
|
|
489
|
-
}
|
|
490
|
-
}
|
package/src/commands/tramp.js
DELETED
|
@@ -1,34 +0,0 @@
|
|
|
1
|
-
import Command from './interface.js';
|
|
2
|
-
import DI from '../di.js';
|
|
3
|
-
|
|
4
|
-
export default class TrampConfig extends Command {
|
|
5
|
-
static getName() {
|
|
6
|
-
return 'tramp:dump-config';
|
|
7
|
-
}
|
|
8
|
-
|
|
9
|
-
static getDescription() {
|
|
10
|
-
return 'Print tramp cli required config json';
|
|
11
|
-
}
|
|
12
|
-
|
|
13
|
-
static getSpec() {
|
|
14
|
-
return {};
|
|
15
|
-
}
|
|
16
|
-
|
|
17
|
-
async run() {
|
|
18
|
-
const config = DI.get('config');
|
|
19
|
-
const dbConfig = config.get('db');
|
|
20
|
-
|
|
21
|
-
console.log(JSON.stringify({
|
|
22
|
-
connection: {
|
|
23
|
-
host: dbConfig.replication.write.host,
|
|
24
|
-
user: dbConfig.replication.write.username,
|
|
25
|
-
password: dbConfig.replication.write.password,
|
|
26
|
-
database: dbConfig.database,
|
|
27
|
-
port: dbConfig.port
|
|
28
|
-
},
|
|
29
|
-
editor: config.get('dev.editor') || 'webstorm',
|
|
30
|
-
paths: dbConfig.migrationPaths
|
|
31
|
-
}));
|
|
32
|
-
}
|
|
33
|
-
}
|
|
34
|
-
|
package/src/config/index.js
DELETED
|
@@ -1,95 +0,0 @@
|
|
|
1
|
-
export default {
|
|
2
|
-
app: {
|
|
3
|
-
name: 'evaengine'
|
|
4
|
-
},
|
|
5
|
-
sequelize: {
|
|
6
|
-
logging: true
|
|
7
|
-
},
|
|
8
|
-
logger: {
|
|
9
|
-
file: false //set to false to disable file logger
|
|
10
|
-
},
|
|
11
|
-
trace: {
|
|
12
|
-
enable: true,
|
|
13
|
-
header: false,
|
|
14
|
-
api: false
|
|
15
|
-
},
|
|
16
|
-
namespace: {
|
|
17
|
-
enable: true,
|
|
18
|
-
defaultName: 'eva.ns'
|
|
19
|
-
},
|
|
20
|
-
cache: {
|
|
21
|
-
prefix: 'eva',
|
|
22
|
-
driver: 'redis'
|
|
23
|
-
},
|
|
24
|
-
redis: {
|
|
25
|
-
host: '127.0.0.1',
|
|
26
|
-
port: 6379,
|
|
27
|
-
lazyConnect: true
|
|
28
|
-
},
|
|
29
|
-
db: {
|
|
30
|
-
dialect: 'mysql',
|
|
31
|
-
port: 3306,
|
|
32
|
-
database: '',
|
|
33
|
-
dialectOptions: {
|
|
34
|
-
multipleStatements: true
|
|
35
|
-
},
|
|
36
|
-
replication: {
|
|
37
|
-
write: {
|
|
38
|
-
host: '',
|
|
39
|
-
username: '',
|
|
40
|
-
password: '',
|
|
41
|
-
pool: {}
|
|
42
|
-
},
|
|
43
|
-
read: []
|
|
44
|
-
}
|
|
45
|
-
},
|
|
46
|
-
session: {
|
|
47
|
-
cookie: {
|
|
48
|
-
path: '/',
|
|
49
|
-
httpOnly: false,
|
|
50
|
-
secure: false,
|
|
51
|
-
maxAge: 3600 * 1000 //这里单位是ms
|
|
52
|
-
},
|
|
53
|
-
store: null,
|
|
54
|
-
secret: 'evaengine',
|
|
55
|
-
resave: true,
|
|
56
|
-
saveUninitialized: true
|
|
57
|
-
},
|
|
58
|
-
token: {
|
|
59
|
-
prefix: '',
|
|
60
|
-
secret: '',
|
|
61
|
-
faker: {
|
|
62
|
-
enable: false,
|
|
63
|
-
key: 'eva',
|
|
64
|
-
uid: 1
|
|
65
|
-
}
|
|
66
|
-
},
|
|
67
|
-
swagger: {
|
|
68
|
-
swagger: '2.0',
|
|
69
|
-
info: {
|
|
70
|
-
title: '',
|
|
71
|
-
description: '',
|
|
72
|
-
version: ''
|
|
73
|
-
},
|
|
74
|
-
produces: [
|
|
75
|
-
'application/json'
|
|
76
|
-
],
|
|
77
|
-
host: '',
|
|
78
|
-
basePath: '/',
|
|
79
|
-
schemes: [
|
|
80
|
-
'http'
|
|
81
|
-
],
|
|
82
|
-
securityDefinitions: {
|
|
83
|
-
api_key: {
|
|
84
|
-
type: 'apiKey',
|
|
85
|
-
name: 'api_key',
|
|
86
|
-
in: 'query'
|
|
87
|
-
}
|
|
88
|
-
},
|
|
89
|
-
security: [{
|
|
90
|
-
api_key: []
|
|
91
|
-
}],
|
|
92
|
-
paths: {},
|
|
93
|
-
definitions: {}
|
|
94
|
-
}
|
|
95
|
-
};
|
package/src/di.js
DELETED
|
@@ -1,96 +0,0 @@
|
|
|
1
|
-
import constitute from 'constitute';
|
|
2
|
-
import { RuntimeException } from './exceptions/index.js';
|
|
3
|
-
import { ServiceProvider } from './services/providers.js';
|
|
4
|
-
|
|
5
|
-
let container = new constitute.Container();
|
|
6
|
-
let bound = {};
|
|
7
|
-
let boundKind = {};
|
|
8
|
-
|
|
9
|
-
const BIND_CLASS = 'class';
|
|
10
|
-
const BIND_VALUE = 'value';
|
|
11
|
-
const BIND_METHOD = 'method';
|
|
12
|
-
|
|
13
|
-
export default class DI {
|
|
14
|
-
static getContainer() {
|
|
15
|
-
return container;
|
|
16
|
-
}
|
|
17
|
-
|
|
18
|
-
static getBound() {
|
|
19
|
-
return bound;
|
|
20
|
-
}
|
|
21
|
-
|
|
22
|
-
static get(service) {
|
|
23
|
-
if (typeof service !== 'string') {
|
|
24
|
-
return container.constitute(service);
|
|
25
|
-
}
|
|
26
|
-
|
|
27
|
-
if (!Object.prototype.hasOwnProperty.call(bound, service)) {
|
|
28
|
-
throw new RuntimeException(`Service ${service} not bound yet`);
|
|
29
|
-
}
|
|
30
|
-
if (boundKind[service] === BIND_VALUE) {
|
|
31
|
-
return bound[service];
|
|
32
|
-
}
|
|
33
|
-
return container.constitute(bound[service]);
|
|
34
|
-
}
|
|
35
|
-
|
|
36
|
-
static bindClass(...args) {
|
|
37
|
-
if (typeof args[0] === 'string') {
|
|
38
|
-
[, bound[args[0]]] = args;
|
|
39
|
-
boundKind[args[0]] = BIND_CLASS;
|
|
40
|
-
}
|
|
41
|
-
return container.bindClass(...args);
|
|
42
|
-
}
|
|
43
|
-
|
|
44
|
-
static bindValue(...args) {
|
|
45
|
-
if (typeof args[0] === 'string') {
|
|
46
|
-
[, bound[args[0]]] = args;
|
|
47
|
-
boundKind[args[0]] = BIND_VALUE;
|
|
48
|
-
}
|
|
49
|
-
return container.bindValue(...args);
|
|
50
|
-
}
|
|
51
|
-
|
|
52
|
-
static bindMethod(...args) {
|
|
53
|
-
if (typeof args[0] === 'string') {
|
|
54
|
-
bound[args[0]] = args[0];
|
|
55
|
-
boundKind[args[0]] = BIND_METHOD;
|
|
56
|
-
}
|
|
57
|
-
return container.bindMethod(...args);
|
|
58
|
-
}
|
|
59
|
-
|
|
60
|
-
static reset() {
|
|
61
|
-
container = new constitute.Container();
|
|
62
|
-
bound = {};
|
|
63
|
-
boundKind = {};
|
|
64
|
-
}
|
|
65
|
-
|
|
66
|
-
/**
|
|
67
|
-
* @param {Array} providers
|
|
68
|
-
* @param {EvaEngine} engine
|
|
69
|
-
*/
|
|
70
|
-
static registerServiceProviders(providers = [], engine) {
|
|
71
|
-
for (const providerClass of providers) {
|
|
72
|
-
DI.registerService(providerClass, engine);
|
|
73
|
-
}
|
|
74
|
-
}
|
|
75
|
-
|
|
76
|
-
/**
|
|
77
|
-
* @param {constructor} ProviderClass
|
|
78
|
-
* @param {EvaEngine} engine
|
|
79
|
-
*/
|
|
80
|
-
static registerService(ProviderClass, engine) {
|
|
81
|
-
const provider = new ProviderClass(engine);
|
|
82
|
-
if (!(provider instanceof ServiceProvider)) {
|
|
83
|
-
throw new RuntimeException(`Input provider ${provider.name} not service provider`);
|
|
84
|
-
}
|
|
85
|
-
provider.register();
|
|
86
|
-
}
|
|
87
|
-
|
|
88
|
-
static registerMockedProviders(providers, configPath) {
|
|
89
|
-
const mockEngine = {
|
|
90
|
-
getMeta: () => ({
|
|
91
|
-
configPath
|
|
92
|
-
})
|
|
93
|
-
};
|
|
94
|
-
DI.registerServiceProviders(providers, mockEngine);
|
|
95
|
-
}
|
|
96
|
-
}
|