eva4j 1.0.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 (115) hide show
  1. package/LICENSE +21 -0
  2. package/QUICK_REFERENCE.md +204 -0
  3. package/README.md +912 -0
  4. package/USAGE.md +349 -0
  5. package/bin/eva4j.js +234 -0
  6. package/config/defaults.json +46 -0
  7. package/package.json +57 -0
  8. package/src/commands/add-kafka-client.js +193 -0
  9. package/src/commands/add-module.js +221 -0
  10. package/src/commands/create.js +92 -0
  11. package/src/commands/detach.js +495 -0
  12. package/src/commands/generate-http-exchange.js +309 -0
  13. package/src/commands/generate-kafka-event.js +453 -0
  14. package/src/commands/generate-kafka-listener.js +267 -0
  15. package/src/commands/generate-resource.js +265 -0
  16. package/src/commands/generate-usecase.js +198 -0
  17. package/src/commands/info.js +63 -0
  18. package/src/generators/base-generator.js +150 -0
  19. package/src/generators/module-generator.js +48 -0
  20. package/src/generators/shared-generator.js +153 -0
  21. package/src/utils/config-manager.js +156 -0
  22. package/src/utils/context-builder.js +149 -0
  23. package/src/utils/naming.js +137 -0
  24. package/src/utils/template-engine.js +55 -0
  25. package/src/utils/validator.js +159 -0
  26. package/templates/base/application/Application.java.ejs +27 -0
  27. package/templates/base/docker/docker-compose.yml.ejs +41 -0
  28. package/templates/base/gradle/build.gradle.ejs +70 -0
  29. package/templates/base/gradle/settings.gradle.ejs +1 -0
  30. package/templates/base/resources/application-develop.yml.ejs +5 -0
  31. package/templates/base/resources/application-local.yml.ejs +5 -0
  32. package/templates/base/resources/application-production.yml.ejs +9 -0
  33. package/templates/base/resources/application-test.yml.ejs +5 -0
  34. package/templates/base/resources/application.yml.ejs +31 -0
  35. package/templates/base/resources/parameters/develop/cors.yml.ejs +4 -0
  36. package/templates/base/resources/parameters/develop/db.yaml.ejs +21 -0
  37. package/templates/base/resources/parameters/develop/kafka.yml.ejs +26 -0
  38. package/templates/base/resources/parameters/local/cors.yml.ejs +4 -0
  39. package/templates/base/resources/parameters/local/db.yaml.ejs +21 -0
  40. package/templates/base/resources/parameters/local/kafka.yml.ejs +26 -0
  41. package/templates/base/resources/parameters/production/cors.yml.ejs +4 -0
  42. package/templates/base/resources/parameters/production/db.yaml.ejs +21 -0
  43. package/templates/base/resources/parameters/production/kafka.yml.ejs +26 -0
  44. package/templates/base/root/README.md.ejs +126 -0
  45. package/templates/base/root/gitignore.ejs +42 -0
  46. package/templates/http-exchange/Adapter.java.ejs +39 -0
  47. package/templates/http-exchange/Config.java.ejs +24 -0
  48. package/templates/http-exchange/FeignClient.java.ejs +23 -0
  49. package/templates/http-exchange/Port.java.ejs +14 -0
  50. package/templates/kafka-event/Event.java.ejs +10 -0
  51. package/templates/kafka-event/KafkaConfigBean.java.ejs +7 -0
  52. package/templates/kafka-event/KafkaMessageBroker.java.ejs +32 -0
  53. package/templates/kafka-event/MessageBroker.java.ejs +8 -0
  54. package/templates/kafka-event/MessageBrokerImplMethod.java.ejs +9 -0
  55. package/templates/kafka-event/MessageBrokerMethod.java.ejs +1 -0
  56. package/templates/kafka-listener/KafkaController.java.ejs +34 -0
  57. package/templates/kafka-listener/ListenerMethod.java.ejs +9 -0
  58. package/templates/kafka-listener/ValueField.java.ejs +4 -0
  59. package/templates/module/controller.java.ejs +96 -0
  60. package/templates/module/exception.java.ejs +18 -0
  61. package/templates/module/mapper.java.ejs +67 -0
  62. package/templates/module/model.java.ejs +29 -0
  63. package/templates/module/package-info.java.ejs +7 -0
  64. package/templates/module/repository.java.ejs +26 -0
  65. package/templates/module/request-dto.java.ejs +24 -0
  66. package/templates/module/response-dto.java.ejs +26 -0
  67. package/templates/module/service-impl.java.ejs +112 -0
  68. package/templates/module/service.java.ejs +45 -0
  69. package/templates/module/update-dto.java.ejs +25 -0
  70. package/templates/resource/Command.java.ejs +9 -0
  71. package/templates/resource/CommandHandler.java.ejs +22 -0
  72. package/templates/resource/Controller.java.ejs +73 -0
  73. package/templates/resource/Query.java.ejs +12 -0
  74. package/templates/resource/QueryHandler.java.ejs +31 -0
  75. package/templates/resource/ResponseDto.java.ejs +6 -0
  76. package/templates/shared/annotations/ApplicationComponent.java.ejs +9 -0
  77. package/templates/shared/annotations/DomainComponent.java.ejs +9 -0
  78. package/templates/shared/annotations/LogAfter.java.ejs +11 -0
  79. package/templates/shared/annotations/LogBefore.java.ejs +11 -0
  80. package/templates/shared/annotations/LogExceptions.java.ejs +11 -0
  81. package/templates/shared/annotations/LogTimer.java.ejs +11 -0
  82. package/templates/shared/configurations/kafkaConfig/KafkaConfig.java.ejs +49 -0
  83. package/templates/shared/configurations/loggerConfig/HandlerLogs.java.ejs +56 -0
  84. package/templates/shared/configurations/securityConfig/SecurityConfig.java.ejs +57 -0
  85. package/templates/shared/configurations/swaggerConfig/SwaggerConfig.java.ejs +31 -0
  86. package/templates/shared/configurations/useCaseConfig/UseCaseAutoRegister.java.ejs +51 -0
  87. package/templates/shared/configurations/useCaseConfig/UseCaseConfig.java.ejs +25 -0
  88. package/templates/shared/configurations/useCaseConfig/UseCaseContainer.java.ejs +29 -0
  89. package/templates/shared/configurations/useCaseConfig/UseCaseMediator.java.ejs +38 -0
  90. package/templates/shared/customExceptions/BadRequestException.java.ejs +11 -0
  91. package/templates/shared/customExceptions/ConflictException.java.ejs +8 -0
  92. package/templates/shared/customExceptions/ForbiddenException.java.ejs +8 -0
  93. package/templates/shared/customExceptions/ImportFileException.java.ejs +6 -0
  94. package/templates/shared/customExceptions/NotFoundException.java.ejs +8 -0
  95. package/templates/shared/customExceptions/UnauthorizedException.java.ejs +9 -0
  96. package/templates/shared/customExceptions/ValidationException.java.ejs +17 -0
  97. package/templates/shared/errorMessage/ErrorMessage.java.ejs +5 -0
  98. package/templates/shared/errorMessage/FullErrorMessage.java.ejs +9 -0
  99. package/templates/shared/errorMessage/ShortErrorMessage.java.ejs +6 -0
  100. package/templates/shared/eventEnvelope/EventEnvelope.java.ejs +13 -0
  101. package/templates/shared/eventEnvelope/EventMetadata.java.ejs +24 -0
  102. package/templates/shared/filters/CorrelationIdFilter.java.ejs +45 -0
  103. package/templates/shared/handlerException/HandlerExceptions.java.ejs +148 -0
  104. package/templates/shared/interfaces/Command.java.ejs +4 -0
  105. package/templates/shared/interfaces/CommandHandler.java.ejs +5 -0
  106. package/templates/shared/interfaces/Dispatchable.java.ejs +4 -0
  107. package/templates/shared/interfaces/Handler.java.ejs +4 -0
  108. package/templates/shared/interfaces/Query.java.ejs +4 -0
  109. package/templates/shared/interfaces/QueryHandler.java.ejs +5 -0
  110. package/templates/shared/package-info.java.ejs +8 -0
  111. package/templates/usecase/command/Command.java.ejs +7 -0
  112. package/templates/usecase/command/CommandHandler.java.ejs +21 -0
  113. package/templates/usecase/query/Query.java.ejs +10 -0
  114. package/templates/usecase/query/QueryHandler.java.ejs +22 -0
  115. package/templates/usecase/query/ResponseDto.java.ejs +5 -0
