eva4j 1.0.16 → 1.0.18

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 (151) hide show
  1. package/AGENTS.md +220 -5
  2. package/DOMAIN_YAML_GUIDE.md +188 -3
  3. package/FUTURE_FEATURES.md +33 -52
  4. package/QUICK_REFERENCE.md +8 -4
  5. package/bin/eva4j.js +70 -2
  6. package/config/defaults.json +1 -0
  7. package/docs/CAMUNDA_DMN_GUIDE.md +1380 -0
  8. package/docs/KAFKA_PRODUCTION_CONFIG.md +441 -0
  9. package/docs/RABBITMQ_PRODUCTION_CONFIG.md +227 -0
  10. package/docs/commands/ADD_RABBITMQ_CLIENT.md +192 -0
  11. package/docs/commands/EVALUATE_SYSTEM.md +290 -10
  12. package/docs/commands/GENERATE_RABBITMQ_EVENT.md +341 -0
  13. package/docs/commands/GENERATE_RABBITMQ_LISTENER.md +595 -0
  14. package/docs/commands/GENERATE_TEMPORAL_FLOW.md +52 -12
  15. package/docs/commands/INDEX.md +27 -3
  16. package/docs/prototype/TEMPORAL_COMMUNICATION_PATTERNS.md +731 -0
  17. package/docs/prototype/TEMPORAL_DESIGN_METHODOLOGY.md +740 -0
  18. package/docs/prototype/system/RISKS.md +277 -0
  19. package/docs/prototype/system/customers.yaml +133 -0
  20. package/docs/prototype/system/inventory.yaml +109 -0
  21. package/docs/prototype/system/notifications.yaml +131 -0
  22. package/docs/prototype/system/orders.yaml +241 -0
  23. package/docs/prototype/system/payments.yaml +256 -0
  24. package/docs/prototype/system/products.yaml +168 -0
  25. package/docs/prototype/system/system.yaml +269 -0
  26. package/examples/domain-endpoints-multi-aggregate.yaml +140 -0
  27. package/examples/domain-events.yaml +26 -0
  28. package/examples/domain-read-models.yaml +113 -0
  29. package/examples/system/customer.yaml +89 -0
  30. package/examples/system/orders.yaml +119 -0
  31. package/examples/system/product.yaml +27 -0
  32. package/examples/system/system.yaml +80 -0
  33. package/package.json +1 -1
  34. package/read-model-spec.md +664 -0
  35. package/src/agents/design-gap-analyst-temporal.agent.md +452 -0
  36. package/src/agents/design-gap-analyst.agent.md +383 -0
  37. package/src/agents/design-reviewer-temporal.agent.md +412 -0
  38. package/src/agents/design-reviewer.agent.md +34 -5
  39. package/src/agents/implement-use-cases.prompt.md +179 -0
  40. package/src/agents/ux-gap-analyst.agent.md +412 -0
  41. package/src/commands/add-rabbitmq-client.js +261 -0
  42. package/src/commands/add-temporal-client.js +22 -2
  43. package/src/commands/build.js +267 -11
  44. package/src/commands/evaluate-system.js +700 -13
  45. package/src/commands/generate-entities.js +560 -24
  46. package/src/commands/generate-http-exchange.js +3 -0
  47. package/src/commands/generate-kafka-event.js +3 -0
  48. package/src/commands/generate-kafka-listener.js +3 -0
  49. package/src/commands/generate-rabbitmq-event.js +665 -0
  50. package/src/commands/generate-rabbitmq-listener.js +205 -0
  51. package/src/commands/generate-record.js +2 -2
  52. package/src/commands/generate-resource.js +4 -1
  53. package/src/commands/generate-temporal-activity.js +970 -33
  54. package/src/commands/generate-temporal-flow.js +98 -38
  55. package/src/commands/generate-temporal-system.js +708 -0
  56. package/src/commands/generate-usecase.js +4 -1
  57. package/src/skills/build-system-yaml/SKILL.md +343 -2
  58. package/src/skills/build-system-yaml/references/domain-yaml-spec.md +253 -26
  59. package/src/skills/build-system-yaml/references/module-spec.md +90 -9
  60. package/src/skills/build-system-yaml/references/system-yaml-spec.md +36 -0
  61. package/src/skills/build-temporal-system/SKILL.md +752 -0
  62. package/src/skills/build-temporal-system/references/temporal-communication-patterns.md +167 -0
  63. package/src/skills/build-temporal-system/references/temporal-domain-yaml-spec.md +449 -0
  64. package/src/skills/build-temporal-system/references/temporal-module-spec.md +353 -0
  65. package/src/skills/build-temporal-system/references/temporal-system-yaml-spec.md +326 -0
  66. package/src/skills/implement-use-case/SKILL.md +350 -0
  67. package/src/skills/implement-use-case/references/use-case-patterns.md +980 -0
  68. package/src/skills/requirements-elicitation/SKILL.md +228 -0
  69. package/src/skills/requirements-elicitation/references/interview-framework.md +260 -0
  70. package/src/skills/requirements-elicitation/references/output-templates.md +368 -0
  71. package/src/utils/bounded-context-diagram.js +844 -0
  72. package/src/utils/config-manager.js +4 -2
  73. package/src/utils/domain-validator.js +495 -17
  74. package/src/utils/naming.js +20 -0
  75. package/src/utils/system-validator.js +169 -11
  76. package/src/utils/system-yaml-parser.js +318 -0
  77. package/src/utils/temporal-validator.js +497 -0
  78. package/src/utils/validator.js +3 -1
  79. package/src/utils/yaml-to-entity.js +281 -9
  80. package/templates/aggregate/AggregateRepository.java.ejs +4 -0
  81. package/templates/aggregate/AggregateRepositoryImpl.java.ejs +8 -0
  82. package/templates/aggregate/AggregateRoot.java.ejs +38 -4
  83. package/templates/aggregate/DomainEventHandler.java.ejs +116 -22
  84. package/templates/aggregate/JpaAggregateRoot.java.ejs +4 -4
  85. package/templates/aggregate/JpaEntity.java.ejs +2 -2
  86. package/templates/base/docker/rabbitmq-services.yaml.ejs +12 -0
  87. package/templates/base/resources/parameters/develop/kafka.yaml.ejs +5 -0
  88. package/templates/base/resources/parameters/develop/rabbitmq.yaml.ejs +15 -0
  89. package/templates/base/resources/parameters/develop/temporal.yaml.ejs +0 -3
  90. package/templates/base/resources/parameters/local/kafka.yaml.ejs +5 -0
  91. package/templates/base/resources/parameters/local/rabbitmq.yaml.ejs +15 -0
  92. package/templates/base/resources/parameters/local/temporal.yaml.ejs +0 -3
  93. package/templates/base/resources/parameters/production/kafka.yaml.ejs +39 -8
  94. package/templates/base/resources/parameters/production/rabbitmq.yaml.ejs +32 -0
  95. package/templates/base/resources/parameters/production/temporal.yaml.ejs +0 -3
  96. package/templates/base/resources/parameters/test/kafka.yaml.ejs +12 -6
  97. package/templates/base/resources/parameters/test/rabbitmq.yaml.ejs +15 -0
  98. package/templates/base/resources/parameters/test/temporal.yaml.ejs +0 -3
  99. package/templates/base/root/AGENTS.md.ejs +1 -1
  100. package/templates/crud/DeleteCommandHandler.java.ejs +19 -1
  101. package/templates/crud/EndpointsController.java.ejs +1 -1
  102. package/templates/crud/ScaffoldCommand.java.ejs +5 -2
  103. package/templates/crud/ScaffoldCommandHandler.java.ejs +3 -1
  104. package/templates/crud/ScaffoldQuery.java.ejs +5 -2
  105. package/templates/crud/ScaffoldQueryHandler.java.ejs +3 -1
  106. package/templates/crud/SubEntityRemoveCommand.java.ejs +1 -1
  107. package/templates/crud/UpdateCommandHandler.java.ejs +53 -2
  108. package/templates/evaluate/report.html.ejs +1447 -90
  109. package/templates/kafka-event/KafkaConfigBean.java.ejs +1 -1
  110. package/templates/kafka-event/KafkaMessageBroker.java.ejs +3 -3
  111. package/templates/ports/PortAclMapper.java.ejs +35 -0
  112. package/templates/ports/PortFeignAdapter.java.ejs +7 -22
  113. package/templates/ports/PortFeignClient.java.ejs +4 -0
  114. package/templates/ports/PortResponseDto.java.ejs +1 -1
  115. package/templates/rabbitmq-event/RabbitConfigBean.java.ejs +33 -0
  116. package/templates/rabbitmq-event/RabbitConfigExchange.java.ejs +12 -0
  117. package/templates/rabbitmq-event/RabbitMessageBroker.java.ejs +35 -0
  118. package/templates/rabbitmq-event/RabbitMessageBrokerMethod.java.ejs +9 -0
  119. package/templates/rabbitmq-listener/RabbitConfigConsumerBean.java.ejs +33 -0
  120. package/templates/rabbitmq-listener/RabbitConfigConsumerExchange.java.ejs +12 -0
  121. package/templates/rabbitmq-listener/RabbitListenerClass.java.ejs +82 -0
  122. package/templates/rabbitmq-listener/RabbitListenerSimple.java.ejs +56 -0
  123. package/templates/read-model/ReadModelDomain.java.ejs +46 -0
  124. package/templates/read-model/ReadModelJpa.java.ejs +58 -0
  125. package/templates/read-model/ReadModelJpaRepository.java.ejs +13 -0
  126. package/templates/read-model/ReadModelKafkaListener.java.ejs +64 -0
  127. package/templates/read-model/ReadModelRabbitListener.java.ejs +71 -0
  128. package/templates/read-model/ReadModelRepository.java.ejs +42 -0
  129. package/templates/read-model/ReadModelRepositoryImpl.java.ejs +85 -0
  130. package/templates/read-model/ReadModelSyncHandler.java.ejs +54 -0
  131. package/templates/shared/configurations/kafkaConfig/KafkaConfig.java.ejs +18 -4
  132. package/templates/shared/configurations/rabbitmqConfig/RabbitMQConfig.java.ejs +100 -0
  133. package/templates/shared/configurations/temporalConfig/TemporalConfig.java.ejs +2 -64
  134. package/templates/shared/configurations/temporalConfig/TemporalWorkerFactoryLifecycle.java.ejs +41 -0
  135. package/templates/temporal-activity/ActivityImpl.java.ejs +68 -2
  136. package/templates/temporal-activity/ActivityInput.java.ejs +14 -0
  137. package/templates/temporal-activity/ActivityInterface.java.ejs +7 -1
  138. package/templates/temporal-activity/ActivityOutput.java.ejs +14 -0
  139. package/templates/temporal-activity/NestedType.java.ejs +12 -0
  140. package/templates/temporal-activity/SharedActivityInput.java.ejs +14 -0
  141. package/templates/temporal-activity/SharedActivityInterface.java.ejs +15 -0
  142. package/templates/temporal-activity/SharedActivityOutput.java.ejs +14 -0
  143. package/templates/temporal-activity/SharedNestedType.java.ejs +12 -0
  144. package/templates/temporal-flow/ModuleHeavyActivity.java.ejs +6 -0
  145. package/templates/temporal-flow/ModuleLightActivity.java.ejs +6 -0
  146. package/templates/temporal-flow/ModuleTemporalWorkerConfig.java.ejs +58 -0
  147. package/templates/temporal-flow/WorkFlowImpl.java.ejs +172 -12
  148. package/templates/temporal-flow/WorkFlowInput.java.ejs +11 -0
  149. package/templates/temporal-flow/WorkFlowInterface.java.ejs +5 -4
  150. package/templates/temporal-flow/WorkFlowService.java.ejs +42 -12
  151. package/COMMAND_EVALUATION.md +0 -911
