@hadss/turbo-trans-json-plugin 1.0.0-rc.0 → 1.0.0-rc.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.
Files changed (88) hide show
  1. package/README.md +1 -1
  2. package/dist/core/Types.d.ts +7 -0
  3. package/dist/core/Types.js +7 -1
  4. package/dist/core/analyzers/ClassAnalyzer.d.ts +15 -0
  5. package/dist/core/analyzers/ClassAnalyzer.js +200 -120
  6. package/dist/core/analyzers/CustomTypeAnalyzer.d.ts +3 -0
  7. package/dist/core/analyzers/CustomTypeAnalyzer.js +65 -60
  8. package/dist/core/constants/DecoratorConstants.d.ts +1 -0
  9. package/dist/core/constants/DecoratorConstants.js +3 -1
  10. package/dist/core/handlers/CustomClassHandler.js +0 -1
  11. package/dist/core/import-rewrite/services/BuildProfileUpdater.js +1 -1
  12. package/dist/core/import-rewrite/services/ImportRewriteService.js +1 -1
  13. package/dist/core/interfaces/index.d.ts +2 -2
  14. package/dist/core/services/CodeAnalysisService.js +2 -1
  15. package/dist/core/services/CodeGenerationService/CodeGenerationService.js +1 -1
  16. package/dist/core/services/CodeGenerationService/generators/MergedSendableClassGenerator.d.ts +0 -1
  17. package/dist/core/services/CodeGenerationService/generators/MergedSendableClassGenerator.js +0 -20
  18. package/dist/core/services/CodeGenerationService/generators/OriginalClassGenerator.d.ts +4 -4
  19. package/dist/core/services/CodeGenerationService/generators/OriginalClassGenerator.js +26 -45
  20. package/dist/core/services/CodeGenerationService/generators/SendableClassGenerator.d.ts +22 -0
  21. package/dist/core/services/CodeGenerationService/generators/SendableClassGenerator.js +194 -129
  22. package/dist/core/services/CodeGenerationService/generators/SerializerGenerator.js +20 -15
  23. package/dist/core/services/CodeGenerationService/generators/TempSerializerGenerator.js +2 -1
  24. package/dist/core/services/CodeGenerationService/shared/ImportManager.d.ts +2 -2
  25. package/dist/core/template/HandlebarsTemplateEngine.d.ts +2 -0
  26. package/dist/core/template/HandlebarsTemplateEngine.js +24 -2
  27. package/dist/core/utils/DeepCopyUtil.js +4 -2
  28. package/dist/core/utils/GenericTypeSubstitutionUtil.d.ts +1 -0
  29. package/dist/core/utils/GenericTypeSubstitutionUtil.js +27 -1
  30. package/dist/core/utils/SerializationPathUtil.d.ts +1 -1
  31. package/dist/core/utils/TsMorphUtil.js +6 -1
  32. package/dist/json-plugin/JSONExecuteController.d.ts +4 -0
  33. package/dist/json-plugin/JSONExecuteController.js +46 -36
  34. package/dist/json-plugin/interfaces/impl/TargetContext.js +4 -2
  35. package/dist/json-plugin/tasks/BaseTask.d.ts +2 -2
  36. package/dist/json-plugin/tasks/WatchTask.js +2 -1
  37. package/package.json +1 -1
  38. package/src/core/Types.ts +97 -89
  39. package/src/core/analyzers/ClassAnalyzer.ts +358 -197
  40. package/src/core/analyzers/CustomTypeAnalyzer.ts +145 -74
  41. package/src/core/constants/DecoratorConstants.ts +7 -5
  42. package/src/core/constants/PathConstants.ts +7 -7
  43. package/src/core/constants/StringConstants.ts +95 -97
  44. package/src/core/handlers/BaseTypeHandler.ts +11 -2
  45. package/src/core/handlers/CustomClassHandler.ts +4 -7
  46. package/src/core/handlers/DateHandler.ts +54 -46
  47. package/src/core/handlers/DecimalHandler.ts +53 -45
  48. package/src/core/handlers/EnumHandler.ts +2 -1
  49. package/src/core/handlers/GenericContainerHandler.ts +3 -1
  50. package/src/core/handlers/TupleHandler.ts +2 -1
  51. package/src/core/handlers/TypeHandlerRegistry.ts +3 -2
  52. package/src/core/handlers/UnionTypeHandler.ts +8 -7
  53. package/src/core/import-rewrite/services/BuildProfileUpdater.ts +7 -5
  54. package/src/core/import-rewrite/services/ImportRewriteService.ts +1 -3
  55. package/src/core/import-rewrite/services/ImportTransformService.ts +2 -2
  56. package/src/core/import-rewrite/types/ImportRewriteTypes.ts +3 -3
  57. package/src/core/index.ts +4 -4
  58. package/src/core/interfaces/ITask.ts +6 -5
  59. package/src/core/interfaces/ITaskContext.ts +9 -9
  60. package/src/core/interfaces/index.ts +2 -2
  61. package/src/core/logger/Logger.ts +28 -28
  62. package/src/core/services/CodeAnalysisService.ts +3 -2
  63. package/src/core/services/CodeGenerationEngine.ts +42 -42
  64. package/src/core/services/CodeGenerationService/CodeGenerationService.ts +1 -2
  65. package/src/core/services/CodeGenerationService/generators/MergedSendableClassGenerator.ts +0 -29
  66. package/src/core/services/CodeGenerationService/generators/OriginalClassGenerator.ts +31 -64
  67. package/src/core/services/CodeGenerationService/generators/SendableClassGenerator.ts +261 -170
  68. package/src/core/services/CodeGenerationService/generators/SerializerGenerator.ts +26 -19
  69. package/src/core/services/CodeGenerationService/generators/TempSerializerGenerator.ts +5 -3
  70. package/src/core/services/CodeGenerationService/shared/ImportManager.ts +8 -8
  71. package/src/core/template/HandlebarsTemplateEngine.ts +43 -10
  72. package/src/core/utils/ConfigManager.ts +2 -1
  73. package/src/core/utils/DeepCopyUtil.ts +4 -2
  74. package/src/core/utils/GenericTypeSubstitutionUtil.ts +45 -2
  75. package/src/core/utils/SerializationPathUtil.ts +7 -6
  76. package/src/core/utils/TsMorphUtil.ts +9 -2
  77. package/src/index.ts +2 -2
  78. package/src/json-plugin/JSONExecuteController.ts +51 -38
  79. package/src/json-plugin/interfaces/IModuleContext.ts +8 -8
  80. package/src/json-plugin/interfaces/ITargetContext.ts +6 -6
  81. package/src/json-plugin/interfaces/impl/ModuleContext.ts +10 -10
  82. package/src/json-plugin/interfaces/impl/TargetContext.ts +63 -58
  83. package/src/json-plugin/tasks/BaseTask.ts +5 -4
  84. package/src/json-plugin/tasks/CleanTask.ts +7 -7
  85. package/src/json-plugin/tasks/WatchTask.ts +20 -18
  86. package/template/SerializerPerformanceTemplate.hbs +14 -4
  87. package/template/SerializerStrictTemplate.hbs +9 -1
  88. package/template/SerializerTemplate.hbs +71 -46
