swagger-typescript-api 10.0.2 → 11.0.0--alpha

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.
Files changed (55) hide show
  1. package/README.md +263 -41
  2. package/index.d.ts +97 -0
  3. package/index.js +242 -115
  4. package/package.json +121 -116
  5. package/src/code-formatter.js +101 -0
  6. package/src/code-gen-process.js +456 -0
  7. package/src/configuration.js +425 -0
  8. package/src/constants.js +14 -31
  9. package/src/index.js +20 -271
  10. package/src/schema-components-map.js +60 -0
  11. package/src/schema-parser/schema-formatters.js +145 -0
  12. package/src/schema-parser/schema-parser.js +497 -0
  13. package/src/schema-parser/schema-routes.js +902 -0
  14. package/src/swagger-schema-resolver.js +187 -0
  15. package/src/templates.js +174 -155
  16. package/src/translators/JavaScript.js +3 -14
  17. package/src/type-name.js +79 -0
  18. package/src/util/file-system.js +76 -0
  19. package/src/{utils → util}/id.js +9 -9
  20. package/src/util/internal-case.js +5 -0
  21. package/src/util/logger.js +100 -0
  22. package/src/{utils/resolveName.js → util/name-resolver.js} +94 -97
  23. package/src/util/object-assign.js +11 -0
  24. package/src/util/pascal-case.js +5 -0
  25. package/src/{utils → util}/random.js +14 -14
  26. package/templates/base/data-contract-jsdoc.ejs +29 -24
  27. package/templates/base/data-contracts.ejs +3 -3
  28. package/templates/base/interface-data-contract.ejs +1 -0
  29. package/templates/base/route-docs.ejs +3 -4
  30. package/templates/base/route-type.ejs +2 -2
  31. package/templates/default/procedure-call.ejs +2 -2
  32. package/templates/default/route-types.ejs +2 -2
  33. package/templates/modular/api.ejs +2 -2
  34. package/templates/modular/procedure-call.ejs +2 -2
  35. package/templates/modular/route-types.ejs +2 -2
  36. package/src/apiConfig.js +0 -30
  37. package/src/common.js +0 -28
  38. package/src/components.js +0 -91
  39. package/src/config.js +0 -106
  40. package/src/filePrefix.js +0 -14
  41. package/src/files.js +0 -56
  42. package/src/formatFileContent.js +0 -81
  43. package/src/logger.js +0 -59
  44. package/src/modelNames.js +0 -78
  45. package/src/modelTypes.js +0 -31
  46. package/src/output.js +0 -165
  47. package/src/prettierOptions.js +0 -23
  48. package/src/render/utils/fmtToJSDocLine.js +0 -10
  49. package/src/render/utils/index.js +0 -31
  50. package/src/render/utils/templateRequire.js +0 -17
  51. package/src/routeNames.js +0 -46
  52. package/src/routes.js +0 -809
  53. package/src/schema.js +0 -474
  54. package/src/swagger.js +0 -152
  55. package/src/typeFormatters.js +0 -121
