可落地的DDD(7)-戰術設計上的一些誤區

来源:https://www.cnblogs.com/stoneFang/archive/2022/07/15/16480628.html
-Advertisement-
Play Games

幾年前我總結過DDD戰術設計的一些可落地的經驗,現在回過頭來發現,當初對這些概念的理解還是沒有到位。比如戰術設計的各個模塊是如協作的。哪些是問題空間問題,哪些是解方案空間問題 這篇文章重新闡述下。 ...


背景

幾年前我總結過DDD戰術設計的一些落地經驗可落地的DDD(5)-戰術設計,和一次關於聚合根的激烈討論最近兩年有些新的落地體驗,回過頭來發現,當初對這些概念的理解還是沒有深入,這篇文章重新闡述下。

之前理解不到位的點有

  1. 戰術設計的各個模塊是的協作關係
  2. 哪些是問題空間問題,哪些是方案空間問題邊界沒有劃分清楚。
  3. 實體和聚合根的區別理解不不深刻,實體和聚合根建模的方法不對。

以上問題將會在下文解釋清楚。

戰術設計拆解

DDD的戰術設計即設計某個子域的領域模型以及代碼落地。領域事件、領域對象、聚合根、實體、值對象、領域服務、工廠、資源庫等這些概念都屬於這個範疇。

筆者將這些概念重新分層組裝了下,如下圖所示。

DDD戰術設計-個人理解版 (3).png
首先將整體分成兩部分,問題空間和方案空間。

  1. 問題空間即領域建模。是對業務問題的描述,以及我們如何對這些問題進行抽象。這些是需要在業務、產品、開發都必須達成一致的,與具體的技術方案無關。
  2. 方案空間即如何用技術手段來解決問題,與具體技術的實現有關。

問題空間即領域建模,是通過實體、值對象、領域服務、領域事件來表達。

  1. 實體和值對象是模型對象,實體是重中之重,包括核心模型數據、行為、狀態。之所以要區分實體和值對象,是為了降低複雜度,因為值對象是個常數對象,不需要花太多精力。
    註意某個對象在某個領域內是個值對象,在另外的領域可能是個實體,所以脫離領域上下文,說某個對象是值對象,肯定是不對的,比如大家常說的地址是個值對象,這一定是對的嗎?

  2. 領域事件即實體產生的事件

  3. 領域服務包括一些邏輯的計算,和業務策略。比如商業決策邏輯、業務流程等。

方案空間即如何解決問題,實現領域模型與代碼的映射。實現設計與實現的一致性。主要通過工廠,聚合,資源庫來表達。

  1. 聚合是對實體、值對象的封裝。領域外部對領域對象所有訪問都基於聚合來。如基礎設施層操作聚合進行數據保存。其他領域引用聚合對象數據。
    聚合的設計一般是圍繞著技術來的,比如聚合對象事務性。

  2. 工廠,複雜對象的創建工廠類

  3. 資源庫,對聚合的操作。

從筆者的實踐角度來說,落地DDD過程中,問題空間比方案空間更重要,收益更大。因為通常我們吐槽的某些代碼寫的爛,貧血模型。背後並不是因為沒有用DDD,而是問題空間沒有定義好,對於業務沒有深刻理解,導致模型抽象不足。

如何建模

為什麼要建模

通常在某個子域落地DDD,我們會按照業務分析-》用例分析-》領域建模(問題空間) -》技術落地(方案空間)這些步驟來操作。但其實即使我們不在代碼里落地DDD,只用前面3步維護一個子域內的領域模型也同樣能夠帶來很多收益,包括但不限於

  1. 統一業務組各個角色的認知,業務、產品、開發大家對同一概念的認知是一致的。
  2. 指導開發工作的拆分。

比如在淘寶有個血的教訓,至今這個歷史債還無法被修複。早期在淘寶開店。一個賣家只能開一個店。賣家和店鋪是兩個領域對象,關係是1:1。店鋪服務覺得是1:1的關係,對外提供的服務有根據sellerId獲取店鋪信息,所以其他調用方就無意識的直接引用了賣家id,這樣也可以拿到店鋪。導致shopId被等同於了sellerID。這個誤引用發生在成千上萬個地方,最後導致後續需要支持一個賣家開多店鋪時無法支持。只能通過其他trick方式實現。

以之前介紹過的CRM領域 來講解。
省略業務分析,直接拿到用例。

用例分析