@@ -29,7 +29,8 @@ class SendableClassGenerator {
29
29
  }
30
30
  getOriginClassDeclaration(result) {
31
31
  const originalContent = result.originalClass?.getFullText();
32
- const copiedSourceFile = TsMorphUtil_1.TsMorphUtil.getProject().createSourceFile('copied-file.ts', originalContent, { overwrite: true });
32
+ const copiedSourceFile = TsMorphUtil_1.TsMorphUtil.getProject()
33
+ .createSourceFile('copied-file.ts', originalContent, { overwrite: true });
33
34
  return copiedSourceFile.getClassOrThrow(result.className);
34
35
  }
35
36
  renameSendableClass(classDecl, result) {
@@ -51,51 +52,67 @@ class SendableClassGenerator {
51
52
  });
52
53
  }
53
54
  removeAllDecorators(classDecl) {
55
+ this.removeClassDecorators(classDecl);
56
+ this.removePropertyDecorators(classDecl);
57
+ this.removeMethodDecorators(classDecl);
58
+ }
59
+ removeClassDecorators(classDecl) {
54
60
  classDecl.getDecorators().forEach((decorator) => {
55
- __1.Logger.warn(`Remove the decorator ${decorator.getName()}, because @Sendable cannot coexist with other decorators`);
56
- decorator.remove();
61
+ this.logAndRemoveDecorator(decorator);
57
62
  });
63
+ }
64
+ removePropertyDecorators(classDecl) {
58
65
  classDecl.getProperties().forEach((property) => {
59
- property.getDecorators().forEach((decorator) => {
60
- __1.Logger.warn(`Remove the decorator ${decorator.getName()}, because @Sendable cannot coexist with other decorators`);
61
- decorator.remove();
62
- });
66
+ property.getDecorators().forEach((decorator) => this.logAndRemoveDecorator(decorator));
63
67
  });
68
+ }
69
+ removeMethodDecorators(classDecl) {
64
70
  classDecl.getMethods().forEach((method) => {
65
- method.getDecorators().forEach((decorator) => {
66
- __1.Logger.warn(`Remove the decorator ${decorator.getName()}, because @Sendable cannot coexist with other decorators`);
67
- decorator.remove();
68
- });
71
+ method.getDecorators().forEach((decorator) => this.logAndRemoveDecorator(decorator));
69
72
  });
70
73
  }