package/src/apiConfig.js DELETED
@@ -1,30 +0,0 @@
1
- const _ = require("lodash");
2
-
3
- const createApiConfig = (swaggerSchema) => {
4
- const { info, servers, host, basePath, externalDocs, tags } = swaggerSchema;
5
- const server = (servers && servers[0]) || { url: "" };
6
- const { title = "No title", version, description: schemaDescription = "" } = info || {};
7
- const { url: serverUrl } = server;
8
-
9
- return {
10
- info: info || {},
11
- servers: servers || [],
12
- basePath,
13
- host,
14
- externalDocs: _.merge(
15
- {
16
- url: "",
17
- description: "",
18
- },
19
- externalDocs,
20
- ),
21
- tags: _.compact(tags),
22
- baseUrl: serverUrl,
23
- title,
24
- version,
25
- };
26
- };
27
-
28
- module.exports = {
29
- createApiConfig,
30
- };
package/src/common.js DELETED
@@ -1,28 +0,0 @@
1
- const _ = require("lodash");
2
-
3
- module.exports = {
4
- formatDescription: (description, inline) => {
5
- if (!description) return "";
6
-
7
- let prettified = description;
8
-
9
- prettified = _.replace(prettified, /\*\//g, "*/");
10
-
11
- const hasMultipleLines = _.includes(prettified, "\n");
12
-
13
- if (!hasMultipleLines) return prettified;
14
-
15
- if (inline) {
16
- return _(prettified)
17
- .split(/\n/g)
18
- .map((part) => _.trim(part))
19
- .compact()
20
- .join(" ")
21
- .valueOf();
22
- }
23
-
24
- return _.replace(prettified, /\n$/g, "");
25
- },
26
- internalCase: (value) => _.camelCase(_.lowerCase(value)),
27
- classNameCase: (value) => _.upperFirst(_.camelCase(value)),
28
- };
package/src/components.js DELETED
@@ -1,91 +0,0 @@
1
- const _ = require("lodash");
2
- const { parseSchema } = require("./schema");
3
- const { config } = require("./config");
4
-
5
- /**
6
- * @typedef {"schemas" | "examples" | "headers" | "parameters" | "requestBodies" | "responses" | "securitySchemes"} ComponentName
7
- * @typedef {object} RawTypeData
8
- * @typedef {{ type, typeIdentifier, name, description, content }} TypeData
9
- *
10
- * @typedef {{
11
- * typeName: string;
12
- * componentName: ComponentName;
13
- * rawTypeData: RawTypeData;
14
- * typeData: TypeData | null;
15
- * }} TypeInfo
16
- */
17
-
18
- /**
19
- *
20
- * @param {ComponentName} componentName
21
- * @param {string} typeName
22
- * @param {RawTypeData} rawTypeData
23
- * @returns {TypeInfo}
24
- */
25
- const createComponent = (componentName, typeName, rawTypeData) => {
26
- const $ref = `#/components/${componentName}/${typeName}`;
27
-
28
- const componentSchema = {
29
- $ref,
30
- typeName,
31
- rawTypeData,
32
- componentName,
33
- typeData: null,
34
- };
35
-
36
- const usageComponent = config.hooks.onCreateComponent(componentSchema) || componentSchema;
37
-
38
- config.componentsMap[$ref] = usageComponent;
39
-
40
- return usageComponent;
41
- };
42
-
43
- /**
44
- * @returns {{ [key: string]: TypeInfo }}
45
- */
46
- const createComponentsMap = (components) => {
47
- config.componentsMap = {};
48
-
49
- _.each(components, (component, componentName) =>
50
- _.each(component, (rawTypeData, typeName) => createComponent(componentName, typeName, rawTypeData)),
51
- );
52
-
53
- return config.componentsMap;
54
- };
55
-
56
- /**
57
- *
58
- * @param {{ [key: string]: TypeInfo }} componentsMap
59
- * @param {ComponentName} componentName
60
- * @returns {TypeInfo[]}
61
- */
62
- const filterComponentsMap = (componentsMap, componentName) =>
63
- _.filter(componentsMap, (v, ref) => _.startsWith(ref, `#/components/${componentName}`));
64
-
65
- /**
66
- *
67
- * @param {TypeInfo} typeInfo
68
- * @returns {TypeData}
69
- */
70
- const getTypeData = (typeInfo) => {
71
- if (!typeInfo.typeData) {
72
- typeInfo.typeData = parseSchema(typeInfo.rawTypeData, typeInfo.typeName);
73
- }
74
-
75
- return typeInfo.typeData;
76
- };
77
-
78
- /**
79
- *
80
- * @param {string} ref
81
- * @returns {TypeInfo | null}
82
- */
83
- const getComponentByRef = (ref) => config.componentsMap[ref] || null;
84
-
85
- module.exports = {
86
- getTypeData,
87
- createComponent,
88
- createComponentsMap,
89
- filterComponentsMap,
90
- getComponentByRef,
91
- };
package/src/config.js DELETED
@@ -1,106 +0,0 @@
1
- const { HTTP_CLIENT, TS_KEYWORDS, PRETTIER_OPTIONS } = require("./constants");
2
- const { NameResolver } = require("./utils/resolveName");
3
-
4
- const config = {
5
- /** CLI flag */
6
- templates: "../templates/default",
7
- /** CLI flag */
8
- generateResponses: false,
9
- /** CLI flag */
10
- defaultResponseAsSuccess: false,
11
- /** CLI flag */
12
- generateRouteTypes: false,
13
- /** CLI flag */
14
- generateClient: true,
15
- /** CLI flag */
16
- generateUnionEnums: false,
17
- /** CLI flag */
18
- addReadonly: false,
19
- enumNamesAsValues: false,
20
- /** parsed swagger schema from getSwaggerObject() */
21
-
22
- /** parsed swagger schema ref */
23
- swaggerSchema: null,
24
- /** original (converted to json) swagger schema ref */
25
- originalSchema: null,
26
-
27
- /** { "#/components/schemas/Foo": @TypeInfo, ... } */
28
- componentsMap: {},
29
- /** flag for catching convertion from swagger 2.0 */
30
- convertedFromSwagger2: false,
31
-
32
- /** url index from paths used for merging into modules */
33
- moduleNameIndex: 0,
34
-
35
- /** use the first tag for the module name */
36
- moduleNameFirstTag: false,
37
- disableStrictSSL: false,
38
- disableProxy: false,
39
- extractRequestParams: false,
40
- extractRequestBody: false,
41
- extractResponseBody: false,
42
- extractResponseError: false,
43
- fileNames: {
44
- dataContracts: "data-contracts",
45
- routeTypes: "route-types",
46
- httpClient: "http-client",
47
- outOfModuleApi: "Common",
48
- },
49
- routeNameDuplicatesMap: new Map(),
50
- prettierOptions: PRETTIER_OPTIONS,
51
- hooks: {
52
- onCreateComponent: (schema) => schema,
53
- onParseSchema: (originalSchema, parsedSchema) => parsedSchema,
54
- onCreateRoute: (routeData) => routeData,
55
- onInit: (config) => config,
56
- onPrepareConfig: (apiConfig) => apiConfig,
57
- onCreateRequestParams: (rawType) => {},
58
- onCreateRouteName: () => {},
59
- onFormatTypeName: (typeName, rawTypeName) => {},
60
- onFormatRouteName: (routeInfo, templateRouteName) => {},
61
- },
62
- defaultResponseType: TS_KEYWORDS.VOID,
63
- singleHttpClient: false,
64
- httpClientType: HTTP_CLIENT.FETCH,
65
- unwrapResponseData: false,
66
- disableThrowOnError: false,
67
- sortTypes: false,
68
- templatePaths: {
69
- /** `templates/base` */
70
- base: "",
71
- /** `templates/default` */
72
- default: "",
73
- /** `templates/modular` */
74
- modular: "",
75
- /** usage path if `--templates` option is not set */
76
- original: "",
77
- /** custom path to templates (`--templates`) */
78
- custom: "",
79
- },
80
- /** Record<templateName, templateContent> */
81
- templatesToRender: {
82
- api: "",
83
- dataContracts: "",
84
- httpClient: "",
85
- routeTypes: "",
86
- routeName: "",
87
- },
88
- toJS: false,
89
- silent: false,
90
- typePrefix: "",
91
- typeSuffix: "",
92
- patch: false,
93
- componentTypeNameResolver: new NameResolver([]),
94
- /** name of the main exported class */
95
- apiClassName: "Api",
96
- debug: false,
97
- internalTemplateOptions: {
98
- addUtilRequiredKeysType: false,
99
- },
100
- };
101
-
102
- /** needs to use data everywhere in project */
103
- module.exports = {
104
- addToConfig: (configParts) => Object.assign(config, configParts),
105
- config,
106
- };
package/src/filePrefix.js DELETED
@@ -1,14 +0,0 @@
1
- module.exports = {
2
- filePrefix: `/* eslint-disable */
3
- /* tslint:disable */
4
- /*
5
- * ---------------------------------------------------------------
6
- * ## THIS FILE WAS GENERATED VIA SWAGGER-TYPESCRIPT-API ##
7
- * ## ##
8
- * ## AUTHOR: acacode ##
9
- * ## SOURCE: https://github.com/acacode/swagger-typescript-api ##
10
- * ---------------------------------------------------------------
11
- */
12
-
13
- `,
14
- };
package/src/files.js DELETED
@@ -1,56 +0,0 @@
1
- const _ = require("lodash");
2
- const fs = require("fs");
3
- const { resolve } = require("path");
4
- const { filePrefix } = require("./filePrefix");
5
- const makeDir = require("make-dir");
6
-
7
- const getFileContent = (path) => {
8
- return fs.readFileSync(path, { encoding: "UTF-8" });
9
- };
10
-
11
- const pathIsDir = (path) => {
12
- if (!path) return false;
13
-
14
- try {
15
- const stat = fs.statSync(path);
16
- return stat.isDirectory();
17
- } catch (e) {
18
- return false;
19
- }
20
- };
21
-
22
- const removeDir = (path) => {
23
- try {
24
- if (typeof fs.rmSync === "function") {
25
- fs.rmSync(path, { recursive: true });
26
- } else {
27
- fs.rmdirSync(path, { recursive: true });
28
- }
29
- } catch (e) {}
30
- };
31
-
32
- const createDir = (path) => {
33
- try {
34
- makeDir.sync(path);
35
- } catch (e) {}
36
- };
37
-
38
- const cleanDir = (path) => {
39
- removeDir(path);
40
- createDir(path);
41
- };
42
-
43
- const pathIsExist = (path) => path && fs.existsSync(path);
44
-
45
- const createFile = ({ path, fileName, content, withPrefix }) =>
46
- fs.writeFileSync(resolve(__dirname, path, `./${fileName}`), `${withPrefix ? filePrefix : ""}${content}`, _.noop);
47
-
48
- module.exports = {
49
- createFile,
50
- pathIsDir,
51
- cleanDir,
52
- pathIsExist,
53
- createDir,
54
- removeDir,
55
- getFileContent,
56
- };
@@ -1,81 +0,0 @@
1
- const _ = require("lodash");
2
- const prettier = require("prettier");
3
- const { config } = require("./config");
4
- const ts = require("typescript");
5
-
6
- class LanguageServiceHost {
7
- constructor(fileName, content) {
8
- const tsconfig = ts.findConfigFile(fileName, ts.sys.fileExists);
9
-
10
- Object.assign(this, {
11
- fileName,
12
- content,
13
- compilerOptions: tsconfig
14
- ? ts.convertCompilerOptionsFromJson(ts.readConfigFile(tsconfig, ts.sys.readFile).config.compilerOptions).options
15
- : ts.getDefaultCompilerOptions(),
16
- });
17
- }
18
-
19
- getNewLine() {
20
- return "newLine" in ts.sys ? ts.sys.newLine : "\n";
21
- }
22
- getScriptFileNames() {
23
- return [this.fileName];
24
- }
25
- getCompilationSettings() {
26
- return this.compilerOptions;
27
- }
28
- getDefaultLibFileName() {
29
- return ts.getDefaultLibFileName(this.getCompilationSettings());
30
- }
31
- getCurrentDirectory() {
32
- return process.cwd();
33
- }
34
- getScriptVersion() {
35
- return ts.version;
36
- }
37
- getScriptSnapshot() {
38
- return ts.ScriptSnapshot.fromString(this.content);
39
- }
40
- readFile(fileName, encoding) {
41
- if (fileName === this.fileName) {
42
- return this.content;
43
- }
44
-
45
- return ts.sys.readFile(fileName, encoding);
46
- }
47
- fileExists(path) {
48
- return ts.sys.fileExists(path);
49
- }
50
- }
51
-
52
- const removeUnusedImports = (content) => {
53
- const tempFileName = "file.ts";
54
-
55
- const host = new LanguageServiceHost(tempFileName, content);
56
- const languageService = ts.createLanguageService(host);
57
-
58
- const fileTextChanges = languageService.organizeImports(
59
- { type: "file", fileName: tempFileName },
60
- { newLineCharacter: ts.sys.newLine },
61
- )[0];
62
-
63
- if (fileTextChanges && fileTextChanges.textChanges.length) {
64
- return _.reduceRight(
65
- fileTextChanges.textChanges,
66
- (content, { span, newText }) =>
67
- `${content.slice(0, span.start)}${newText}${content.slice(span.start + span.length)}`,
68
- content,
69
- );
70
- }
71
-
72
- return content;
73
- };
74
-
75
- const prettierFormat = (content) => {
76
- return prettier.format(content, config.prettierOptions);
77
- };
78
-
79
- const formatters = [removeUnusedImports, prettierFormat];
80
-
81
- module.exports = (content) => formatters.reduce((fixedContent, formatter) => formatter(fixedContent), content);
package/src/logger.js DELETED
@@ -1,59 +0,0 @@
1
- const _ = require("lodash");
2
- const { config } = require("./config");
3
- const { emojify, emoji } = require("node-emoji");
4
-
5
- /**
6
- *
7
- * @param {{ type: "warn" | "log" | "error", emojiName: keyof emoji, messages: unknown[] }} payload
8
- * @returns {void}
9
- */
10
- const createLogMessage = ({ type, emojiName, messages }) => {
11
- if (config.silent) return;
12
-
13
- const emoji = emojify(emojiName);
14
-
15
- console[type](
16
- emoji,
17
- " ",
18
- ..._.map(messages, (message) =>
19
- _.startsWith(message, "\n") ? `\n${emoji} ${message.replace(/\n/, "")}` : message,
20
- ),
21
- );
22
- };
23
-
24
- const logger = {
25
- log: (...messages) =>
26
- createLogMessage({
27
- type: "log",
28
- emojiName: ":sparkles:",
29
- messages,
30
- }),
31
- event: (...messages) =>
32
- createLogMessage({
33
- type: "log",
34
- emojiName: ":comet: ",
35
- messages,
36
- }),
37
- success: (...messages) =>
38
- createLogMessage({
39
- type: "log",
40
- emojiName: ":white_check_mark:",
41
- messages,
42
- }),
43
- warn: (...messages) =>
44
- createLogMessage({
45
- type: "warn",
46
- emojiName: ":warning: ",
47
- messages,
48
- }),
49
- error: (...messages) =>
50
- createLogMessage({
51
- type: "error",
52
- emojiName: ":exclamation:",
53
- messages,
54
- }),
55
- };
56
-
57
- module.exports = {
58
- logger,
59
- };
package/src/modelNames.js DELETED
@@ -1,78 +0,0 @@
1
- const _ = require("lodash");
2
- const { config } = require("./config");
3
- const { logger } = require("./logger");
4
-
5
- const isValidName = (name) => /^([A-Za-z$_]{1,})$/g.test(name);
6
-
7
- const formattedModelNamesMap = new Map();
8
-
9
- const fixModelName = (name) => {
10
- if (!isValidName(name)) {
11
- if (!/^[a-zA-Z_$]/g.test(name)) {
12
- name = `Type ${name}`;
13
- }
14
-
15
- // specific replaces for TSOA 3.x
16
- if (name.includes("."))
17
- name = name
18
- .replace(/Exclude_keyof[A-Za-z]{1,}/g, (match) => "ExcludeKeys")
19
- .replace(/%22\~AND\~%22/g, "And")
20
- .replace(/%22\~OR\~%22/g, "Or")
21
- .replace(/(\.?%22)|\./g, "_")
22
- .replace(/__+$/, "");
23
-
24
- if (name.includes("-")) name = _.startCase(name).replace(/ /g, "");
25
- }
26
-
27
- return name;
28
- };
29
-
30
- /**
31
- *
32
- * @param {string} name
33
- * @param {{ ignorePrefix?: boolean; ignoreSuffix?: boolean }} options
34
- * @returns
35
- */
36
- const formatModelName = (name, options) => {
37
- const typePrefix = options && options.ignorePrefix ? "" : config.typePrefix;
38
- const typeSuffix = options && options.ignoreSuffix ? "" : config.typeSuffix;
39
- const hashKey = `${typePrefix}_${name}_${typeSuffix}`;
40
-
41
- if (typeof name !== "string") {
42
- logger.warn("wrong name of the model name", name);
43
- return name;
44
- }
45
-
46
- if (/^([A-Z_]{1,})$/g.test(name)) {
47
- return _.compact([typePrefix, name, typeSuffix]).join("_");
48
- }
49
-
50
- if (formattedModelNamesMap.has(hashKey)) {
51
- return formattedModelNamesMap.get(hashKey);
52
- }
53
-
54
- const fixedModelName = fixModelName(name);
55
-
56
- const formattedModelName = _.replace(
57
- _.startCase(`${typePrefix}_${fixedModelName}_${typeSuffix}`),
58
- /\s/g,
59
- "",
60
- );
61
- const modelName = config.hooks.onFormatTypeName(formattedModelName, name) || formattedModelName;
62
-
63
- formattedModelNamesMap.set(hashKey, modelName);
64
-
65
- return modelName;
66
- };
67
-
68
- const formatEnumKey = (key) =>
69
- formatModelName(key, {
70
- ignorePrefix: true,
71
- ignoreSuffix: true,
72
- });
73
-
74
- module.exports = {
75
- formatModelName: formatModelName,
76
- formatEnumKey: formatEnumKey,
77
- isValidName,
78
- };
package/src/modelTypes.js DELETED
@@ -1,31 +0,0 @@
1
- const { formatters } = require("./typeFormatters");
2
- const { formatModelName } = require("./modelNames");
3
- const { config } = require("./config");
4
- const { getTypeData } = require("./components");
5
-
6
- /**
7
- *
8
- * @param {import("./components").TypeInfo} typeInfo
9
- * @returns
10
- */
11
- const prepareModelType = (typeInfo) => {
12
- const rawTypeData = getTypeData(typeInfo);
13
- const typeData = formatters[rawTypeData.type] ? formatters[rawTypeData.type](rawTypeData) : rawTypeData;
14
- let { typeIdentifier, name: originalName, content, description } = typeData;
15
- const name = formatModelName(originalName);
16
-
17
- return {
18
- ...typeData,
19
- typeIdentifier,
20
- name,
21
- description,
22
- $content: rawTypeData.content,
23
- rawContent: rawTypeData.content,
24
- content: content,
25
- typeData,
26
- };
27
- };
28
-
29
- module.exports = {
30
- prepareModelType,
31
- };