@@ -0,0 +1,353 @@
1
+ # Temporal Module Specification — Documentation Templates
2
+
3
+ Reference for generating `system/system.md` and `system/{module}.md` in a Temporal-based system.
4
+
5
+ > **PATH RULE:** All documentation files MUST be saved inside the `system/` directory (e.g., `system/system.md`, `system/orders.md`). NEVER save at the project root.
6
+
7
+ ---
8
+
9
+ ## Part 1 — system.md (global narrative specification)
10
+
11
+ ### Location: `system/system.md`
12
+
13
+ Narrative technical specification of the complete system. One `##` section per module with detailed subsections.
14
+
15
+ ### Mandatory structure
16
+
17
+ ```markdown
18
+ # system.md — Technical Specification
19
+
20
+ ## {module-name}
21
+
22
+ ### Module Role
23
+ [3–5 detailed paragraphs]
24
+ - What business problem it solves and what entities/concepts it manages
25
+ - Its exclusive responsibilities (bounded context boundaries)
26
+ - What is NOT this module's responsibility
27
+ - How it collaborates with other modules via Temporal activities
28
+ - Business invariants it protects
29
+
30
+ ### Use Cases
31
+ [One `####` section per useCase in exposes:]
32
+
33
+ #### {UseCaseName}
34
+ **What it does:** [detailed business logic description]
35
+ **Preconditions:** [required state, entities that must exist]
36
+ **Postconditions:** [system state after successful execution]
37
+ **Validations and errors:** [exception conditions and error types]
38
+ **Events emitted:** [DomainEvent name and what workflow it triggers, or "none"]
39
+ **Operations:**
40
+ 1. [Load entity / validate precondition — throw NotFoundException or 400 if invalid]
41
+ 2. [External port call: {PortName}.{method}() — if applicable (**ONLY for external services** like payment gateways, NOT for other modules**)]
42
+ 3. [Invoke domain method: entity.{method}()]
43
+ 4. [Persist via repository]
44
+ 5. [Emit event → triggers {WorkflowName} — if applicable]
45
+
46
+ > **⚠️ Important:** Handlers do NOT invoke activities from other modules (or their own). Cross-module data is obtained via activities orchestrated by workflows. If this use case needs external data, it should emit a Domain Event with `notifies:` that triggers a workflow containing the required read activities.
47
+
48
+ ### Exposed Endpoints
49
+ [One `####` per endpoint in exposes:]
50
+
51
+ #### {METHOD} {/path}
52
+ **Purpose:** [endpoint description and usage context]
53
+ **Path params:** [param — Type — Description; omit if none]
54
+ **Query params:** [GET/DELETE only — param: Type, required/optional, default, description; omit if none]
55
+ **Request body:** [POST/PUT/PATCH only — field: Type — constraint; omit for GET/DELETE]
56
+ **Response:** [GET only — field: Type — business meaning; list endpoints include {content:[...], totalElements, page, size}]
57
+ **Errors:** [HTTP status — condition]
58
+
59
+ ### Activities Exposed
60
+ [One `####` per activity declared in module's domain.yaml]
61
+
62
+ #### {ActivityName}
63
+ **Type:** `light` | `heavy`
64
+ **Task Queue:** `{MODULE}_LIGHT_TASK_QUEUE` | `{MODULE}_HEAVY_TASK_QUEUE`
65
+ **Invoked by:** [workflow name(s) from system.yaml or domain.yaml]
66
+ **Input:** [field names and types]
67
+ **Output:** [field names and types, or "void"]
68
+ **Compensation:** [{compensation activity name} or "none"]
69
+ **What it does:** [detailed description of the business operation]
70
+ **Data access:** [what this activity reads/writes in its own database]
71
+
72
+ ### Workflows Triggered
73
+ [Only if module has events with notifies:]
74
+
75
+ #### {EventName} → {WorkflowName}
76
+ **When:** [exact business condition that fires the event]
77
+ **Workflow:** [{WorkflowName} — defined in system.yaml]
78
+ **Steps summary:** [brief description of what the workflow does]
79
+
80
+ ### Single-Module Workflows
81
+ [Only if module has workflows: in its domain.yaml]
82
+
83
+ #### {WorkflowName}
84
+ **Trigger:** [what internal event or condition starts it]
85
+ **Task Queue:** [{QUEUE_NAME}]
86
+ **Steps:** [ordered list of activities with descriptions]
87
+ **Purpose:** [why this internal workflow exists]
88
+
89
+ ### Ports (external services)
90
+ [Only if module has ports: in its domain.yaml]
91
+
92
+ #### {PortName} → {target}
93
+ **When called:** [in which activity or use case]
94
+ **Endpoints used:** [METHOD /path list]
95
+ **Data obtained and how it's used:** [detailed description]
96
+ ```
97
+
98
+ ### Rules for system.md
99
+
100
+ - **Be EXTREMELY specific**: entity states, concrete validations, relevant fields
101
+ - **End-to-end flows**: if `ConfirmOrder` is invoked as an activity by `PlaceOrderWorkflow`, explain it in both sections
102
+ - **Activities are the collaboration mechanism**: explain which workflows invoke each activity
103
+ - **Reference modules by name**
104
+ - **State machines** when there are lifecycles
105
+ - **Detailed endpoints**: separate path params from query params. For GETs provide the key response fields with types. For POST/PUT/PATCH list body fields with types and constraints. Never use "see request" as a response description.
106
+ - **Operations in use cases**: the `**Operations:**` field is mandatory in each `#### {UseCaseName}`. Each item describes a concrete handler step referencing real repository, port, domain method, and event names. No generic items like "execute business logic".
107
+ - Omit non-applicable sections
108
+
109
+ ---
110
+
111
+ ## Part 2 — {module}.md (technical specification per module)
112
+
113
+ ### Location: `system/{module-name}.md`
114
+
115
+ Complete, standalone specification for each module. A developer can read it without knowing the full system.
116
+
117
+ ### Mandatory structure
118
+
119
+ ```markdown
120
+ # {module-name} — Technical Specification
121
+
122
+ ## Module Role
123
+ [3–5 VERY detailed paragraphs]
124
+ - What business problem it solves and what entities/concepts it manages
125
+ - Exclusive responsibilities (bounded context boundaries)
126
+ - What is NOT this module's responsibility
127
+ - How it collaborates with other modules via Temporal activities
128
+ - How it is different from a broker-based architecture
129
+
130
+ ## Invariants
131
+
132
+ > Invariants are conditions that must be **always true** within this bounded context.
133
+ > Violating an invariant is a **critical business error** that must throw an exception.
134
+
135
+ | ID | Invariant | Violation consequence |
136
+ |----|-----------|----------------------|
137
+ | INV-01 | [condition] | [exception / what it prevents] |
138
+
139
+ > Each use case and activity must verify relevant invariants **before** persisting.
140
+
141
+ ## State Machine
142
+ [ONLY if the module manages entity lifecycle — omit otherwise]
143
+
144
+ ```mermaid
145
+ stateDiagram-v2
146
+ [*] --> INITIAL_STATE
147
+ INITIAL_STATE --> NEXT_STATE : event / action
148
+ ```
149
+
150
+ ## Interaction Diagram
151
+
152
+ > Shows: REST endpoints → use cases, activities invoked by workflows, events triggered.
153
+ > Uses Temporal-specific iconography.
154
+
155
+ ```mermaid
156
+ flowchart TD
157
+ subgraph HTTP["REST Endpoints"]
158
+ EP1["METHOD /path"]
159
+ end
160
+
161
+ subgraph ACTIVITIES["Activities Exposed"]
162
+ ACT1["⚡ ActivityName"]
163
+ end
164
+
165
+ subgraph USE_CASES["Use Cases"]
166
+ UC1["UseCaseName"]
167
+ end
168
+
169
+ subgraph EVENTS_OUT["Events → Workflows"]
170
+ EO1["📤 EventName → WorkflowName"]
171
+ end
172
+
173
+ EP1 --> UC1
174
+ UC1 --> EO1
175
+ ACT1 -->|"invoked by WorkflowName"| IMPL["Internal logic"]
176
+ ```
177
+
178
+ > Node conventions:
179
+ > - HTTP endpoints → rectangles with method and path
180
+ > - Activities → `⚡` prefix with activity name
181
+ > - Use cases → rectangles with handler name
182
+ > - Events with workflows → `📤` prefix + event → workflow
183
+ > - Omit sections if not applicable
184
+
185
+ ## Sequence Diagram
186
+ [Chronological interactions for main flows]
187
+
188
+ ```mermaid
189
+ sequenceDiagram
190
+ actor Client as Client
191
+ participant API as REST API
192
+ participant Handler as CommandHandler
193
+ participant Domain as Domain Entity
194
+ participant Repo as Repository
195
+ participant Temporal as Temporal Server
196
+
197
+ Client->>API: POST /resource {payload}
198
+ API->>Handler: CreateResourceCommand
199
+ Handler->>Domain: new Resource(...)
200
+ Domain-->>Handler: entity with DomainEvent
201
+ Handler->>Repo: save(entity)
202
+ Note over Repo,Temporal: DomainEventHandler intercepts event
203
+ Repo->>Temporal: startWorkflow(ResourceCreatedWorkflow)
204
+ Handler-->>API: resourceId
205
+ API-->>Client: 201 Created {resourceId}
206
+ ```
207
+
208
+ > **Key constraint:** The handler above does NOT call any activity. It persists the entity, and the DomainEventHandler starts the workflow. Activities are ONLY invoked from within workflows (see activity invocation diagram below).
209
+
210
+ > For activity invocations:
211
+
212
+ ```mermaid
213
+ sequenceDiagram
214
+ participant Temporal as Temporal Server
215
+ participant Worker as Module Worker
216
+ participant Activity as ActivityImpl
217
+ participant Repo as Repository
218
+
219
+ Note over Temporal,Repo: Activities are ONLY invoked from workflows via Temporal stubs — never from handlers
220
+ Temporal->>Worker: schedule ActivityName
221
+ Worker->>Activity: execute(input)
222
+ Activity->>Repo: findById(id)
223
+ Repo-->>Activity: entity
224
+ Activity->>Activity: businessLogic()
225
+ Activity->>Repo: save(entity)
226
+ Activity-->>Worker: result
227
+ Worker-->>Temporal: complete(result)
228
+ ```
229
+
230
+ ## Use Cases
231
+ [One `###` per useCase in exposes:]
232
+
233
+ ### {UseCaseName}
234
+ **Type:** `HTTP`
235
+ **What it does:** [detailed business logic description]
236
+ **Preconditions:** [valid states, entities that must exist]
237
+ **Postconditions:** [system state after successful execution]
238
+ **Invariants verified:** [ID list]
239
+ **Validations and errors:** [exception conditions]
240
+ **Events emitted:** [{EventName} → triggers {WorkflowName}, or "none"]
241
+ **Operations:**
242
+ 1. [Load entity by id via {Repository}.findById() — throw NotFoundException if absent]
243
+ 2. [Call {PortName}.{method}() to obtain cross-module data — if applicable]
244
+ 3. [Invoke entity.{domainMethod}() — domain enforces invariants]
245
+ 4. [Persist via {Repository}.save(entity)]
246
+ 5. [DomainEventHandler publishes event → Temporal starts {WorkflowName} — if applicable]
247
+
248
+ ## Activities Exposed
249
+ [One `###` per activity in activities:]
250
+
251
+ ### {ActivityName}
252
+ **Type:** `light` | `heavy`
253
+ **Invoked by:** [{WorkflowName} from system.yaml or internal workflow]
254
+ **Input:** [fields with types and descriptions]
255
+ **Output:** [fields with types, or "void"]
256
+ **Compensation:** [{compensation activity} or "none — irreversible"]
257
+ **What it does:** [detailed business logic]
258
+ **Invariants verified:** [ID list]
259
+ **Operations:**
260
+ 1. [Load entity by id via {Repository}.findById() — throw ApplicationFailure if absent (workflow handles)]
261
+ 2. [Call {PortName}.{method}() — if applicable]
262
+ 3. [Invoke entity.{domainMethod}() — domain enforces invariants]
263
+ 4. [Persist via {Repository}.save(entity)]
264
+ 5. [Return {OutputType} to workflow]
265
+ **Data access:** [repositories and operations performed]
266
+
267
+ **Flow diagram:**
268
+ ```mermaid
269
+ flowchart TD
270
+ IN["⚡ ActivityName invoked by WorkflowName"] --> CHECK{"Validate invariants"}
271
+ CHECK -->|"violated"| ERR[/"Exception → workflow handles"/]
272
+ CHECK -->|"passed"| BIZ["Execute business logic"]
273
+ BIZ --> SAVE["Persist changes"]
274
+ SAVE --> OUT["Return result to workflow"]
275
+ ```
276
+
277
+ ## Exposed Endpoints
278
+ [One `###` per endpoint]
279
+
280
+ ### {METHOD} {/path}
281
+ **Use case:** `{UseCase}`
282
+ **Purpose:** [description]
283
+ **Path params:** _(omit table if none)_
284
+
285
+ | Param | Type | Description |
286
+ |-------|------|-------------|
287
+ | {param} | `String` | [description] |
288
+
289
+ **Query params:** _(GET / DELETE only — omit table if none)_
290
+
291
+ | Param | Type | Required | Default | Description |
292
+ |-------|------|----------|---------|-------------|
293
+ | {param} | `String` | No | — | [description] |
294
+
295
+ **Request body:** _(POST / PUT / PATCH only — omit for GET / DELETE)_
296
+ ```json
297
+ {
298
+ "field": "String", // required — [constraint]
299
+ "otherField": "Integer" // optional — [constraint]
300
+ }
301
+ ```
302
+
303
+ **Response schema:** _(GET single only — omit for mutations)_
304
+ ```json
305
+ {
306
+ "id": "String",
307
+ "field": "Type" // [business meaning]
308
+ }
309
+ ```
310
+ _(For GET list: `{ "content": [...], "totalElements": "Long", "page": "Integer", "size": "Integer" }`)_
311
+
312
+ **Errors:**
313
+
314
+ | Status | Condition |
315
+ |--------|-----------|
316
+ | 404 | [entity] not found |
317
+ | 400 | [validation failure] |
318
+ | 409 | [invariant violated] |
319
+
320
+ ## Single-Module Workflows
321
+ [Only if workflows: in domain.yaml]
322
+
323
+ ### {WorkflowName}
324
+ **Trigger:** [internal event or condition]
325
+ **Task Queue:** [{QUEUE_NAME}]
326
+ **Purpose:** [why this internal workflow exists]
327
+ **Steps:**
328
+ 1. [Step description]
329
+ 2. [Step description]
330
+
331
+ ## Ports (External Services)
332
+ [Only if ports: in domain.yaml]
333
+
334
+ ### {PortName} → {target}
335
+ **When called:** [in which activity]
336
+ **Endpoints used:** [METHOD /path list]
337
+ **Data obtained and how it's used:** [description]
338
+ ```
339
+
340
+ ---
341
+
342
+ ### Rules for module specifications
343
+
344
+ - **All in English**: titles, sections, descriptions, invariants, use cases.
345
+ - **MANDATORY invariants**: at least 2–3 per module. Analyze uniqueness, valid states, ranges, transition preconditions.
346
+ - **MANDATORY interaction diagram**: all endpoints, activities, and events.
347
+ - **MANDATORY sequence diagram**: at least one covering the happy path. Additional for branching (error, compensation).
348
+ - **Flow diagram per use case and activity**: `flowchart TD` with trigger, invariants, logic, and output.
349
+ - **State machine**: only if entities have lifecycle. Transition restrictions are implicit invariants.
350
+ - **Reference invariants** in each use case and activity (INV-01, INV-02...).
351
+ - **Endpoints with rich contracts**: for each endpoint, separate path params, query params, body, and response into distinct blocks. Use real domain field names and types — never generic placeholders. GET endpoints must include the JSON response schema; POST/PUT/PATCH must include the JSON body. List endpoints include pagination wrapper `{ content, totalElements, page, size }`.
352
+ - **Operations in use cases and activities**: the `**Operations:**` field is **mandatory** in each `### {UseCase}` and `### {ActivityName}`. Lists the handler/activity steps with concrete names: repository, port, domain method, event, and workflow. Acts as an evaluable implementation specification for human reviewers before code generation.
353
+ - Files in `system/{module-name}.md`.
@@ -0,0 +1,326 @@
1
+ # Temporal system.yaml — Complete Specification
2
+
3
+ Reference for building and validating `system/system.yaml` in a Temporal-based system.
4
+
5
+ > **PATH RULE:** The file MUST be saved as `system/system.yaml` — inside the `system/` directory at the project root. NEVER save as `system.yaml` at the project root.
6
+
7
+ ---
8
+
9
+ ## Complete structure
10
+
11
+ ```yaml
12
+ system:
13
+ name: project-name # kebab-case
14
+ groupId: com.example
15
+ javaVersion: 21
16
+ springBootVersion: 3.5.5
17
+ database: postgresql # h2 | postgresql | mysql
18
+
19
+ # ─── Temporal replaces both messaging (Kafka) and sync (Feign) ───────────────
20
+ orchestration:
21
+ enabled: true
22
+ engine: temporal
23
+ temporal:
24
+ target: localhost:7233
25
+ namespace: project-name
26
+ # Task queues are module-prefixed (module-scoped):
27
+ # {MODULE}_WORKFLOW_QUEUE — Workflows of the module
28
+ # {MODULE}_LIGHT_TASK_QUEUE — Fast activities (< 30s)
29
+ # {MODULE}_HEAVY_TASK_QUEUE — Heavy activities (up to 2min)
30
+
31
+ modules:
32
+ - name: orders # plural, kebab-case
33
+ description: "Order lifecycle management"
34
+ exposes:
35
+ - method: GET # GET | POST | PUT | PATCH | DELETE
36
+ path: /orders/{id}
37
+ useCase: GetOrder
38
+ description: "Get order by ID"
39
+ - method: POST
40
+ path: /orders
41
+ useCase: CreateOrder
42
+ description: "Create a new order"
43
+
44
+ - name: notifications
45
+ description: "Notification delivery service"
46
+ # No REST endpoints — only exposes activities
47
+
48
+ # ─── WORKFLOWS: Cross-module business flows orchestrated by Temporal ─────────
49
+ # Only REAL business flows — no data-sync workflows.
50
+ # Cross-module data is obtained on-demand with Remote Activities (reads).
51
+ workflows:
52
+
53
+ - name: PlaceOrderWorkflow
54
+ trigger:
55
+ module: orders # Module that triggers this workflow
56
+ on: create # Business event: create | cancel | confirm | etc.
57
+ taskQueue: ORDER_WORKFLOW_QUEUE
58
+ saga: true # Enables compensation on failure
59
+ steps:
60
+ - activity: GetOrderDetails
61
+ target: orders # Module that owns this activity
62
+ type: sync # sync = wait for result | async = fire-and-forget
63
+ input: [orderId]
64
+ output: [customerId, items, totalAmount]
65
+ timeout: 5s
66
+
67
+ - activity: GetCustomerById
68
+ target: customers
69
+ type: sync
70
+ input: [customerId]
71
+ output: [customerId, firstName, lastName, email]
72
+ timeout: 5s
73
+
74
+ - activity: ReserveStock
75
+ target: inventory
76
+ type: sync
77
+ input: [orderId, items]
78
+ compensation: ReleaseStock # Activity to call on saga rollback
79
+ timeout: 10s
80
+
81
+ - activity: ProcessOrderPayment
82
+ target: payments
83
+ type: sync
84
+ input: [orderId, customerId, totalAmount]
85
+ output: [paymentId]
86
+ compensation: RefundPayment
87
+ timeout: 30s
88
+
89
+ - activity: ConfirmOrder
90
+ target: orders
91
+ type: sync
92
+ input: [orderId]
93
+
94
+ - activity: NotifyOrderPlaced
95
+ target: notifications
96
+ type: async # Fire-and-forget — does NOT block saga
97
+ input: [orderId, email, firstName, totalAmount]
98
+ ```
99
+
100
+ ---
101
+
102
+ ## Sections NOT present in Temporal system.yaml
103
+
104
+ These sections from broker-based systems are **replaced** by Temporal:
105
+
106
+ | Absent section | Replacement |
107
+ |---|---|
108
+ | `messaging:` | `orchestration:` |
109
+ | `integrations.async:` | `workflows:` with cross-module steps |
110
+ | `integrations.sync:` | `workflows:` with Remote Activity steps |
111
+
112
+ ---
113
+
114
+ ## Naming conventions
115
+
116
+ | Element | Convention | Valid example | Invalid example |
117
+ |---|---|---|---|
118
+ | Modules | plural, kebab-case | `orders`, `order-items` | `Order`, `order_items` |
119
+ | Workflows | PascalCase + `Workflow` | `PlaceOrderWorkflow` | `placeOrderWorkflow` |
120
+ | Activities | PascalCase, verb + noun | `ReserveStock`, `GetCustomerById` | `reserveStock` |
121
+ | Task Queues | SCREAMING_SNAKE_CASE | `ORDER_WORKFLOW_QUEUE` | `order-queue` |
122
+ | Events (in domain.yaml) | PascalCase + past + `Event` | `OrderPlacedEvent` | `PlaceOrderEvent` |
123
+ | useCases | PascalCase, verb + noun | `CreateOrder`, `ConfirmOrder` | `createOrder` |
124
+
125
+ ### Task Queue naming
126
+
127
+ ```
128
+ {MODULE_SCREAMING_SNAKE}_WORKFLOW_QUEUE → ORDER_WORKFLOW_QUEUE
129
+ {MODULE_SCREAMING_SNAKE}_LIGHT_TASK_QUEUE → CUSTOMER_LIGHT_TASK_QUEUE
130
+ {MODULE_SCREAMING_SNAKE}_HEAVY_TASK_QUEUE → PAYMENT_HEAVY_TASK_QUEUE
131
+ ```
132
+
133
+ ### Activity naming
134
+
135
+ | Type | Pattern | Example |
136
+ |------|---------|---------|
137
+ | Read singular | `Get{Entity}ById` | `GetCustomerById` |
138
+ | Read batch | `Get{Entities}ByIds` | `GetProductsByIds` |
139
+ | Write | `{Verb}{Noun}` | `ReserveStock`, `ProcessOrderPayment` |
140
+ | Compensation | `{InverseVerb}{Noun}` | `ReleaseStock`, `RefundPayment` |
141
+ | Reactor | `Notify{Event}` | `NotifyOrderPlaced` |
142
+ | Local | `{Verb}{Noun}` | `ConfirmOrder`, `RetryCharge` |
143
+
144
+ ### Workflow naming
145
+
146
+ ```
147
+ {Verb}{Entity}Workflow → PlaceOrderWorkflow
148
+ {Entity}{Event}Workflow → ProductCreatedWorkflow
149
+ ```
150
+
151
+ ---
152
+
153
+ ## Workflow step properties
154
+
155
+ | Property | Required | Description |
156
+ |---|---|---|
157
+ | `activity` | ✅ | Name of the activity to invoke |
158
+ | `target` | ✅ | Module that owns the activity |
159
+ | `type` | ✅ | `sync` (wait for result) or `async` (fire-and-forget) |
160
+ | `input` | ✅ | List of input field names |
161
+ | `output` | ❌ | List of output field names (for sync steps that return data) |
162
+ | `compensation` | ❌ | Activity name to call on saga rollback |
163
+ | `timeout` | ❌ | Step timeout (e.g., `10s`, `30s`, `2m`) |
164
+ | `optional` | ❌ | `true` if the step can fail without failing the saga |
165
+ | `parallel` | ❌ | `true` to execute in parallel with adjacent parallel steps |
166
+
167
+ ### Parallel steps
168
+
169
+ Steps marked `parallel: true` are executed concurrently using `Async.function()`:
170
+
171
+ ```yaml
172
+ steps:
173
+ - activity: GetProductsByIds
174
+ target: products
175
+ type: sync
176
+ parallel: true # ⎫ executed in parallel
177
+ - activity: ReserveStock # ⎭
178
+ target: inventory
179
+ type: sync
180
+ parallel: true
181
+ - activity: ProcessOrderPayment # after both parallel steps
182
+ target: payments
183
+ type: sync
184
+ ```
185
+
186
+ ---
187
+
188
+ ## Structural restrictions
189
+
190
+ - ❌ **No `messaging:` section** — Temporal replaces Kafka/RabbitMQ
191
+ - ❌ **No `integrations:` section** — replaced by `workflows:`
192
+ - ❌ **No data-sync workflows** — use on-demand reads via Activities
193
+ - ❌ **No activities that do cross-module lookups** — workflow assembles data
194
+ - ✅ Each workflow step `target` must reference an existing module in `modules:`
195
+ - ✅ `compensation:` activities must be declared in the target module's domain.yaml
196
+ - ✅ `saga: true` workflows should have `compensation:` on reversible steps
197
+ - ✅ `type: async` only for non-critical steps (notifications, analytics)
198
+ - ✅ `ports:` only for external services (not between internal modules)
199
+ - ✅ All content in English
200
+
201
+ ---
202
+
203
+ ## Workflow patterns
204
+
205
+ ### Pattern 1: Saga with Compensation
206
+
207
+ Multi-step flow where failure of a step reverses the previous ones.
208
+
209
+ ```yaml
210
+ workflows:
211
+ - name: PlaceOrderWorkflow
212
+ saga: true
213
+ steps:
214
+ - activity: ReserveStock
215
+ compensation: ReleaseStock
216
+ - activity: ProcessOrderPayment
217
+ compensation: RefundPayment
218
+ - activity: ConfirmOrder # last step — no compensation needed
219
+ ```
220
+
221
+ ### Pattern 2: Enrichment + Action
222
+
223
+ Obtain read data before executing the main action.
224
+
225
+ ```yaml
226
+ steps:
227
+ - activity: GetCustomerById # read (enrichment)
228
+ output: [firstName, email]
229
+ - activity: ProcessOrderPayment # action (uses enrichment data)
230
+ input: [orderId, customerId, totalAmount]
231
+ ```
232
+
233
+ ### Pattern 3: Parallel Steps
234
+
235
+ Execute independent steps simultaneously.
236
+
237
+ ```yaml
238
+ steps:
239
+ - activity: GetProductsByIds
240
+ parallel: true
241
+ - activity: ReserveStock
242
+ parallel: true
243
+ - activity: ProcessOrderPayment # after both complete
244
+ ```
245
+
246
+ ### Pattern 4: Single Business Effect
247
+
248
+ An event triggers a single action in another module.
249
+
250
+ ```yaml
251
+ workflows:
252
+ - name: ProductCreatedWorkflow
253
+ trigger:
254
+ module: products
255
+ on: create
256
+ steps:
257
+ - activity: InitializeStock
258
+ compensation: DeleteStock
259
+ ```
260
+
261
+ ### Pattern 5: Non-Blocking Notification
262
+
263
+ Last step, doesn't affect saga outcome.
264
+
265
+ ```yaml
266
+ steps:
267
+ - activity: NotifyOrderPlaced
268
+ type: async # fire-and-forget
269
+ # NO compensation — failure doesn't reverse the saga
270
+ ```
271
+
272
+ ---
273
+
274
+ ## useCases — naming patterns
275
+
276
+ ### Verbs by operation type
277
+
278
+ | Operation | Recommended verbs | Example |
279
+ |---|---|---|
280
+ | Create resource | `Create` | `CreateOrder` |
281
+ | Update | `Update` | `UpdateOrder` |
282
+ | Delete | `Delete` | `DeleteOrder` |
283
+ | Get by ID | `Get` | `GetOrder` |
284
+ | List with pagination | `FindAll` | `FindAllOrders` |
285
+ | State transition | `Confirm`, `Cancel`, `Approve` | `ConfirmOrder` |
286
+ | Punctual action | `Send`, `Process`, `Calculate` | `ProcessPayment` |
287
+
288
+ ### CRUD standard — generates complete implementation:
289
+
290
+ | Pattern | HTTP | Implementation |
291
+ |---|---|---|
292
+ | `Create{Aggregate}` | POST `/resource` | Complete handler |
293
+ | `Update{Aggregate}` | PUT `/resource/{id}` | Complete handler |
294
+ | `Delete{Aggregate}` | DELETE `/resource/{id}` | Complete handler |
295
+ | `Get{Aggregate}` | GET `/resource/{id}` | Complete handler |
296
+ | `FindAll{PluralAggregate}` | GET `/resource` | Complete handler |
297
+
298
+ ### Business useCases — generates scaffold:
299
+
300
+ ```java
301
+ public class ConfirmOrderCommandHandler implements CommandHandler<ConfirmOrderCommand, Void> {
302
+ @Override
303
+ public Void handle(ConfirmOrderCommand command) {
304
+ throw new UnsupportedOperationException("ConfirmOrderCommandHandler not implemented yet");
305
+ }
306
+ }
307
+ ```
308
+
309
+ ---
310
+
311
+ ## Validation checklist
312
+
313
+ - [ ] Modules in plural kebab-case
314
+ - [ ] `orchestration:` section present with `engine: temporal`
315
+ - [ ] No `messaging:` section
316
+ - [ ] No `integrations:` section
317
+ - [ ] All workflow steps have `activity:`, `target:`, `type:`
318
+ - [ ] All `target:` modules exist in `modules:`
319
+ - [ ] Saga workflows have `saga: true`
320
+ - [ ] Reversible steps in sagas have `compensation:`
321
+ - [ ] `type: async` only for non-critical steps
322
+ - [ ] No data-sync workflows
323
+ - [ ] Task queues follow module-prefixed naming
324
+ - [ ] useCases in PascalCase
325
+ - [ ] All content in English
326
+ - [ ] File saved inside `system/` directory as `system/system.yaml` (NEVER at the project root)