74
+ logAndRemoveDecorator(decorator) {
75
+ __1.Logger.warn(`Remove the decorator ${decorator.getName()}, because @Sendable cannot coexist with other decorators`);
76
+ decorator.remove();
77
+ }
71
78
  convertPropertyTypesToSendable(classDecl, result) {
72
79
  const properties = classDecl.getProperties();
73
80
  properties.forEach((property) => {
74
- const propertyName = property.getName();
75
- __1.Logger.debug(`Converting property ${propertyName} to sendable`);
76
- const propertyAnalysis = result.properties.find((p) => p.name === propertyName);
77
- if (!propertyAnalysis) {
78
- __1.Logger.warn(`未找到属性 ${propertyName} 的分析信息`);
79
- return;
80
- }
81
- __1.Logger.debug(`Found property ${propertyName} analysis info: ${propertyAnalysis.name} ${propertyAnalysis.type.sourceText}`);
82
- const sendableType = this.convertToSendableType(propertyAnalysis.type);
83
- __1.Logger.debug(`Converted type ${propertyAnalysis.type.sourceText} to ${sendableType}`);
84
- if (sendableType !== propertyAnalysis.type.sourceText) {
85
- property.setType(sendableType);
86
- __1.Logger.debug(`属性 ${propertyName} 类型从 ${propertyAnalysis.type.sourceText} 转换为 ${sendableType}`);
87
- }
88
- const initializer = property.getInitializer();
89
- if (initializer) {
90
- const initializerText = initializer.getText();
91
- const convertedInitializer = this.convertInitializerToSendable(initializerText);
92
- if (convertedInitializer !== initializerText) {
93
- property.setInitializer(convertedInitializer);
94
- __1.Logger.debug(`属性 ${propertyName} 默认值从 ${initializerText} 转换为 ${convertedInitializer}`);
95
- }
96
- }
81
+ this.convertSinglePropertyToSendable(property, result);
97
82
  });
98
83
  }
