@gravito/satellite-invoice 0.1.5 → 0.2.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 (40) hide show
  1. package/REFACTOR_PLAN.md +238 -0
  2. package/dist/index.js +1097 -56
  3. package/package.json +4 -2
  4. package/package.json.bak +29 -0
  5. package/src/Application/Contexts/InvoiceAuditContext.ts +96 -0
  6. package/src/Application/Contexts/InvoiceCancellationContext.ts +60 -0
  7. package/src/Application/Contexts/InvoiceIssuanceContext.ts +42 -0
  8. package/src/Application/Roles/InvoiceCancellerRole.ts +97 -0
  9. package/src/Application/Roles/InvoiceIssuerRole.ts +72 -0
  10. package/src/Application/Roles/InvoiceTrackerRole.ts +112 -0
  11. package/src/Application/UseCases/CancelInvoice.ts +32 -0
  12. package/src/Application/UseCases/IssueInvoice.ts +13 -26
  13. package/src/Application/UseCases/QueryInvoiceStatus.ts +56 -0
  14. package/src/Domain/Contracts/IInvoiceRepository.ts +3 -0
  15. package/src/Domain/Entities/Invoice.ts +178 -20
  16. package/src/Domain/Errors/InvoiceError.ts +89 -0
  17. package/src/Domain/ValueObjects/InvoiceAmount.ts +86 -0
  18. package/src/Domain/ValueObjects/InvoiceNumber.ts +52 -0
  19. package/src/Domain/ValueObjects/InvoiceStatus.ts +131 -0
  20. package/src/Domain/ValueObjects/InvoiceTax.ts +71 -0
  21. package/src/Infrastructure/Persistence/AtlasInvoiceRepository.ts +135 -6
  22. package/src/Interface/Http/Controllers/AdminInvoiceController.ts +264 -18
  23. package/src/index.ts +57 -3
  24. package/tests/Application/Contexts/InvoiceAuditContext.test.ts +198 -0
  25. package/tests/Application/Contexts/InvoiceCancellationContext.test.ts +232 -0
  26. package/tests/Application/Contexts/InvoiceIssuanceContext.test.ts +180 -0
  27. package/tests/Application/Roles/InvoiceCancellerRole.test.ts +109 -0
  28. package/tests/Application/Roles/InvoiceIssuerRole.test.ts +66 -0
  29. package/tests/Application/Roles/InvoiceTrackerRole.test.ts +126 -0
  30. package/tests/Application/UseCases/CancelInvoice.test.ts +175 -0
  31. package/tests/Application/UseCases/IssueInvoice.test.ts +169 -0
  32. package/tests/Application/UseCases/QueryInvoiceStatus.test.ts +191 -0
  33. package/tests/Domain/Errors/InvoiceError.test.ts +96 -0
  34. package/tests/Domain/ValueObjects/InvoiceAmount.test.ts +84 -0
  35. package/tests/Domain/ValueObjects/InvoiceNumber.test.ts +60 -0
  36. package/tests/Domain/ValueObjects/InvoiceStatus.test.ts +89 -0
  37. package/tests/Domain/ValueObjects/InvoiceTax.test.ts +66 -0
  38. package/tests/Interface/Http/Controllers/AdminInvoiceController.test.ts +294 -0
  39. package/tests/domain.test.ts +244 -0
  40. package/dist/index.d.ts +0 -8
