@buildvision/nest-sdk-generator 1.1.3

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 (69) hide show
  1. package/.prettierrc +6 -0
  2. package/LICENSE.md +9 -0
  3. package/README.md +353 -0
  4. package/build/analyzer/builtin.d.ts +2 -0
  5. package/build/analyzer/builtin.js +11 -0
  6. package/build/analyzer/classdeps.d.ts +6 -0
  7. package/build/analyzer/classdeps.js +27 -0
  8. package/build/analyzer/controller.d.ts +26 -0
  9. package/build/analyzer/controller.js +103 -0
  10. package/build/analyzer/controllers.d.ts +7 -0
  11. package/build/analyzer/controllers.js +79 -0
  12. package/build/analyzer/decorator.d.ts +10 -0
  13. package/build/analyzer/decorator.js +29 -0
  14. package/build/analyzer/extractor.d.ts +107 -0
  15. package/build/analyzer/extractor.js +349 -0
  16. package/build/analyzer/index.d.ts +16 -0
  17. package/build/analyzer/index.js +101 -0
  18. package/build/analyzer/methods.d.ts +42 -0
  19. package/build/analyzer/methods.js +115 -0
  20. package/build/analyzer/module.d.ts +11 -0
  21. package/build/analyzer/module.js +41 -0
  22. package/build/analyzer/params.d.ts +38 -0
  23. package/build/analyzer/params.js +163 -0
  24. package/build/analyzer/route.d.ts +53 -0
  25. package/build/analyzer/route.js +131 -0
  26. package/build/analyzer/typedeps.d.ts +49 -0
  27. package/build/analyzer/typedeps.js +86 -0
  28. package/build/bin.d.ts +2 -0
  29. package/build/bin.js +39 -0
  30. package/build/config.d.ts +44 -0
  31. package/build/config.js +31 -0
  32. package/build/generator/genmodules.d.ts +24 -0
  33. package/build/generator/genmodules.js +134 -0
  34. package/build/generator/gentypes.d.ts +10 -0
  35. package/build/generator/gentypes.js +62 -0
  36. package/build/generator/index.d.ts +6 -0
  37. package/build/generator/index.js +83 -0
  38. package/build/generator/prettier.d.ts +16 -0
  39. package/build/generator/prettier.js +43 -0
  40. package/build/generator/sdk-interface.d.ts +1 -0
  41. package/build/generator/sdk-interface.js +36 -0
  42. package/build/logging.d.ts +6 -0
  43. package/build/logging.js +37 -0
  44. package/build/tsconfig.tsbuildinfo +1 -0
  45. package/build/utils.d.ts +9 -0
  46. package/build/utils.js +56 -0
  47. package/package.json +34 -0
  48. package/src/analyzer/builtin.ts +9 -0
  49. package/src/analyzer/classdeps.ts +37 -0
  50. package/src/analyzer/controller.ts +135 -0
  51. package/src/analyzer/controllers.ts +117 -0
  52. package/src/analyzer/decorator.ts +29 -0
  53. package/src/analyzer/extractor.ts +491 -0
  54. package/src/analyzer/index.ts +136 -0
  55. package/src/analyzer/methods.ts +166 -0
  56. package/src/analyzer/module.ts +56 -0
  57. package/src/analyzer/params.ts +241 -0
  58. package/src/analyzer/route.ts +156 -0
  59. package/src/analyzer/typedeps.ts +130 -0
  60. package/src/bin.ts +33 -0
  61. package/src/config.ts +89 -0
  62. package/src/generator/genmodules.ts +163 -0
  63. package/src/generator/gentypes.ts +73 -0
  64. package/src/generator/index.ts +92 -0
  65. package/src/generator/prettier.ts +46 -0
  66. package/src/generator/sdk-interface.ts +32 -0
  67. package/src/logging.ts +35 -0
  68. package/src/utils.ts +61 -0
  69. package/tsconfig.json +26 -0
