@currentjs/gen 0.2.1 → 0.3.0

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (41) hide show
  1. package/CHANGELOG.md +120 -0
  2. package/README.md +256 -8
  3. package/dist/cli.js +26 -0
  4. package/dist/commands/commit.js +4 -0
  5. package/dist/commands/createApp.js +7 -0
  6. package/dist/commands/diff.js +4 -0
  7. package/dist/commands/generateAll.js +159 -29
  8. package/dist/commands/migrateCommit.d.ts +1 -0
  9. package/dist/commands/migrateCommit.js +201 -0
  10. package/dist/generators/controllerGenerator.d.ts +7 -0
  11. package/dist/generators/controllerGenerator.js +60 -29
  12. package/dist/generators/domainModelGenerator.d.ts +8 -0
  13. package/dist/generators/domainModelGenerator.js +71 -4
  14. package/dist/generators/serviceGenerator.d.ts +17 -1
  15. package/dist/generators/serviceGenerator.js +139 -12
  16. package/dist/generators/storeGenerator.d.ts +9 -0
  17. package/dist/generators/storeGenerator.js +148 -8
  18. package/dist/generators/templateGenerator.d.ts +19 -0
  19. package/dist/generators/templateGenerator.js +216 -11
  20. package/dist/generators/templates/appTemplates.d.ts +8 -7
  21. package/dist/generators/templates/appTemplates.js +11 -1572
  22. package/dist/generators/templates/data/appTsTemplate +39 -0
  23. package/dist/generators/templates/data/appYamlTemplate +4 -0
  24. package/dist/generators/templates/data/cursorRulesTemplate +671 -0
  25. package/dist/generators/templates/data/errorTemplate +28 -0
  26. package/dist/generators/templates/data/frontendScriptTemplate +739 -0
  27. package/dist/generators/templates/data/mainViewTemplate +16 -0
  28. package/dist/generators/templates/data/translationsTemplate +68 -0
  29. package/dist/generators/templates/data/tsConfigTemplate +19 -0
  30. package/dist/generators/templates/viewTemplates.d.ts +10 -1
  31. package/dist/generators/templates/viewTemplates.js +138 -6
  32. package/dist/generators/validationGenerator.d.ts +5 -0
  33. package/dist/generators/validationGenerator.js +51 -0
  34. package/dist/utils/cliUtils.d.ts +6 -0
  35. package/dist/utils/cliUtils.js +24 -0
  36. package/dist/utils/constants.d.ts +3 -0
  37. package/dist/utils/constants.js +5 -2
  38. package/dist/utils/migrationUtils.d.ts +49 -0
  39. package/dist/utils/migrationUtils.js +291 -0
  40. package/howto.md +158 -66
  41. package/package.json +3 -2
package/CHANGELOG.md CHANGED
@@ -4,38 +4,158 @@ All notable changes to this project will be documented in this file.
4
4
 
5
5
 
6
6
 
7
+
8
+
9
+ ## [0.3.0] - 2025-10-03
10
+
11
+ - model relationship (between each other); - frontend script cleanup; - new command: migrate commit; - small refactoring.
12
+
13
+ ## [0.2.2] - 2025-10-02
14
+
15
+ fix bug: required params after optional in the generated models; fix: views(templates) are not stored in the registry and being regenerated (overwritten); small readme fix; running 'npm i' on 'create app' and 'npm run build' on 'generate'
16
+
17
+
18
+ ## [0.3.0] - 2025-10-03
19
+
20
+ - model relationship (between each other); - frontend script cleanup; - new command: migrate commit; - small refactoring.
21
+
7
22
  ## [0.2.1] - 2025-09-18
8
23
 
9
24
  Improve generated package.json
10
25
 
26
+
27
+
28
+ ## [0.3.0] - 2025-10-03
29
+
30
+ - model relationship (between each other); - frontend script cleanup; - new command: migrate commit; - small refactoring.
31
+
32
+ ## [0.2.2] - 2025-10-02
33
+
34
+ fix bug: required params after optional in the generated models; fix: views(templates) are not stored in the registry and being regenerated (overwritten); small readme fix; running 'npm i' on 'create app' and 'npm run build' on 'generate'
35
+
36
+
37
+ ## [0.3.0] - 2025-10-03
38
+
39
+ - model relationship (between each other); - frontend script cleanup; - new command: migrate commit; - small refactoring.
40
+
11
41
  ## [0.2.0] - 2025-09-18