@@ -0,0 +1,238 @@
1
+ # Invoice Satellite - DDD + DCI 重構計畫
2
+
3
+ ## 📋 概述
4
+
5
+ 將 `satellites/invoice` 從基礎 DDD 架構升級為完整的 **DDD + DCI** 實現,引入角色(Roles)和上下文(Contexts)以支持複雜的業務流程編排。
6
+
7
+ ## 🎯 目標
8
+
9
+ - ✅ 強化 Domain 層(ValueObject、Error 類別)
10
+ - ✅ 引入 DCI Roles(InvoiceIssuer、InvoiceCanceller、InvoiceTracker)
11
+ - ✅ 實現 DCI Contexts(InvoiceIssuance、InvoiceCancellation、InvoiceAudit)
12
+ - ✅ 薄殼化 UseCase(委派到 Context)
13
+ - ✅ 完整型別定義(零 `as any`)
14
+ - ✅ 80%+ 測試覆蓋率
15
+
16
+ ## 📊 分段計畫
17
+
18
+ ### Phase 1:Domain 層強化(基礎設施)
19
+
20
+ **檔案清單:**
21
+ 1. `src/Domain/Errors/InvoiceError.ts` - 錯誤基類
22
+ 2. `src/Domain/ValueObjects/InvoiceNumber.ts` - 發票號碼 VO
23
+ 3. `src/Domain/ValueObjects/InvoiceTax.ts` - 稅額 VO
24
+ 4. `src/Domain/ValueObjects/InvoiceAmount.ts` - 金額 VO
25
+ 5. `src/Domain/ValueObjects/InvoiceStatus.ts` - 狀態 VO
26
+ 6. 強化 `src/Domain/Entities/Invoice.ts` - 添加驗證與狀態轉換
27
+
28
+ **改進點:**
29
+ - 提取發票號碼、稅額、金額、狀態為 ValueObject
30
+ - 添加領域錯誤類別(DuplicateInvoice、InvalidAmount、InvalidTransition)
31
+ - 強化 Invoice Entity 的狀態機(cancel()、return()、verify())
32
+ - 移除 mutation,使用不變性模式
33
+
34
+ **預期測試:**
35
+ - VO 單元測試 (20 個)
36
+ - Entity 狀態轉換測試 (15 個)
37
+ - 總計:35 個測試
38
+
39
+ **驗收條件:**
40
+ - [ ] 所有 VO 創建完成
41
+ - [ ] Entity 強化完成
42
+ - [ ] TypeScript 類型檢查通過
43
+ - [ ] 35 個測試全部通過
44
+
45
+ ---
46
+
47
+ ### Phase 2:DCI Roles + Contexts(業務流程編排)
48
+
49
+ #### A. 角色定義(3 個 Roles)
50
+
51
+ **1. InvoiceIssuerRole.ts** - 發票開立者
52
+ ```typescript
53
+ export interface InvoiceIssuerRole {
54
+ generateInvoiceNumber(): string
55
+ calculateTax(amount: number, taxRate: number): number
56
+ validateOrderForInvoicing(orderId: string): Promise<boolean>
57
+ }
58
+ ```
59
+
60
+ **2. InvoiceCancellerRole.ts** - 發票取消者
61
+ ```typescript
62
+ export interface InvoiceCancellerRole {
63
+ validateCancellationEligibility(invoice: Invoice): boolean
64
+ recordCancellationReason(reason: string): void
65
+ notifyRelatedServices(): Promise<void>
66
+ }
67
+ ```
68
+
69
+ **3. InvoiceTrackerRole.ts** - 發票追蹤者
70
+ ```typescript
71
+ export interface InvoiceTrackerRole {
72
+ trackInvoiceStatus(invoiceId: string): Promise<InvoiceStatus>
73
+ auditTrail(invoiceId: string): Promise<AuditLog[]>
74
+ generateReport(startDate: Date, endDate: Date): Promise<InvoiceReport>
75
+ }
76
+ ```
77
+
78
+ #### B. 上下文定義(3 個 Contexts)
79
+
80
+ **1. InvoiceIssuanceContext.ts** - 發票開立流程
81
+ ```typescript
82
+ export class InvoiceIssuanceContext {
83
+ // 參與者
84
+ issuer: InvoiceIssuerRole
85
+ repository: IInvoiceRepository
86
+ eventBus: IEventBus
87
+
88
+ // 編排流程
89
+ async orchestrate(input: IssueInvoiceInput): Promise<Invoice> {
90
+ // 1. 驗證訂單
91
+ // 2. 檢查重複
92
+ // 3. 生成發票號碼
93
+ // 4. 計算稅額
94
+ // 5. 創建 Invoice Entity
95
+ // 6. 保存
96
+ // 7. 發佈事件
97
+ }
98
+ }
99
+ ```
100
+
101
+ **2. InvoiceCancellationContext.ts** - 發票取消流程
102
+ ```typescript
103
+ export class InvoiceCancellationContext {
104
+ // 參與者
105
+ canceller: InvoiceCancellerRole
106
+ repository: IInvoiceRepository
107
+ eventBus: IEventBus
108
+
109
+ // 編排流程
110
+ async orchestrate(invoiceId: string, reason: string): Promise<void> {
111
+ // 1. 查詢 Invoice
112
+ // 2. 驗證取消資格
113
+ // 3. 記錄取消原因
114
+ // 4. 更新狀態為 CANCELLED
115
+ // 5. 通知相關服務
116
+ // 6. 發佈事件
117
+ }
118
+ }
119
+ ```
120
+
121
+ **3. InvoiceAuditContext.ts** - 發票審計追蹤
122
+ ```typescript
123
+ export class InvoiceAuditContext {
124
+ // 參與者
125
+ tracker: InvoiceTrackerRole
126
+ repository: IInvoiceRepository
127
+ auditLog: IAuditLogRepository
128
+
129
+ // 編排流程
130
+ async queryStatus(invoiceId: string): Promise<InvoiceStatus>
131
+ async getAuditTrail(invoiceId: string): Promise<AuditLog[]>
132
+ async generateReport(period: DateRange): Promise<InvoiceReport>
133
+ }
134
+ ```
135
+
136
+ **測試檔案:**
137
+ - `tests/Application/Roles/InvoiceIssuerRole.test.ts` (6 個測試)
138
+ - `tests/Application/Roles/InvoiceCancellerRole.test.ts` (6 個測試)
139
+ - `tests/Application/Roles/InvoiceTrackerRole.test.ts` (5 個測試)
140
+ - `tests/Application/Contexts/InvoiceIssuanceContext.test.ts` (7 個測試)
141
+ - `tests/Application/Contexts/InvoiceCancellationContext.test.ts` (6 個測試)
142
+ - `tests/Application/Contexts/InvoiceAuditContext.test.ts` (5 個測試)
143
+
144
+ **預期測試:**
145
+ - 3 個 Role 角色:17 個測試
146
+ - 3 個 Context 上下文:18 個測試
147
+ - 總計:35 個測試
148
+
149
+ **驗收條件:**
150
+ - [ ] 3 個 Roles 完成 + 注入函式
151
+ - [ ] 3 個 Contexts 完成(完整流程編排)
152
+ - [ ] 35 個測試全部通過
153
+ - [ ] TypeScript 型別檢查通過
154
+ - [ ] 零 `as any`、零 `@ts-expect-error`
155
+
156
+ ---
157
+
158
+ ### Phase 3:UseCase 薄殼化 + 強化 Repository
159
+
160
+ **修改 UseCase:**
161
+ 1. `IssueInvoice.ts` - 委派到 InvoiceIssuanceContext
162
+ 2. `CancelInvoice.ts` - 委派到 InvoiceCancellationContext(新建)
163
+ 3. `QueryInvoiceStatus.ts` - 委派到 InvoiceAuditContext(新建)
164
+
165
+ **強化 Repository:**
166
+ 1. 添加 `findBynvoiceNumber()` - 按發票號碼查詢
167
+ 2. 添加 `findByStatus()` - 按狀態查詢
168
+ 3. 添加 `findByDateRange()` - 按日期範圍查詢
169
+
170
+ **預期測試:**
171
+ - UseCase 集成測試 (9 個)
172
+
173
+ **驗收條件:**
174
+ - [ ] 所有 UseCase 委派到對應 Context
175
+ - [ ] Repository 新增查詢方法
176
+ - [ ] 9 個集成測試通過
177
+
178
+ ---
179
+
180
+ ### Phase 4:Controller 適配 + 清理
181
+
182
+ **改進 Controller:**
183
+ 1. `AdminInvoiceController.ts` - 移除 `as any`、使用 DTO
184
+ 2. 添加錯誤處理(捕捉領域異常)
185
+ 3. 完整的 API 端點(issue、cancel、query、list)
186
+
187
+ **測試:**
188
+ - Controller 單元測試 (8 個)
189
+
190
+ **驗收條件:**
191
+ - [ ] 所有 API 端點完成
192
+ - [ ] 零 `as any`、零 `@ts-expect-error`
193
+ - [ ] 8 個 Controller 測試通過
194
+
195
+ ---
196
+
197
+ ## 📈 預期成果
198
+
199
+ | 階段 | 檔案數 | 測試數 | 主要成果 |
200
+ |------|--------|---------|---------|
201
+ | Phase 1 | 6 | 35 | Domain 層強化 |
202
+ | Phase 2 | 6 + 6 | 35 | Roles + Contexts |
203
+ | Phase 3 | 3 + 1 | 9 | UseCase 薄殼化 |
204
+ | Phase 4 | 1 | 8 | Controller 適配 |
205
+ | **總計** | **~23** | **~87** | **完整 DDD + DCI** |
206
+
207
+ **最終指標:**
208
+ - ✅ 87 個單元/集成測試(100% 通過)
209
+ - ✅ 零 `as any`、零 `@ts-expect-error`
210
+ - ✅ 完整 TypeScript 型別檢查
211
+ - ✅ 100% Domain 層覆蓋率
212
+ - ✅ 80%+ 應用層覆蓋率
213
+
214
+ ---
215
+
216
+ ## 🚀 開始時機
217
+
218
+ **當前狀態:**
219
+ - Worktree 已建立:`worktree-invoice-ddd-dci`
220
+ - 分支名稱:`worktree-invoice-ddd-dci`
221
+ - 位置:`.claude/worktrees/invoice-ddd-dci`
222
+
223
+ **下一步:**
224
+ 1. 執行 Phase 1 - Domain 層強化
225
+ 2. 驗證所有測試通過 (35 個)
226
+ 3. TypeScript 類型檢查通過
227
+ 4. 進入 Phase 2
228
+
229
+ ---
230
+
231
+ ## 📝 注意事項
232
+
233
+ - **不變性原則**:所有 Entity 操作返回新對象,禁止 mutation
234
+ - **錯誤處理**:使用領域錯誤類別,禁止拋出 Error
235
+ - **事件驅動**:重要操作應發佈領域事件
236
+ - **Satellite 隔離**:不與其他 Satellite 直接耦合
237
+ - **代碼風格**:100 字元寬、2 空格、單引號、無分號
238
+