openapi-ts-request 0.1.2 → 0.2.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 +2 -1
- package/dist/cli.js +0 -0
- package/dist/generator/config.d.ts +4 -1
- package/dist/generator/config.js +5 -1
- package/dist/generator/serviceGenarator.js +16 -8
- package/dist/index.d.ts +4 -0
- package/dist/index.js +1 -1
- package/package.json +13 -15
- package/templates/displayTypeLabel.njk +42 -0
package/README.md
CHANGED
|
@@ -9,7 +9,7 @@
|
|
|
9
9
|
## Features
|
|
10
10
|
|
|
11
11
|
* supports Swagger2.0/OpenAPI 3.0,3.1 specifications
|
|
12
|
-
* generate TypeScript Interfaces, Reuquest clients, Request Mock Service, Enum, Display Field
|
|
12
|
+
* generate TypeScript Interfaces, Reuquest clients, Request Mock Service, Enum, Display Type Field Label
|
|
13
13
|
* supports Custom Request Function, Fetch、Axios、Uniapp-Request、Node.js、XHR client available
|
|
14
14
|
* supports filter specifications by tags
|
|
15
15
|
* supports JSON specifications
|
|
@@ -108,6 +108,7 @@ npm run openapi
|
|
|
108
108
|
| requestOptionsType | 否 | 自定义请求方法 options 参数类型 | string | '{ [key: string]: unknown }' |
|
|
109
109
|
| requestImportStatement | 否 | 自定义请求方法表达式,例如:'@/request' | string | - |
|
|
110
110
|
| apiPrefix | 否 | api 的前缀,例如:'api'(动态变量), 指定字符串("'api'") | string | - |
|
|
111
|
+
| isDisplayTypeLabel | 否 | 是否生成 type 对应的label | boolean | false |
|
|
111
112
|
| dataFields | 否 | 定义 response 中数据字段类型 | string[] | - |
|
|
112
113
|
| mockFolder | 否 | mock目录 | string | './mocks' |
|
|
113
114
|
| nullable | 否 | 使用null代替可选 | boolean | false |
|
package/dist/cli.js
CHANGED
|
File without changes
|
|
@@ -3,11 +3,13 @@ import { ParameterObject, SchemaObject } from '../type';
|
|
|
3
3
|
export declare const serviceEntryFileName = "index";
|
|
4
4
|
export declare const interfaceFileName = "types";
|
|
5
5
|
export declare const displayEnumLabelFileName = "displayEnumLabel";
|
|
6
|
+
export declare const displayTypeLabelFileName = "displayTypeLabel";
|
|
6
7
|
export declare enum TypescriptFileType {
|
|
7
8
|
interface = "interface",
|
|
8
9
|
serviceController = "serviceController",
|
|
9
10
|
serviceIndex = "serviceIndex",
|
|
10
|
-
displayEnumLabel = "displayEnumLabel"
|
|
11
|
+
displayEnumLabel = "displayEnumLabel",
|
|
12
|
+
displayTypeLabel = "displayTypeLabel"
|
|
11
13
|
}
|
|
12
14
|
export declare const DEFAULT_SCHEMA: SchemaObject;
|
|
13
15
|
export declare const DEFAULT_PATH_PARAM: ParameterObject & Dictionary<unknown>;
|
|
@@ -27,3 +29,4 @@ export declare enum parametersInsEnum {
|
|
|
27
29
|
}
|
|
28
30
|
export declare const parametersIn: string[];
|
|
29
31
|
export declare const numberEnum: string[];
|
|
32
|
+
export declare const lineBreakReg: RegExp;
|
package/dist/generator/config.js
CHANGED
|
@@ -1,15 +1,17 @@
|
|
|
1
1
|
"use strict";
|
|
2
2
|
Object.defineProperty(exports, "__esModule", { value: true });
|
|
3
|
-
exports.numberEnum = exports.parametersIn = exports.parametersInsEnum = exports.methods = exports.DEFAULT_PATH_PARAM = exports.DEFAULT_SCHEMA = exports.TypescriptFileType = exports.displayEnumLabelFileName = exports.interfaceFileName = exports.serviceEntryFileName = void 0;
|
|
3
|
+
exports.lineBreakReg = exports.numberEnum = exports.parametersIn = exports.parametersInsEnum = exports.methods = exports.DEFAULT_PATH_PARAM = exports.DEFAULT_SCHEMA = exports.TypescriptFileType = exports.displayTypeLabelFileName = exports.displayEnumLabelFileName = exports.interfaceFileName = exports.serviceEntryFileName = void 0;
|
|
4
4
|
exports.serviceEntryFileName = 'index';
|
|
5
5
|
exports.interfaceFileName = 'types';
|
|
6
6
|
exports.displayEnumLabelFileName = 'displayEnumLabel';
|
|
7
|
+
exports.displayTypeLabelFileName = 'displayTypeLabel';
|
|
7
8
|
var TypescriptFileType;
|
|
8
9
|
(function (TypescriptFileType) {
|
|
9
10
|
TypescriptFileType["interface"] = "interface";
|
|
10
11
|
TypescriptFileType["serviceController"] = "serviceController";
|
|
11
12
|
TypescriptFileType["serviceIndex"] = "serviceIndex";
|
|
12
13
|
TypescriptFileType["displayEnumLabel"] = "displayEnumLabel";
|
|
14
|
+
TypescriptFileType["displayTypeLabel"] = "displayTypeLabel";
|
|
13
15
|
})(TypescriptFileType || (exports.TypescriptFileType = TypescriptFileType = {}));
|
|
14
16
|
exports.DEFAULT_SCHEMA = {
|
|
15
17
|
type: 'object',
|
|
@@ -55,3 +57,5 @@ exports.numberEnum = [
|
|
|
55
57
|
'int32',
|
|
56
58
|
'int64',
|
|
57
59
|
];
|
|
60
|
+
// 匹配换行符的正则
|
|
61
|
+
exports.lineBreakReg = /[\r\n]+/g;
|
|
@@ -82,6 +82,14 @@ class ServiceGenerator {
|
|
|
82
82
|
namespace: this.config.namespace,
|
|
83
83
|
interfaceFileName: config_1.interfaceFileName,
|
|
84
84
|
});
|
|
85
|
+
// 生成 type 翻译
|
|
86
|
+
if (this.config.isDisplayTypeLabel) {
|
|
87
|
+
this.genFileFromTemplate(`${config_1.displayTypeLabelFileName}.ts`, config_1.TypescriptFileType.displayTypeLabel, {
|
|
88
|
+
list: (0, lodash_1.filter)(interfaceTPConfigs, (item) => !item.isEnum),
|
|
89
|
+
namespace: this.config.namespace,
|
|
90
|
+
interfaceFileName: config_1.interfaceFileName,
|
|
91
|
+
});
|
|
92
|
+
}
|
|
85
93
|
const prettierError = [];
|
|
86
94
|
// 生成 service controller 文件
|
|
87
95
|
this.getServiceTPConfigs().forEach((tp) => {
|
|
@@ -129,7 +137,7 @@ class ServiceGenerator {
|
|
|
129
137
|
var _a;
|
|
130
138
|
props.push({
|
|
131
139
|
name: parameter.name,
|
|
132
|
-
desc: (_a = parameter.description) !== null && _a !== void 0 ? _a : '',
|
|
140
|
+
desc: ((_a = parameter.description) !== null && _a !== void 0 ? _a : '').replace(config_1.lineBreakReg, ''),
|
|
133
141
|
required: parameter.required || false,
|
|
134
142
|
type: this.getType(parameter.schema),
|
|
135
143
|
});
|
|
@@ -139,7 +147,7 @@ class ServiceGenerator {
|
|
|
139
147
|
var _a;
|
|
140
148
|
props.push({
|
|
141
149
|
name: parameter.name,
|
|
142
|
-
desc: (_a = parameter.description) !== null && _a !== void 0 ? _a : '',
|
|
150
|
+
desc: ((_a = parameter.description) !== null && _a !== void 0 ? _a : '').replace(config_1.lineBreakReg, ''),
|
|
143
151
|
required: parameter.required,
|
|
144
152
|
type: this.getType(parameter.schema),
|
|
145
153
|
});
|
|
@@ -159,7 +167,6 @@ class ServiceGenerator {
|
|
|
159
167
|
const result = this.resolveObject(schema);
|
|
160
168
|
const getDefinesType = () => {
|
|
161
169
|
if (result === null || result === void 0 ? void 0 : result.type) {
|
|
162
|
-
console.log('888', result);
|
|
163
170
|
return schema.type === 'object'
|
|
164
171
|
? type_1.SchemaObjectType.object
|
|
165
172
|
: config_1.numberEnum.includes(result.type)
|
|
@@ -188,7 +195,6 @@ class ServiceGenerator {
|
|
|
188
195
|
schema.isAllowed) {
|
|
189
196
|
const isEnum = result.isEnum;
|
|
190
197
|
const typeName = (0, util_1.resolveTypeName)(schemaKey);
|
|
191
|
-
console.log('name:', typeName, getDefinesType());
|
|
192
198
|
lastTypes.push({
|
|
193
199
|
typeName,
|
|
194
200
|
type: getDefinesType(),
|
|
@@ -281,7 +287,7 @@ class ServiceGenerator {
|
|
|
281
287
|
: functionName, typeName: this.getTypeName(newApi), path: getPrefixPath(), pathInComment: formattedPath.replace(/\*/g, '*'), hasPathVariables: formattedPath.includes('{'), hasApiPrefix: !!this.config.apiPrefix, method: newApi.method,
|
|
282
288
|
// 如果 functionName 和 summary 相同,则不显示 summary
|
|
283
289
|
desc: functionName === newApi.summary
|
|
284
|
-
? newApi.description
|
|
290
|
+
? (newApi.description || '').replace(config_1.lineBreakReg, '')
|
|
285
291
|
: [
|
|
286
292
|
newApi.summary,
|
|
287
293
|
newApi.description,
|
|
@@ -290,7 +296,8 @@ class ServiceGenerator {
|
|
|
290
296
|
: '',
|
|
291
297
|
]
|
|
292
298
|
.filter((s) => s)
|
|
293
|
-
.join(' ')
|
|
299
|
+
.join(' ')
|
|
300
|
+
.replace(config_1.lineBreakReg, ''), hasHeader: !!(params === null || params === void 0 ? void 0 : params.header) || !!(body === null || body === void 0 ? void 0 : body.mediaType), params: finalParams, hasParams: Boolean((0, lodash_1.keys)(finalParams).length), options: ((_f = (_e = this.config.hook) === null || _e === void 0 ? void 0 : _e.customOptionsDefaultValue) === null || _f === void 0 ? void 0 : _f.call(_e, newApi)) || {}, body,
|
|
294
301
|
file, hasFormData: formData, response });
|
|
295
302
|
}
|
|
296
303
|
catch (error) {
|
|
@@ -327,7 +334,7 @@ class ServiceGenerator {
|
|
|
327
334
|
nunjucks_1.default.configure({
|
|
328
335
|
autoescape: false,
|
|
329
336
|
});
|
|
330
|
-
return (0, file_1.writeFile)(this.config.serversPath, fileName, nunjucks_1.default.renderString(template, Object.assign({
|
|
337
|
+
return (0, file_1.writeFile)(this.config.serversPath, fileName, nunjucks_1.default.renderString(template, Object.assign({ disableTypeCheck: false }, params)));
|
|
331
338
|
}
|
|
332
339
|
catch (error) {
|
|
333
340
|
console.error('[GenSDK] file gen fail:', fileName, 'type:', type);
|
|
@@ -614,7 +621,8 @@ class ServiceGenerator {
|
|
|
614
621
|
// 复用 schema 部分字段
|
|
615
622
|
return Object.assign(Object.assign({}, schema), { name: propKey, type: this.getType(schema), desc: [schema.title, schema.description]
|
|
616
623
|
.filter((item) => item)
|
|
617
|
-
.join(' ')
|
|
624
|
+
.join(' ')
|
|
625
|
+
.replace(config_1.lineBreakReg, ''),
|
|
618
626
|
// 如果没有 required 信息,默认全部是非必填
|
|
619
627
|
required: requiredPropKeys
|
|
620
628
|
? requiredPropKeys.some((key) => key === propKey)
|
package/dist/index.d.ts
CHANGED
package/dist/index.js
CHANGED
|
@@ -17,7 +17,7 @@ function generateService(_a) {
|
|
|
17
17
|
return;
|
|
18
18
|
}
|
|
19
19
|
const requestImportStatement = (0, util_1.getImportStatement)(requestLibPath);
|
|
20
|
-
const serviceGenerator = new serviceGenarator_1.default(Object.assign({ schemaPath, serversPath: './src/apis', requestImportStatement, requestOptionsType: '{[key: string]: unknown}', namespace: 'API', nullable: false, isCamelCase: true, allowedTags: allowedTags
|
|
20
|
+
const serviceGenerator = new serviceGenarator_1.default(Object.assign({ schemaPath, serversPath: './src/apis', requestImportStatement, requestOptionsType: '{[key: string]: unknown}', namespace: 'API', nullable: false, isCamelCase: true, isDisplayTypeLabel: false, allowedTags: allowedTags
|
|
21
21
|
? (0, lodash_1.map)(allowedTags, (item) => item.toLowerCase())
|
|
22
22
|
: null }, rest), openAPI);
|
|
23
23
|
serviceGenerator.genFile();
|
package/package.json
CHANGED
|
@@ -1,8 +1,7 @@
|
|
|
1
1
|
{
|
|
2
2
|
"name": "openapi-ts-request",
|
|
3
|
-
"version": "0.
|
|
3
|
+
"version": "0.2.0",
|
|
4
4
|
"description": "Swagger2/OpenAPI3 to TypeScript, Request Client, Request Mock Service, Enum, Display Field Label",
|
|
5
|
-
"packageManager": "pnpm@9.4.0",
|
|
6
5
|
"repository": {
|
|
7
6
|
"type": "git",
|
|
8
7
|
"url": "git+git@github.com:openapi-ui/openapi-ts-request.git"
|
|
@@ -19,17 +18,6 @@
|
|
|
19
18
|
"templates",
|
|
20
19
|
"prettier.config.cjs"
|
|
21
20
|
],
|
|
22
|
-
"scripts": {
|
|
23
|
-
"start": "tsc -w",
|
|
24
|
-
"build": "tsc",
|
|
25
|
-
"changeset": "changeset",
|
|
26
|
-
"prepublish:test": "npm run build && np --no-cleanup --yolo --no-publish --any-branch",
|
|
27
|
-
"lint": "eslint ./src --report-unused-disable-directives --max-warnings=0",
|
|
28
|
-
"lint:fix": "eslint ./src --report-unused-disable-directives --max-warnings=0 --fix",
|
|
29
|
-
"test": "rm -rf ./test/apis/ ./test/mocks && npm run build && cd ./test && node ./test.js && cd ..",
|
|
30
|
-
"test:windows": "rimraf ./test/apis/ ./test/mocks && npm run build && cd ./test && node ./test.js && cd ..",
|
|
31
|
-
"prepare": "husky"
|
|
32
|
-
},
|
|
33
21
|
"dependencies": {
|
|
34
22
|
"@prettier/sync": "^0.5.2",
|
|
35
23
|
"axios": "^1.7.2",
|
|
@@ -78,5 +66,15 @@
|
|
|
78
66
|
"openapi to axios client",
|
|
79
67
|
"openapi to fetch client",
|
|
80
68
|
"openapi to uni.request client"
|
|
81
|
-
]
|
|
82
|
-
|
|
69
|
+
],
|
|
70
|
+
"scripts": {
|
|
71
|
+
"start": "tsc -w",
|
|
72
|
+
"build": "tsc",
|
|
73
|
+
"changeset": "changeset",
|
|
74
|
+
"prepublish:test": "npm run build && np --no-cleanup --yolo --no-publish --any-branch",
|
|
75
|
+
"lint": "eslint ./src --report-unused-disable-directives --max-warnings=0",
|
|
76
|
+
"lint:fix": "eslint ./src --report-unused-disable-directives --max-warnings=0 --fix",
|
|
77
|
+
"test": "rm -rf ./test/apis/ ./test/mocks && npm run build && cd ./test && node ./test.js && cd ..",
|
|
78
|
+
"test:windows": "rimraf ./test/apis/ ./test/mocks && npm run build && cd ./test && node ./test.js && cd .."
|
|
79
|
+
}
|
|
80
|
+
}
|
|
@@ -0,0 +1,42 @@
|
|
|
1
|
+
/* eslint-disable */
|
|
2
|
+
// @ts-ignore
|
|
3
|
+
import * as {{ namespace }} from './{{ interfaceFileName }}';
|
|
4
|
+
|
|
5
|
+
{% for type in list -%}
|
|
6
|
+
{%- if type.props.length %}
|
|
7
|
+
export function display{{ type.typeName }}(field: keyof {{ namespace }}.{{ type.typeName }}) {
|
|
8
|
+
return (
|
|
9
|
+
{%- for prop in type.props %}
|
|
10
|
+
{%- if prop.length > 1 %}
|
|
11
|
+
{
|
|
12
|
+
{%- endif %}
|
|
13
|
+
{%- if prop.length == 1 %}
|
|
14
|
+
{%- if not prop[0].$ref or prop[0].name %}
|
|
15
|
+
{
|
|
16
|
+
{%- endif %}
|
|
17
|
+
{%- endif %}
|
|
18
|
+
{%- for p in prop %}
|
|
19
|
+
{%- if p["$ref"] and not p.name %}
|
|
20
|
+
display{{ p.type | safe }}(field as keyof {{ namespace }}.{{ p.type }})
|
|
21
|
+
{%- else %}
|
|
22
|
+
{{ p.name }}: '{{ p.desc if p.desc else p.name }}',
|
|
23
|
+
{%- endif %}
|
|
24
|
+
{%- endfor %}
|
|
25
|
+
{%- if prop.length > 1 %}
|
|
26
|
+
}[field]
|
|
27
|
+
{%- endif %}
|
|
28
|
+
{%- if prop.length == 1 %}
|
|
29
|
+
{%- if not prop[0].$ref or prop[0].name %}
|
|
30
|
+
}[field]
|
|
31
|
+
{%- endif %}
|
|
32
|
+
{%- endif %}
|
|
33
|
+
{%- if prop.length == 0 %}
|
|
34
|
+
{}
|
|
35
|
+
{%- endif %}
|
|
36
|
+
{{ '' if loop.last === true else ' || ' }}
|
|
37
|
+
{%- endfor %}
|
|
38
|
+
)
|
|
39
|
+
}
|
|
40
|
+
{%- endif %}
|
|
41
|
+
|
|
42
|
+
{% endfor -%}
|