package/USAGE.md ADDED
@@ -0,0 +1,349 @@
1
+ # eva4j - Installation & Usage Guide
2
+
3
+ ## Installation
4
+
5
+ ### Local Development
6
+
7
+ 1. Clone or navigate to the eva4j directory:
8
+ ```bash
9
+ cd c:\Documentos\eva4j
10
+ ```
11
+
12
+ 2. Install dependencies:
13
+ ```bash
14
+ npm install
15
+ ```
16
+
17
+ 3. Link the CLI globally (for local testing):
18
+ ```bash
19
+ npm link
20
+ ```
21
+
22
+ Now you can use `eva4j` command from anywhere!
23
+
24
+ ### Publish to npm (optional)
25
+
26
+ ```bash
27
+ npm publish
28
+ ```
29
+
30
+ Then install globally:
31
+ ```bash
32
+ npm install -g eva4j
33
+ ```
34
+
35
+ ## Usage
36
+
37
+ ### 1. Create a New Spring Boot Project
38
+
39
+ ```bash
40
+ eva4j create my-shop
41
+ ```
42
+
43
+ This will prompt you for:
44
+ - Group ID (e.g., `com.company`)
45
+ - Java version (21, 22, or 23)
46
+ - Spring Boot version
47
+ - Dependencies (Web, JPA, Security, Validation, Actuator)
48
+ - Database type (PostgreSQL, MySQL, H2)
49
+ - Author name
50
+
51
+ **Generated structure:**
52
+ ```
53
+ my-shop/
54
+ ├── src/main/java/com/company/myshop/
55
+ │ └── MyShopApplication.java
56
+ ├── src/main/resources/
57
+ │ ├── application.yml (base config)
58
+ │ ├── application-local.yml
59
+ │ ├── application-develop.yml
60
+ │ ├── application-test.yml
61
+ │ └── application-production.yml
62
+ ├── build.gradle (includes Spring Modulith)
63
+ ├── settings.gradle
64
+ ├── .eva4j.json (project configuration)
65
+ ├── docker-compose.yml (if database selected)
66
+ ├── .gitignore
67
+ └── README.md
68
+ ```
69
+
70
+ ### 2. Add Your First Module
71
+
72
+ Navigate to your project:
73
+ ```bash
74
+ cd my-shop
75
+ ```
76
+
77
+ Add a domain module (e.g., "user"):
78
+ ```bash
79
+ eva4j add module user
80
+ ```
81
+
82
+ **First module automatically creates `shared` module!**
83
+
84
+ The CLI will:
85
+ 1. Detect this is the first module
86
+ 2. Create the `shared` module with:
87
+ - Base entities (BaseEntity, AuditableEntity, SoftDeletableEntity)
88
+ - Value objects (Money, Email, Address)
89
+ - Domain exceptions
90
+ - Common DTOs (ApiResponse, PageResponse)
91
+ - Enums (Status, Currency, ErrorCode)
92
+ 3. Create the `user` module with Spring Modulith structure:
93
+ - `package-info.java` with @ApplicationModule annotation
94
+ - `application/` - Empty directory for controllers, services, DTOs
95
+ - `domain/` - Empty directory for entities and value objects
96
+ - `infrastructure/` - Empty directory for repositories
97
+
98
+ ### 3. Add More Modules
99
+
100
+ ```bash
101
+ eva4j add module product
102
+ eva4j add module order
103
+ ```
104
+
105
+ Each module includes:
106
+ - **package-info.java**: Spring Modulith configuration with `@ApplicationModule`
107
+ - **application/**: Empty directory for controllers, services, DTOs, mappers
108
+ - **domain/**: Empty directory for entities, value objects, domain logic
109
+ - **infrastructure/**: Empty directory for repositories, external integrations
110
+
111
+ You can then add your own classes following hexagonal/modular architecture principles.
112
+
113
+ ## Project Structure
114
+
115
+ ```
116
+ my-shop/
117
+ ├── src/
118
+ │ ├── main/java/com/company/myshop/
119
+ │ │ ├── MyShopApplication.java
120
+ │ │ ├── shared/ # Domain (business)
121
+ │ │ │ ├── domain/
122
+ │ │ │ │ ├── base/
123
+ │ │ │ │ │ ├── BaseEntity.java
124
+ │ │ │ │ │ ├── AuditableEntity.java
125
+ │ │ │ │ │ └── SoftDeletableEntity.java
126
+ │ │ │ │ ├── valueobject/
127
+ │ │ │ │ │ ├── Money.java
128
+ │ │ │ │ │ ├── Email.java
129
+ │ │ │ │ │ └── Address.java
130
+ │ │ │ │ └── exception/
131
+ │ │ │ │ ├── DomainException.java
132
+ │ │ │ │ ├── EntityNotFoundException.java
133
+ │ │ │ │ └── ValidationException.java
134
+ │ │ │ ├── dto/base/
135
+ │ │ │ │ ├── ApiResponse.java
136
+ │ │ │ │ ├── PageResponse.java
137
+ │ │ │ │ └── ErrorDetail.java
138
+ │ │ │ ├── enums/
139
+ │ │ │ │ ├── Status.java
140
+ │ │ │ │ ├── Currency.java
141
+ │ │ │ │ └── ErrorCode.java
142
+ │ │ │ └── constants/
143
+ │ │ │ └── DomainConstants.java
144
+ │ │ ├── user/ # Domain module
145
+ │ │ │ ├── package-info.java # @ApplicationModule
146
+ │ │ │ ├── application/ # Controllers, Services, DTOs
147
+ │ │ │ ├── domain/ # Entities, Value Objects
148
+ │ │ │ └── infrastructure/ # Repositories
149
+ │ │ └── product/ # Another domain module
150
+ │ │ └── ... (same structure)
151
+ │ └── resources/
152
+ │ ├── application.yml
153
+ │ ├── application-local.yml
154
+ │ ├── application-develop.yml
155
+ │ ├── application-test.yml
156
+ │ └── application-production.yml
157
+ └── build.gradle
158
+ ```
159
+
160
+ ## Running the Application
161
+
162
+ ```bash
163
+ # Using Gradle wrapper
164
+ ./gradlew bootRun
165
+
166
+ # Or build and run
167
+ ./gradlew build
168
+ java -jar build/libs/my-shop-1.0.0.jar
169
+ ```
170
+
171
+ ## Environment Profiles
172
+
173
+ The application includes multiple Spring profiles:
174
+
175
+ - **local**: Development on local machine (DEBUG logs, create-drop, SQL visible)
176
+ - **develop**: Development environment (INFO logs, update schema)
177
+ - **test**: Testing environment (INFO logs, update schema)
178
+ - **production**: Production environment (WARN logs, validate schema, swagger disabled)
179
+
180
+ Set the profile using the `PROFILE` environment variable:
181
+
182
+ ```bash
183
+ # Local development (default if not set)
184
+ PROFILE=local ./gradlew bootRun
185
+
186
+ # Development environment
187
+ PROFILE=develop ./gradlew bootRun
188
+
189
+ # Production
190
+ PROFILE=production java -jar build/libs/my-shop-1.0.0.jar
191
+ ```
192
+
193
+ Default profile: `develop`
194
+
195
+ ## API Documentation
196
+
197
+ Once running, visit:
198
+ - Swagger UI: http://localhost:8001/api/v1/swagger-ui.html
199
+ - OpenAPI: http://localhost:8001/api/v1/api-docs
200
+ - Health: http://localhost:8001/api/v1/actuator/health
201
+
202
+ **Note**: Context path is `/api/v1` and default port is `8001` (configurable in application.yml)
203
+
204
+ ## Architecture
205
+
206
+ ### Spring Modulith
207
+ The project uses Spring Modulith for modular monolith architecture. Each module is annotated with `@ApplicationModule` and can only depend on the `shared` module.
208
+
209
+ ### Shared Module (Domain)
210
+ Business domain: base entities, value objects, domain exceptions, shared enums. This module is automatically created when you add your first domain module.
211
+
212
+ ### Domain Modules (Features)
213
+ Each module follows a layered structure:
214
+ - **application/**: Application layer (controllers, services, DTOs, mappers)
215
+ - **domain/**: Domain layer (entities, value objects, domain logic)
216
+ - **infrastructure/**: Infrastructure layer (repositories, external integrations)
217
+
218
+ Modules are self-contained and can only reference the `shared` module, promoting loose coupling.
219
+
220
+ ## Commands Reference
221
+
222
+ ```bash
223
+ # Create project
224
+ eva4j create <project-name>
225
+
226
+ # Add module
227
+ eva4j add module <module-name>
228
+
229
+ # Display project info
230
+ eva4j info
231
+
232
+ # Version
233
+ eva4j -v
234
+
235
+ # Help
236
+ eva4j --help
237
+ ```
238
+
239
+ ## Project Configuration Persistence
240
+
241
+ Eva4j automatically saves project configuration in `.eva4j.json` file at the project root. This file tracks:
242
+ - Project metadata (name, group ID, package name, versions)
243
+ - Selected dependencies
244
+ - Added modules with their options (soft-delete, audit)
245
+ - Creation and update timestamps
246
+
247
+ **Benefits:**
248
+ - Persist configuration across sessions
249
+ - Track module history
250
+ - Share configuration with team members (committed to git)
251
+ - Validate module additions against existing modules
252
+
253
+ **Example `.eva4j.json`:**
254
+ ```json
255
+ {
256
+ "projectName": "my-shop",
257
+ "groupId": "com.company",
258
+ "artifactId": "my-shop",
259
+ "packageName": "com.company.myshop",
260
+ "javaVersion": "21",
261
+ "springBootVersion": "3.5.5",
262
+ "springModulithVersion": "1.4.6",
263
+ "dependencies": ["web", "data-jpa", "validation"],
264
+ "modules": [
265
+ {
266
+ "name": "user",
267
+ "hasSoftDelete": true,
268
+ "hasAudit": true,
269
+ "createdAt": "2026-01-27T10:30:00.000Z"
270
+ }
271
+ ],
272
+ "createdAt": "2026-01-27T10:25:00.000Z",
273
+ "updatedAt": "2026-01-27T10:30:00.000Z"
274
+ }
275
+ ```
276
+
277
+ **View project info:**
278
+ ```bash
279
+ cd my-shop
280
+ eva4j info
281
+ ```
282
+
283
+ This displays:
284
+ - Project details (name, group ID, package)
285
+ - Versions (Java, Spring Boot, Spring Modulith)
286
+ - Dependencies
287
+ - Modules with features
288
+ - Timestamps
289
+
290
+ ## Tips
291
+
292
+ 1. **First Module**: Always generates the shared module automatically
293
+ 2. **Soft Delete**: Enable for entities that should not be permanently deleted
294
+ 3. **Audit Fields**: Enable to track who created/modified entities
295
+ 4. **Spring Modulith**: Each module is isolated and can only depend on `shared`
296
+ 5. **Profiles**: Use `local` for development, `production` for deployment
297
+ 6. **Virtual Threads**: Enabled by default for better performance (Java 21+)
298
+ 7. **Configuration Tracking**: Use `eva4j info` to view project details and module history
299
+ 8. **Team Collaboration**: `.eva4j.json` is tracked in git for team coordination
300
+
301
+ ## Example Workflow
302
+
303
+ ```bash
304
+ # 1. Create project
305
+ eva4j create ecommerce
306
+
307
+ # 2. Navigate to project
308
+ cd ecommerce
309
+
310
+ # 3. View project info
311
+ eva4j info
312
+
313
+ # 4. Add domain modules
314
+ eva4j add module user # Creates shared + user
315
+ eva4j add module product # Just creates product
316
+ eva4j add module order # Just creates order
317
+ eva4j add module payment # Just creates payment
318
+
319
+ # 5. Check configuration and modules
320
+ eva4j info
321
+
322
+ # 6. Start database (if using Docker)
323
+ docker-compose up -d
324
+
325
+ # 7. Run application
326
+ ./gradlew bootRun
327
+
328
+ # 8. Visit Swagger
329
+ # http://localhost:8001/api/v1/swagger-ui.html
330
+ ```
331
+
332
+ ## Troubleshooting
333
+
334
+ **Issue**: "Not in a Spring Boot project directory"
335
+ - Solution: Make sure you're in the project root (where build.gradle exists)
336
+
337
+ **Issue**: Module already exists
338
+ - Solution: Choose a different module name or delete the existing module folder
339
+
340
+ **Issue**: Permission denied (Linux/Mac)
341
+ - Solution: `chmod +x ./gradlew`
342
+
343
+ ## Contributing
344
+
345
+ Issues and pull requests welcome at: https://github.com/your-repo/eva4j
346
+
347
+ ## License
348
+
349
+ MIT
package/bin/eva4j.js ADDED
@@ -0,0 +1,234 @@
1
+ #!/usr/bin/env node
2
+
3
+ const { Command } = require('commander');
4
+ const chalk = require('chalk');
5
+ const packageJson = require('../package.json');
6
+ const createCommand = require('../src/commands/create');
7
+ const addModuleCommand = require('../src/commands/add-module');
8
+ const addKafkaClientCommand = require('../src/commands/add-kafka-client');
9
+ const generateUsecaseCommand = require('../src/commands/generate-usecase');
10
+ const generateHttpExchangeCommand = require('../src/commands/generate-http-exchange');
11
+ const generateKafkaEventCommand = require('../src/commands/generate-kafka-event');
12
+ const generateKafkaListenerCommand = require('../src/commands/generate-kafka-listener');
13
+ const generateResourceCommand = require('../src/commands/generate-resource');
14
+ const infoCommand = require('../src/commands/info');
15
+ const detachCommand = require('../src/commands/detach');
16
+
17
+ const program = new Command();
18
+
19
+ program
20
+ .name('eva4j')
21
+ .description(chalk.blue('CLI for generating Spring Boot projects with modular architecture'))
22
+ .version(packageJson.version, '-v, --version', 'Output the current version');
23
+
24
+ // Create command
25
+ program
26
+ .command('create <project-name>')
27
+ .description('Create a new Spring Boot project')
28
+ .action(async (projectName, options) => {
29
+ try {
30
+ await createCommand(projectName, options);
31
+ } catch (error) {
32
+ console.error(chalk.red('Error:'), error.message);
33
+ process.exit(1);
34
+ }
35
+ });
36
+
37
+ // Add module command
38
+ program
39
+ .command('add <type> [name]')
40
+ .description('Add components to the project. Use: module [name], kafka-client')
41
+ .action(async (type, name, options) => {
42
+ if (type === 'kafka-client') {
43
+ try {
44
+ await addKafkaClientCommand(options);
45
+ } catch (error) {
46
+ console.error(chalk.red('Error:'), error.message);
47
+ process.exit(1);
48
+ }
49
+ return;
50
+ }
51
+
52
+ if (type !== 'module') {
53
+ console.error(chalk.red(`❌ Unknown type: ${type}`));
54
+ console.log(chalk.yellow('\nUsage:'));
55
+ console.log(chalk.gray(' eva4j add module [module-name] # Interactive or with name'));
56
+ console.log(chalk.gray(' eva4j add kafka-client'));
57
+ console.log(chalk.gray('\nExamples:'));
58
+ console.log(chalk.gray(' eva4j add module user'));
59
+ console.log(chalk.gray(' eva4j add module # Will prompt for name\n'));
60
+ process.exit(1);
61
+ }
62
+
63
+ try {
64
+ await addModuleCommand(name, options);
65
+ } catch (error) {
66
+ console.error(chalk.red('Error:'), error.message);
67
+ process.exit(1);
68
+ }
69
+ });
70
+
71
+ // Generate command
72
+ program
73
+ .command('generate <type> <module> [name]')
74
+ .alias('g')
75
+ .description('Generate components (usecase, http-exchange, kafka-event, kafka-listener, resource)')
76
+ .action(async (type, module, name, options) => {
77
+ if (type === 'usecase') {
78
+ if (!module) {
79
+ console.error(chalk.red('❌ Module name is required'));
80
+ console.log(chalk.gray('Usage: eva4j generate usecase <module> [name]'));
81
+ console.log(chalk.gray('Examples:'));
82
+ console.log(chalk.gray(' eva4j generate usecase user create-user'));
83
+ console.log(chalk.gray(' eva4j generate usecase user # Will prompt for name\n'));
84
+ process.exit(1);
85
+ }
86
+ try {
87
+ await generateUsecaseCommand(module, name, options);
88
+ } catch (error) {
89
+ console.error(chalk.red('Error:'), error.message);
90
+ process.exit(1);
91
+ }
92
+ return;
93
+ }
94
+
95
+ if (type === 'http-exchange') {
96
+ if (!module) {
97
+ console.error(chalk.red('❌ Module name is required'));
98
+ console.log(chalk.gray('Usage: eva4j generate http-exchange <module> [port-name]'));
99
+ console.log(chalk.gray('Examples:'));
100
+ console.log(chalk.gray(' eva4j generate http-exchange user product-service'));
101
+ console.log(chalk.gray(' eva4j generate http-exchange user # Will prompt for port name\n'));
102
+ process.exit(1);
103
+ }
104
+ try {
105
+ await generateHttpExchangeCommand(module, name, options);
106
+ } catch (error) {
107
+ console.error(chalk.red('Error:'), error.message);
108
+ process.exit(1);
109
+ }
110
+ return;
111
+ }
112
+
113
+ if (type === 'kafka-event') {
114
+ if (!module) {
115
+ console.error(chalk.red('❌ Module name is required'));
116
+ console.log(chalk.gray('Usage: eva4j generate kafka-event <module> [event-name]'));
117
+ console.log(chalk.gray('Examples:'));
118
+ console.log(chalk.gray(' eva4j generate kafka-event user product-created'));
119
+ console.log(chalk.gray(' eva4j generate kafka-event user # Will prompt for event name\n'));
120
+ process.exit(1);
121
+ }
122
+ try {
123
+ await generateKafkaEventCommand(module, name, options);
124
+ } catch (error) {
125
+ console.error(chalk.red('Error:'), error.message);
126
+ process.exit(1);
127
+ }
128
+ return;
129
+ }
130
+
131
+ if (type === 'kafka-listener') {
132
+ if (!module) {
133
+ console.error(chalk.red('❌ Module name is required'));
134
+ console.log(chalk.gray('Usage: eva4j generate kafka-listener <module>'));
135
+ console.log(chalk.gray('Examples:'));
136
+ console.log(chalk.gray(' eva4j generate kafka-listener user'));
137
+ console.log(chalk.gray(' eva4j g kafka-listener order\n'));
138
+ process.exit(1);
139
+ }
140
+ try {
141
+ await generateKafkaListenerCommand(module, options);
142
+ } catch (error) {
143
+ console.error(chalk.red('Error:'), error.message);
144
+ process.exit(1);
145
+ }
146
+ return;
147
+ }
148
+
149
+ if (type === 'resource') {
150
+ if (!module) {
151
+ console.error(chalk.red('❌ Module name is required'));
152
+ console.log(chalk.gray('Usage: eva4j generate resource <module>'));
153
+ console.log(chalk.gray('Examples:'));
154
+ console.log(chalk.gray(' eva4j generate resource user'));
155
+ console.log(chalk.gray(' eva4j g resource product\n'));
156
+ process.exit(1);
157
+ }
158
+ try {
159
+ await generateResourceCommand(module, options);
160
+ } catch (error) {
161
+ console.error(chalk.red('Error:'), error.message);
162
+ process.exit(1);
163
+ }
164
+ return;
165
+ }
166
+
167
+ console.error(chalk.red(`❌ Unknown type: ${type}`));
168
+ console.log(chalk.yellow('\nUsage:'));
169
+ console.log(chalk.gray(' eva4j generate usecase <name> <module>'));
170
+ console.log(chalk.gray(' eva4j generate http-exchange <port-name> <module>'));
171
+ console.log(chalk.gray(' eva4j generate kafka-event <event-name> <module>'));
172
+ console.log(chalk.gray(' eva4j generate kafka-listener <module>'));
173
+ console.log(chalk.gray(' eva4j generate resource <module>'));
174
+ console.log(chalk.gray('\nExamples:'));
175
+ console.log(chalk.gray(' eva4j generate usecase create-provider provider'));
176
+ console.log(chalk.gray(' eva4j g http-exchange user-service-port user'));
177
+ console.log(chalk.gray(' eva4j g kafka-event user-created user'));
178
+ console.log(chalk.gray(' eva4j g kafka-listener user'));
179
+ console.log(chalk.gray(' eva4j g resource product\n'));
180
+ process.exit(1);
181
+ });
182
+
183
+ // Info command
184
+ program
185
+ .command('info')
186
+ .description('Display project information and configuration')
187
+ .action(async (options) => {
188
+ try {
189
+ await infoCommand(options);
190
+ } catch (error) {
191
+ console.error(chalk.red('Error:'), error.message);
192
+ process.exit(1);
193
+ }
194
+ });
195
+
196
+ // Detach command
197
+ program
198
+ .command('detach [module-name]')
199
+ .description('Extract a module into a standalone microservice')
200
+ .action(async (moduleName, options) => {
201
+ try {
202
+ await detachCommand(moduleName, options);
203
+ } catch (error) {
204
+ console.error(chalk.red('Error:'), error.message);
205
+ process.exit(1);
206
+ }
207
+ });
208
+
209
+ // Help command
210
+ program.on('--help', () => {
211
+ console.log('');
212
+ console.log(chalk.blue('Examples:'));
213
+ console.log(chalk.gray(' $ eva4j create my-project'));
214
+ console.log(chalk.gray(' $ eva4j add module user'));
215
+ console.log(chalk.gray(' $ eva4j add module product'));
216
+ console.log(chalk.gray(' $ eva4j add kafka-client'));
217
+ console.log(chalk.gray(' $ eva4j generate usecase create-provider provider'));
218
+ console.log(chalk.gray(' $ eva4j g usecase get-all-products product'));
219
+ console.log(chalk.gray(' $ eva4j g http-exchange user-service-port user'));
220
+ console.log(chalk.gray(' $ eva4j g kafka-event user-created user'));
221
+ console.log(chalk.gray(' $ eva4j detach user'));
222
+ console.log(chalk.gray(' $ eva4j info'));
223
+ console.log('');
224
+ console.log(chalk.blue('For more information, visit:'));
225
+ console.log(chalk.gray(' https://github.com/your-repo/eva4j'));
226
+ console.log('');
227
+ });
228
+
229
+ // Show help if no command provided
230
+ if (!process.argv.slice(2).length) {
231
+ program.outputHelp();
232
+ }
233
+
234
+ program.parse(process.argv);
@@ -0,0 +1,46 @@
1
+ {
2
+ "version": "1.0.0",
3
+ "javaVersion": 21,
4
+ "springBootVersion": "3.5.5",
5
+ "dependencyManagementVersion": "1.1.7",
6
+ "springModulithVersion": "1.4.6",
7
+ "springCloudVersion": "2025.0.0",
8
+ "gradleVersion": "8.7",
9
+ "encoding": "UTF-8",
10
+ "server": {
11
+ "port": 8040,
12
+ "contextPath": "/"
13
+ },
14
+ "database": {
15
+ "type": "h2",
16
+ "ddlAuto": "update",
17
+ "showSql": true
18
+ },
19
+ "logging": {
20
+ "level": "INFO"
21
+ },
22
+ "features": {
23
+ "enableScheduling": false,
24
+ "enableAsync": false,
25
+ "includeSwagger": true,
26
+ "includeActuator": true,
27
+ "includeDevtools": true,
28
+ "includeLombok": true,
29
+ "includeDocker": true
30
+ },
31
+ "testing": {
32
+ "includeTestcontainers": false,
33
+ "includeIntegrationTests": true
34
+ },
35
+ "shared": {
36
+ "hasSoftDelete": true,
37
+ "hasAudit": true,
38
+ "includeValueObjects": true,
39
+ "includeDomainEvents": false
40
+ },
41
+ "module": {
42
+ "hasSoftDelete": true,
43
+ "hasAudit": true,
44
+ "generateTests": true
45
+ }
46
+ }
package/package.json ADDED
@@ -0,0 +1,57 @@
1
+ {
2
+ "name": "eva4j",
3
+ "version": "1.0.0",
4
+ "description": "A powerful Node.js CLI for generating Spring Boot projects with modular architecture that enables efficient monolith-first development with seamless transition to microservices",
5
+ "main": "bin/eva4j.js",
6
+ "bin": {
7
+ "eva4j": "./bin/eva4j.js"
8
+ },
9
+ "scripts": {
10
+ "start": "node bin/eva4j.js",
11
+ "test": "echo \"Error: no test specified\" && exit 1"
12
+ },
13
+ "keywords": [
14
+ "cli",
15
+ "spring-boot",
16
+ "java",
17
+ "gradle",
18
+ "scaffolding",
19
+ "generator",
20
+ "microservices",
21
+ "hexagonal-architecture",
22
+ "clean-architecture",
23
+ "cqrs",
24
+ "spring-modulith",
25
+ "modular-monolith",
26
+ "kafka",
27
+ "rest-api",
28
+ "boilerplate",
29
+ "code-generator",
30
+ "openfeign",
31
+ "event-driven"
32
+ ],
33
+ "author": "asuridev",
34
+ "license": "MIT",
35
+ "repository": {
36
+ "type": "git",
37
+ "url": "git+https://github.com/asuridev/eva4j.git"
38
+ },
39
+ "bugs": {
40
+ "url": "https://github.com/asuridev/eva4j/issues"
41
+ },
42
+ "homepage": "https://github.com/asuridev/eva4j#readme",
43
+ "dependencies": {
44
+ "chalk": "^4.1.2",
45
+ "commander": "^11.1.0",
46
+ "ejs": "^3.1.9",
47
+ "fs-extra": "^11.2.0",
48
+ "inquirer": "^8.2.6",
49
+ "js-yaml": "^4.1.0",
50
+ "ora": "^5.4.1",
51
+ "pluralize": "^8.0.0"
52
+ },
53
+ "devDependencies": {},
54
+ "engines": {
55
+ "node": ">=14.0.0"
56
+ }
57
+ }