@@ -0,0 +1,79 @@
1
+ "use strict";
2
+ /**
3
+ * @file Analyzer for the source API's controllers
4
+ */
5
+ Object.defineProperty(exports, "__esModule", { value: true });
6
+ exports.analyzeControllers = void 0;
7
+ const os = require("os");
8
+ const path = require("path");
9
+ const logging_1 = require("../logging");
10
+ const utils_1 = require("../utils");
11
+ const controller_1 = require("./controller");
12
+ const module_1 = require("./module");
13
+ function analyzeControllers(controllers, absoluteSrcPath, project) {
14
+ /** Hierarchised SDK informations */
15
+ const collected = new Map();
16
+ /**
17
+ * Modules cache: contains for a given directory the nearest module file's path and name
18
+ * This allows to avoid having to analyze the whole directory structure for each controller
19
+ */
20
+ const modulesCache = new Map();
21
+ /**
22
+ * Path of the declared modules
23
+ * When a module is detected and put in the cache, its name is registered here along with its path
24
+ * This allows to ensure there is no name clash between two different modules
25
+ */
26
+ const declaredModulesPath = new Map();
27
+ (0, logging_1.debug)(`Analyzing {yellow} controllers...`, controllers.length);
28
+ controllers.forEach((relativeControllerPath, i) => {
29
+ const absoluteControllerPath = path.resolve(absoluteSrcPath, relativeControllerPath);
30
+ (0, logging_1.debug)('\n{cyan} {yellow}: {magentaBright} {cyan}\n', '===== Analyzing controller', `${i + 1}/${controllers.length}`, relativeControllerPath, '=====');
31
+ const basePath = path.dirname(absoluteControllerPath);
32
+ let moduleName = modulesCache.get(basePath);
33
+ // Check if the module's name is in cache
34
+ if (!moduleName) {
35
+ // Else, find the nearest module file
36
+ const absoluteModulePath = (0, utils_1.findFileAbove)(/^.*\.module\.ts$/, path.resolve(absoluteSrcPath, basePath));
37
+ if (absoluteModulePath === null) {
38
+ (0, logging_1.panic)('No module file was found for controller at path: {yellow}', absoluteControllerPath);
39
+ }
40
+ const relativeModulePath = path.relative(absoluteSrcPath, absoluteModulePath);
41
+ // Get the module's name
42
+ moduleName = (0, module_1.getModuleName)(project, relativeModulePath, absoluteSrcPath);
43
+ (0, logging_1.debug)('Discovered module: {yellow}', moduleName);
44
+ // Ensure this module is unique
45
+ const cachedModulePath = declaredModulesPath.get(moduleName);
46
+ if (cachedModulePath) {
47
+ (0, logging_1.panic)(`Two modules were declared with the same name {yellow}:\n` + `- One in {yellow}\n` + `- One in {yellow}`, moduleName, cachedModulePath, relativeModulePath);
48
+ }
49
+ modulesCache.set(basePath, moduleName);
50
+ }
51
+ if (moduleName in {}) {
52
+ (0, logging_1.panic)(`Detected module whose name {yellow} collides with a JavaScript's native object property`, moduleName);
53
+ }
54
+ let moduleSdkInfos = collected.get(moduleName);
55
+ if (!moduleSdkInfos) {
56
+ moduleSdkInfos = new Map();
57
+ collected.set(moduleName, moduleSdkInfos);
58
+ }
59
+ if (i === 0) {
60
+ if (process.platform === 'linux' && os.release().toLocaleLowerCase().includes('microsoft') && absoluteSrcPath.startsWith('/mnt/')) {
61
+ (0, logging_1.warn)("NOTE: On WSL, the first type analysis on a project located in Windows's filesystem may take a long time to complete.");
62
+ (0, logging_1.warn)('Please consider moving your project to WSL, or running this tool directly from Windows');
63
+ }
64
+ }
65
+ const metadata = (0, controller_1.analyzeController)(project, relativeControllerPath, absoluteSrcPath);
66
+ if (metadata instanceof Error) {
67
+ throw new Error((0, logging_1.format)('Failed to analyze controller at path {magenta}:\n{}', relativeControllerPath, metadata.message));
68
+ }
69
+ if (metadata) {
70
+ if (metadata.registrationName in {}) {
71
+ (0, logging_1.panic)(`Detected controller whose registration name {yellow} collides with a JavaScript's native object property`, metadata.registrationName);
72
+ }
73
+ moduleSdkInfos.set(metadata.camelClassName, metadata);
74
+ }
75
+ });
76
+ return collected;
77
+ }
78
+ exports.analyzeControllers = analyzeControllers;
79
+ //# sourceMappingURL=data:application/json;base64,eyJ2ZXJzaW9uIjozLCJmaWxlIjoiY29udHJvbGxlcnMuanMiLCJzb3VyY2VSb290IjoiIiwic291cmNlcyI6WyIuLi8uLi9zcmMvYW5hbHl6ZXIvY29udHJvbGxlcnMudHMiXSwibmFtZXMiOltdLCJtYXBwaW5ncyI6IjtBQUFBOztHQUVHOzs7QUFFSCx5QkFBd0I7QUFDeEIsNkJBQTRCO0FBRTVCLHdDQUF1RDtBQUN2RCxvQ0FBd0M7QUFDeEMsNkNBQStEO0FBQy9ELHFDQUF3QztBQUl4QyxTQUFnQixrQkFBa0IsQ0FBQyxXQUFxQixFQUFFLGVBQXVCLEVBQUUsT0FBZ0I7SUFDakcsb0NBQW9DO0lBQ3BDLE1BQU0sU0FBUyxHQUFHLElBQUksR0FBRyxFQUFzQyxDQUFBO0lBRS9EOzs7T0FHRztJQUNILE1BQU0sWUFBWSxHQUFHLElBQUksR0FBRyxFQUFrQixDQUFBO0lBRTlDOzs7O09BSUc7SUFDSCxNQUFNLG1CQUFtQixHQUFHLElBQUksR0FBRyxFQUFrQixDQUFBO0lBRXJELElBQUEsZUFBSyxFQUFDLG1DQUFtQyxFQUFFLFdBQVcsQ0FBQyxNQUFNLENBQUMsQ0FBQTtJQUU5RCxXQUFXLENBQUMsT0FBTyxDQUFDLENBQUMsc0JBQXNCLEVBQUUsQ0FBQyxFQUFFLEVBQUU7UUFDaEQsTUFBTSxzQkFBc0IsR0FBRyxJQUFJLENBQUMsT0FBTyxDQUFDLGVBQWUsRUFBRSxzQkFBc0IsQ0FBQyxDQUFBO1FBRXBGLElBQUEsZUFBSyxFQUNILDZDQUE2QyxFQUM3Qyw0QkFBNEIsRUFDNUIsR0FBRyxDQUFDLEdBQUcsQ0FBQyxJQUFJLFdBQVcsQ0FBQyxNQUFNLEVBQUUsRUFDaEMsc0JBQXNCLEVBQ3RCLE9BQU8sQ0FDUixDQUFBO1FBRUQsTUFBTSxRQUFRLEdBQUcsSUFBSSxDQUFDLE9BQU8sQ0FBQyxzQkFBc0IsQ0FBQyxDQUFBO1FBRXJELElBQUksVUFBVSxHQUFHLFlBQVksQ0FBQyxHQUFHLENBQUMsUUFBUSxDQUFDLENBQUE7UUFFM0MseUNBQXlDO1FBQ3pDLElBQUksQ0FBQyxVQUFVLEVBQUU7WUFD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
@@ -0,0 +1,10 @@
1
+ /**
2
+ * @file Utilities for analyzing the source API's decorators
3
+ */
4
+ import { Decorator } from 'ts-morph';
5
+ /**
6
+ * Expect a decorator to have a single, string literal argument
7
+ * @param dec The decorator
8
+ * @returns Nothing if the decorator has no argument, a { lit: string } if the decorator has a string literal, an Error else
9
+ */
10
+ export declare function expectSingleStrLitDecorator(dec: Decorator): string | null | Error;
@@ -0,0 +1,29 @@
1
+ "use strict";
2
+ /**
3
+ * @file Utilities for analyzing the source API's decorators
4
+ */
5
+ Object.defineProperty(exports, "__esModule", { value: true });
6
+ exports.expectSingleStrLitDecorator = void 0;
7
+ const ts_morph_1 = require("ts-morph");
8
+ const logging_1 = require("../logging");
9
+ /**
10
+ * Expect a decorator to have a single, string literal argument
11
+ * @param dec The decorator
12
+ * @returns Nothing if the decorator has no argument, a { lit: string } if the decorator has a string literal, an Error else
13
+ */
14
+ function expectSingleStrLitDecorator(dec) {
15
+ const args = dec.getArguments();
16
+ if (args.length > 1) {
17
+ return new Error(`Multiple (${args.length}) arguments were provided to the decorator`);
18
+ }
19
+ else if (args.length === 0) {
20
+ return null;
21
+ }
22
+ const [arg] = args;
23
+ if (!ts_morph_1.Node.isStringLiteral(arg)) {
24
+ return new Error((0, logging_1.format)('The argument provided to the decorator is not a string literal:\n>>> {cyan}', arg.getText()));
25
+ }
26
+ return arg.getLiteralText();
27
+ }
28
+ exports.expectSingleStrLitDecorator = expectSingleStrLitDecorator;
29
+ //# sourceMappingURL=data:application/json;base64,eyJ2ZXJzaW9uIjozLCJmaWxlIjoiZGVjb3JhdG9yLmpzIiwic291cmNlUm9vdCI6IiIsInNvdXJjZXMiOlsiLi4vLi4vc3JjL2FuYWx5emVyL2RlY29yYXRvci50cyJdLCJuYW1lcyI6W10sIm1hcHBpbmdzIjoiO0FBQUE7O0dBRUc7OztBQUVILHVDQUEwQztBQUMxQyx3Q0FBbUM7QUFFbkM7Ozs7R0FJRztBQUNILFNBQWdCLDJCQUEyQixDQUFDLEdBQWM7SUFDeEQsTUFBTSxJQUFJLEdBQUcsR0FBRyxDQUFDLFlBQVksRUFBRSxDQUFBO0lBRS9CLElBQUksSUFBSSxDQUFDLE1BQU0sR0FBRyxDQUFDLEVBQUU7UUFDbkIsT0FBTyxJQUFJLEtBQUssQ0FBQyxhQUFhLElBQUksQ0FBQyxNQUFNLDRDQUE0QyxDQUFDLENBQUE7S0FDdkY7U0FBTSxJQUFJLElBQUksQ0FBQyxNQUFNLEtBQUssQ0FBQyxFQUFFO1FBQzVCLE9BQU8sSUFBSSxDQUFBO0tBQ1o7SUFFRCxNQUFNLENBQUMsR0FBRyxDQUFDLEdBQUcsSUFBSSxDQUFBO0lBRWxCLElBQUksQ0FBQyxlQUFJLENBQUMsZUFBZSxDQUFDLEdBQUcsQ0FBQyxFQUFFO1FBQzlCLE9BQU8sSUFBSSxLQUFLLENBQUMsSUFBQSxnQkFBTSxFQUFDLDZFQUE2RSxFQUFFLEdBQUcsQ0FBQyxPQUFPLEVBQUUsQ0FBQyxDQUFDLENBQUE7S0FDdkg7SUFFRCxPQUFPLEdBQUcsQ0FBQyxjQUFjLEVBQUUsQ0FBQTtBQUM3QixDQUFDO0FBaEJELGtFQWdCQyJ9
@@ -0,0 +1,107 @@
1
+ /**
2
+ * @file Types extractor to use in the generated SDK
3
+ */
4
+ import { Project } from 'ts-morph';
5
+ import { MagicType } from '../config';
6
+ import { SdkModules } from './controllers';
7
+ import { ResolvedTypeDeps } from './typedeps';
8
+ /** Valid extensions for TypeScript module files */
9
+ export declare const MODULE_EXTENSIONS: string[];
10
+ /**
11
+ * Location of an imported type
12
+ */
13
+ export interface TypeLocation {
14
+ readonly typename: string;
15
+ readonly relativePathNoExt: string;
16
+ }
17
+ /**
18
+ * Location of an imported type after figuring out its extension
19
+ */
20
+ export interface TypeLocationWithExt extends TypeLocation {
21
+ readonly relativePath: string;
22
+ }
23
+ /**
24
+ * Extracted imported type
25
+ */
26
+ export interface ExtractedType extends TypeLocationWithExt {
27
+ /** Type's declaration */
28
+ readonly content: string;
29
+ /** Type parameters (e.g. <T>) */
30
+ readonly typeParams: string[];
31
+ /** Types this one depends on */
32
+ readonly dependencies: TypeLocationWithExt[];
33
+ }
34
+ export declare type TypesExtractorContent = Map<string, Map<string, ExtractedType>>;
35
+ /**
36
+ * Types extractor
37
+ */
38
+ export declare class TypesExtractor {
39
+ /** TS-Morph project */
40
+ readonly project: Project;
41
+ /** Absolute source path */
42
+ readonly absoluteSrcPath: string;
43
+ /** Magic types to replace non-portable types */
44
+ readonly magicTypes: Array<MagicType>;
45
+ /** Extracted types */
46
+ readonly extracted: TypesExtractorContent;
47
+ constructor(
48
+ /** TS-Morph project */
49
+ project: Project,
50
+ /** Absolute source path */
51
+ absoluteSrcPath: string,
52
+ /** Magic types to replace non-portable types */
53
+ magicTypes: Array<MagicType>,
54
+ /** Extracted types */
55
+ extracted?: TypesExtractorContent);
56
+ /**
57
+ * Check if a type has already been extracted
58
+ */
59
+ hasExtractedType(loc: TypeLocationWithExt): boolean;
60
+ /**
61
+ * Get a type that was previously extracted
62
+ */
63
+ getExtractedType(loc: TypeLocationWithExt): ExtractedType | null;
64
+ /**
65
+ * Find the extension of a TypeScript module
66
+ * @param loc
67
+ * @returns
68
+ */
69
+ guessExtractedTypeModuleFileExt(loc: TypeLocation): string | null;
70
+ /**
71
+ * Find if a type has previously been extracted, without providing its extension
72
+ * @param loc
73
+ * @returns
74
+ */
75
+ findExtractedTypeWithoutExt(loc: TypeLocation): ExtractedType | null;
76
+ /**
77
+ * Memorize an extracted type so it can be reused later on
78
+ * @param loc
79
+ * @param extracted
80
+ */
81
+ memorizeExtractedType(loc: TypeLocationWithExt, extracted: ExtractedType): void;
82
+ /**
83
+ * Find the relative file location of a type
84
+ * @param loc
85
+ * @returns
86
+ */
87
+ findTypeRelativeFilePath(loc: TypeLocation): string | Error;
88
+ /**
89
+ * Extract a type
90
+ * @param loc
91
+ * @param typesPath
92
+ * @returns
93
+ */
94
+ extractType(loc: TypeLocation, typesPath?: string[]): ExtractedType | Error;
95
+ }
96
+ /**
97
+ * Locate the files containing a list of a resolved types
98
+ * @param resolvedTypes
99
+ * @returns
100
+ */
101
+ export declare function locateTypesFile(resolvedTypes: Array<ResolvedTypeDeps>): TypeLocation[];
102
+ /**
103
+ * Flatten a tree of resolved type dependencies
104
+ * @param sdkModules
105
+ * @returns
106
+ */
107
+ export declare function flattenSdkResolvedTypes(sdkModules: SdkModules): ResolvedTypeDeps[];
@@ -0,0 +1,349 @@
1
+ "use strict";
2
+ /**
3
+ * @file Types extractor to use in the generated SDK
4
+ */
5
+ Object.defineProperty(exports, "__esModule", { value: true });
6
+ exports.flattenSdkResolvedTypes = exports.locateTypesFile = exports.TypesExtractor = exports.MODULE_EXTENSIONS = void 0;
7
+ const path = require("path");
8
+ const ts_morph_1 = require("ts-morph");
9
+ const logging_1 = require("../logging");
10
+ const classdeps_1 = require("./classdeps");
11
+ const typedeps_1 = require("./typedeps");
12
+ /** Valid extensions for TypeScript module files */
13
+ exports.MODULE_EXTENSIONS = ['.ts', '.d.ts', '.tsx', '.d.tsx', '.js', '.jsx'];
14
+ /**
15
+ * Types extractor
16
+ */
17
+ class TypesExtractor {
18
+ constructor(
19
+ /** TS-Morph project */
20
+ project,
21
+ /** Absolute source path */
22
+ absoluteSrcPath,
23
+ /** Magic types to replace non-portable types */
24
+ magicTypes,
25
+ /** Extracted types */
26
+ extracted = new Map()) {
27
+ this.project = project;
28
+ this.absoluteSrcPath = absoluteSrcPath;
29
+ this.magicTypes = magicTypes;
30
+ this.extracted = extracted;
31
+ }
32
+ /**
33
+ * Check if a type has already been extracted
34
+ */
35
+ hasExtractedType(loc) {
36
+ const files = this.extracted.get(loc.relativePath);
37
+ return files ? files.has(loc.typename) : false;
38
+ }
39
+ /**
40
+ * Get a type that was previously extracted
41
+ */
42
+ getExtractedType(loc) {
43
+ var _a, _b;
44
+ return (_b = (_a = this.extracted.get(loc.relativePath)) === null || _a === void 0 ? void 0 : _a.get(loc.typename)) !== null && _b !== void 0 ? _b : null;
45
+ }
46
+ /**
47
+ * Find the extension of a TypeScript module
48
+ * @param loc
49
+ * @returns
50
+ */
51
+ guessExtractedTypeModuleFileExt(loc) {
52
+ for (const ext of exports.MODULE_EXTENSIONS) {
53
+ if (this.extracted.has(loc.relativePathNoExt + ext)) {
54
+ return loc.relativePathNoExt + ext;
55
+ }
56
+ }
57
+ return null;
58
+ }
59
+ /**
60
+ * Find if a type has previously been extracted, without providing its extension
61
+ * @param loc
62
+ * @returns
63
+ */
64
+ findExtractedTypeWithoutExt(loc) {
65
+ var _a;
66
+ for (const ext of exports.MODULE_EXTENSIONS) {
67
+ const typ = (_a = this.extracted.get(loc.relativePathNoExt + ext)) === null || _a === void 0 ? void 0 : _a.get(loc.typename);
68
+ if (typ) {
69
+ return typ;
70
+ }
71
+ }
72
+ return null;
73
+ }
74
+ /**
75
+ * Memorize an extracted type so it can be reused later on
76
+ * @param loc
77
+ * @param extracted
78
+ */
79
+ memorizeExtractedType(loc, extracted) {
80
+ let files = this.extracted.get(loc.relativePath);
81
+ if (!files) {
82
+ files = new Map();
83
+ this.extracted.set(loc.relativePath, files);
84
+ }
85
+ if (!files.has(loc.typename)) {
86
+ files.set(loc.typename, extracted);
87
+ }
88
+ }
89
+ /**
90
+ * Find the relative file location of a type
91
+ * @param loc
92
+ * @returns
93
+ */
94
+ findTypeRelativeFilePath(loc) {
95
+ if (path.isAbsolute(loc.relativePathNoExt)) {
96
+ (0, logging_1.unreachable)('Internal error: got absolute file path in types extractor, when expecting a relative one (got {magentaBright})', loc.relativePathNoExt);
97
+ }
98
+ const absolutePathNoExt = path.resolve(this.absoluteSrcPath, loc.relativePathNoExt);
99
+ const cached = this.findExtractedTypeWithoutExt(loc);
100
+ if (cached) {
101
+ return cached.relativePath;
102
+ }
103
+ let relativeFilePath = null;
104
+ for (const ext of exports.MODULE_EXTENSIONS) {
105
+ try {
106
+ this.project.getSourceFileOrThrow(absolutePathNoExt + ext);
107
+ relativeFilePath = loc.relativePathNoExt + ext;
108
+ }
109
+ catch (e) {
110
+ continue;
111
+ }
112
+ }
113
+ return (relativeFilePath !== null && relativeFilePath !== void 0 ? relativeFilePath : new Error((0, logging_1.format)('File {magenta} was not found (was expected to contain dependency type {yellow})', loc.relativePathNoExt, loc.typename)));
114
+ }
115
+ /**
116
+ * Extract a type
117
+ * @param loc
118
+ * @param typesPath
119
+ * @returns
120
+ */
121
+ extractType(loc, typesPath = []) {
122
+ var _a, _b;
123
+ if (path.isAbsolute(loc.relativePathNoExt)) {
124
+ (0, logging_1.unreachable)('Internal error: got absolute file path in types extractor, when expecting a relative one (got {magentaBright})', loc.relativePathNoExt);
125
+ }
126
+ // Get the absolute path of the type's parent file
127
+ // We don't know its extension yet as imported file names in import statements don't have an extension
128
+ const absolutePathNoExt = path.resolve(this.absoluteSrcPath, loc.relativePathNoExt);
129
+ // If the type is already in cache, return it directly
130
+ const cached = this.findExtractedTypeWithoutExt(loc);
131
+ if (cached) {
132
+ return cached;
133
+ }
134
+ // Try to find the path with extension of the file and get it as a TS-Morph file
135
+ let fileAndPath = null;
136
+ for (const ext of exports.MODULE_EXTENSIONS) {
137
+ try {
138
+ fileAndPath = [this.project.getSourceFileOrThrow(absolutePathNoExt + ext), loc.relativePathNoExt + ext];
139
+ }
140
+ catch (e) {
141
+ continue;
142
+ }
143
+ }
144
+ if (!fileAndPath) {
145
+ return new Error((0, logging_1.format)('File {magenta} was not found (was expected to contain dependency type {yellow})', loc.relativePathNoExt, loc.typename));
146
+ }
147
+ const [file, relativeFilePath] = fileAndPath;
148
+ // Use magic types to replace non-portable types
149
+ for (const magicType of this.magicTypes) {
150
+ if (relativeFilePath.endsWith(`node_modules/${magicType.nodeModuleFilePath}`) && loc.typename === magicType.typeName) {
151
+ (0, logging_1.debug)('-> '.repeat(typesPath.length + 1) +
152
+ 'Found magic type {yellow} from external module file {magentaBright}, using provided placeholder.', loc.typename, relativeFilePath);
153
+ const extracted = {
154
+ content: '/** @file Magic placeholder from configuration file */\n\n' + magicType.placeholderContent,
155
+ relativePath: relativeFilePath,
156
+ relativePathNoExt: loc.relativePathNoExt,
157
+ typename: loc.typename,
158
+ typeParams: [],
159
+ dependencies: [],
160
+ };
161
+ typesPath.pop();
162
+ let types = this.extracted.get(relativeFilePath);
163
+ if (!types) {
164
+ types = new Map();
165
+ this.extracted.set(relativeFilePath, types);
166
+ }
167
+ types.set(loc.typename, extracted);
168
+ return extracted;
169
+ }
170
+ }
171
+ (0, logging_1.debug)('-> '.repeat(typesPath.length + 1) + 'Extracting type {yellow} from file {magentaBright}...', loc.typename, relativeFilePath);
172
+ // Analyze the type's declaration
173
+ const decl = file.forEachChildAsArray().find((node) => {
174
+ return ((ts_morph_1.Node.isEnumDeclaration(node) ||
175
+ ts_morph_1.Node.isTypeAliasDeclaration(node) ||
176
+ ts_morph_1.Node.isInterfaceDeclaration(node) ||
177
+ ts_morph_1.Node.isClassDeclaration(node) ||
178
+ ts_morph_1.Node.isFunctionDeclaration(node)) &&
179
+ node.getName() === loc.typename);
180
+ });
181
+ if (!decl) {
182
+ return new Error((0, logging_1.format)(`Type {yellow} was not found in file {magenta}`, loc.typename, relativeFilePath));
183
+ }
184
+ // Handle a limitation of the tool: you can't import two types from two files at the same path with just two different extensions
185
+ // Example: importing a type named "User" from two files in the same directory called "user.entity.ts" and "user.entity.js"
186
+ const typ = this.findExtractedTypeWithoutExt(loc);
187
+ if (typ && typ.relativePath !== relativeFilePath) {
188
+ (0, logging_1.panic)('Found two conflicting files at same path but with different extensions:\n> {magentaBright}\n> {magentaBright}', typ.relativePath, relativeFilePath);
189
+ }
190
+ /** Resolved type's dependencies */
191
+ let resolvedDeps;
192
+ /** Type's parameters (e.g. <T>) */
193
+ let typeParams;
194
+ /** Type declaration */
195
+ let extractedDecl = decl.getText();
196
+ // Handle enumerations
197
+ if (ts_morph_1.Node.isEnumDeclaration(decl)) {
198
+ resolvedDeps = [];
199
+ typeParams = [];
200
+ }
201
+ // Handle type aliases
202
+ else if (ts_morph_1.Node.isTypeAliasDeclaration(decl)) {
203
+ resolvedDeps = [(0, typedeps_1.resolveTypeDependencies)(decl.getType(), relativeFilePath, this.absoluteSrcPath)];
204
+ typeParams = [];
205
+ }
206
+ // Handle interfaces
207
+ else if (ts_morph_1.Node.isInterfaceDeclaration(decl)) {
208
+ resolvedDeps = (0, classdeps_1.analyzeClassDeps)(decl, relativeFilePath, this.absoluteSrcPath);
209
+ typeParams = decl.getTypeParameters().map((tp) => tp.getText());
210
+ }
211
+ // Handle classes
212
+ // Methods are not handled because they shouldn't be used as DTOs and won't be decodable from JSON in all cases
213
+ // This part is tricky as we remake the class from scratch using the informations we have on it, given we have to get rid
214
+ // of methods as well as removing decorators
215
+ else if (ts_morph_1.Node.isClassDeclaration(decl)) {
216
+ const classHead = decl.getText().match(/\b(export[^{]+class[^{]+{)/);
217
+ if (!classHead) {
218
+ (0, logging_1.unreachable)('Internal error: failed to match class head in declaration: {yellow}', decl.getText());
219
+ }
220
+ extractedDecl = classHead[1];
221
+ const index = (_a = decl.getType().getStringIndexType()) !== null && _a !== void 0 ? _a : decl.getType().getNumberIndexType();
222
+ if (index) {
223
+ extractedDecl += '\npublic [input: string | number]: ' + (0, typedeps_1.getImportResolvedType)(index);
224
+ }
225
+ // Export all members
226
+ for (const member of decl.getMembers()) {
227
+ if (!ts_morph_1.Node.isPropertyDeclaration(member)) {
228
+ (0, logging_1.warn)('Found non-property member in class {cyan}: {magenta}', (_b = decl.getName()) !== null && _b !== void 0 ? _b : '<anonymous>', member.getText());
229
+ continue;
230
+ }
231
+ const memberType = member.getType();
232
+ extractedDecl += `\npublic ${member.getName()}${member.getText().includes('?') ? '?' : member.getText().includes('!:') ? '!' : ''}: ${(0, typedeps_1.getImportResolvedType)(memberType)};`;
233
+ }
234
+ extractedDecl += '\n}';
235
+ resolvedDeps = (0, classdeps_1.analyzeClassDeps)(decl, relativeFilePath, this.absoluteSrcPath);
236
+ typeParams = decl.getTypeParameters().map((tp) => tp.getText());
237
+ }
238
+ // Handle functions
239
+ else if (ts_morph_1.Node.isFunctionDeclaration(decl)) {
240
+ resolvedDeps = [];
241
+ typeParams = [];
242
+ }
243
+ // Handle unknown types
244
+ else {
245
+ (0, logging_1.panic)('Unknown node type when extracting types: ' + decl.getKindName());
246
+ }
247
+ /** Normalized dependencies */
248
+ const dependencies = [];
249
+ // Ensure we're not stuck in an infinite loop where we analyze a type A, then its dependency B, which itself depends on A, and so on
250
+ if (typesPath.includes(loc.typename)) {
251
+ (0, logging_1.unreachable)(`Internal error: infinite loop detected in types extracted: {yellow}`, typesPath.join(' -> '));
252
+ }
253
+ typesPath.push(loc.typename);
254
+ // Analyze all dependencies
255
+ for (const dependencyLoc of locateTypesFile(resolvedDeps)) {
256
+ // If the "dependency" is one of the type's parameters (e.g. "T"), ignore this part
257
+ if (typeParams.includes(dependencyLoc.typename)) {
258
+ continue;
259
+ }
260
+ // Find the dependency's relative path
261
+ let relativePath;
262
+ const cached = this.findExtractedTypeWithoutExt(dependencyLoc);
263
+ if (cached) {
264
+ relativePath = cached.relativePath;
265
+ }
266
+ else if (typesPath.includes(dependencyLoc.typename)) {
267
+ relativePath = this.findTypeRelativeFilePath(dependencyLoc);
268
+ }
269
+ else {
270
+ const extracted = this.extractType(dependencyLoc, typesPath);
271
+ relativePath = extracted instanceof Error ? extracted : extracted.relativePath;
272
+ }
273
+ if (relativePath instanceof Error) {
274
+ return new Error((0, logging_1.format)('├─ Failed to extract type {yellow} due to an error in dependency type {yellow}\nfrom file {magenta} :\n{}', loc.typename, dependencyLoc.typename, relativeFilePath, relativePath.message.replace(/^/gm, ' ')));
275
+ }
276
+ // Update dependencies
277
+ dependencies.push(Object.assign(Object.assign({}, dependencyLoc), { relativePath }));
278
+ }
279
+ const extracted = Object.assign(Object.assign({}, loc), { relativePath: relativeFilePath, typeParams, content: extractedDecl, dependencies });
280
+ typesPath.pop();
281
+ let types = this.extracted.get(relativeFilePath);
282
+ if (!types) {
283
+ types = new Map();
284
+ this.extracted.set(relativeFilePath, types);
285
+ }
286
+ // Save the dependency
287
+ types.set(loc.typename, extracted);
288
+ return extracted;
289
+ }
290
+ }
291
+ exports.TypesExtractor = TypesExtractor;
292
+ /**
293
+ * Locate the files containing a list of a resolved types
294
+ * @param resolvedTypes
295
+ * @returns
296
+ */
297
+ function locateTypesFile(resolvedTypes) {
298
+ const out = new Array();
299
+ for (const resolved of resolvedTypes) {
300
+ for (const [file, types] of resolved.dependencies) {
301
+ for (const typename of types) {
302
+ if (!out.find((loc) => loc.typename === typename && loc.relativePathNoExt === file)) {
303
+ out.push({ typename, relativePathNoExt: file });
304
+ }
305
+ }
306
+ }
307
+ for (const typename of resolved.localTypes) {
308
+ if (!out.find((loc) => loc.typename === typename && loc.relativePathNoExt === resolved.relativeFilePath)) {
309
+ out.push({ typename, relativePathNoExt: resolved.relativeFilePath });
310
+ }
311
+ }
312
+ }
313
+ return out;
314
+ }
315
+ exports.locateTypesFile = locateTypesFile;
316
+ /**
317
+ * Flatten a tree of resolved type dependencies
318
+ * @param sdkModules
319
+ * @returns
320
+ */
321
+ function flattenSdkResolvedTypes(sdkModules) {
322
+ const flattened = new Array();
323
+ for (const module of sdkModules.values()) {
324
+ for (const controller of module.values()) {
325
+ for (const method of controller.methods.values()) {
326
+ const { parameters: args, query, body } = method.params;
327
+ flattened.push(method.returnType);
328
+ if (args) {
329
+ flattened.push(...args.values());
330
+ }
331
+ if (query) {
332
+ flattened.push(...query.values());
333
+ }
334
+ if (!body) {
335
+ continue;
336
+ }
337
+ if (body.full) {
338
+ flattened.push(body.type);
339
+ }
340
+ else {
341
+ flattened.push(...body.fields.values());
342
+ }
343
+ }
344
+ }
345
+ }
346
+ return flattened;
347
+ }
348
+ exports.flattenSdkResolvedTypes = flattenSdkResolvedTypes;
349
+ //# sourceMappingURL=data:application/json;base64,eyJ2ZXJzaW9uIjozLCJmaWxlIjoiZXh0cmFjdG9yLmpzIiwic291cmNlUm9vdCI6IiIsInNvdXJjZXMiOlsiLi4vLi4vc3JjL2FuYWx5emVyL2V4dHJhY3Rvci50cyJdLCJuYW1lcyI6W10sIm1hcHBpbmdzIjoiO0FBQUE7O0dBRUc7OztBQUVILDZCQUE0QjtBQUM1Qix1Q0FBb0Q7QUFFcEQsd0NBQW9FO0FBQ3BFLDJDQUE4QztBQUU5Qyx5Q0FBNkY7QUFFN0YsbURBQW1EO0FBQ3RDLFFBQUEsaUJBQWlCLEdBQUcsQ0FBQyxLQUFLLEVBQUUsT0FBTyxFQUFFLE1BQU0sRUFBRSxRQUFRLEVBQUUsS0FBSyxFQUFFLE1BQU0sQ0FBQyxDQUFBO0FBa0NsRjs7R0FFRztBQUNILE1BQWEsY0FBYztJQUN6QjtJQUNFLHVCQUF1QjtJQUNQLE9BQWdCO0lBRWhDLDJCQUEyQjtJQUNYLGVBQXVCO0lBRXZDLGdEQUFnRDtJQUNoQyxVQUE0QjtJQUU1QyxzQkFBc0I7SUFDTixZQUFtQyxJQUFJLEdBQUcsRUFBRTtRQVQ1QyxZQUFPLEdBQVAsT0FBTyxDQUFTO1FBR2hCLG9CQUFlLEdBQWYsZUFBZSxDQUFRO1FBR3ZCLGVBQVUsR0FBVixVQUFVLENBQWtCO1FBRzVCLGNBQVMsR0FBVCxTQUFTLENBQW1DO0lBQzNELENBQUM7SUFFSjs7T0FFRztJQUNILGdCQUFnQixDQUFDLEdBQXdCO1FBQ3ZDLE1BQU0sS0FBSyxHQUFHLElBQUksQ0FBQyxTQUFTLENBQUMsR0FBRyxDQUFDLEdBQUcsQ0FBQyxZQUFZLENBQUMsQ0FBQTtRQUNsRCxPQUFPLEtBQUssQ0FBQyxDQUFDLENBQUMsS0FBSyxDQUFDLEdBQUcsQ0FBQyxHQUFHLENBQUMsUUFBUSxDQUFDLENBQUMsQ0FBQyxDQUFDLEtBQUssQ0FBQTtJQUNoRCxDQUFDO0lBRUQ7O09BRUc7SUFDSCxnQkFBZ0IsQ0FBQyxHQUF3Qjs7UUFDdkMsT0FBTyxNQUFBLE1BQUEsSUFBSSxDQUFDLFNBQVMsQ0FBQyxHQUFHLENBQUMsR0FBRyxDQUFDLFlBQVksQ0FBQywwQ0FBRSxHQUFH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
@@ -0,0 +1,16 @@
1
+ /**
2
+ * @file Entrypoint of the source API analyzer, used to generate the final SDK
3
+ */
4
+ import { Config } from '../config';
5
+ import { SdkModules } from './controllers';
6
+ import { TypesExtractorContent } from './extractor';
7
+ export interface SdkContent {
8
+ readonly modules: SdkModules;
9
+ readonly types: TypesExtractorContent;
10
+ }
11
+ export interface MagicType {
12
+ readonly package: string;
13
+ readonly typeName: string;
14
+ readonly content: string;
15
+ }
16
+ export declare function analyzerCli(config: Config): Promise<SdkContent>;