淺談CQRS

CQRS (Command Query Responsibility Segregation) 命令查詢職責分離模式,在談論這個之前必須要先談論OO(Object-Oriented)裡面的CQS(Command Query Separation)因為兩者的概念一樣,只是應用層級不太一樣。

CQS

CQS 使用於寫程式層級,將Object主要分為兩種動作command、query:

  • Command: 指的是改變物件狀態的動作,ex: Create, Update, Delete

  • Query: 指的是不會改變物件狀態的動作,ex: Read.

舉個例子:

function Array() {
    this.arr = []
}

// Insert 屬於 "Command" 因為所執行的事情是將element 存入 arr 中,改變了狀態
Array.prototype.Insert = function (element) {
    this.arr.push(element)
}

// Read 屬於 "Query" 因為只是讀取並未改變Array 整個物件的狀態
Array.prototype.Read = function (index) {
    return this.arr[index]
}

其中CQS 有一個特性,會改變狀態的方法不會回應物件狀態,反之不會改變狀態的回應物件狀態。換句話說command 因為是改變狀態的動作,則會不會有Return ; Query 則會有Return。

CQRS

也別於CQS,CQRS 則是將 Command、Query的概念拉到系統層級,以資料庫中Create, Read, Update, Delete (CRUD) 四個動作為例,大多時候Read才是大量被使用的。而使用CQRS 就能夠輕易的增加Read 用的伺服器,為此增加彈性,並且能夠輕易的做出針對性的效能教調。

舉個例子:

如果將資料庫的存取拆分成Command、Query,資料庫的選擇上會有一些變化,如Command 換成寫入較快的,Query 則換成讀取較快的。透過資料庫本身的Master-slaves 模式就可以進而提昇效能。如下示意圖。

master-slave pattern 指的是主動或者被動的方式將資料同步到其他資料庫

參考資料

[1] https://martinfowler.com/bliki/CQRS.html [2] https://martinfowler.com/bliki/CommandQuerySeparation.html

Last updated