12
42
 
13
43
  implement multi-model generation (controllers, services); fix service-controller interaction; update documentation: more clear & reflect important things
14
44
 
15
45
 
46
+
47
+
48
+ ## [0.3.0] - 2025-10-03
49
+
50
+ - model relationship (between each other); - frontend script cleanup; - new command: migrate commit; - small refactoring.
51
+
52
+ ## [0.2.2] - 2025-10-02
53
+
54
+ fix bug: required params after optional in the generated models; fix: views(templates) are not stored in the registry and being regenerated (overwritten); small readme fix; running 'npm i' on 'create app' and 'npm run build' on 'generate'
55
+
56
+
57
+ ## [0.3.0] - 2025-10-03
58
+
59
+ - model relationship (between each other); - frontend script cleanup; - new command: migrate commit; - small refactoring.
60
+
16
61
  ## [0.2.1] - 2025-09-18
17
62
 
18
63
  Improve generated package.json
19
64
 
65
+
66
+
67
+ ## [0.3.0] - 2025-10-03
68
+
69
+ - model relationship (between each other); - frontend script cleanup; - new command: migrate commit; - small refactoring.
70
+
71
+ ## [0.2.2] - 2025-10-02
72
+
73
+ fix bug: required params after optional in the generated models; fix: views(templates) are not stored in the registry and being regenerated (overwritten); small readme fix; running 'npm i' on 'create app' and 'npm run build' on 'generate'
74
+
75
+
76
+ ## [0.3.0] - 2025-10-03
77
+
78
+ - model relationship (between each other); - frontend script cleanup; - new command: migrate commit; - small refactoring.
79
+
20
80
  ## [0.1.2] - 2025-09-18
21
81
 
22
82
  fix: failed to generate with empty permissions actions
23
83
 
24
84
 
25
85
 
86
+
87
+
88
+ ## [0.3.0] - 2025-10-03
89
+
90
+ - model relationship (between each other); - frontend script cleanup; - new command: migrate commit; - small refactoring.
91
+
92
+ ## [0.2.2] - 2025-10-02
93
+
94
+ fix bug: required params after optional in the generated models; fix: views(templates) are not stored in the registry and being regenerated (overwritten); small readme fix; running 'npm i' on 'create app' and 'npm run build' on 'generate'
95
+
96
+
97
+ ## [0.3.0] - 2025-10-03
98
+
99
+ - model relationship (between each other); - frontend script cleanup; - new command: migrate commit; - small refactoring.
100
+
26
101
  ## [0.2.1] - 2025-09-18
27
102
 
28
103
  Improve generated package.json
29
104
 
105
+
106
+
107
+ ## [0.3.0] - 2025-10-03
108
+
109
+ - model relationship (between each other); - frontend script cleanup; - new command: migrate commit; - small refactoring.
110
+
111
+ ## [0.2.2] - 2025-10-02
112
+
113
+ fix bug: required params after optional in the generated models; fix: views(templates) are not stored in the registry and being regenerated (overwritten); small readme fix; running 'npm i' on 'create app' and 'npm run build' on 'generate'
114
+
115
+
116
+ ## [0.3.0] - 2025-10-03
117
+
118
+ - model relationship (between each other); - frontend script cleanup; - new command: migrate commit; - small refactoring.
119
+
30
120
  ## [0.2.0] - 2025-09-18
31
121
 
32
122
  implement multi-model generation (controllers, services); fix service-controller interaction; update documentation: more clear & reflect important things
33
123
 
34
124
 
125
+
126
+
127
+ ## [0.3.0] - 2025-10-03
128
+
129
+ - model relationship (between each other); - frontend script cleanup; - new command: migrate commit; - small refactoring.
130
+
131
+ ## [0.2.2] - 2025-10-02
132
+
133
+ fix bug: required params after optional in the generated models; fix: views(templates) are not stored in the registry and being regenerated (overwritten); small readme fix; running 'npm i' on 'create app' and 'npm run build' on 'generate'
134
+
135
+
136
+ ## [0.3.0] - 2025-10-03
137
+
138
+ - model relationship (between each other); - frontend script cleanup; - new command: migrate commit; - small refactoring.
139
+
35
140
  ## [0.2.1] - 2025-09-18
