@jayfong/x-server 1.10.3 → 1.11.2
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/CHANGELOG.md +21 -0
- package/lib/_cjs/cli/api_generator.js +295 -0
- package/lib/_cjs/cli/build_util.js +146 -0
- package/lib/_cjs/cli/cli.js +190 -0
- package/lib/_cjs/cli/deploy_util.js +61 -0
- package/lib/_cjs/cli/env_util.js +145 -0
- package/lib/_cjs/cli/register.js +8 -0
- package/lib/_cjs/cli/template_util.js +77 -0
- package/lib/_cjs/cli/templates/handlers.ts +3 -0
- package/lib/_cjs/cli/templates/hooks.ts +2 -0
- package/lib/_cjs/cli/templates/models.ts +22 -0
- package/lib/_cjs/cli/templates/package.json +3 -0
- package/lib/_cjs/cli/templates/routes.ts +26 -0
- package/lib/_cjs/cli/templates/tasks.ts +2 -0
- package/lib/_cjs/core/define_bus.js +28 -0
- package/lib/_cjs/core/define_handler.js +43 -0
- package/lib/_cjs/core/define_hook.js +10 -0
- package/lib/_cjs/core/define_server.js +12 -0
- package/lib/_cjs/core/define_task.js +30 -0
- package/lib/_cjs/core/handler.js +90 -0
- package/lib/_cjs/core/http_error.js +9 -0
- package/lib/_cjs/core/http_method.js +12 -0
- package/lib/_cjs/core/server.js +145 -0
- package/lib/_cjs/core/types.js +18 -0
- package/lib/_cjs/index.js +179 -0
- package/lib/_cjs/plugins/base.js +3 -0
- package/lib/_cjs/plugins/cors.js +44 -0
- package/lib/_cjs/plugins/file_parser.js +24 -0
- package/lib/_cjs/plugins/ws_parser.js +24 -0
- package/lib/_cjs/plugins/xml_parser.js +61 -0
- package/lib/_cjs/services/base.js +3 -0
- package/lib/_cjs/services/cache.js +231 -0
- package/lib/_cjs/services/captcha.js +45 -0
- package/lib/_cjs/services/dispose.js +33 -0
- package/lib/_cjs/services/jwt.js +59 -0
- package/lib/_cjs/services/redis.js +18 -0
- package/lib/_cjs/x.js +20 -0
- package/lib/cli/api_generator.js +269 -332
- package/lib/cli/build_util.d.ts +1 -0
- package/lib/cli/build_util.js +108 -130
- package/lib/cli/cli.js +161 -181
- package/lib/cli/deploy_util.js +37 -41
- package/lib/cli/env_util.js +112 -120
- package/lib/cli/register.js +5 -7
- package/lib/cli/template_util.js +47 -52
- package/lib/core/define_bus.js +22 -14
- package/lib/core/define_handler.js +31 -36
- package/lib/core/define_hook.js +4 -8
- package/lib/core/define_server.js +6 -10
- package/lib/core/define_task.js +20 -25
- package/lib/core/handler.js +78 -74
- package/lib/core/http_error.js +2 -8
- package/lib/core/http_method.js +7 -10
- package/lib/core/server.js +125 -139
- package/lib/core/types.js +11 -2
- package/lib/index.js +23 -39
- package/lib/plugins/base.js +1 -2
- package/lib/plugins/cors.js +30 -36
- package/lib/plugins/file_parser.d.ts +1 -1
- package/lib/plugins/file_parser.js +12 -16
- package/lib/plugins/ws_parser.d.ts +1 -1
- package/lib/plugins/ws_parser.js +12 -16
- package/lib/plugins/xml_parser.d.ts +1 -1
- package/lib/plugins/xml_parser.js +47 -43
- package/lib/services/base.js +1 -2
- package/lib/services/cache.js +213 -190
- package/lib/services/captcha.js +32 -33
- package/lib/services/dispose.d.ts +1 -1
- package/lib/services/dispose.js +22 -23
- package/lib/services/jwt.js +45 -48
- package/lib/services/redis.js +8 -14
- package/lib/x.js +12 -15
- package/package.json +6 -4
|
@@ -0,0 +1,61 @@
|
|
|
1
|
+
"use strict";
|
|
2
|
+
|
|
3
|
+
var _interopRequireDefault = require("@babel/runtime/helpers/interopRequireDefault").default;
|
|
4
|
+
|
|
5
|
+
exports.__esModule = true;
|
|
6
|
+
exports.DeployUtil = void 0;
|
|
7
|
+
|
|
8
|
+
var _fsExtra = _interopRequireDefault(require("fs-extra"));
|
|
9
|
+
|
|
10
|
+
var _path = _interopRequireDefault(require("path"));
|
|
11
|
+
|
|
12
|
+
var _vtils = require("vtils");
|
|
13
|
+
|
|
14
|
+
var _nodeSsh = require("node-ssh");
|
|
15
|
+
|
|
16
|
+
class DeployUtil {
|
|
17
|
+
static async deploy(options) {
|
|
18
|
+
const pkgContent = await _fsExtra.default.readJson(_path.default.join(options.cwd, 'package.json'));
|
|
19
|
+
|
|
20
|
+
const appFile = _path.default.join(options.cwd, `temp/app.${pkgContent.version}.tgz`);
|
|
21
|
+
|
|
22
|
+
if (!(await _fsExtra.default.pathExists(appFile))) {
|
|
23
|
+
throw new Error('请先构建');
|
|
24
|
+
}
|
|
25
|
+
|
|
26
|
+
const ssh = new _nodeSsh.NodeSSH();
|
|
27
|
+
await ssh.connect({
|
|
28
|
+
host: options.host,
|
|
29
|
+
username: options.user,
|
|
30
|
+
privateKey: options.key
|
|
31
|
+
});
|
|
32
|
+
const appName = pkgContent.name;
|
|
33
|
+
const appDir = `./${appName}`;
|
|
34
|
+
await ssh.execCommand((0, _vtils.dedent)`
|
|
35
|
+
set -ex
|
|
36
|
+
mkdir -p app_files/${appName}
|
|
37
|
+
rm -rf ${appDir}
|
|
38
|
+
mkdir ${appDir}
|
|
39
|
+
`, {
|
|
40
|
+
cwd: options.dir,
|
|
41
|
+
onStdout: buf => console.log(buf.toString()),
|
|
42
|
+
onStderr: buf => console.log(buf.toString())
|
|
43
|
+
});
|
|
44
|
+
const remoteAppFile = `${options.dir}/app_files/${appName}/${_path.default.basename(appFile)}`;
|
|
45
|
+
await ssh.putFile(appFile, remoteAppFile);
|
|
46
|
+
await ssh.execCommand((0, _vtils.dedent)`
|
|
47
|
+
set -ex
|
|
48
|
+
tar -zxvf ${remoteAppFile} -C ${appDir}
|
|
49
|
+
cd ${appDir}/dist
|
|
50
|
+
pm2 startOrReload pm2.config.js
|
|
51
|
+
`, {
|
|
52
|
+
cwd: options.cwd,
|
|
53
|
+
onStdout: buf => console.log(buf.toString()),
|
|
54
|
+
onStderr: buf => console.log(buf.toString())
|
|
55
|
+
});
|
|
56
|
+
ssh.dispose();
|
|
57
|
+
}
|
|
58
|
+
|
|
59
|
+
}
|
|
60
|
+
|
|
61
|
+
exports.DeployUtil = DeployUtil;
|
|
@@ -0,0 +1,145 @@
|
|
|
1
|
+
"use strict";
|
|
2
|
+
|
|
3
|
+
var _interopRequireDefault = require("@babel/runtime/helpers/interopRequireDefault").default;
|
|
4
|
+
|
|
5
|
+
exports.__esModule = true;
|
|
6
|
+
exports.EnvUtil = void 0;
|
|
7
|
+
|
|
8
|
+
var _fsExtra = _interopRequireDefault(require("fs-extra"));
|
|
9
|
+
|
|
10
|
+
var _nodePath = _interopRequireDefault(require("node:path"));
|
|
11
|
+
|
|
12
|
+
var _vtils = require("vtils");
|
|
13
|
+
|
|
14
|
+
class EnvUtil {
|
|
15
|
+
static normalizeValue(value) {
|
|
16
|
+
if (value.includes(' || ')) {
|
|
17
|
+
const [devValue, prodValue] = value.split(/\s+\|\|\s+/);
|
|
18
|
+
return (0, _vtils.devOrProd)(() => EnvUtil.normalizeValue(devValue), () => EnvUtil.normalizeValue(prodValue));
|
|
19
|
+
}
|
|
20
|
+
|
|
21
|
+
return value === 'true' ? true : value === 'false' ? false : value.startsWith('[') && value.endsWith(']') || value.startsWith('{') && value.endsWith('}') ? JSON.parse(value) : (0, _vtils.isNumeric)(value) ? Number(value) : value;
|
|
22
|
+
}
|
|
23
|
+
|
|
24
|
+
static parseContent(src) {
|
|
25
|
+
const envs = []; // https://github.com/andreialecu/dotenv/blob/feat-multiline/lib/main.js
|
|
26
|
+
|
|
27
|
+
const multilineLineBreaks = true; // convert Buffers before splitting into lines and processing
|
|
28
|
+
|
|
29
|
+
const lines = src.toString().split(EnvUtil.NEWLINES_MATCH);
|
|
30
|
+
let lastComment = '';
|
|
31
|
+
|
|
32
|
+
for (let idx = 0; idx < lines.length; idx++) {
|
|
33
|
+
let line = lines[idx]; // matching "KEY' and 'VAL' in 'KEY=VAL'
|
|
34
|
+
|
|
35
|
+
const keyValueArr = line.match(EnvUtil.RE_INI_KEY_VAL); // matched?
|
|
36
|
+
|
|
37
|
+
if (keyValueArr != null) {
|
|
38
|
+
const key = keyValueArr[1]; // default undefined or missing values to empty string
|
|
39
|
+
|
|
40
|
+
let val = keyValueArr[2] || '';
|
|
41
|
+
let end = val.length - 1;
|
|
42
|
+
const isDoubleQuoted = val[0] === '"' && val[end] === '"';
|
|
43
|
+
const isSingleQuoted = val[0] === "'" && val[end] === "'";
|
|
44
|
+
const isMultilineDoubleQuoted = val[0] === '"' && (val.length === 1 || val[end] !== '"');
|
|
45
|
+
const isMultilineSingleQuoted = val[0] === "'" && (val.length === 1 || val[end] !== "'"); // if parsing line breaks and the value starts with a quote
|
|
46
|
+
|
|
47
|
+
if (multilineLineBreaks && (isMultilineDoubleQuoted || isMultilineSingleQuoted)) {
|
|
48
|
+
const quoteChar = isMultilineDoubleQuoted ? '"' : "'";
|
|
49
|
+
val = val.substring(1);
|
|
50
|
+
|
|
51
|
+
while (idx++ < lines.length - 1) {
|
|
52
|
+
line = lines[idx];
|
|
53
|
+
end = line.length - 1;
|
|
54
|
+
|
|
55
|
+
if (line[end] === quoteChar) {
|
|
56
|
+
val += EnvUtil.NEWLINE + line.substring(0, end);
|
|
57
|
+
break;
|
|
58
|
+
}
|
|
59
|
+
|
|
60
|
+
val += EnvUtil.NEWLINE + line;
|
|
61
|
+
}
|
|
62
|
+
|
|
63
|
+
val = (0, _vtils.dedent)(val); // if single or double quoted, remove quotes
|
|
64
|
+
} else if (isSingleQuoted || isDoubleQuoted) {
|
|
65
|
+
val = val.substring(1, end); // if double quoted, expand newlines
|
|
66
|
+
|
|
67
|
+
if (isDoubleQuoted) {
|
|
68
|
+
val = val.replace(EnvUtil.RE_NEWLINES, EnvUtil.NEWLINE);
|
|
69
|
+
}
|
|
70
|
+
|
|
71
|
+
val = (0, _vtils.dedent)(val);
|
|
72
|
+
} else {
|
|
73
|
+
// remove surrounding whitespace
|
|
74
|
+
val = (0, _vtils.dedent)(val).trim();
|
|
75
|
+
}
|
|
76
|
+
|
|
77
|
+
envs.push({
|
|
78
|
+
key: key,
|
|
79
|
+
value: EnvUtil.normalizeValue(val),
|
|
80
|
+
comment: lastComment
|
|
81
|
+
});
|
|
82
|
+
lastComment = '';
|
|
83
|
+
} else {
|
|
84
|
+
const commentArr = line.match(EnvUtil.COMMENT_MATCH);
|
|
85
|
+
|
|
86
|
+
if (commentArr) {
|
|
87
|
+
lastComment = commentArr[1];
|
|
88
|
+
}
|
|
89
|
+
}
|
|
90
|
+
}
|
|
91
|
+
|
|
92
|
+
return envs;
|
|
93
|
+
}
|
|
94
|
+
|
|
95
|
+
static async parseFile(options) {
|
|
96
|
+
const envFile = _nodePath.default.join(options.cwd, options.file);
|
|
97
|
+
|
|
98
|
+
if (await _fsExtra.default.pathExists(envFile)) {
|
|
99
|
+
const envContent = await _fsExtra.default.readFile(envFile, 'utf-8');
|
|
100
|
+
const envs = EnvUtil.parseContent(envContent);
|
|
101
|
+
return envs;
|
|
102
|
+
}
|
|
103
|
+
|
|
104
|
+
return [];
|
|
105
|
+
}
|
|
106
|
+
|
|
107
|
+
static async importFile(options) {
|
|
108
|
+
for (const env of await EnvUtil.parseFile(options)) {
|
|
109
|
+
process.env[env.key] = env.value;
|
|
110
|
+
}
|
|
111
|
+
}
|
|
112
|
+
|
|
113
|
+
static makeTypes(envs) {
|
|
114
|
+
return (0, _vtils.dedent)`
|
|
115
|
+
declare namespace NodeJS {
|
|
116
|
+
interface ProcessEnv {
|
|
117
|
+
/** 当前环境 */
|
|
118
|
+
NODE_ENV: 'development' | 'production';
|
|
119
|
+
${envs.map(env => (0, _vtils.dedent)`
|
|
120
|
+
${env.comment ? `/** ${env.comment} */` : ''}
|
|
121
|
+
${env.key}: ${// TODO: 优化类型推断
|
|
122
|
+
Array.isArray(env.value) ? `Array<${typeof env.value[0]}>` : typeof env.value};
|
|
123
|
+
`).join('\n')}
|
|
124
|
+
}
|
|
125
|
+
}
|
|
126
|
+
`;
|
|
127
|
+
}
|
|
128
|
+
|
|
129
|
+
static async outputTypes(options) {
|
|
130
|
+
const envs = await EnvUtil.parseFile(options);
|
|
131
|
+
|
|
132
|
+
const outFile = _nodePath.default.join(options.cwd, options.outFile);
|
|
133
|
+
|
|
134
|
+
const types = EnvUtil.makeTypes(envs);
|
|
135
|
+
await _fsExtra.default.outputFile(outFile, types);
|
|
136
|
+
}
|
|
137
|
+
|
|
138
|
+
}
|
|
139
|
+
|
|
140
|
+
exports.EnvUtil = EnvUtil;
|
|
141
|
+
EnvUtil.NEWLINE = '\n';
|
|
142
|
+
EnvUtil.RE_INI_KEY_VAL = /^\s*([\w.-]+)\s*=\s*(.*)?\s*$/;
|
|
143
|
+
EnvUtil.RE_NEWLINES = /\\n/g;
|
|
144
|
+
EnvUtil.NEWLINES_MATCH = /\r\n|\n|\r/;
|
|
145
|
+
EnvUtil.COMMENT_MATCH = /^#\s*(.+?)\s*$/;
|
|
@@ -0,0 +1,77 @@
|
|
|
1
|
+
"use strict";
|
|
2
|
+
|
|
3
|
+
var _interopRequireDefault = require("@babel/runtime/helpers/interopRequireDefault").default;
|
|
4
|
+
|
|
5
|
+
exports.__esModule = true;
|
|
6
|
+
exports.TemplateUtil = void 0;
|
|
7
|
+
|
|
8
|
+
var _fsExtra = _interopRequireDefault(require("fs-extra"));
|
|
9
|
+
|
|
10
|
+
var _path = _interopRequireDefault(require("path"));
|
|
11
|
+
|
|
12
|
+
var _vtils = require("vtils");
|
|
13
|
+
|
|
14
|
+
var _vscodeGenerateIndexStandalone = require("vscode-generate-index-standalone");
|
|
15
|
+
|
|
16
|
+
class TemplateUtil {
|
|
17
|
+
/**
|
|
18
|
+
* 初始化辅助包。
|
|
19
|
+
*/
|
|
20
|
+
static async initHelperPackage(cwd) {
|
|
21
|
+
const fromDir = _path.default.join(__dirname, 'templates');
|
|
22
|
+
|
|
23
|
+
const toDir = _path.default.join(cwd, 'node_modules/.x');
|
|
24
|
+
|
|
25
|
+
await _fsExtra.default.copy(fromDir, toDir, {
|
|
26
|
+
overwrite: true
|
|
27
|
+
});
|
|
28
|
+
}
|
|
29
|
+
/**
|
|
30
|
+
* 初始化模型。
|
|
31
|
+
*/
|
|
32
|
+
|
|
33
|
+
|
|
34
|
+
static async initModels(cwd) {
|
|
35
|
+
const modelsDir = _path.default.join(cwd, 'src/models');
|
|
36
|
+
|
|
37
|
+
const indexFile = _path.default.join(modelsDir, 'index.ts');
|
|
38
|
+
|
|
39
|
+
const indexFile2 = _path.default.join(cwd, 'node_modules/.x/models.ts');
|
|
40
|
+
|
|
41
|
+
const prismaClientFile = _path.default.join(cwd, 'node_modules/.prisma/client/index.d.ts');
|
|
42
|
+
|
|
43
|
+
const prismaClientFileContent = await _fsExtra.default.readFile(prismaClientFile, 'utf8');
|
|
44
|
+
const modelNames = [...prismaClientFileContent.match(/(?<=const ModelName:).+?(?=\})/s)[0].matchAll(/(\S+?):/g)].map(match => (0, _vtils.camelCase)(match[1]));
|
|
45
|
+
await Promise.all(modelNames.map(async modelName => {
|
|
46
|
+
const model_name = (0, _vtils.snakeCase)(modelName);
|
|
47
|
+
const ModelName = (0, _vtils.upperFirst)(modelName);
|
|
48
|
+
|
|
49
|
+
const modelFile = _path.default.join(modelsDir, `${model_name}.ts`);
|
|
50
|
+
|
|
51
|
+
if (!(await _fsExtra.default.pathExists(modelFile))) {
|
|
52
|
+
await _fsExtra.default.outputFile(modelFile, (0, _vtils.dedent)`
|
|
53
|
+
import { ${ModelName}BaseModel } from '@jayfong/x-server'
|
|
54
|
+
|
|
55
|
+
export class ${ModelName}Model extends ${ModelName}BaseModel {}
|
|
56
|
+
|
|
57
|
+
export const ${modelName}Model = new ${ModelName}Model()
|
|
58
|
+
`);
|
|
59
|
+
}
|
|
60
|
+
}));
|
|
61
|
+
|
|
62
|
+
if (!(await _fsExtra.default.pathExists(indexFile))) {
|
|
63
|
+
await _fsExtra.default.outputFile(indexFile, (0, _vtils.dedent)`
|
|
64
|
+
// @index(['./**/*.ts', '!**/*.test.ts', '!**/_*'], f => \`export * from '\${f.path}'\`)
|
|
65
|
+
// @endindex
|
|
66
|
+
`);
|
|
67
|
+
}
|
|
68
|
+
|
|
69
|
+
await (0, _vscodeGenerateIndexStandalone.generateManyIndex)({
|
|
70
|
+
patterns: [indexFile, indexFile2],
|
|
71
|
+
replaceFile: true
|
|
72
|
+
});
|
|
73
|
+
}
|
|
74
|
+
|
|
75
|
+
}
|
|
76
|
+
|
|
77
|
+
exports.TemplateUtil = TemplateUtil;
|
|
@@ -0,0 +1,22 @@
|
|
|
1
|
+
import { x, HttpError } from '@jayfong/x-server'
|
|
2
|
+
import { PrismaClient } from '@prisma/client'
|
|
3
|
+
|
|
4
|
+
const prisma = new PrismaClient({
|
|
5
|
+
rejectOnNotFound: err => new HttpError.NotFound(err.message),
|
|
6
|
+
})
|
|
7
|
+
|
|
8
|
+
x.dispose.add(() => prisma.$disconnect())
|
|
9
|
+
|
|
10
|
+
type ModelName =
|
|
11
|
+
// @index('../.prisma/client/index.d.ts', /(?<=const ModelName:).+?(?=\})/s, /(\S+?):/g, (m, _) => `| '${_.camel(m[1])}'`)
|
|
12
|
+
''
|
|
13
|
+
// @endindex
|
|
14
|
+
|
|
15
|
+
function makeBaseModel<TModelName extends ModelName>(name: TModelName) {
|
|
16
|
+
return class BaseModel {
|
|
17
|
+
public query = prisma[name]
|
|
18
|
+
}
|
|
19
|
+
}
|
|
20
|
+
|
|
21
|
+
// @index('../.prisma/client/index.d.ts', /(?<=const ModelName:).+?(?=\})/s, /(\S+?):/g, (m, _) => `export const ${_.pascal(m[1])}BaseModel = makeBaseModel('${_.camel(m[1])}')`)
|
|
22
|
+
// @endindex
|
|
@@ -0,0 +1,26 @@
|
|
|
1
|
+
import * as handlers from './handlers'
|
|
2
|
+
import { Handler, XServer } from '@jayfong/x-server'
|
|
3
|
+
|
|
4
|
+
const basePathWithHandlers: Array<[string, Record<string, Handler>]> = [
|
|
5
|
+
// @index('../../src/handlers/**/*.ts', (f, _) => `['${('/'+_.snake(f.path.replace('/src/handlers/', '')).replace(/_/g, '/')+'/').replace(/\/{2,}/g, '/')}', handlers.__${_.pascal(f.path.replace('/src/handlers/', ''))}__ as any],`)
|
|
6
|
+
// @endindex
|
|
7
|
+
]
|
|
8
|
+
|
|
9
|
+
export const routes: XServer.Route[] = basePathWithHandlers.reduce<
|
|
10
|
+
XServer.Route[]
|
|
11
|
+
>((res, item) => {
|
|
12
|
+
const validHandlerNames = Object.keys(item[1]).filter(
|
|
13
|
+
name => !name.startsWith('_') && name !== 'default',
|
|
14
|
+
)
|
|
15
|
+
for (const handlerName of validHandlerNames) {
|
|
16
|
+
const path = item[1][handlerName].options.requestPath || handlerName
|
|
17
|
+
const paths = Array.isArray(path) ? path : [path]
|
|
18
|
+
for (const path of paths) {
|
|
19
|
+
res.push({
|
|
20
|
+
path: `${item[0]}${path}`,
|
|
21
|
+
handler: item[1][handlerName],
|
|
22
|
+
})
|
|
23
|
+
}
|
|
24
|
+
}
|
|
25
|
+
return res
|
|
26
|
+
}, [])
|
|
@@ -0,0 +1,28 @@
|
|
|
1
|
+
"use strict";
|
|
2
|
+
|
|
3
|
+
exports.__esModule = true;
|
|
4
|
+
exports.defineBus = defineBus;
|
|
5
|
+
|
|
6
|
+
var _nodeEvents = require("node:events");
|
|
7
|
+
|
|
8
|
+
class EventBus extends _nodeEvents.EventEmitter {
|
|
9
|
+
onReturnOff(event, listener) {
|
|
10
|
+
this.on(event, listener);
|
|
11
|
+
return () => this.off(event, listener);
|
|
12
|
+
}
|
|
13
|
+
|
|
14
|
+
}
|
|
15
|
+
|
|
16
|
+
function defineBus() {
|
|
17
|
+
const eventEmitter = new EventBus();
|
|
18
|
+
return eventEmitter;
|
|
19
|
+
} // strict-event-emitter-types
|
|
20
|
+
// https://github.com/bterlson/strict-event-emitter-types/blob/9ed45fc68a69f0b7f85ce4e5fe11ff53cc6a009e/src/index.ts
|
|
21
|
+
// the overridden signatures need to be assignment compatible, but
|
|
22
|
+
// due to how tuple types work[0] it's not possible to be assignment
|
|
23
|
+
// compatible anymore. This hack fixes it with a unique symbol that
|
|
24
|
+
// won't ever show up in parameter help etc.
|
|
25
|
+
//
|
|
26
|
+
// Unfortunately, this has the result of giving a poor error message when
|
|
27
|
+
// you mix up types.
|
|
28
|
+
// 0: https://github.com/Microsoft/TypeScript/issues/26013)
|
|
@@ -0,0 +1,43 @@
|
|
|
1
|
+
"use strict";
|
|
2
|
+
|
|
3
|
+
exports.__esModule = true;
|
|
4
|
+
exports.defineHandler = defineHandler;
|
|
5
|
+
|
|
6
|
+
var _handler = require("./handler");
|
|
7
|
+
|
|
8
|
+
function defineHandler(options) {
|
|
9
|
+
const handler = new _handler.Handler({ ...options,
|
|
10
|
+
requestMethod: 'POST'
|
|
11
|
+
});
|
|
12
|
+
return handler;
|
|
13
|
+
}
|
|
14
|
+
|
|
15
|
+
defineHandler.POST = defineHandler;
|
|
16
|
+
|
|
17
|
+
defineHandler.GET = options => {
|
|
18
|
+
const handler = new _handler.Handler({ ...options,
|
|
19
|
+
requestMethod: 'GET'
|
|
20
|
+
});
|
|
21
|
+
return handler;
|
|
22
|
+
};
|
|
23
|
+
|
|
24
|
+
defineHandler.FILE = options => {
|
|
25
|
+
const handler = new _handler.Handler({ ...options,
|
|
26
|
+
requestMethod: 'FILE'
|
|
27
|
+
});
|
|
28
|
+
return handler;
|
|
29
|
+
};
|
|
30
|
+
|
|
31
|
+
defineHandler.WS = options => {
|
|
32
|
+
const handler = new _handler.Handler({ ...options,
|
|
33
|
+
requestMethod: 'WS'
|
|
34
|
+
});
|
|
35
|
+
return handler;
|
|
36
|
+
};
|
|
37
|
+
|
|
38
|
+
defineHandler.XML = options => {
|
|
39
|
+
const handler = new _handler.Handler({ ...options,
|
|
40
|
+
requestMethod: 'XML'
|
|
41
|
+
});
|
|
42
|
+
return handler;
|
|
43
|
+
};
|
|
@@ -0,0 +1,12 @@
|
|
|
1
|
+
"use strict";
|
|
2
|
+
|
|
3
|
+
exports.__esModule = true;
|
|
4
|
+
exports.defineServer = defineServer;
|
|
5
|
+
|
|
6
|
+
var _server = require("./server");
|
|
7
|
+
|
|
8
|
+
async function defineServer(options) {
|
|
9
|
+
const server = new _server.Server(options);
|
|
10
|
+
await server.start();
|
|
11
|
+
return server;
|
|
12
|
+
}
|
|
@@ -0,0 +1,30 @@
|
|
|
1
|
+
"use strict";
|
|
2
|
+
|
|
3
|
+
var _interopRequireDefault = require("@babel/runtime/helpers/interopRequireDefault").default;
|
|
4
|
+
|
|
5
|
+
exports.__esModule = true;
|
|
6
|
+
exports.defineTask = defineTask;
|
|
7
|
+
|
|
8
|
+
var _bull = _interopRequireDefault(require("bull"));
|
|
9
|
+
|
|
10
|
+
var _x = require("../x");
|
|
11
|
+
|
|
12
|
+
async function defineTask(options) {
|
|
13
|
+
const queue = new _bull.default(options.name, {
|
|
14
|
+
redis: _x.x.redis.options,
|
|
15
|
+
prefix: `${_x.x.appName}_task`
|
|
16
|
+
});
|
|
17
|
+
queue.process(async job => {
|
|
18
|
+
return options.handle(job.data);
|
|
19
|
+
});
|
|
20
|
+
|
|
21
|
+
if (options.cron) {
|
|
22
|
+
queue.add({}, {
|
|
23
|
+
repeat: {
|
|
24
|
+
cron: options.cron
|
|
25
|
+
}
|
|
26
|
+
});
|
|
27
|
+
}
|
|
28
|
+
|
|
29
|
+
return queue;
|
|
30
|
+
}
|
|
@@ -0,0 +1,90 @@
|
|
|
1
|
+
"use strict";
|
|
2
|
+
|
|
3
|
+
exports.__esModule = true;
|
|
4
|
+
exports.Handler = void 0;
|
|
5
|
+
|
|
6
|
+
var _vtils = require("vtils");
|
|
7
|
+
|
|
8
|
+
var _dispose = require("../services/dispose");
|
|
9
|
+
|
|
10
|
+
var _http_error = require("../core/http_error");
|
|
11
|
+
|
|
12
|
+
class Handler {
|
|
13
|
+
constructor(options) {
|
|
14
|
+
this.options = options;
|
|
15
|
+
|
|
16
|
+
this.handle = async (data, ctx) => {
|
|
17
|
+
// 前置 hook
|
|
18
|
+
if (Handler.hooks.length) {
|
|
19
|
+
await Promise.all(Handler.hooks.map(hook => hook(this.options, data, ctx)));
|
|
20
|
+
}
|
|
21
|
+
|
|
22
|
+
if (this.options.requestMethod === 'WS') {
|
|
23
|
+
return this.handleWs(data, ctx);
|
|
24
|
+
}
|
|
25
|
+
|
|
26
|
+
return this.handleHttp(data, ctx);
|
|
27
|
+
};
|
|
28
|
+
|
|
29
|
+
this.handleHttp = async (data, ctx) => {
|
|
30
|
+
let res = await this.options.handle(data, ctx); // 打包返回数据
|
|
31
|
+
|
|
32
|
+
if (this.options.responseDataPack) {
|
|
33
|
+
res = _vtils.DataPacker.packAsRawType(res);
|
|
34
|
+
}
|
|
35
|
+
|
|
36
|
+
return res;
|
|
37
|
+
};
|
|
38
|
+
|
|
39
|
+
this.handleWs = async (data, ctx) => {
|
|
40
|
+
const dispose = new _dispose.DisposeService();
|
|
41
|
+
ctx.ws.socket.on('message', async payload => {
|
|
42
|
+
try {
|
|
43
|
+
const _ = JSON.parse(payload.toString('utf8'));
|
|
44
|
+
|
|
45
|
+
const send = data => {
|
|
46
|
+
ctx.ws.socket.send(JSON.stringify({
|
|
47
|
+
id: _.id,
|
|
48
|
+
data: data
|
|
49
|
+
}));
|
|
50
|
+
};
|
|
51
|
+
|
|
52
|
+
const process = async (type, fn) => {
|
|
53
|
+
if (_.type === type) {
|
|
54
|
+
await fn({
|
|
55
|
+
data: _.data,
|
|
56
|
+
send: send,
|
|
57
|
+
dispose: dispose
|
|
58
|
+
});
|
|
59
|
+
}
|
|
60
|
+
};
|
|
61
|
+
|
|
62
|
+
if (_.type === 'ping') {
|
|
63
|
+
send();
|
|
64
|
+
} else {
|
|
65
|
+
await this.options.handle(process, ctx);
|
|
66
|
+
}
|
|
67
|
+
} catch (err) {
|
|
68
|
+
const _err = _http_error.HttpError.isHttpError(err) ? err : new _http_error.HttpError.InternalServerError();
|
|
69
|
+
|
|
70
|
+
ctx.ws.socket.send(JSON.stringify({
|
|
71
|
+
statusCode: _err.statusCode,
|
|
72
|
+
error: _err.name,
|
|
73
|
+
message: _err.message
|
|
74
|
+
}));
|
|
75
|
+
}
|
|
76
|
+
});
|
|
77
|
+
ctx.ws.socket.on('close', () => {
|
|
78
|
+
dispose.dispose();
|
|
79
|
+
});
|
|
80
|
+
};
|
|
81
|
+
}
|
|
82
|
+
|
|
83
|
+
static addHook(hook) {
|
|
84
|
+
this.hooks.push(hook);
|
|
85
|
+
}
|
|
86
|
+
|
|
87
|
+
}
|
|
88
|
+
|
|
89
|
+
exports.Handler = Handler;
|
|
90
|
+
Handler.hooks = [];
|
|
@@ -0,0 +1,12 @@
|
|
|
1
|
+
"use strict";
|
|
2
|
+
|
|
3
|
+
exports.__esModule = true;
|
|
4
|
+
exports.HandlerMethodToHttpMethod = void 0;
|
|
5
|
+
const HandlerMethodToHttpMethod = {
|
|
6
|
+
GET: 'GET',
|
|
7
|
+
POST: 'POST',
|
|
8
|
+
FILE: 'POST',
|
|
9
|
+
WS: 'GET',
|
|
10
|
+
XML: 'POST'
|
|
11
|
+
};
|
|
12
|
+
exports.HandlerMethodToHttpMethod = HandlerMethodToHttpMethod;
|