線上教育crm用例.png
按用戶角色羅列所有的用例,用來推導模型、以及模型之間的關係。領域模型建立好了,需要根據列出的用例來走查一遍,要確保所有的用例都能走通。完整的用例集才能推導出正確的模型,所以當有變化時,首先調整用例集,再來修改領域模型

建模

領域建模就是定義模型對象,以及模型對象之間的關聯關係。分兩步建模,第一步通過名詞找模型對象。第二步通過動詞、形容詞分析對象關聯關係

名詞

通常反覆出現的主語和賓語中的名詞就是模型對象,比如市場人員創建一個活動,活動就是一個模型對象。當然定語中出現的名詞也可能是模型對象。

1.名詞的定義一定要清晰。比如說crm領域有通用的名詞叫商機。但是你對口的產品經理不熟悉crm領域,新造了一個詞,那你要及早糾正他。

2.名詞的含義在限界上下文內語義唯一,在不同的上下文中概念就不一定一樣了。比如市場人員創建的活動,和做營銷時創建的活動就不一定。

動詞、活動

1個市場人員可以創建多個活動,所以市場人員和活動關聯關係是1對多。兩者獨立存在,普通關聯關係。

這裡為了簡化描述,只列了市場活動、線索、客戶、商機這些域。用戶、角色、許可權、數據分析這些域先忽略了。

線上教育crm領域模型 (1).png

產出物

在推導的過程中,我們是按照自底向上的方式推導的,最後我們呈現出來的結果是按照如下方式

  1. 領功能變數名稱詞
    市場活動: 市場人員為了展示公司形象、推廣公司產品,獲取線索而舉辦的活動。一個活動中可以創建多個線索。

線索: 銷售人員基於線索發掘潛在客戶,多個線索轉換為一個客戶。線索可以由一個市場活動生成,或者其他渠道。

客戶:有意向購買公司產品的用戶,銷售人員可以通過跟進客戶,轉化銷售機會。

銷售機會:更高質量的線索,有機會簽單。可以通過客戶轉換得到,也可以通過其他渠道來獲取

  1. 領域模型
    如上圖

  2. 主要領域狀態轉換。
    因為複雜的領域對象生命周期以及一些跨領域對象交互情況在領域模型圖中表達不出來,所以需要藉助額外的圖來表達。

線上教育crm領域狀態.png


您的分享是我們最大的動力!