36
141
 
37
142
  Improve generated package.json
38
143
 
144
+
145
+
146
+ ## [0.3.0] - 2025-10-03
147
+
148
+ - model relationship (between each other); - frontend script cleanup; - new command: migrate commit; - small refactoring.
149
+
150
+ ## [0.2.2] - 2025-10-02
151
+
152
+ fix bug: required params after optional in the generated models; fix: views(templates) are not stored in the registry and being regenerated (overwritten); small readme fix; running 'npm i' on 'create app' and 'npm run build' on 'generate'
153
+
154
+
155
+ ## [0.3.0] - 2025-10-03
156
+
157
+ - model relationship (between each other); - frontend script cleanup; - new command: migrate commit; - small refactoring.
158
+
39
159
  ## [0.1.1] - 2025-09-17
40
160
 
41
161
  Initial release
package/README.md CHANGED
@@ -213,7 +213,6 @@ currentjs diff Blog
213
213
  # In your deployment pipeline
214
214
  git clone your-repo
215
215
  currentjs generate # Recreates all source code from YAML + patches
216
- npm run build
217
216
  npm run deploy
218
217
  ```
219
218
 
@@ -258,6 +257,94 @@ dist/
258
257
 
259
258
  With this setup, your repository stays focused on what matters: your specifications and customizations, not generated boilerplate!
260
259
 
260
+ ## Multi-Model Endpoint Support 🔀
261
+
262
+ Working with multiple related models in a single module? CurrentJS now supports flexible endpoint configurations for multi-model scenarios.
263
+
264
+ ### Per-Endpoint Model Override
265
+
266
+ Override the model for specific endpoints when you need to mix models within the same API or routes section:
267
+
268
+ ```yaml
269
+ models:
270
+ - name: Cat
271
+ fields:
272
+ - name: name
273
+ type: string
274
+ - name: Person
275
+ fields:
276
+ - name: name
277
+ type: string
278
+ - name: email
279
+ type: string
280
+
281
+ routes:
282
+ prefix: /cat
283
+ model: Cat # Default model for this section
284
+ endpoints:
285
+ - path: /create
286
+ action: empty
287
+ view: catCreate
288
+ # Uses Cat model (from default)
289
+
290
+ - path: /createOwner
291
+ action: empty
292
+ view: ownerCreate
293
+ model: Person # Override to use Person model for this endpoint
294
+ ```
295
+
296
+ **Result**: The `/cat/createOwner` page will generate a form with Person fields (name, email), not Cat fields.
297
+
298
+ ### Multiple API/Routes Sections
299
+
300
+ Organize endpoints by model or functionality using arrays:
301
+
302
+ ```yaml
303
+ # Multiple routes sections for different models
304
+ routes:
305
+ - prefix: /cat
306
+ model: Cat
307
+ endpoints:
308
+ - path: /
309
+ action: list
310
+ view: catList
311
+ - path: /create
312
+ action: empty
313
+ view: catCreate
314
+
315
+ - prefix: /person
316
+ model: Person
317
+ endpoints:
318
+ - path: /
319
+ action: list
320
+ view: personList
321
+ - path: /create
322
+ action: empty
323
+ view: personCreate
324
+ ```
325
+
326
+ **Result**: Generates separate controllers with their own base paths and endpoints.
327
+
328
+ ### Automatic Model Inference
329
+
330
+ If you don't specify a `model`, the system will infer it from the action handler:
331
+
332
+ ```yaml
333
+ routes:
334
+ prefix: /cat
335
+ endpoints:
336
+ - path: /createOwner
337
+ action: createOwner
338
+ view: ownerCreate
339
+ # No model specified - inferred from action below
340
+
341
+ actions:
342
+ createOwner:
343
+ handlers: [Person:default:create] # Infers Person model
344
+ ```
345
+
346
+ **Priority**: `endpoint.model` → inferred from handler → section `model` → first model in array
347
+
261
348
  ## Example: Building a Blog System 📝
262
349
 
263
350
  Here's how you'd create a complete very simple blog system:
@@ -345,7 +432,6 @@ permissions: []
345
432
  ### 3. Generate everything
346
433
  ```bash
347
434
  currentjs generate
348
- npm run build
349
435
  npm start
350
436
  ```
351
437
 
@@ -538,6 +624,174 @@ models:
538
624
  required: false
539
625
  ```
