nestjs-ddd-cli 3.2.1 ā 3.2.2
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/dist/commands/generate-all.js +198 -162
- package/dist/commands/generate-all.js.map +1 -1
- package/dist/commands/generate-entity.js +37 -33
- package/dist/commands/generate-entity.js.map +1 -1
- package/dist/commands/generate-module.js +37 -29
- package/dist/commands/generate-module.js.map +1 -1
- package/dist/commands/recipe.js +59 -12
- package/dist/commands/recipe.js.map +1 -1
- package/dist/commands/recipes/index.d.ts +1 -0
- package/dist/commands/recipes/index.js +1 -0
- package/dist/commands/recipes/index.js.map +1 -1
- package/dist/commands/recipes/joi-env.recipe.d.ts +1 -0
- package/dist/commands/recipes/joi-env.recipe.js +301 -0
- package/dist/commands/recipes/joi-env.recipe.js.map +1 -0
- package/dist/index.js +6 -3
- package/dist/index.js.map +1 -1
- package/dist/templates/ai-context/CLAUDE.md.hbs +15 -0
- package/dist/templates/ai-context/conventions.md.hbs +7 -0
- package/dist/templates/mapper/mapper.hbs +1 -1
- package/dist/templates/repository/repository.hbs +1 -1
- package/dist/templates/test/repository.spec.hbs +1 -1
- package/dist/templates/test/usecase.spec.hbs +1 -1
- package/dist/templates/usecase/create-usecase.hbs +1 -1
- package/dist/templates/usecase/update-usecase.hbs +1 -1
- package/dist/utils/dependency.utils.d.ts +2 -0
- package/dist/utils/dependency.utils.js +44 -3
- package/dist/utils/dependency.utils.js.map +1 -1
- package/dist/utils/field.utils.js +32 -20
- package/dist/utils/field.utils.js.map +1 -1
- package/dist/utils/file.utils.d.ts +16 -2
- package/dist/utils/file.utils.js +113 -12
- package/dist/utils/file.utils.js.map +1 -1
- package/dist/utils/template-engine.utils.js +83 -68
- package/dist/utils/template-engine.utils.js.map +1 -1
- package/package.json +10 -8
|
@@ -47,6 +47,11 @@ const dependency_utils_1 = require("../utils/dependency.utils");
|
|
|
47
47
|
async function generateAll(entityName, options) {
|
|
48
48
|
console.log(chalk_1.default.blue(`\nš Generating complete scaffolding for: ${entityName}`));
|
|
49
49
|
const orm = options.orm || 'typeorm';
|
|
50
|
+
const dryRun = !!options.dryRun;
|
|
51
|
+
if (dryRun) {
|
|
52
|
+
(0, file_utils_1.resetDryRunFiles)();
|
|
53
|
+
console.log(chalk_1.default.yellow(' Dry run: no files, directories, or dependencies will be written.'));
|
|
54
|
+
}
|
|
50
55
|
// Check if we need to install dependencies
|
|
51
56
|
const requiredDeps = ['@nestjs/cqrs', 'class-validator', 'class-transformer', '@nestjs/swagger'];
|
|
52
57
|
if (orm === 'prisma') {
|
|
@@ -55,9 +60,12 @@ async function generateAll(entityName, options) {
|
|
|
55
60
|
else {
|
|
56
61
|
requiredDeps.push('typeorm', '@nestjs/typeorm');
|
|
57
62
|
}
|
|
58
|
-
if (options.installDeps) {
|
|
63
|
+
if (options.installDeps && !dryRun) {
|
|
59
64
|
await (0, dependency_utils_1.installDependencies)(options.path || process.cwd(), requiredDeps);
|
|
60
65
|
}
|
|
66
|
+
else if (options.installDeps && dryRun) {
|
|
67
|
+
console.log(chalk_1.default.yellow(` Dry run: would install dependencies: ${requiredDeps.join(', ')}`));
|
|
68
|
+
}
|
|
61
69
|
const moduleName = options.module || entityName;
|
|
62
70
|
const basePath = options.path || process.cwd();
|
|
63
71
|
const modulePath = (0, file_utils_1.getModulePath)(basePath, moduleName);
|
|
@@ -66,62 +74,73 @@ async function generateAll(entityName, options) {
|
|
|
66
74
|
const moduleFilePath = path.join(modulePath, `${(0, naming_utils_1.toKebabCase)(moduleName)}.module.ts`);
|
|
67
75
|
if (!(await (0, file_utils_1.fileExists)(moduleFilePath))) {
|
|
68
76
|
console.log(chalk_1.default.yellow(` Module ${moduleName} doesn't exist. Creating...`));
|
|
69
|
-
await (0, generate_module_1.generateModule)(moduleName, options);
|
|
77
|
+
await (0, generate_module_1.generateModule)(moduleName, { ...options, dryRun });
|
|
70
78
|
}
|
|
71
79
|
// Prepare template data with fields
|
|
72
80
|
const templateData = (0, file_utils_1.prepareTemplateData)(entityName, moduleName, fieldsString);
|
|
73
81
|
// Generate entity with all related files
|
|
74
|
-
await (0, generate_entity_1.generateEntity)(entityName, {
|
|
82
|
+
await (0, generate_entity_1.generateEntity)(entityName, {
|
|
83
|
+
...options,
|
|
84
|
+
module: moduleName,
|
|
85
|
+
fields: fieldsString,
|
|
86
|
+
orm,
|
|
87
|
+
dryRun,
|
|
88
|
+
_fromGenerateAll: true,
|
|
89
|
+
});
|
|
75
90
|
// Generate PrismaService if using Prisma
|
|
76
91
|
if (orm === 'prisma') {
|
|
77
|
-
await generatePrismaService(basePath);
|
|
92
|
+
await generatePrismaService(basePath, dryRun);
|
|
78
93
|
}
|
|
79
94
|
// Generate CRUD commands
|
|
80
95
|
console.log(chalk_1.default.cyan(' Generating commands...'));
|
|
81
|
-
await generateCommand('create', entityName, modulePath, templateData);
|
|
82
|
-
await generateCommand('update', entityName, modulePath, templateData);
|
|
83
|
-
await generateCommand('delete', entityName, modulePath, templateData);
|
|
96
|
+
await generateCommand('create', entityName, modulePath, templateData, dryRun);
|
|
97
|
+
await generateCommand('update', entityName, modulePath, templateData, dryRun);
|
|
98
|
+
await generateCommand('delete', entityName, modulePath, templateData, dryRun);
|
|
84
99
|
// Generate use cases
|
|
85
100
|
console.log(chalk_1.default.cyan(' Generating use cases...'));
|
|
86
|
-
await generateUseCase('create', entityName, modulePath, templateData);
|
|
87
|
-
await generateUseCase('update', entityName, modulePath, templateData);
|
|
88
|
-
await generateUseCase('delete', entityName, modulePath, templateData);
|
|
101
|
+
await generateUseCase('create', entityName, modulePath, templateData, dryRun);
|
|
102
|
+
await generateUseCase('update', entityName, modulePath, templateData, dryRun);
|
|
103
|
+
await generateUseCase('delete', entityName, modulePath, templateData, dryRun);
|
|
89
104
|
// Generate queries
|
|
90
105
|
console.log(chalk_1.default.cyan(' Generating queries...'));
|
|
91
|
-
await generateQueryHandler('get-by-id', entityName, modulePath, templateData);
|
|
92
|
-
await generateQueryHandler('get-all', entityName, modulePath, templateData);
|
|
106
|
+
await generateQueryHandler('get-by-id', entityName, modulePath, templateData, dryRun);
|
|
107
|
+
await generateQueryHandler('get-all', entityName, modulePath, templateData, dryRun);
|
|
93
108
|
// Generate DTOs
|
|
94
109
|
console.log(chalk_1.default.cyan(' Generating DTOs...'));
|
|
95
|
-
await generateDto('create', entityName, modulePath, templateData);
|
|
96
|
-
await generateDto('update', entityName, modulePath, templateData);
|
|
97
|
-
await generateDto('response', entityName, modulePath, templateData);
|
|
98
|
-
await generatePaginationDtos(modulePath);
|
|
110
|
+
await generateDto('create', entityName, modulePath, templateData, dryRun);
|
|
111
|
+
await generateDto('update', entityName, modulePath, templateData, dryRun);
|
|
112
|
+
await generateDto('response', entityName, modulePath, templateData, dryRun);
|
|
113
|
+
await generatePaginationDtos(modulePath, dryRun);
|
|
99
114
|
// Generate controller
|
|
100
115
|
console.log(chalk_1.default.cyan(' Generating controller...'));
|
|
101
116
|
const controllerTemplatePath = path.join(__dirname, '../templates/controller/controller.hbs');
|
|
102
117
|
const controllerOutputPath = path.join(modulePath, 'application/controllers', `${(0, naming_utils_1.toKebabCase)(entityName)}.controller.ts`);
|
|
103
|
-
await (0, file_utils_1.generateFromTemplate)(controllerTemplatePath, controllerOutputPath, templateData);
|
|
118
|
+
await (0, file_utils_1.generateFromTemplate)(controllerTemplatePath, controllerOutputPath, templateData, dryRun);
|
|
104
119
|
// Generate migration file or Prisma schema snippet
|
|
105
120
|
if (orm === 'prisma') {
|
|
106
121
|
console.log(chalk_1.default.cyan(' Generating Prisma schema snippet...'));
|
|
107
|
-
await generatePrismaSchemaSnippet(entityName, basePath, templateData);
|
|
122
|
+
await generatePrismaSchemaSnippet(entityName, basePath, templateData, dryRun);
|
|
108
123
|
}
|
|
109
124
|
else {
|
|
110
125
|
console.log(chalk_1.default.cyan(' Generating migration...'));
|
|
111
|
-
await generateMigration(entityName, basePath, templateData);
|
|
126
|
+
await generateMigration(entityName, basePath, templateData, dryRun);
|
|
112
127
|
}
|
|
113
128
|
// Generate barrel exports
|
|
114
129
|
console.log(chalk_1.default.cyan(' Generating barrel exports...'));
|
|
115
|
-
await generateBarrelExports(entityName, modulePath, orm);
|
|
130
|
+
await generateBarrelExports(entityName, modulePath, orm, dryRun);
|
|
116
131
|
// Generate tests if requested
|
|
117
132
|
if (options.withTests) {
|
|
118
133
|
console.log(chalk_1.default.cyan(' Generating tests...'));
|
|
119
|
-
await generateTests(entityName, modulePath, templateData);
|
|
134
|
+
await generateTests(entityName, modulePath, templateData, dryRun);
|
|
120
135
|
}
|
|
121
136
|
// Generate GraphQL files if requested
|
|
122
137
|
if (options.withGraphql) {
|
|
123
138
|
console.log(chalk_1.default.cyan(' Generating GraphQL resolvers and types...'));
|
|
124
|
-
await generateGraphQL(entityName, modulePath, templateData);
|
|
139
|
+
await generateGraphQL(entityName, modulePath, templateData, dryRun);
|
|
140
|
+
}
|
|
141
|
+
if (dryRun) {
|
|
142
|
+
printDryRunSummary(basePath);
|
|
143
|
+
return;
|
|
125
144
|
}
|
|
126
145
|
console.log(chalk_1.default.green(`\nā
Complete scaffolding generated successfully!`));
|
|
127
146
|
console.log(chalk_1.default.cyan(`\nš Generated structure:`));
|
|
@@ -139,7 +158,7 @@ async function generateAll(entityName, options) {
|
|
|
139
158
|
console.log(` ${chalk_1.default.white('GraphQL:')} Resolver, Types, Inputs`);
|
|
140
159
|
}
|
|
141
160
|
if (templateData.hasFields) {
|
|
142
|
-
console.log(chalk_1.default.green(`\n⨠Fields generated: ${templateData.fields?.map(f => f.name).join(', ')}`));
|
|
161
|
+
console.log(chalk_1.default.green(`\n⨠Fields generated: ${templateData.fields?.map((f) => f.name).join(', ')}`));
|
|
143
162
|
}
|
|
144
163
|
console.log(chalk_1.default.yellow(`\nš Next steps:`));
|
|
145
164
|
console.log(` 1. ${templateData.hasFields ? 'Review' : 'Add properties to'} your entity and DTOs`);
|
|
@@ -152,24 +171,39 @@ async function generateAll(entityName, options) {
|
|
|
152
171
|
console.log(` 2. Run the migration: ${chalk_1.default.cyan('npm run migration:run')}`);
|
|
153
172
|
}
|
|
154
173
|
console.log(` ${orm === 'prisma' ? '5' : '3'}. Import ${(0, naming_utils_1.toPascalCase)(moduleName)}Module in your app.module.ts`);
|
|
155
|
-
console.log(` ${orm === 'prisma' ? '6' : '4'}. Start your server and test the API at ${chalk_1.default.cyan(`/${
|
|
174
|
+
console.log(` ${orm === 'prisma' ? '6' : '4'}. Start your server and test the API at ${chalk_1.default.cyan(`/${templateData.entityNamePluralKebab}`)}`);
|
|
156
175
|
}
|
|
157
|
-
|
|
176
|
+
function printDryRunSummary(basePath) {
|
|
177
|
+
const changes = (0, file_utils_1.getDryRunFiles)();
|
|
178
|
+
console.log(chalk_1.default.cyan(`\nš§Ŗ Dry run complete. Planned file changes (${changes.length}):`));
|
|
179
|
+
if (!changes.length) {
|
|
180
|
+
console.log(chalk_1.default.gray(' No file changes planned.'));
|
|
181
|
+
return;
|
|
182
|
+
}
|
|
183
|
+
for (const change of changes) {
|
|
184
|
+
const relativePath = path.relative(basePath, change.filePath);
|
|
185
|
+
console.log(` ${change.action.padEnd(6)} ${relativePath}`);
|
|
186
|
+
}
|
|
187
|
+
}
|
|
188
|
+
async function generateCommand(action, entityName, modulePath, templateData, dryRun = false) {
|
|
158
189
|
const templatePath = path.join(__dirname, `../templates/command/${action}-command.hbs`);
|
|
159
190
|
const outputPath = path.join(modulePath, 'application/commands', `${action}-${(0, naming_utils_1.toKebabCase)(entityName)}.command.ts`);
|
|
160
|
-
await (0, file_utils_1.generateFromTemplate)(templatePath, outputPath, templateData);
|
|
191
|
+
await (0, file_utils_1.generateFromTemplate)(templatePath, outputPath, templateData, dryRun);
|
|
161
192
|
}
|
|
162
|
-
async function generateUseCase(action, entityName, modulePath, templateData) {
|
|
193
|
+
async function generateUseCase(action, entityName, modulePath, templateData, dryRun = false) {
|
|
163
194
|
const templatePath = path.join(__dirname, `../templates/usecase/${action}-usecase.hbs`);
|
|
164
195
|
const outputPath = path.join(modulePath, 'application/domain/usecases', `${action}-${(0, naming_utils_1.toKebabCase)(entityName)}.use-case.ts`);
|
|
165
|
-
await (0, file_utils_1.generateFromTemplate)(templatePath, outputPath, templateData);
|
|
196
|
+
await (0, file_utils_1.generateFromTemplate)(templatePath, outputPath, templateData, dryRun);
|
|
166
197
|
}
|
|
167
|
-
async function generateQueryHandler(type, entityName, modulePath, templateData) {
|
|
198
|
+
async function generateQueryHandler(type, entityName, modulePath, templateData, dryRun = false) {
|
|
199
|
+
const fileName = type === 'get-all'
|
|
200
|
+
? `get-all-${templateData.entityNamePluralKebab}.query.ts`
|
|
201
|
+
: `get-${(0, naming_utils_1.toKebabCase)(entityName)}-by-id.query.ts`;
|
|
168
202
|
const templatePath = path.join(__dirname, `../templates/query/${type}.query.hbs`);
|
|
169
|
-
const outputPath = path.join(modulePath, 'application/queries',
|
|
170
|
-
await (0, file_utils_1.generateFromTemplate)(templatePath, outputPath, templateData);
|
|
203
|
+
const outputPath = path.join(modulePath, 'application/queries', fileName);
|
|
204
|
+
await (0, file_utils_1.generateFromTemplate)(templatePath, outputPath, templateData, dryRun);
|
|
171
205
|
}
|
|
172
|
-
async function generateDto(type, entityName, modulePath, templateData) {
|
|
206
|
+
async function generateDto(type, entityName, modulePath, templateData, dryRun = false) {
|
|
173
207
|
const templateMap = {
|
|
174
208
|
create: 'create-dto.hbs',
|
|
175
209
|
update: 'update-dto.hbs',
|
|
@@ -187,28 +221,29 @@ async function generateDto(type, entityName, modulePath, templateData) {
|
|
|
187
221
|
};
|
|
188
222
|
const templatePath = path.join(__dirname, `../templates/dto/${templateMap[type]}`);
|
|
189
223
|
const outputPath = path.join(modulePath, `application/dto/${outputDirMap[type]}`, fileNameMap[type]);
|
|
190
|
-
await (0, file_utils_1.generateFromTemplate)(templatePath, outputPath, templateData);
|
|
224
|
+
await (0, file_utils_1.generateFromTemplate)(templatePath, outputPath, templateData, dryRun);
|
|
191
225
|
}
|
|
192
|
-
async function generatePaginationDtos(modulePath) {
|
|
226
|
+
async function generatePaginationDtos(modulePath, dryRun = false) {
|
|
193
227
|
// Generate pagination query DTO
|
|
194
228
|
const paginationQueryTemplatePath = path.join(__dirname, '../templates/dto/pagination-query.dto.hbs');
|
|
195
229
|
const paginationQueryOutputPath = path.join(modulePath, 'application/dto/requests', 'pagination.query.dto.ts');
|
|
196
230
|
if (!(await (0, file_utils_1.fileExists)(paginationQueryOutputPath))) {
|
|
197
|
-
await (0, file_utils_1.generateFromTemplate)(paginationQueryTemplatePath, paginationQueryOutputPath, (0, file_utils_1.prepareTemplateData)('Pagination', 'shared'));
|
|
231
|
+
await (0, file_utils_1.generateFromTemplate)(paginationQueryTemplatePath, paginationQueryOutputPath, (0, file_utils_1.prepareTemplateData)('Pagination', 'shared'), dryRun);
|
|
198
232
|
}
|
|
199
233
|
// Generate paginated response DTO
|
|
200
234
|
const paginatedResponseTemplatePath = path.join(__dirname, '../templates/dto/paginated-response.dto.hbs');
|
|
201
235
|
const paginatedResponseOutputPath = path.join(modulePath, 'application/dto/responses', 'paginated.response.dto.ts');
|
|
202
236
|
if (!(await (0, file_utils_1.fileExists)(paginatedResponseOutputPath))) {
|
|
203
|
-
await (0, file_utils_1.generateFromTemplate)(paginatedResponseTemplatePath, paginatedResponseOutputPath, (0, file_utils_1.prepareTemplateData)('Paginated', 'shared'));
|
|
237
|
+
await (0, file_utils_1.generateFromTemplate)(paginatedResponseTemplatePath, paginatedResponseOutputPath, (0, file_utils_1.prepareTemplateData)('Paginated', 'shared'), dryRun);
|
|
204
238
|
}
|
|
205
239
|
}
|
|
206
|
-
async function generateMigration(entityName, basePath, templateData) {
|
|
240
|
+
async function generateMigration(entityName, basePath, templateData, dryRun = false) {
|
|
207
241
|
const timestamp = Date.now();
|
|
208
242
|
const tableName = templateData.tableName;
|
|
209
243
|
const migrationName = `create_${tableName}_table`;
|
|
210
244
|
const fileName = `${timestamp}-${migrationName}.ts`;
|
|
211
|
-
const fieldsColumns = templateData.migrationColumns ||
|
|
245
|
+
const fieldsColumns = templateData.migrationColumns ||
|
|
246
|
+
` // Add your custom columns here
|
|
212
247
|
// Example:
|
|
213
248
|
// {
|
|
214
249
|
// name: "name",
|
|
@@ -263,162 +298,163 @@ ${fieldsColumns}
|
|
|
263
298
|
}
|
|
264
299
|
`;
|
|
265
300
|
const migrationPath = path.join(basePath, 'src/migrations', fileName);
|
|
266
|
-
await (0, file_utils_1.
|
|
301
|
+
await (0, file_utils_1.writeGeneratedFile)(migrationPath, content, dryRun);
|
|
267
302
|
console.log(chalk_1.default.green(` ā Migration: ${fileName}`));
|
|
268
303
|
}
|
|
269
|
-
async function generateBarrelExports(entityName, modulePath, orm = 'typeorm') {
|
|
304
|
+
async function generateBarrelExports(entityName, modulePath, orm = 'typeorm', dryRun = false) {
|
|
270
305
|
const entityNameKebab = (0, naming_utils_1.toKebabCase)(entityName);
|
|
271
306
|
const entityNamePascal = (0, naming_utils_1.toPascalCase)(entityName);
|
|
307
|
+
const entityNamePluralKebab = (0, naming_utils_1.toKebabCase)((0, naming_utils_1.toPlural)(entityName));
|
|
308
|
+
const entityNamePluralPascal = (0, naming_utils_1.toPlural)((0, naming_utils_1.toPascalCase)(entityName));
|
|
272
309
|
const isPrisma = orm === 'prisma';
|
|
273
310
|
// Commands index
|
|
274
311
|
const commandsIndexPath = path.join(modulePath, 'application/commands/index.ts');
|
|
275
|
-
|
|
276
|
-
|
|
277
|
-
export * from './
|
|
278
|
-
|
|
279
|
-
|
|
280
|
-
|
|
281
|
-
|
|
282
|
-
|
|
283
|
-
|
|
284
|
-
|
|
285
|
-
|
|
286
|
-
|
|
287
|
-
|
|
288
|
-
|
|
289
|
-
|
|
312
|
+
await (0, file_utils_1.updateBarrelFile)(commandsIndexPath, {
|
|
313
|
+
exports: [
|
|
314
|
+
`export * from './create-${entityNameKebab}.command';`,
|
|
315
|
+
`export * from './update-${entityNameKebab}.command';`,
|
|
316
|
+
`export * from './delete-${entityNameKebab}.command';`,
|
|
317
|
+
],
|
|
318
|
+
imports: [
|
|
319
|
+
`import { Create${entityNamePascal}Handler } from './create-${entityNameKebab}.command';`,
|
|
320
|
+
`import { Update${entityNamePascal}Handler } from './update-${entityNameKebab}.command';`,
|
|
321
|
+
`import { Delete${entityNamePascal}Handler } from './delete-${entityNameKebab}.command';`,
|
|
322
|
+
],
|
|
323
|
+
arrayName: 'CommandHandlers',
|
|
324
|
+
arrayItems: [
|
|
325
|
+
`Create${entityNamePascal}Handler`,
|
|
326
|
+
`Update${entityNamePascal}Handler`,
|
|
327
|
+
`Delete${entityNamePascal}Handler`,
|
|
328
|
+
],
|
|
329
|
+
dryRun,
|
|
330
|
+
});
|
|
290
331
|
// Queries index
|
|
291
332
|
const queriesIndexPath = path.join(modulePath, 'application/queries/index.ts');
|
|
292
|
-
|
|
293
|
-
|
|
294
|
-
export * from './get
|
|
295
|
-
|
|
296
|
-
|
|
297
|
-
|
|
298
|
-
|
|
299
|
-
|
|
300
|
-
|
|
301
|
-
|
|
302
|
-
]
|
|
303
|
-
|
|
304
|
-
|
|
333
|
+
await (0, file_utils_1.updateBarrelFile)(queriesIndexPath, {
|
|
334
|
+
exports: [
|
|
335
|
+
`export * from './get-${entityNameKebab}-by-id.query';`,
|
|
336
|
+
`export * from './get-all-${entityNamePluralKebab}.query';`,
|
|
337
|
+
],
|
|
338
|
+
imports: [
|
|
339
|
+
`import { Get${entityNamePascal}ByIdHandler } from './get-${entityNameKebab}-by-id.query';`,
|
|
340
|
+
`import { GetAll${entityNamePluralPascal}Handler } from './get-all-${entityNamePluralKebab}.query';`,
|
|
341
|
+
],
|
|
342
|
+
arrayName: 'Queries',
|
|
343
|
+
arrayItems: [`Get${entityNamePascal}ByIdHandler`, `GetAll${entityNamePluralPascal}Handler`],
|
|
344
|
+
dryRun,
|
|
345
|
+
});
|
|
305
346
|
// Use cases index
|
|
306
347
|
const useCasesIndexPath = path.join(modulePath, 'application/domain/usecases/index.ts');
|
|
307
|
-
|
|
308
|
-
|
|
309
|
-
export * from './
|
|
310
|
-
|
|
311
|
-
|
|
312
|
-
|
|
313
|
-
|
|
314
|
-
|
|
315
|
-
|
|
316
|
-
|
|
317
|
-
|
|
318
|
-
|
|
319
|
-
|
|
320
|
-
|
|
321
|
-
|
|
348
|
+
await (0, file_utils_1.updateBarrelFile)(useCasesIndexPath, {
|
|
349
|
+
exports: [
|
|
350
|
+
`export * from './create-${entityNameKebab}.use-case';`,
|
|
351
|
+
`export * from './update-${entityNameKebab}.use-case';`,
|
|
352
|
+
`export * from './delete-${entityNameKebab}.use-case';`,
|
|
353
|
+
],
|
|
354
|
+
imports: [
|
|
355
|
+
`import { Create${entityNamePascal}UseCase } from './create-${entityNameKebab}.use-case';`,
|
|
356
|
+
`import { Update${entityNamePascal}UseCase } from './update-${entityNameKebab}.use-case';`,
|
|
357
|
+
`import { Delete${entityNamePascal}UseCase } from './delete-${entityNameKebab}.use-case';`,
|
|
358
|
+
],
|
|
359
|
+
arrayName: 'UseCases',
|
|
360
|
+
arrayItems: [
|
|
361
|
+
`Create${entityNamePascal}UseCase`,
|
|
362
|
+
`Update${entityNamePascal}UseCase`,
|
|
363
|
+
`Delete${entityNamePascal}UseCase`,
|
|
364
|
+
],
|
|
365
|
+
dryRun,
|
|
366
|
+
});
|
|
322
367
|
// DTOs index
|
|
323
368
|
const dtosIndexPath = path.join(modulePath, 'application/dto/index.ts');
|
|
324
|
-
|
|
325
|
-
export * from './responses'
|
|
326
|
-
|
|
327
|
-
|
|
369
|
+
await (0, file_utils_1.updateBarrelFile)(dtosIndexPath, {
|
|
370
|
+
exports: [`export * from './requests';`, `export * from './responses';`],
|
|
371
|
+
dryRun,
|
|
372
|
+
});
|
|
328
373
|
// Requests index
|
|
329
374
|
const requestsIndexPath = path.join(modulePath, 'application/dto/requests/index.ts');
|
|
330
|
-
|
|
331
|
-
|
|
332
|
-
export * from './
|
|
333
|
-
|
|
334
|
-
|
|
375
|
+
await (0, file_utils_1.updateBarrelFile)(requestsIndexPath, {
|
|
376
|
+
exports: [
|
|
377
|
+
`export * from './create-${entityNameKebab}.dto';`,
|
|
378
|
+
`export * from './update-${entityNameKebab}.dto';`,
|
|
379
|
+
`export * from './pagination.query.dto';`,
|
|
380
|
+
],
|
|
381
|
+
dryRun,
|
|
382
|
+
});
|
|
335
383
|
// Responses index
|
|
336
384
|
const responsesIndexPath = path.join(modulePath, 'application/dto/responses/index.ts');
|
|
337
|
-
|
|
338
|
-
|
|
339
|
-
|
|
340
|
-
|
|
385
|
+
await (0, file_utils_1.updateBarrelFile)(responsesIndexPath, {
|
|
386
|
+
exports: [
|
|
387
|
+
`export * from './${entityNameKebab}.response.dto';`,
|
|
388
|
+
`export * from './paginated.response.dto';`,
|
|
389
|
+
],
|
|
390
|
+
dryRun,
|
|
391
|
+
});
|
|
341
392
|
// Controllers index
|
|
342
393
|
const controllersIndexPath = path.join(modulePath, 'application/controllers/index.ts');
|
|
343
|
-
|
|
344
|
-
|
|
345
|
-
import { ${entityNamePascal}Controller } from './${entityNameKebab}.controller'
|
|
346
|
-
|
|
347
|
-
|
|
348
|
-
|
|
349
|
-
|
|
394
|
+
await (0, file_utils_1.updateBarrelFile)(controllersIndexPath, {
|
|
395
|
+
exports: [`export * from './${entityNameKebab}.controller';`],
|
|
396
|
+
imports: [`import { ${entityNamePascal}Controller } from './${entityNameKebab}.controller';`],
|
|
397
|
+
arrayName: 'Controllers',
|
|
398
|
+
arrayItems: [`${entityNamePascal}Controller`],
|
|
399
|
+
dryRun,
|
|
400
|
+
});
|
|
350
401
|
// Entities index
|
|
351
402
|
const entitiesIndexPath = path.join(modulePath, 'application/domain/entities/index.ts');
|
|
352
|
-
|
|
353
|
-
|
|
354
|
-
|
|
403
|
+
await (0, file_utils_1.updateBarrelFile)(entitiesIndexPath, {
|
|
404
|
+
exports: [`export * from './${entityNameKebab}.entity';`],
|
|
405
|
+
dryRun,
|
|
406
|
+
});
|
|
355
407
|
// Repositories index
|
|
356
408
|
const repositoriesIndexPath = path.join(modulePath, 'infrastructure/repositories/index.ts');
|
|
357
|
-
|
|
358
|
-
|
|
359
|
-
import { ${entityNamePascal}Repository } from './${entityNameKebab}.repository'
|
|
360
|
-
|
|
361
|
-
|
|
362
|
-
|
|
363
|
-
|
|
409
|
+
await (0, file_utils_1.updateBarrelFile)(repositoriesIndexPath, {
|
|
410
|
+
exports: [`export * from './${entityNameKebab}.repository';`],
|
|
411
|
+
imports: [`import { ${entityNamePascal}Repository } from './${entityNameKebab}.repository';`],
|
|
412
|
+
arrayName: 'Repositories',
|
|
413
|
+
arrayItems: [`${entityNamePascal}Repository`],
|
|
414
|
+
dryRun,
|
|
415
|
+
});
|
|
364
416
|
// Mappers index
|
|
365
417
|
const mappersIndexPath = path.join(modulePath, 'infrastructure/mappers/index.ts');
|
|
366
|
-
|
|
367
|
-
|
|
368
|
-
import { ${entityNamePascal}Mapper } from './${entityNameKebab}.mapper'
|
|
369
|
-
|
|
370
|
-
|
|
371
|
-
|
|
372
|
-
|
|
418
|
+
await (0, file_utils_1.updateBarrelFile)(mappersIndexPath, {
|
|
419
|
+
exports: [`export * from './${entityNameKebab}.mapper';`],
|
|
420
|
+
imports: [`import { ${entityNamePascal}Mapper } from './${entityNameKebab}.mapper';`],
|
|
421
|
+
arrayName: 'Mappers',
|
|
422
|
+
arrayItems: [`${entityNamePascal}Mapper`],
|
|
423
|
+
dryRun,
|
|
424
|
+
});
|
|
373
425
|
// ORM entities index (TypeORM only)
|
|
374
426
|
if (!isPrisma) {
|
|
375
427
|
const ormEntitiesIndexPath = path.join(modulePath, 'infrastructure/orm-entities/index.ts');
|
|
376
|
-
|
|
377
|
-
|
|
378
|
-
import { ${entityNamePascal}OrmEntity } from './${entityNameKebab}.orm-entity'
|
|
379
|
-
|
|
380
|
-
|
|
381
|
-
|
|
382
|
-
|
|
428
|
+
await (0, file_utils_1.updateBarrelFile)(ormEntitiesIndexPath, {
|
|
429
|
+
exports: [`export * from './${entityNameKebab}.orm-entity';`],
|
|
430
|
+
imports: [`import { ${entityNamePascal}OrmEntity } from './${entityNameKebab}.orm-entity';`],
|
|
431
|
+
arrayName: 'OrmEntities',
|
|
432
|
+
arrayItems: [`${entityNamePascal}OrmEntity`],
|
|
433
|
+
dryRun,
|
|
434
|
+
});
|
|
383
435
|
}
|
|
384
|
-
// Services index (empty for now)
|
|
385
|
-
const servicesIndexPath = path.join(modulePath, 'application/domain/services/index.ts');
|
|
386
|
-
const servicesIndexContent = `// Export your domain services here
|
|
387
|
-
// import { YourService } from './your.service';
|
|
388
|
-
// export const Services = [YourService];
|
|
389
|
-
|
|
390
|
-
export const Services: any[] = [];
|
|
391
|
-
`;
|
|
392
|
-
await (0, file_utils_1.writeFile)(servicesIndexPath, servicesIndexContent);
|
|
393
|
-
// Events index (empty for now)
|
|
394
|
-
const eventsIndexPath = path.join(modulePath, 'application/domain/events/index.ts');
|
|
395
|
-
const eventsIndexContent = `// Export your domain events here
|
|
396
|
-
// export * from './your-event.event';
|
|
397
|
-
`;
|
|
398
|
-
await (0, file_utils_1.writeFile)(eventsIndexPath, eventsIndexContent);
|
|
399
436
|
}
|
|
400
|
-
async function generateTests(entityName, modulePath, templateData) {
|
|
437
|
+
async function generateTests(entityName, modulePath, templateData, dryRun = false) {
|
|
401
438
|
const entityNameKebab = (0, naming_utils_1.toKebabCase)(entityName);
|
|
402
439
|
// Repository test
|
|
403
440
|
const repoTestTemplatePath = path.join(__dirname, '../templates/test/repository.spec.hbs');
|
|
404
441
|
const repoTestOutputPath = path.join(modulePath, 'infrastructure/repositories', `${entityNameKebab}.repository.spec.ts`);
|
|
405
|
-
await (0, file_utils_1.generateFromTemplate)(repoTestTemplatePath, repoTestOutputPath, templateData);
|
|
442
|
+
await (0, file_utils_1.generateFromTemplate)(repoTestTemplatePath, repoTestOutputPath, templateData, dryRun);
|
|
406
443
|
console.log(chalk_1.default.green(` ā Repository test`));
|
|
407
444
|
// Use case tests
|
|
408
445
|
const useCaseTestTemplatePath = path.join(__dirname, '../templates/test/usecase.spec.hbs');
|
|
409
446
|
const useCaseTestOutputPath = path.join(modulePath, 'application/domain/usecases', `${entityNameKebab}.use-case.spec.ts`);
|
|
410
|
-
await (0, file_utils_1.generateFromTemplate)(useCaseTestTemplatePath, useCaseTestOutputPath, templateData);
|
|
447
|
+
await (0, file_utils_1.generateFromTemplate)(useCaseTestTemplatePath, useCaseTestOutputPath, templateData, dryRun);
|
|
411
448
|
console.log(chalk_1.default.green(` ā Use case tests`));
|
|
412
449
|
// Controller test
|
|
413
450
|
const controllerTestTemplatePath = path.join(__dirname, '../templates/test/controller.spec.hbs');
|
|
414
451
|
const controllerTestOutputPath = path.join(modulePath, 'application/controllers', `${entityNameKebab}.controller.spec.ts`);
|
|
415
|
-
await (0, file_utils_1.generateFromTemplate)(controllerTestTemplatePath, controllerTestOutputPath, templateData);
|
|
452
|
+
await (0, file_utils_1.generateFromTemplate)(controllerTestTemplatePath, controllerTestOutputPath, templateData, dryRun);
|
|
416
453
|
console.log(chalk_1.default.green(` ā Controller test`));
|
|
417
454
|
}
|
|
418
|
-
async function generateGraphQL(entityName, modulePath, templateData) {
|
|
455
|
+
async function generateGraphQL(entityName, modulePath, templateData, dryRun = false) {
|
|
419
456
|
const entityNameKebab = (0, naming_utils_1.toKebabCase)(entityName);
|
|
420
457
|
const entityNamePascal = (0, naming_utils_1.toPascalCase)(entityName);
|
|
421
|
-
const entityNamePluralKebab = (0, naming_utils_1.toKebabCase)(templateData.entityNamePlural);
|
|
422
458
|
// Create GraphQL directories
|
|
423
459
|
const graphqlPath = path.join(modulePath, 'application/graphql');
|
|
424
460
|
const typesPath = path.join(graphqlPath, 'types');
|
|
@@ -427,35 +463,35 @@ async function generateGraphQL(entityName, modulePath, templateData) {
|
|
|
427
463
|
// Generate resolver
|
|
428
464
|
const resolverTemplatePath = path.join(__dirname, '../templates/resolver/resolver.hbs');
|
|
429
465
|
const resolverOutputPath = path.join(graphqlPath, `${entityNameKebab}.resolver.ts`);
|
|
430
|
-
await (0, file_utils_1.generateFromTemplate)(resolverTemplatePath, resolverOutputPath, templateData);
|
|
466
|
+
await (0, file_utils_1.generateFromTemplate)(resolverTemplatePath, resolverOutputPath, templateData, dryRun);
|
|
431
467
|
console.log(chalk_1.default.green(` ā Resolver`));
|
|
432
468
|
// Generate GraphQL type
|
|
433
469
|
const typeTemplatePath = path.join(__dirname, '../templates/resolver/graphql-type.hbs');
|
|
434
470
|
const typeOutputPath = path.join(typesPath, `${entityNameKebab}.type.ts`);
|
|
435
|
-
await (0, file_utils_1.generateFromTemplate)(typeTemplatePath, typeOutputPath, templateData);
|
|
471
|
+
await (0, file_utils_1.generateFromTemplate)(typeTemplatePath, typeOutputPath, templateData, dryRun);
|
|
436
472
|
console.log(chalk_1.default.green(` ā GraphQL Type`));
|
|
437
473
|
// Generate GraphQL inputs
|
|
438
474
|
const inputTemplatePath = path.join(__dirname, '../templates/resolver/graphql-input.hbs');
|
|
439
475
|
const inputOutputPath = path.join(inputsPath, `${entityNameKebab}.input.ts`);
|
|
440
|
-
await (0, file_utils_1.generateFromTemplate)(inputTemplatePath, inputOutputPath, templateData);
|
|
476
|
+
await (0, file_utils_1.generateFromTemplate)(inputTemplatePath, inputOutputPath, templateData, dryRun);
|
|
441
477
|
console.log(chalk_1.default.green(` ā GraphQL Inputs`));
|
|
442
478
|
// Generate pagination args (if not exists)
|
|
443
479
|
const paginationArgsPath = path.join(argsPath, 'pagination.args.ts');
|
|
444
480
|
if (!(await (0, file_utils_1.fileExists)(paginationArgsPath))) {
|
|
445
481
|
const paginationArgsTemplatePath = path.join(__dirname, '../templates/resolver/pagination-args.hbs');
|
|
446
|
-
await (0, file_utils_1.generateFromTemplate)(paginationArgsTemplatePath, paginationArgsPath, templateData);
|
|
482
|
+
await (0, file_utils_1.generateFromTemplate)(paginationArgsTemplatePath, paginationArgsPath, templateData, dryRun);
|
|
447
483
|
console.log(chalk_1.default.green(` ā Pagination Args`));
|
|
448
484
|
}
|
|
449
485
|
// Generate barrel exports
|
|
450
486
|
const typesIndexContent = `export * from "./${entityNameKebab}.type";
|
|
451
487
|
`;
|
|
452
|
-
await (0, file_utils_1.
|
|
488
|
+
await (0, file_utils_1.writeGeneratedFile)(path.join(typesPath, 'index.ts'), typesIndexContent, dryRun);
|
|
453
489
|
const inputsIndexContent = `export * from "./${entityNameKebab}.input";
|
|
454
490
|
`;
|
|
455
|
-
await (0, file_utils_1.
|
|
491
|
+
await (0, file_utils_1.writeGeneratedFile)(path.join(inputsPath, 'index.ts'), inputsIndexContent, dryRun);
|
|
456
492
|
const argsIndexContent = `export * from "./pagination.args";
|
|
457
493
|
`;
|
|
458
|
-
await (0, file_utils_1.
|
|
494
|
+
await (0, file_utils_1.writeGeneratedFile)(path.join(argsPath, 'index.ts'), argsIndexContent, dryRun);
|
|
459
495
|
const graphqlIndexContent = `export * from "./${entityNameKebab}.resolver";
|
|
460
496
|
export * from "./types";
|
|
461
497
|
export * from "./inputs";
|
|
@@ -465,9 +501,9 @@ import { ${entityNamePascal}Resolver } from "./${entityNameKebab}.resolver";
|
|
|
465
501
|
|
|
466
502
|
export const Resolvers = [${entityNamePascal}Resolver];
|
|
467
503
|
`;
|
|
468
|
-
await (0, file_utils_1.
|
|
504
|
+
await (0, file_utils_1.writeGeneratedFile)(path.join(graphqlPath, 'index.ts'), graphqlIndexContent, dryRun);
|
|
469
505
|
}
|
|
470
|
-
async function generatePrismaService(basePath) {
|
|
506
|
+
async function generatePrismaService(basePath, dryRun = false) {
|
|
471
507
|
const prismaServicePath = path.join(basePath, 'src/prisma/prisma.service.ts');
|
|
472
508
|
if (await (0, file_utils_1.fileExists)(prismaServicePath)) {
|
|
473
509
|
console.log(chalk_1.default.yellow(` PrismaService already exists. Skipping...`));
|
|
@@ -525,7 +561,7 @@ export class PrismaService extends PrismaClient implements OnModuleInit, OnModul
|
|
|
525
561
|
}
|
|
526
562
|
}
|
|
527
563
|
`;
|
|
528
|
-
await (0, file_utils_1.
|
|
564
|
+
await (0, file_utils_1.writeGeneratedFile)(prismaServicePath, content, dryRun);
|
|
529
565
|
console.log(chalk_1.default.green(` ā PrismaService`));
|
|
530
566
|
// Also generate prisma.module.ts
|
|
531
567
|
const prismaModulePath = path.join(basePath, 'src/prisma/prisma.module.ts');
|
|
@@ -540,7 +576,7 @@ import { PrismaService } from "./prisma.service";
|
|
|
540
576
|
})
|
|
541
577
|
export class PrismaModule {}
|
|
542
578
|
`;
|
|
543
|
-
await (0, file_utils_1.
|
|
579
|
+
await (0, file_utils_1.writeGeneratedFile)(prismaModulePath, moduleContent, dryRun);
|
|
544
580
|
console.log(chalk_1.default.green(` ā PrismaModule`));
|
|
545
581
|
}
|
|
546
582
|
// Generate index.ts
|
|
@@ -549,10 +585,10 @@ export class PrismaModule {}
|
|
|
549
585
|
const indexContent = `export * from "./prisma.service";
|
|
550
586
|
export * from "./prisma.module";
|
|
551
587
|
`;
|
|
552
|
-
await (0, file_utils_1.
|
|
588
|
+
await (0, file_utils_1.writeGeneratedFile)(indexPath, indexContent, dryRun);
|
|
553
589
|
}
|
|
554
590
|
}
|
|
555
|
-
async function generatePrismaSchemaSnippet(entityName, basePath, templateData) {
|
|
591
|
+
async function generatePrismaSchemaSnippet(entityName, basePath, templateData, dryRun = false) {
|
|
556
592
|
const tableName = templateData.tableName;
|
|
557
593
|
const entityNamePascal = (0, naming_utils_1.toPascalCase)(entityName);
|
|
558
594
|
// Generate fields for Prisma schema
|
|
@@ -597,7 +633,7 @@ ${fieldsContent}
|
|
|
597
633
|
// =============================================================
|
|
598
634
|
`;
|
|
599
635
|
const snippetPath = path.join(basePath, `prisma/snippets/${(0, naming_utils_1.toKebabCase)(entityName)}.prisma`);
|
|
600
|
-
await (0, file_utils_1.
|
|
636
|
+
await (0, file_utils_1.writeGeneratedFile)(snippetPath, content, dryRun);
|
|
601
637
|
console.log(chalk_1.default.green(` ā Prisma schema snippet: prisma/snippets/${(0, naming_utils_1.toKebabCase)(entityName)}.prisma`));
|
|
602
638
|
}
|
|
603
639
|
//# sourceMappingURL=generate-all.js.map
|