從增刪改查到事件溯源 - PHP

xuding發表於2021-07-03

增刪改查

如果你是一名 PHP 後端開發,增刪改查(CRUD)對你來說,一定不陌生。簡單來說,它是指對資料庫進行增加,刪除,修改,查閱基本操作。增刪改查是面向資料庫的一種建模方式。PHP 簡直是為增刪改查而生,它語法簡單,無需編譯,ORM 遍地開花,你可以快速地將資料庫表和網頁打通,從而實現增刪改查功能。這種快感給人一種錯覺,似乎這就是一個後端開發者的核心工作。

讓我們用增刪改查的思路,設計一個簡單購物車:

資料庫設計

增刪改查的第一步必然是資料庫設計。為便於演示,我們設計從簡,省去了很多細節,所以千萬不要將這種設計用於你的產品中。我們僅使用一個表 carts 來儲存購物車商品。

db-design.png

演示

當產品 p-1(ID:1)被加入購物車時,在 carts 表中增添一條資料:

demo-1.png

當產品 p-2(ID:2)被加入購物車時,在 carts 表中再次增添一條資料:

demo-2.png

當產品 p-1(ID:1)被再次加入購物車時,更新 carts 表中相應資料:

demo-3.png

當產品 p-2 被移除購物車時,刪除 carts 表中對應資料:

demo-4.png

購物車的內容被實時地記錄在資料庫中,這是增刪改查的主要特徵。

讓我們再來看看另一種截然不同的思想。

事件溯源

事件溯源(Event Sourcing)是領域驅動設計(Domain Driven Design)設計思想中的架構模式之一。領域驅動設計是面向業務的一種建模方式。它幫助我們將注意點放回業務本身。

事件溯源的核心是事件,所有聚合(一種特殊的類)的狀態源頭來自於事件,所以它叫事件溯源。這裡的事件叫做領域事件,與我們通常所講的事件不同的是,領域事件是指領域專家所關心,業務過程中所發生的事情,它與業務息息相關。

讓我們用事件溯源的思想來設計上文中的購物車。

使用領域事件

在購物車這個業務中,假設自己是一個使用者的話,我們最感興趣的幾件事情是將商品加入購物車,將商品移除購物車以及對購物車進行結算。於是我們可以總結出幾個領域事件。值得注意的是,領域事件都應該是過去式。

當產品 p-1(ID:1)被加入購物車時,在 events 表中增添一條事件資料:

de-1.png

當產品 p-2(ID:2)被加入購物車時,在 events 表中增添一條事件資料:

de-2.png

當產品 p-1 被再次加入購物車時,在 events 表中增添一條事件資料:

de-3.png

當產品 p-2 被移除購物車時,仍然在 events 表中增添一條事件資料:

de-4.png

購物車的內容以事件的形式記錄了下來,事件只可追加,不可以刪除或者改動。

讀取購物車商品

當需要展示購物車內容時,重播 events 表中所儲存的事件即可:

read-product.png

擁抱事件溯源

事件溯源要求開發者改變自己的傳統的,以資料庫設計為源頭的思想,從業務開始分析問題。用其開發的系統不僅僅自帶日誌,而且可以以領域事件為中心來方便地排查問題,同時事件驅動建立的聚合模型也非常容易編寫單元測試。

增刪改查並非惡魔

需要補充的是,增刪改查並非一無是處,相反,在適合它的領域,它是非常強大的。在一些領域,增刪改查就是當前的業務。比如一個簡單的 CMS,比如 IoT 專案中對資料的儲存。

結語

本文轉載自【何以解耦】:codedecoupled.com/php-to-ddd.html,如果你也對 TDD,DDD以及簡潔程式碼感興趣,歡迎關注公眾號【何以解耦】,一起探索軟體開發之道。

本作品採用《CC 協議》,轉載必須註明作者和本文連結
Know how, know why meanwhile.

相關文章