540
626
 
627
+ ### 🔗 Model Relationships
628
+
629
+ You can define relationships between models by specifying another model name as the field type. The generator will automatically handle foreign keys, type checking, and UI components.
630
+
631
+ **Basic Relationship Example:**
632
+ ```yaml
633
+ models:
634
+ - name: Owner
635
+ fields:
636
+ - name: name
637
+ type: string
638
+ required: true
639
+ - name: email
640
+ type: string
641
+ required: true
642
+
643
+ - name: Cat
644
+ fields:
645
+ - name: name
646
+ type: string
647
+ required: true
648
+ - name: breed
649
+ type: string
650
+ required: false
651
+ - name: owner
652
+ type: Owner # Relationship to Owner model
653
+ required: true
654
+ ```
655
+
656
+ **Architecture: Rich Domain Models**
657
+
658
+ The generator uses **Infrastructure-Level Relationship Assembly**:
659
+
660
+ - **Domain Layer**: Works with full objects (no FKs)
661
+ - **Infrastructure (Store)**: Handles FK ↔ Object conversion
662
+ - **DTOs**: Use FKs for API transmission
663
+
664
+ **What Gets Generated:**
665
+
666
+ 1. **Domain Model**: Pure business objects
667
+ ```typescript
668
+ import { Owner } from './Owner';
669
+
670
+ export class Cat {
671
+ constructor(
672
+ public id: number,
673
+ public name: string,
674
+ public breed?: string,
675
+ public owner: Owner // ✨ Full object, no FK!
676
+ ) {}
677
+ }
678
+ ```
679
+
680
+ 2. **DTOs**: Use foreign keys for API
681
+ ```typescript
682
+ export interface CatDTO {
683
+ name: string;
684
+ breed?: string;
685
+ ownerId: number; // ✨ FK for over-the-wire
686
+ }
687
+ ```
688
+
689
+ 3. **Store**: Converts FK ↔ Object
690
+ ```typescript
691
+ export class CatStore {
692
+ constructor(
693
+ private db: ISqlProvider,
694
+ private ownerStore: OwnerStore // ✨ Foreign store dependency
695
+ ) {}
696
+
697
+ async loadRelationships(entity: Cat, row: CatRow): Promise<Cat> {
698
+ const owner = await this.ownerStore.getById(row.ownerId);
699
+ if (owner) entity.setOwner(owner);
700
+ return entity;
701
+ }
702
+
703
+ async insert(cat: Cat): Promise<Cat> {
704
+ const row = {
705
+ name: cat.name,
706
+ ownerId: cat.owner?.id // ✨ Extract FK to save
707
+ };
708
+ // ...
709
+ }
710
+ }
711
+ ```
712
+
713
+ 4. **Service**: Loads objects from FKs
714
+ ```typescript
715
+ export class CatService {
716
+ constructor(
717
+ private catStore: CatStore,
718
+ private ownerStore: OwnerStore // ✨ To load relationships
719
+ ) {}
720
+
721
+ async create(catData: CatDTO): Promise<Cat> {
722
+ // ✨ Load full owner object from FK
723
+ const owner = await this.ownerStore.getById(catData.ownerId);
724
+ const cat = new Cat(0, catData.name, catData.breed, owner);
725
+ return await this.catStore.insert(cat);
726
+ }
727
+ }
728
+ ```
729
+
730
+ 5. **HTML Forms**: Select dropdown with "Create New" button
731
+ ```html
732
+ <select id="ownerId" name="ownerId" required>
733
+ <option value="">-- Select Owner --</option>
734
+ <!-- Options loaded from /api/owner -->
735
+ </select>
736
+ <button onclick="window.open('/owner/create')">+ New</button>
737
+ ```
738
+
739
+ **Relationship Naming Convention:**
740
+
741
+ The generator automatically creates foreign key fields following this convention:
742
+ - **Field name**: `owner` → **Foreign key**: `ownerId`
743
+ - **Field name**: `author` → **Foreign key**: `authorId`
744
+ - **Field name**: `parentComment` → **Foreign key**: `parentCommentId`
745
+
746
+ The foreign key always references the `id` field of the related model.
747
+
748
+ **Optional Configuration:**
749
+
750
+ ```yaml
751
+ models:
752
+ - name: Post
753
+ fields:
754
+ - name: title
755
+ type: string
756
+ required: true
757
+ - name: author
758
+ type: User
759
+ required: true
760
+ displayFields: [name, email] # Fields to show in dropdowns (optional)
761
+ ```
762
+
763
+ **Configuration Options:**
764
+ - `displayFields`: Array of fields from the related model to display in UI dropdowns (optional, defaults to showing the ID)
765
+
766
+ **Multiple Relationships:**
767
+ ```yaml
768
+ models:
769
+ - name: Comment
770
+ fields:
771
+ - name: content
772
+ type: string
773
+ required: true
774
+ - name: post
775
+ type: Post # Creates foreign key: postId
776
+ required: true
777
+ - name: author
778
+ type: User # Creates foreign key: authorId
779
+ required: true
780
+ displayFields: [username, email]
781
+ - name: parentComment
782
+ type: Comment # Self-referential relationship
783
+ required: false # Creates foreign key: parentCommentId
784
+ ```
785
+
786
+ **Relationship Best Practices:**
787
+ - ✅ Always define the foreign model first in the same module
788
+ - ✅ Use descriptive field names for relationships (e.g., `author` instead of `user`)
789
+ - ✅ Set appropriate `displayFields` to show meaningful data in dropdowns
790
+ - ✅ Use `required: false` for optional relationships
791
+ - ✅ Foreign keys are auto-generated following the pattern `fieldName + 'Id'`
792
+ - ❌ Don't manually add foreign key fields (they're auto-generated)
793
+ - ❌ Don't create circular dependencies between modules
794
+
541
795
  ### Action Handlers Explained