-Advertisement-
Play Games
更多相關文章
  • 【2022年7月15日,杭州】HUAWEI Developer Day(華為開發者日,簡稱HDD)杭州站拉開帷幕。在數字經濟不斷發展的今天,開發者對圖形圖像的開發需求更加深入和多樣化,從虛擬環境重構到用戶交互再到視覺呈現,開發者對於數字世界存在一個完整的需求鏈條。在HMS Core.Sparkle應 ...
  • 目前很多應用都有身份證、銀行卡一鍵識別功能,但面對各種會員卡、通行證、駕駛證、行駛證等日常生活中經常用到的卡證,因為不同商家的卡號位置,版面樣式各異,所以無法使用類似身份證的專門的身份證識別API,如果要在旅游類App、商超類App等手動輸入卡證號碼,不僅繁瑣還容易出錯,沒有很好的交互體驗。此時,使 ...
  • 生命周期 組件從開始到結束的全過程 創建階段:beforeCreate、created 掛載階段:beforeMount、mounted 更新階段:beforeUpdate、updated 銷毀階段:beforeDestroy、destroyed 與動態組件有關的兩個特殊的鉤子: activated ...
  • 自己的官方模板一直沒有弄,今天看到了一個不錯的主題網站,於是果斷尋求方法進行美化,看了不少博客園的博客,發現一些博客非常驚艷,這些基本都屬於自己定製的,於是開始自定義美化起來。 1. 開通javaScript許可權 進入管理>設置>勾選下麵的JS許可權,然後填寫一下開通的理由等待管理員進行審核通過。 2 ...
  • 混合指令(Mixin)用於定義可重覆使用的樣式,避免了使用無語意的 class,比如 .float-left。混合指令可以包含所有的 CSS 規則,絕大部分 Sass 規則,甚至通過參數功能引入變數,輸出多樣化的樣式。 ...
  • 本文簡介 本文主要講解使用 NodeJS 操作 Redis ,順便會先帶一帶 Redis 基礎用法。 在寫本文時,使用 NPM 安裝的 Redis 依賴包已經到了 4.1.0 版本了。我以前用過 2.8 ,這兩個版本在用法上也是有差別的。可能一些老項目還在用老版本的依賴包。所以我會把2個版本的用法都 ...
  • java基礎知識圖解 軟體開發 軟體開發 軟體,即一系列按照特定順序組織的電腦數據和指令的集合。有系統軟體和應用軟體之分。 人機交互方式 圖形化界面(Graphical User Interface GUI):這種方式簡單直觀,使用者易於接受,容易上手操作。 命令行方式(Command Line ...
  • 利用spring boot多數據源功能,可以同時支持不同類型資料庫mysql,oracle,postsql,sql server等,以及相同類型資料庫不同的schema。 ...
一周排行
    -Advertisement-
    Play Games
  • 移動開發(一):使用.NET MAUI開發第一個安卓APP 對於工作多年的C#程式員來說,近來想嘗試開發一款安卓APP,考慮了很久最終選擇使用.NET MAUI這個微軟官方的框架來嘗試體驗開發安卓APP,畢竟是使用Visual Studio開發工具,使用起來也比較的順手,結合微軟官方的教程進行了安卓 ...
  • 前言 QuestPDF 是一個開源 .NET 庫,用於生成 PDF 文檔。使用了C# Fluent API方式可簡化開發、減少錯誤並提高工作效率。利用它可以輕鬆生成 PDF 報告、發票、導出文件等。 項目介紹 QuestPDF 是一個革命性的開源 .NET 庫,它徹底改變了我們生成 PDF 文檔的方 ...
  • 項目地址 項目後端地址: https://github.com/ZyPLJ/ZYTteeHole 項目前端頁面地址: ZyPLJ/TreeHoleVue (github.com) https://github.com/ZyPLJ/TreeHoleVue 目前項目測試訪問地址: http://tree ...
  • 話不多說,直接開乾 一.下載 1.官方鏈接下載: https://www.microsoft.com/zh-cn/sql-server/sql-server-downloads 2.在下載目錄中找到下麵這個小的安裝包 SQL2022-SSEI-Dev.exe,運行開始下載SQL server; 二. ...
  • 前言 隨著物聯網(IoT)技術的迅猛發展,MQTT(消息隊列遙測傳輸)協議憑藉其輕量級和高效性,已成為眾多物聯網應用的首選通信標準。 MQTTnet 作為一個高性能的 .NET 開源庫,為 .NET 平臺上的 MQTT 客戶端與伺服器開發提供了強大的支持。 本文將全面介紹 MQTTnet 的核心功能 ...
  • Serilog支持多種接收器用於日誌存儲,增強器用於添加屬性,LogContext管理動態屬性,支持多種輸出格式包括純文本、JSON及ExpressionTemplate。還提供了自定義格式化選項,適用於不同需求。 ...
  • 目錄簡介獲取 HTML 文檔解析 HTML 文檔測試參考文章 簡介 動態內容網站使用 JavaScript 腳本動態檢索和渲染數據,爬取信息時需要模擬瀏覽器行為,否則獲取到的源碼基本是空的。 本文使用的爬取步驟如下: 使用 Selenium 獲取渲染後的 HTML 文檔 使用 HtmlAgility ...
  • 1.前言 什麼是熱更新 游戲或者軟體更新時,無需重新下載客戶端進行安裝,而是在應用程式啟動的情況下,在內部進行資源或者代碼更新 Unity目前常用熱更新解決方案 HybridCLR,Xlua,ILRuntime等 Unity目前常用資源管理解決方案 AssetBundles,Addressable, ...
  • 本文章主要是在C# ASP.NET Core Web API框架實現向手機發送驗證碼簡訊功能。這裡我選擇是一個互億無線簡訊驗證碼平臺,其實像阿裡雲,騰訊雲上面也可以。 首先我們先去 互億無線 https://www.ihuyi.com/api/sms.html 去註冊一個賬號 註冊完成賬號後,它會送 ...
  • 通過以下方式可以高效,並保證數據同步的可靠性 1.API設計 使用RESTful設計,確保API端點明確,並使用適當的HTTP方法(如POST用於創建,PUT用於更新)。 設計清晰的請求和響應模型,以確保客戶端能夠理解預期格式。 2.數據驗證 在伺服器端進行嚴格的數據驗證,確保接收到的數據符合預期格 ...