84
+ convertSinglePropertyToSendable(property, result) {
85
+ const propertyName = property.getName();
86
+ __1.Logger.debug(`Converting property ${propertyName} to sendable`);
87
+ const propertyAnalysis = result.properties.find((p) => p.name === propertyName);
88
+ if (!propertyAnalysis) {
89
+ __1.Logger.warn(`未找到属性 ${propertyName} 的分析信息`);
90
+ return;
91
+ }
92
+ __1.Logger.debug(`Found property ${propertyName} analysis info: ${propertyAnalysis.name} ${propertyAnalysis.type.sourceText}`);
93
+ this.updatePropertyType(property, propertyAnalysis);
94
+ this.updatePropertyInitializer(property, propertyAnalysis.name);
95
+ }
96
+ updatePropertyType(property, propertyAnalysis) {
97
+ const sendableType = this.convertToSendableType(propertyAnalysis.type);
98
+ __1.Logger.debug(`Converted type ${propertyAnalysis.type.sourceText} to ${sendableType}`);
99
+ if (sendableType !== propertyAnalysis.type.sourceText) {
100
+ property.setType(sendableType);
101
+ __1.Logger.debug(`属性 ${propertyAnalysis.name} 类型从 ${propertyAnalysis.type.sourceText} 转换为 ${sendableType}`);
102
+ }
103
+ }
104
+ updatePropertyInitializer(property, propertyName) {
105
+ const initializer = property.getInitializer();
106
+ if (!initializer) {
107
+ return;
108
+ }
109
+ const initializerText = initializer.getText();
110
+ const convertedInitializer = this.convertInitializerToSendable(initializerText);
111
+ if (convertedInitializer !== initializerText) {
112
+ property.setInitializer(convertedInitializer);
113
+ __1.Logger.debug(`属性 ${propertyName} 默认值从 ${initializerText} 转换为 ${convertedInitializer}`);
114
+ }
115
+ }
99
116
  addSendableConstraints(classDecl) {
100
117
  classDecl.addDecorator({ name: 'Sendable' });
101
118
  classDecl.addImplements('lang.ISendable');
@@ -115,7 +132,24 @@ class SendableClassGenerator {
115
132
  }
116
133
  generatedToOriginMethodBody(result, returnType) {
117
134
  const statements = [];
118
- let constructorCall;
135
+ const constructorCall = this.getConstructorCall(result, returnType);
136
+ statements.push(`const origin = ${constructorCall};`);
137
+ const assignmentProps = result.properties.filter((p) => {
138
+ return result.constructorParams.every((cp) => cp.name !== p.name);
139
+ });
140
+ if (assignmentProps.length > 0) {
141
+ statements.push('');
142
+ statements.push('// 非构造函数属性赋值');
143
+ assignmentProps.forEach((prop) => {
144
+ const assignment = this.generatePropertyConversion(prop, 'this.');
145
+ statements.push(`origin.${prop.name} = ${assignment};`);
146
+ });
147
+ }
148
+ statements.push('');
149
+ statements.push('return origin;');
150
+ return statements.join('\n');
151
+ }
152
+ getConstructorCall(result, returnType) {
119
153
  if (result.constructorParams.length > 0) {
120
154
  const constructorProps = [];
121
155
  result.properties.forEach((p) => {
@@ -135,26 +169,11 @@ class SendableClassGenerator {
135
169
  return this.generatePropertyConversion(prop, 'this.');
136
170
  })
137
171
  .join(', ');
138
- constructorCall = `new ${returnType}(${args})`;
172
+ return `new ${returnType}(${args})`;
139
173
  }
140
174
  else {
141
- constructorCall = `new ${returnType}()`;
175
+ return `new ${returnType}()`;
142
176
  }
143
- statements.push(`const origin = ${constructorCall};`);
144
- const assignmentProps = result.properties.filter((p) => {
145
- return result.constructorParams.every((cp) => cp.name !== p.name);
146
- });
147
- if (assignmentProps.length > 0) {
148
- statements.push('');
149
- statements.push('// 非构造函数属性赋值');
150
- assignmentProps.forEach((prop) => {
151
- const assignment = this.generatePropertyConversion(prop, 'this.');
152
- statements.push(`origin.${prop.name} = ${assignment};`);
153
- });
154
- }
155
- statements.push('');
156
- statements.push('return origin;');
157
- return statements.join('\n');
158
177
  }
159
178
  generatePropertyConversion(prop, prefix) {
160
179
  const sourceValue = `${prefix}${prop.name}`;
@@ -175,74 +194,108 @@ class SendableClassGenerator {
175
194
  return `Sendable${result.className}`;
176
195
  }
177
196
  addNecessaryImports(result, importManager) {
197
+ this.processPropertyDependencyImports(result, importManager);
198
+ this.processBaseClassImport(result, importManager);
199
+ this.processCollectionsImport(result, importManager);
200
+ this.copySourceFileImports(result, importManager);
201
+ }
202
+ processPropertyDependencyImports(result, importManager) {
178
203
  result.properties.forEach((property) => {
179
204
  property.type.dependencies.forEach((dependency) => {
180
- if (dependency.typeKind === __1.TypeKind.CLASS) {
181
- const classAnalysis = ClassAnalyzer_1.ClassAnalyzer.analyzeClass(dependency.details.classDecl);
182
- if (classAnalysis.decorators.serializable?.generateSendable) {
183
- importManager.registerCustomImport('./Sendable' + dependency.typeName, 'Sendable' + dependency.typeName);
184
- }
185
- else {
186
- importManager.registerCustomTypeImport(dependency.source.sourceFilePath, dependency.typeName);
187
- }
188
- }
189
- else {
190
- importManager.registerCustomTypeImport(dependency.source.sourceFilePath, dependency.typeName);
191
- }
205
+ this.registerDependencyImport(dependency, importManager);
192
206
  });
193
207
  });
208
+ }
209
+ registerDependencyImport(dependency, importManager) {
210
+ if (dependency.typeKind !== __1.TypeKind.CLASS) {
211
+ importManager.registerCustomTypeImport(dependency.source.sourceFilePath, dependency.typeName);
212
+ return;
213
+ }
214
+ const classAnalysis = ClassAnalyzer_1.ClassAnalyzer.analyzeClass(dependency.details.classDecl);
215
+ if (classAnalysis.decorators.serializable?.generateSendable) {
216
+ importManager.registerCustomImport('./Sendable' + dependency.typeName, 'Sendable' + dependency.typeName);
217
+ }
218
+ else {
219
+ importManager.registerCustomTypeImport(dependency.source.sourceFilePath, dependency.typeName);
220
+ }
221
+ }
222
+ processBaseClassImport(result, importManager) {
194
223
  const baseClass = result.inheritance.baseClassAnalysis;
195
- if (baseClass) {
196
- importManager.registerCustomImport('./Sendable' + baseClass.className, 'Sendable' + baseClass.className);
224
+ if (!baseClass) {
225
+ return;
197
226
  }
227
+ importManager.registerCustomImport('./Sendable' + baseClass.className, 'Sendable' + baseClass.className);
228
+ }
229
+ processCollectionsImport(result, importManager) {
198
230
  const needsCollections = this.needsCollectionsImport(result);
199
- if (needsCollections) {
200
- importManager.registerArkTSImports(['collections']);
201
- }
202
- result.originalClass?.getSourceFile().getImportDeclarations().forEach(importDecl => {
203
- const specifier = importDecl.getModuleSpecifierValue();
204
- const names = importDecl.getNamedImports().map((names) => names.getName());
205
- const defaultImport = importDecl.getDefaultImport();
206
- const originalDir = SerializationPathUtil_1.default.dirname(result.sourceFilePath);
207
- const importOriginAbs = SerializationPathUtil_1.default.pathResolve(originalDir, specifier);
208
- if (SerializationPathUtil_1.default.exist(importOriginAbs + '.ets')) {
209
- const importOriginAbsWithExt = importOriginAbs + '.ets';
210
- names.forEach((name) => {
211
- importManager.registerCustomTypeImport(importOriginAbsWithExt, name);
212
- });
213
- if (defaultImport) {
214
- importManager.registerDefaultImport(importOriginAbsWithExt, defaultImport.getText());
215
- }
216
- }
217
- else {
218
- names.forEach((name) => {
219
- importManager.registerCustomImport(specifier, name);
220
- });
221
- if (defaultImport) {
222
- importManager.registerDefaultImport(specifier, defaultImport.getText());
223
- }
224
- }
231
+ if (!needsCollections) {
232
+ return;
233
+ }
234
+ importManager.registerArkTSImports(['collections']);
235
+ }
236
+ copySourceFileImports(result, importManager) {
237
+ const importDeclarations = result.originalClass?.getSourceFile().getImportDeclarations();
238
+ if (!importDeclarations) {
239
+ return;
240
+ }
241
+ importDeclarations.forEach((importDecl) => {
242
+ this.processSingleImportDeclaration(importDecl, result, importManager);
225
243
  });
226
244
  }
245
+ processSingleImportDeclaration(importDecl, result, importManager) {
246
+ const specifier = importDecl.getModuleSpecifierValue();
247
+ const names = importDecl.getNamedImports().map((n) => n.getName());
248
+ const defaultImport = importDecl.getDefaultImport();
249
+ const originalDir = SerializationPathUtil_1.default.dirname(result.sourceFilePath);
250
+ const importOriginAbs = SerializationPathUtil_1.default.pathResolve(originalDir, specifier);
251
+ if (SerializationPathUtil_1.default.exist(importOriginAbs + '.ets')) {
252
+ this.registerModuleImports(importOriginAbs + '.ets', names, defaultImport, importManager);
253
+ }
254
+ else {
255
+ this.registerPackageImports(specifier, names, defaultImport, importManager);
256
+ }
257
+ }
258
+ registerModuleImports(absPath, names, defaultImport, importManager) {
259
+ names.forEach((name) => {
260
+ importManager.registerCustomTypeImport(absPath, name);
261
+ });
262
+ if (defaultImport) {
263
+ importManager.registerDefaultImport(absPath, defaultImport.getText());
264
+ }
265
+ }
266
+ registerPackageImports(specifier, names, defaultImport, importManager) {
267
+ names.forEach((name) => {
268
+ importManager.registerCustomImport(specifier, name);
269
+ });
270
+ if (defaultImport) {
271
+ importManager.registerDefaultImport(specifier, defaultImport.getText());
272
+ }
273
+ }
227
274
  convertConstructorParameterTypes(classDecl, result) {
228
275
  const constructors = classDecl.getConstructors();
229
276
  constructors.forEach((constructor) => {
230
- const parameters = constructor.getParameters();
231
- parameters.forEach((parameter) => {
232
- const paramName = parameter.getName();
233
- const propertyAnalysis = result.properties.find((p) => p.name === paramName);
234
- if (!propertyAnalysis) {
235
- __1.Logger.warn(`未找到构造函数参数 ${paramName} 的分析信息`);
236
- return;
237
- }
238
- const sendableType = this.convertToSendableType(propertyAnalysis.type);
239
- if (sendableType !== propertyAnalysis.type.sourceText) {
240
- parameter.setType(sendableType);
241
- __1.Logger.debug(`构造函数参数 ${paramName} 类型从 ${propertyAnalysis.type.sourceText} 转换为 ${sendableType}`);
242
- }
243
- });
277
+ this.convertSingleConstructorParameters(constructor, result);
278
+ });
279
+ }
280
+ convertSingleConstructorParameters(constructor, result) {
281
+ const parameters = constructor.getParameters();
282
+ parameters.forEach((parameter) => {
283
+ this.convertSingleParameter(parameter, result);
244
284
  });
245
285
  }
286
+ convertSingleParameter(parameter, result) {
287
+ const paramName = parameter.getName();
288
+ const propertyAnalysis = result.properties.find((p) => p.name === paramName);
289
+ if (!propertyAnalysis) {
290
+ __1.Logger.warn(`未找到构造函数参数 ${paramName} 的分析信息`);
291
+ return;
292
+ }
293
+ const sendableType = this.convertToSendableType(propertyAnalysis.type);
294
+ if (sendableType !== propertyAnalysis.type.sourceText) {
295
+ parameter.setType(sendableType);
296
+ __1.Logger.debug(`构造函数参数 ${paramName} 类型从 ${propertyAnalysis.type.sourceText} 转换为 ${sendableType}`);
297
+ }
298
+ }
246
299
  isObjectType(typeName) {
247
300
  const primitiveTypes = ['string', 'number', 'boolean', 'bigint', 'null', 'undefined'];
248
301
  if (primitiveTypes.includes(typeName)) {
@@ -266,33 +319,45 @@ class SendableClassGenerator {
266
319
  });
267
320
  }
268
321
  convertInitializerToSendable(initializerText) {
269
- let convertedText = initializerText;
270
- if (convertedText === '[]') {
271
- convertedText = 'new collections.Array()';
272
- }
273
- else if (convertedText.startsWith('[') && convertedText.endsWith(']')) {
274
- const arrayContent = convertedText.slice(1, -1);
275
- if (arrayContent.trim()) {
276
- convertedText = `new collections.Array(${arrayContent})`;
277
- }
278
- else {
279
- convertedText = 'new collections.Array()';
280
- }
322
+ let convertedText = this.convertArrayLiteralToSendable(initializerText);
323
+ convertedText = this.replaceCollectionTypes(convertedText);
324
+ convertedText = this.replaceObjectConstructors(convertedText);
325
+ __1.Logger.debug(`初始化器转换: ${initializerText} -> ${convertedText}`);
326
+ return convertedText;
327
+ }
328
+ convertArrayLiteralToSendable(text) {
329
+ if (text === '[]') {
330
+ return 'new collections.Array()';
331
+ }
332
+ if (!text.startsWith('[') || !text.endsWith(']')) {
333
+ return text;
334
+ }
335
+ const arrayContent = text.slice(1, -1);
336
+ if (arrayContent.trim()) {
337
+ return `new collections.Array(${arrayContent})`;
281
338
  }
339
+ return 'new collections.Array()';
340
+ }
341
+ replaceObjectConstructors(text) {
342
+ const objectConstructorPattern = /new\s+(\w+)\s*\(/g;
343
+ return text.replace(objectConstructorPattern, (match, className) => {
344
+ return this.replaceObjectConstructorMatch(match, className);
345
+ });
346
+ }
347
+ replaceObjectConstructorMatch(match, className) {
348
+ if (className === 'collections' || match.includes('collections.')) {
349
+ return match;
350
+ }
351
+ if (this.isObjectType(className)) {
352
+ return match.replace(className, `Sendable${className}`);
353
+ }
354
+ return match;
355
+ }
356
+ replaceCollectionTypes(text) {
357
+ let convertedText = text;
282
358
  convertedText = convertedText.replace(/new\s+Set\s*\(/g, 'new collections.Set(');
283
359
  convertedText = convertedText.replace(/new\s+Map\s*\(/g, 'new collections.Map(');
284
360
  convertedText = convertedText.replace(/new\s+Array\s*\(/g, 'new collections.Array(');
285
- const objectConstructorPattern = /new\s+(\w+)\s*\(/g;
286
- convertedText = convertedText.replace(objectConstructorPattern, (match, className) => {
287
- if (className === 'collections' || match.includes('collections.')) {
288
- return match;
289
- }
290
- if (this.isObjectType(className)) {
291
- return match.replace(className, `Sendable${className}`);
292
- }
293
- return match;
294
- });
295
- __1.Logger.debug(`初始化器转换: ${initializerText} -> ${convertedText}`);
296
361
  return convertedText;
297
362
  }
298
363
  convertToSendableType(structure) {
@@ -20,7 +20,7 @@ class SerializerGenerator {
20
20
  generate(sourceFile, result, context) {
21
21
  if (result.decorators?.serializable?.with) {
22
22
  sourceFile.addStatements(this.generateBuiltinSerializerRegistrationForSupplementary(context, result));
23
- return this.generateCustomSerializerRegistration(sourceFile, result);
23
+ return this.generateCustomSerializerRegistration(result);
24
24
  }
25
25
  this.registerImports(result);
26
26
  const templateContext = {
@@ -49,7 +49,8 @@ class SerializerGenerator {
49
49
  const requiredBuiltinSerializers = this.getAllRequiredSerializers(result.properties);
50
50
  this.importManager.registerCoreImports([
51
51
  'Serializer', 'SerialDescriptor', 'buildClassSerialDescriptor',
52
- 'Encoder', 'Decoder', 'registerAutoGeneratedSerializerEntry', 'registerAutoGeneratedSerializerEntryProviderForSupplementary',
52
+ 'Encoder', 'Decoder', 'registerAutoGeneratedSerializerEntry', 'ObjectUtils',
53
+ 'registerAutoGeneratedSerializerEntryProviderForSupplementary', 'lazy',
53
54
  ...requiredBuiltinSerializers
54
55
  ]);
55
56
  this.registerDecoratorsImports(result);
@@ -120,15 +121,15 @@ class SerializerGenerator {
120
121
  this.importManager.registerCoreImports(['WithEntryContextualSerializer']);
121
122
  }
122
123
  }
123
- this.execPropertyImports(property.type.dependencies);
124
+ this.execPropertyImports(property.type.dependencies, !!property.decorators?.with);
124
125
  }
125
126
  }
126
- execPropertyImports(dependencies) {
127
+ execPropertyImports(dependencies, hasWithParam) {
127
128
  dependencies.forEach((dependency) => {
128
- this.processDependency(dependency);
129
+ this.processDependency(dependency, hasWithParam);
129
130
  });
130
131
  }
131
- processDependency(dependency) {
132
+ processDependency(dependency, hasWithParam) {
132
133
  const source = dependency.source;
133
134
  if (source.type !== 'imported' && source.type !== 'local') {
134
135
  return;
@@ -138,14 +139,14 @@ class SerializerGenerator {
138
139
  }
139
140
  switch (dependency.typeKind) {
140
141
  case __1.TypeKind.CLASS:
141
- this.processClassDependency(dependency, source);
142
+ this.processClassDependency(dependency, source, hasWithParam);
142
143
  break;
143
144
  case __1.TypeKind.INTERFACE:
144
- this.processInterfaceDependency(dependency);
145
+ this.processInterfaceDependency(dependency, hasWithParam);
145
146
  break;
146
147
  }
147
148
  }
148
- processClassDependency(dependency, source) {
149
+ processClassDependency(dependency, source, hasWithParam) {
149
150
  const classDetails = dependency.details;
150
151
  const tempClassAnalysis = ClassAnalyzer_1.ClassAnalyzer.analyzeClass(classDetails.classDecl);
151
152
  if (!tempClassAnalysis.decorators.serializable) {
@@ -157,6 +158,9 @@ class SerializerGenerator {
157
158
  this.handleSerializableClass(dependency, source, serializerName);
158
159
  }
159
160
  else {
161
+ if (hasWithParam) {
162
+ return;
163
+ }
160
164
  this.importManager.registerTempSerializerImport(`${dependency.typeName}${serializerName}`);
161
165
  }
162
166
  }
@@ -165,7 +169,10 @@ class SerializerGenerator {
165
169
  this.importManager.registerCustomTypeImport(source.sourceFilePath, `${dependency.typeName}${serializerName}`);
166
170
  }
167
171
  }
168
- processInterfaceDependency(dependency) {
172
+ processInterfaceDependency(dependency, hasWithParam) {
173
+ if (hasWithParam) {
174
+ return;
175
+ }
169
176
  const interfaceDetails = dependency.details;
170
177
  const tempClassAnalysis = ClassAnalyzer_1.ClassAnalyzer.analyzeInterface(interfaceDetails.interfaceDecl);
171
178
  TempSerializerGenerator_1.TempSerializerGenerator.getInstance().generateSerializer(tempClassAnalysis);
@@ -173,19 +180,17 @@ class SerializerGenerator {
173
180
  __1.StringConstants.SERIALIZER;
174
181
  this.importManager.registerTempSerializerImport(`${dependency.typeName}${serializerName}`);
175
182
  }
176
- generateCustomSerializerRegistration(sourceFile, result) {
183
+ generateCustomSerializerRegistration(result) {
177
184
  this.importManager.registerCoreImports(['registerAutoGeneratedSerializerEntry']);
178
185
  const customSerializer = result.decorators.serializable.with;
179
- const registrationCode = `registerAutoGeneratedSerializerEntry(${result.className}, ${customSerializer});`;
180
- return registrationCode;
186
+ return `registerAutoGeneratedSerializerEntry(${result.className}, ${customSerializer});`;
181
187
  }
182
188
  generateBuiltinSerializerRegistrationForSupplementary(context, result) {
183
189
  this.importManager.registerCoreImports(['registerAutoGeneratedSerializerEntryProviderForSupplementary']);
184
190
  const serialNameConstant = this.generateSerialNameConstant(result, context);
185
191
  const customSerializer = result.decorators.serializable.with;
186
- const registrationCode = `const ${result.className}_SERIAL_NAME = '${serialNameConstant}';\n
192
+ return `const ${result.className}_SERIAL_NAME = '${serialNameConstant}';\n
187
193
  registerAutoGeneratedSerializerEntryProviderForSupplementary(${result.className}_SERIAL_NAME, () => [${result.className}, ${customSerializer}]);`;
188
- return registrationCode;
189
194
  }
190
195
  getAllRequiredSerializers(properties) {
191
196
  const requiredSerializers = new Set();
@@ -111,7 +111,8 @@ class TempSerializerGenerator {
111
111
  const indexSourceFile = TsMorphUtil_1.TsMorphUtil.getProject().createSourceFile(indexFilePath, '', { overwrite: true });
112
112
  const classNameMap = new Map();
113
113
  for (const [_, fileInfo] of this.serializerFiles) {
114
- const serializerName = `${fileInfo.className}${fileInfo.isGeneric ? __1.StringConstants.SERIALIZER_FACTORY : __1.StringConstants.SERIALIZER}`;
114
+ const serializerName = `${fileInfo.className}${fileInfo.isGeneric ? __1.StringConstants.SERIALIZER_FACTORY :
115
+ __1.StringConstants.SERIALIZER}`;
115
116
  if (!classNameMap.has(serializerName)) {
116
117
  classNameMap.set(serializerName, []);
117
118
  }
@@ -12,10 +12,10 @@ export declare class ImportManager {
12
12
  private isModularPath;
13
13
  private isRelativePath;
14
14
  private removeImportFromModule;
15
- getImportDeclarations(): {
15
+ getImportDeclarations(): Array<{
16
16
  specifier: string;
17
17
  names: string[];
18
- }[];
18
+ }>;
19
19
  getDefaultImport(): Array<{
20
20
  specifier: string;
21
21
  name: string;
@@ -14,6 +14,8 @@ export declare class HandlebarsTemplateEngine {
14
14
  registerHelper(name: string, helper: Handlebars.HelperDelegate): void;
15
15
  loadTemplateFromString(template: string): HandlebarsTemplateDelegate;
16
16
  private registerBuiltinHelpers;
17
+ private isPrimitiveType;
18
+ private toUpperCase;
17
19
  private registerComparisonHelpers;
18
20
  private registerTypeCheckHelpers;
19
21
  private hasNonSerializableClassDecorator;
@@ -93,13 +93,21 @@ class HandlebarsTemplateEngine {
93
93
  this.registerConstructorHelpers();
94
94
  this.registerLogicHelpers();
95
95
  }
96
+ isPrimitiveType(kind) {
97
+ return ['string', 'number', 'boolean', 'bigint', 'undefined', 'null'].includes(kind);
98
+ }
99
+ toUpperCase(name) {
100
+ if (!name) {
101
+ return '';
102
+ }
103
+ return name.charAt(0).toUpperCase() + name.substring(1);
104
+ }
96
105
  registerComparisonHelpers() {
97
106
  this.registerHelper('eq', (arg1, arg2) => {
98
107
  return (arg1 === arg2);
99
108
  });
100
109
  this.registerHelper('eqPrimitiveType', (kind) => {
101
- const primitives = ['string', 'number', 'boolean', 'bigint', 'undefined', 'null'];
102
- return primitives.includes(kind);
110
+ return this.isPrimitiveType(kind);
103
111
  });
104
112
  this.registerHelper('eqEmptyType', (kind) => {
105
113
  return ['null', 'undefined'].includes(kind);
@@ -182,12 +190,26 @@ class HandlebarsTemplateEngine {
182
190
  this.registerHelper('toLowerCase', (str) => {
183
191
  return str.toLowerCase();
184
192
  });
193
+ this.registerHelper('toUpperCase', (str) => {
194
+ return this.toUpperCase(str);
195
+ });
196
+ this.registerHelper('getSerializer', (analysis) => {
197
+ if (this.isPrimitiveType(analysis.type.kind)) {
198
+ return `${analysis.name}Serializer`;
199
+ }
200
+ else {
201
+ return `get${this.toUpperCase(analysis.name)}Serializer()`;
202
+ }
203
+ });
185
204
  this.registerHelper('genericParametersString', (parameters) => {
186
205
  return parameters.join(', ');
187
206
  });
188
207
  this.registerHelper('genericParametersESObjString', (parameters) => {
189
208
  return parameters.map(() => 'ESObject').join(', ');
190
209
  });
210
+ this.registerHelper('filterGenericProperties', (properties) => {
211
+ return properties.filter(p => p.analysis.type.kind === __1.PropertyKind.GENERIC && !p.analysis.decorators?.isTransient);
212
+ });
191
213
  }
192
214
  registerPropertyAnalysisHelpers() {
193
215
  this.registerHelper('getPropertyIndex', (property, properties) => {
@@ -8,7 +8,8 @@ class DeepCopyUtil {
8
8
  defaultValue: original.defaultValue,
9
9
  decorators: this.copyPropertyDecorators(original.decorators),
10
10
  isMust: original.isMust,
11
- type: this.copyTypeStructure(original.type)
11
+ type: this.copyTypeStructure(original.type),
12
+ visibility: original.visibility
12
13
  };
13
14
  }
14
15
  static copyPropertyDecorators(original) {
@@ -19,6 +20,7 @@ class DeepCopyUtil {
19
20
  serialName: original.serialName,
20
21
  isRequired: original.isRequired,
21
22
  isTransient: original.isTransient,
23
+ isPlainValue: original.isPlainValue,
22
24
  with: original.with
23
25
  };
24
26
  }
@@ -126,7 +128,7 @@ class DeepCopyUtil {
126
128
  if (typeof obj === 'object') {
127
129
  const copy = {};
128
130
  for (const key in obj) {
129
- if (obj.hasOwnProperty(key)) {
131
+ if (Object.prototype.hasOwnProperty.call(obj, key)) {
130
132
  copy[key] = this.deepCopy(obj[key]);
131
133
  }
132
134
  }
@@ -5,5 +5,6 @@ export declare class GenericTypeSubstitutionUtil {
5
5
  static substitutePropertyType(property: PropertyAnalysis, genericMapping: Map<string, TypeNode>, currentClassGenericParams?: string[]): PropertyAnalysis;
6
6
  private static substituteTypeStructure;
7
7
  private static constructTypeStructureFromTypeName;
8
+ private static regenerateSourceText;
8
9
  private static collectDependenciesFromChildren;
9
10
  }