542
796
 
543
797
  **🔄 Handler vs Action Distinction:**
@@ -632,12 +886,6 @@ api:
632
886
  prefix: /api/posts
633
887
  endpoints: [...]
634
888
 
635
- # You can create separate API configs for other models
636
- commentApi:
637
- model: Comment # This API serves the Comment model
638
- prefix: /api/comments
639
- endpoints: [...]
640
-
641
889
  actions:
642
890
  createPost:
643
891
  handlers: [Post:default:create] # Calls PostService.create()
package/dist/cli.js CHANGED
@@ -8,6 +8,9 @@ const commit_1 = require("./commands/commit");
8
8
  const diff_1 = require("./commands/diff");
9
9
  const colors_1 = require("./utils/colors");
10
10
  const infer_1 = require("./commands/infer");
11
+ const migrateCommit_1 = require("./commands/migrateCommit");
12
+ // import { handleMigratePush } from './commands/migratePush';
13
+ // import { handleMigrateUpdate } from './commands/migrateUpdate';
11
14
  function printHelp() {
12
15
  const title = colors_1.colors.bold(colors_1.colors.brightCyan('currentjs - Clean architecture CLI'));
13
16
  const usage = colors_1.colors.bold('Usage:');
@@ -24,6 +27,7 @@ ${usage}
24
27
  ${cmd('currentjs commit')} ${colors_1.colors.gray('[<file> ...]')} ${flag('--yaml')} ${colors_1.colors.gray('app.yaml')}
25
28
  ${cmd('currentjs diff')} ${colors_1.colors.gray('<module|*>')} ${flag('--yaml')} ${colors_1.colors.gray('app.yaml')}
26
29
  ${cmd('currentjs infer')} ${flag('--file')} ${colors_1.colors.gray('src/modules/<Module>/domain/entities/<Entity>.ts')} ${colors_1.colors.gray('[')}${flag('--write')}${colors_1.colors.gray(']')}
30
+ ${cmd('currentjs migrate commit')} ${flag('--yaml')} ${colors_1.colors.gray('app.yaml')}
27
31
 
28
32
  ${options}
29
33
  ${flag('--yaml')} <path> ${colors_1.colors.gray('Path to app.yaml (default: ./app.yaml)')}
@@ -65,6 +69,9 @@ function parseArgs(argv) {
65
69
  else if (result.command === 'infer') {
66
70
  // no subcommands
67
71
  }
72
+ else if (result.command === 'migrate') {
73
+ result.sub = rest.shift();
74
+ }
68
75
  for (let i = 0; i < rest.length; i += 1) {
69
76
  const token = rest[i];
70
77
  if (token === '--yaml') {
@@ -127,6 +134,25 @@ async function run() {
127
134
  (0, infer_1.handleInfer)(fileArg, write);
128
135
  return;
129
136
  }
137
+ case 'migrate': {
138
+ if (args.sub === 'commit') {
139
+ (0, migrateCommit_1.handleMigrateCommit)(args.yaml);
140
+ return;
141
+ }
142
+ if (args.sub === 'push') {
143
+ console.log(colors_1.colors.yellow('⚠️ Not implemented yet'));
144
+ // await handleMigratePush(args.yaml);
145
+ return;
146
+ }
147
+ if (args.sub === 'update') {
148
+ console.log(colors_1.colors.yellow('⚠️ Not implemented yet'));
149
+ // await handleMigrateUpdate(args.yaml);
150
+ return;
151
+ }
152
+ printHelp();
153
+ process.exitCode = 1;
154
+ return;
155
+ }
130
156
  default: {
131
157
  printHelp();
132
158
  process.exitCode = 1;
@@ -43,6 +43,7 @@ const validationGenerator_1 = require("../generators/validationGenerator");
43
43
  const serviceGenerator_1 = require("../generators/serviceGenerator");
44
44
  const controllerGenerator_1 = require("../generators/controllerGenerator");
45
45
  const storeGenerator_1 = require("../generators/storeGenerator");
46
+ const templateGenerator_1 = require("../generators/templateGenerator");
46
47
  const generationRegistry_1 = require("../utils/generationRegistry");
47
48
  const commitUtils_1 = require("../utils/commitUtils");
48
49
  const colors_1 = require("../utils/colors");
@@ -88,6 +89,7 @@ function handleCommit(yamlPathArg, files) {
88
89
  const svcGen = new serviceGenerator_1.ServiceGenerator();
89
90
  const ctrlGen = new controllerGenerator_1.ControllerGenerator();
90
91
  const storeGen = new storeGenerator_1.StoreGenerator();
92
+ const tplGen = new templateGenerator_1.TemplateGenerator();
91
93
  const diffs = [];
92
94
  modulesList.forEach(moduleYamlRel => {
93
95
  const moduleYamlPath = path.isAbsolute(moduleYamlRel)
@@ -109,6 +111,7 @@ function handleCommit(yamlPathArg, files) {
109
111
  const nextServices = svcGen.generateFromYamlFile(moduleYamlPath);
110
112
  const nextControllers = ctrlGen.generateFromYamlFile(moduleYamlPath);
111
113
  const nextStores = storeGen.generateFromYamlFile(moduleYamlPath);
114
+ const nextTemplates = tplGen.generateFromYamlFile(moduleYamlPath);
112
115
  // Helper to evaluate only user-changed files and compute diff vs freshly generated code
113
116
  const consider = (target, generated) => {
114
117
  if (!fs.existsSync(target))
@@ -143,6 +146,7 @@ function handleCommit(yamlPathArg, files) {
143
146
  Object.entries(nextServices).forEach(([entity, code]) => consider(path.join(appOut, 'services', `${entity}Service.ts`), code));
144
147
  Object.entries(nextControllers).forEach(([entity, code]) => consider(path.join(infraOut, 'controllers', `${entity}Controller.ts`), code));
145
148
  Object.entries(nextStores).forEach(([entity, code]) => consider(path.join(infraOut, 'stores', `${entity}Store.ts`), code));
149
+ Object.entries(nextTemplates).forEach(([, { file, contents }]) => consider(file, contents));
146
150
  });
147
151
  const commitsDir = (0, generationRegistry_1.ensureCommitsDir)();
148
152
  const timestamp = new Date().toISOString().replace(/[:.]/g, '-');
@@ -46,11 +46,13 @@ function handleCreateApp(rawName) {
46
46
  const webDir = path.join(targetRoot, appTemplates_1.DEFAULT_DIRECTORIES.WEB);
47
47
  const templatesDir = path.join(targetRoot, appTemplates_1.DEFAULT_DIRECTORIES.TEMPLATES);
48
48
  const servicesDir = path.join(targetRoot, appTemplates_1.DEFAULT_DIRECTORIES.SERVICES);
49
+ const migrationsDir = path.join(targetRoot, appTemplates_1.DEFAULT_DIRECTORIES.MIGRATIONS);
49
50
  (0, cliUtils_1.ensureDir)(srcDir);
50
51
  (0, cliUtils_1.ensureDir)(distDir);
51
52
  (0, cliUtils_1.ensureDir)(webDir);
52
53
  (0, cliUtils_1.ensureDir)(templatesDir);
53
54
  (0, cliUtils_1.ensureDir)(servicesDir);
55
+ (0, cliUtils_1.ensureDir)(migrationsDir);
54
56
  // Files using imported templates
55
57
  (0, cliUtils_1.writeFileIfMissing)(path.join(targetRoot, appTemplates_1.DEFAULT_FILES.PACKAGE_JSON), (0, appTemplates_1.packageJsonTemplate)(path.basename(targetRoot)));
56
58
  (0, cliUtils_1.writeFileIfMissing)(path.join(targetRoot, appTemplates_1.DEFAULT_FILES.TSCONFIG), appTemplates_1.tsconfigTemplate);
@@ -61,4 +63,9 @@ function handleCreateApp(rawName) {
61
63
  (0, cliUtils_1.writeFileIfMissing)(path.join(templatesDir, appTemplates_1.DEFAULT_FILES.ERROR_TEMPLATE), appTemplates_1.errorTemplate);
62
64
  (0, cliUtils_1.writeFileIfMissing)(path.join(webDir, appTemplates_1.DEFAULT_FILES.FRONTEND_SCRIPT), appTemplates_1.frontendScriptTemplate);
63
65
  (0, cliUtils_1.writeFileIfMissing)(path.join(webDir, appTemplates_1.DEFAULT_FILES.TRANSLATIONS), appTemplates_1.translationsTemplate);
66
+ // Run npm install
67
+ (0, cliUtils_1.runCommand)('npm install', {
68
+ cwd: targetRoot,
69
+ errorMessage: '[X] Failed to install dependencies:'
70
+ });
64
71
  }
@@ -43,6 +43,7 @@ const validationGenerator_1 = require("../generators/validationGenerator");
43
43
  const serviceGenerator_1 = require("../generators/serviceGenerator");
44
44
  const controllerGenerator_1 = require("../generators/controllerGenerator");
45
45
  const storeGenerator_1 = require("../generators/storeGenerator");
46
+ const templateGenerator_1 = require("../generators/templateGenerator");
46
47
  const generationRegistry_1 = require("../utils/generationRegistry");
47
48
  const commitUtils_1 = require("../utils/commitUtils");
48
49
  const colors_1 = require("../utils/colors");
@@ -81,6 +82,7 @@ async function handleDiff(yamlPathArg, moduleName) {
81
82
  const svcGen = new serviceGenerator_1.ServiceGenerator();
82
83
  const ctrlGen = new controllerGenerator_1.ControllerGenerator();
83
84
  const storeGen = new storeGenerator_1.StoreGenerator();
85
+ const tplGen = new templateGenerator_1.TemplateGenerator();
84
86
  const results = [];
85
87
  for (const moduleYamlRel of filteredModules) {
86
88
  const moduleYamlPath = path.isAbsolute(moduleYamlRel)
@@ -97,6 +99,7 @@ async function handleDiff(yamlPathArg, moduleName) {
97
99
  const nextServices = svcGen.generateFromYamlFile(moduleYamlPath);
98
100
  const nextControllers = ctrlGen.generateFromYamlFile(moduleYamlPath);
99
101
  const nextStores = storeGen.generateFromYamlFile(moduleYamlPath);
102
+ const nextTemplates = tplGen.generateFromYamlFile(moduleYamlPath);
100
103
  const consider = (target, generated) => {
101
104
  const rel = path.relative(process.cwd(), target);
102
105
  if (!fs.existsSync(target)) {
@@ -136,6 +139,7 @@ async function handleDiff(yamlPathArg, moduleName) {
136
139
  Object.entries(nextServices).forEach(([e, code]) => consider(path.join(appOut, 'services', `${e}Service.ts`), code));
137
140
  Object.entries(nextControllers).forEach(([e, code]) => consider(path.join(infraOut, 'controllers', `${e}Controller.ts`), code));
138
141
  Object.entries(nextStores).forEach(([e, code]) => consider(path.join(infraOut, 'stores', `${e}Store.ts`), code));
142
+ Object.entries(nextTemplates).forEach(([, { file, contents }]) => consider(file, contents));
139
143
  }
140
144
  if (results.length === 0) {
141
145
  // eslint-disable-next-line no-console