《Domain-Driven Design 領域驅動設計》Podcast 準備稿:突破與隱含概念明確化
書名: 領域驅動設計 Domain-Driven Design(Tackling Complexity in the Heart of Software) 作者: Eric Evans 系列: 啃一本大書(恩普拉氏) 公開標題建議: 啃一本大書|Domain-Driven Design.模型突破:那一刻複雜度突然崩塌 (7/13) 涵蓋範圍: Part III 第8章 突破(Breakthrough)+ 第9章 讓隱含概念明確化(Making Implicit Concepts Explicit)
背景速覽
進入我認為全書最精彩的 Part III「重構邁向深層理解」。前面講的是「怎麼建一個好模型」,這個 Part 講「怎麼讓模型變深」。這集兩章:第8章用一個驚心動魄的銀行聯貸系統真實故事,講什麼是「模型突破」(Breakthrough)——重構的回報不是線性的,有時一個深層洞見會讓複雜度瞬間崩塌;第9章則給出系統化方法:怎麼把藏在程式碼和對話裡的「隱含概念」挖出來、變成模型裡的明確元素。
一句話重點
深層模型不會線性累積——它常以「突破」的形式降臨:一個被壓抑的隱含概念突然被辨識、明確化,複雜度應聲崩塌、表達力暴增;而觸發突破的方法,是系統化地傾聽語言、審視笨拙之處、思考矛盾、閱讀領域書籍。
值得討論的重點
1. 聯貸系統的突破故事:Share Pie
第8章是全書最戲劇性的一章。Evans 做一個銀行聯貸(Syndicated Loan)系統——多家銀行組銀團共同放一筆十億美元的貸款。團隊辛苦四個月做出一個「看似合理」的模型,但麻煩不斷:複雜度持續增加不收斂、出現詭異的捨入不一致(rounding 怎麼算都對不齊)。銀行家不在乎多幾分錢,但不信任算不準每一分錢的軟體。
某一週團隊頓悟:模型把 Facility 份額和 Loan 份額綁死了,但業務上它們可以獨立變化。專家還納悶「你們怎麼現在才懂」。新的洞見是 Share(份額) 是個通用概念,Evans 幾天內畫出 Share Pie 模型——所有份額都拆解成更直覺的份額餅,可以做「份額數學」。結果:Loan Adjustment 不需要了、Loan Investment 消失了(這詞根本不是銀行術語,是團隊自己造的)、最頑固的捨入問題從根源解決、複雜的捨入程式碼直接刪掉。
2. 突破的代價:恐懼與勇氣
Evans 誠實寫出突破的真實感受——不是狂喜,是恐懼。專案已嚴重落後、團隊精疲力竭、那是沒有自動化測試的年代、重構中間幾乎沒有穩定的中繼點。他描述一場難忘的會議:專案經理問「要多久?」(三週)「不做行不行?」(可能可以但不確定)「你們覺得這是對的嗎?」(是,更簡單、更貼業務、長期風險更低)。經理批准了,說他扛壓力。三週後重構順利完成,那些莫名其妙的需求變更停了、第二版的路暢通了。Share Pie 成了整個應用的統一主題、進了統一語言。
3. 挖掘隱含概念的四種方法
第9章把「怎麼觸發突破」系統化。四種挖掘途徑:
- 傾聽語言:專家反覆用某個詞、或聽到某說法眼睛一亮——如果這詞不在設計裡,就是改善契機。航運例子:專家一直講 “itinerary”(行程),系統有所有資料卻沒這個統一概念,把 Itinerary 明確化後好處一串。
- 審視笨拙之處:某段程序複雜又難解釋、每個新需求都讓複雜度飆升——那裡藏著遺漏的概念。利息計算的例子最終挖出 Accrual(應計) 這個缺失的核心概念。
- 思考矛盾:不同專家、甚至同一人前後說法不一致,這些矛盾是通往深層模型的線索(Evans 用伽利略的慣性參考框架類比)。
- 閱讀書籍:領域本身有書(會計入門書教你 Accrual Basis Accounting)、軟體領域也有書(Fowler 的 Analysis Patterns)。
4. 三類常被遺漏的概念:Constraint、Process、Specification
物件導向教我們找「名詞和動詞」,但還有三類概念該明確化:
- Constraint(約束):別把約束藏在程序碼裡。把它抽成有意圖揭示名稱的方法或獨立物件(Bucket 容量限制、Overbooking Policy)。
- Process(流程):用 Service 或 Strategy 表達。判準很簡單:這是專家會談論的事,還是只是電腦程式的機制?
- Specification(規格):Evans 和 Fowler 合作的模式。一個 predicate 式的 Value Object,陳述「對另一個物件狀態的約束」。它統一了三種看似不同的用途——驗證(這張發票逾期嗎)、查詢(找出所有逾期客戶)、按規格建造(化學品該裝什麼容器)。把規則留在領域層、不淹沒物件的清晰語意。
注意事項
⚠️ 別把突破當成可以「規劃」的東西。 Evans 講得很清楚:突破不是技術、是事件,無法強求。挑戰在於「辨認它正在發生、並決定如何應對」。更重要的是——突破通常在許多適度的重構之後才出現。所以不要因為追求突破而癱瘓,先把基本功(消化知識、養統一語言、明確化概念、精煉設計)做好,為突破鋪路。
⚠️ 第9章的「傾聽語言」不是老套的「名詞就是物件」。聽到新詞只是線索,後面還要透過對話和消化知識淬煉出清晰實用的概念。別退化成「把專家講的每個名詞都做成 class」。
⚠️ Specification 模式很強大但容易過度設計。Evans 自己提醒:完整的通用性(AND/OR/NOT 全做)並非總是必要,AND 最常用、複雜度也最低,只實作 AND 沒關係。別為了模式的完美而做一堆用不到的組合邏輯。(這條在第 8 集講柔性設計時會再深化。)
專家補充
💡 第8章的「勇氣與信任」這段,是整本書少見的「軟性」內容,但極其重要。技術上知道該重構是一回事,在落後的專案、沒有測試、團隊燒乾的情況下還敢做,是另一回事。這需要團隊和管理層之間的信任。這也悄悄論證了「為什麼要有自動化測試」——Evans 那次是裸奔成功的,但他明說「那是測試還沒普及的年代」。換成今天,自動化測試就是讓你敢於追求突破的安全網。這條可以接到 TDD、接到 Uncle Bob 的測試紀律。
💡 Accrual(應計)的例子有個很妙的對照:第9章給了兩個版本——一個是專家配合、挖得很深的模型;一個是專家沒空、開發者自己去書店買會計書、挖得淺一點但仍抓到 Accrual 的模型。Evans 想說的是:就算條件不理想,也能往深層模型走一步,後續迭代再精煉。這對「我們沒有領域專家可以一直問」的團隊是很實際的鼓勵。
💡 Specification 模式是 DDD 戰術裡 CP 值很高、卻常被忽略的一個。它在現代很實用——你可以把「VIP 客戶的判定規則」「訂單能否取消的規則」做成 Specification 物件,規則就從散落的 if 變成可命名、可組合、可測試、可重用的領域概念。它和 Repository 結合還能做動態查詢。想找一個「明天就能用」的東西,Specification 是好選擇。
討論問題
🎙️ 開場鉤子:「你有沒有經歷過那種時刻——一個模組你越改越複雜、怎麼都不對勁,然後某天突然『啊我懂了』,整個設計瞬間變簡單?那不是運氣,那是 Evans 說的『模型突破』。這集講它怎麼來、以及來的時候你敢不敢接住它。」
🎙️ 自問自答:「怎麼知道模型裡藏著一個沒被講出來的概念?」——三個訊號:專家反覆講一個你 code 裡沒有的詞;某段程式碼複雜到難以解釋;前後說法互相矛盾。這三個地方,都在喊「這裡缺一個概念」。
🎙️ 帶走的一題:「回想最近一次跟業務方開會,他有沒有講過一個你系統裡『沒有對應物件』的詞?把它記下來——那很可能就是你下一個模型突破的入口。」
更大範圍關聯
- Part III 的開場與方法論:第8章給「為什麼」(突破的威力與代價),第9章給「怎麼做」(挖掘隱含概念的四方法 + 三類概念)。這是全書從「建模型」轉向「深化模型」的轉折點。
- 連到《重構》(Fowler):「重構邁向深層理解」和 Fowler 的《Refactoring》是同源異流——Fowler 重構改善程式碼結構,Evans 重構改善領域模型的深度。觸發點不同:Fowler 看 code smell,Evans 看「模型語言跟領域脫節」。這正是程式碼設計三本要搭讀的關鍵接點(最後一集會收)。
- 連到測試文化:突破需要勇氣,而自動化測試是讓你敢於大膽重構的安全網。這條接 TDD、接 Uncle Bob 的紀律。沒有測試的重構是裸奔。
- Specification 模式的後續:第 8 集(柔性設計)會把 Specification 用 AND/OR/NOT 組合,做成 Composite,這集先打基礎。
錄製建議
- 建議時長:約 26-28 分鐘(兩章,且第8章的故事值得完整講)。配比:聯貸系統突破故事約 12 分(這是全書最有戲劇張力的故事,務必把「四個月→捨入問題→頓悟→恐懼→勇氣→三週成功」這條敘事完整講出來)、挖掘隱含概念四方法約 8 分、三類概念(Constraint/Process/Specification)約 6 分。
- 討論策略:第8章用「說故事」的方式錄,效果會炸裂——它有懸念(捨入怎麼都對不齊)、有轉折(頓悟 Share Pie)、有人性(恐懼與勇氣)、有結局(三週成功)。這是整季最適合「講一個故事」的一集,別把它講成方法論。第9章再切回「所以我們學到什麼方法」。
- 強調這一集的情緒線:DDD 不只是技術,它關乎團隊敢不敢在壓力下追求更好的模型。這是這本書比一般技術書更深的地方。