RxJS observable V.S Mobx observable

可觀測資料流的兩大工具PK

Laura Lee
uwillx
9 min readMar 30, 2018

--

這次不是寫 Angular 切版實戰,因為.…..內容實在太龐大了有點難寫(光想要寫個「 如何用 Angular 建立 high order component 」就讓人很頭大)。所以決定先來開小差,寫最近遇到如何用 observable 來處理 Data Flow 的問題。

然後,最近也開始寫 React component,結果發現超好寫(自爆),不禁覺得 Angular 真的要再多加油,如果世界觀再打平一點就好了QQ。

這篇文章建議先有 observable (一種處理非同步工作的工具)的概念再來閱讀,可先看以下文章,他的實例非常好懂:

以前在處理非同步的工作、資料傳遞(像是跟 server API 拿資料、等待結果回傳再進行下一步動作),常用的有 promise 和 async await,observable 跟他們最大的差異,就是能夠

  1. 實現 functional,取得 response 後可直接進行資料 parsing ,直觀好懂
  2. 實現 change listener,一旦訂閱,即可監聽未來所有數值的改變

RxJS observable 用起來像這樣:

由以上可知,我們在 DataStore 先設定了一個可供訂閱的 dataSubject、初始值為 0。ButtonComponentconstructor運作後就會訂閱 dataSubject 的所有變動,一旦變動就把最新的數值存到 data 裡面, 當按鈕按下去,會去呼叫 dataStore.update()dataSubject 存放的數值加一,進而觸發 data 改變。

這裡要注意到一點是,dataStore.dataSubject 只要有任何更新,所有訂閱他的元件都會拿取到最新的數值,這就是 observable 強大的地方,將所有與 dataStore 相關連的元件的資料溝通綁定在一起,不會再有一個動作改 A 元件結果沒改到 B 元件的情況。

Mobx observable 用起來像這樣:

看起來 Mobx 較為直觀好懂,因為他藉由 decorator @ 讓變數有了可被觀測的能力。這裡注意一下我沒有使用 observe(dataStore.data, ...) 因為 observe 只支援觀測物件!如果要觀測 primitive value 要使用 observable box ,文章之後也會提到。

但接下來,將會遇到 Mobx 的弱點:
我們設定一個情境,要觀測資料開始 loading 與 loading完成的過程,加入isDataLoading 標記著資料開始改變到改變結束的狀態。

RxJS

Mobx

這裡會有個情況導致錯誤,observe 只有在 dataStore.data 改變時才會觸發,當我們執行 this.dataStore.update(this.data)因為數值沒改變,observe 無法觸發,將導致 isDataLoading 一直為 true。

必須改寫成:

這裡可看見 dataObservable 是個可觀測的 box 物件,便能使用observe(dataStore.dataObservable, ...) 並且不論數值是否更新,dataObserve.set(v) 都會觸發 observe 變動。

綜合以上想做個結論,一般在處理單純的資料同步上,Mobx 提供相當簡易好用的 coding style,而若牽涉到動作開始與結束、並非單純只要觀測資料數值的情境下,RxJS 提供了較簡單的作法。可在不同的情境上,自由取用合適的工具。譬如 data cache,user 不需知道 data cache 何時開始與結束,就可優先考慮 Mobx ;而頁面資料 API,幾乎都要提示 user 並在載入前後顯示 loading 狀態,就可考慮 observable。

參考資料

--

--

Laura Lee
uwillx

Front-End developer. Love to think about what Front-End can do to benefit the world.