JavaScript
reactjs
redux

redux-thunkなのかredux-promiseなのかredux-sagaなのか、それともredux#bindActionCreatorsをやめるのか

More than 1 year has passed since last update.


前提

ここで書くのはあくまで個人的な意見です。

react, reduxはどちらも使い方次第でフレームワークっぽくも使えるし、ただのツールとしても使える。だからreact, reduxを使ったフロントアーキテクチャはいくらでもあっていいと思う。

これはそのうちの一つを提案するものです。

とはいえ特別な実装方式を編み出したわけでは全然なくて、むしろ1周して出戻りしたかんじ。


結論

非同期処理をコンテナ(またはそこで使うモジュール)に書くだけ。

今は、非同期処理をするためのredux middlewareを使ってないです。

過去記事(react, redux周りのパッケージ選定とKPT[2016-05-27現在])にて、この辺についてもなんやかんやと言っているけど、今はthunkもpromiseもsagaも使っていない。その実装が凄くシンプルで気に入ってるので紹介します。


どうやるのか


  1. redux#bindActionCreatorsを使わない。

  2. コンテナにconnectするmapDispatchToPropsで非同期処理を書く


    • 普通にPromiseでかく

    • async/awaitだとより素敵に書ける



  3. api呼び出しやvalidationは、専用のモジュールを切ってそこに書き、それをmapDispatchToPropsで使う。


    • モジュールがactionCreatorを知っててdispatchを委譲する感じで書いてるなう。

    • actionsとイベントと各モジュールは疎結合で、コンテナでDIするイメージ、って実装もあるみたい。

    • どっちが良いか悩み中。。




before, after

dispatchが副作用を持ってたのが

IMG_0807.JPG

非同期処理の発生がコンテナで明示的に書かれたものだけになる。

IMG_0843.JPG


何が幸せ?


  • redux-sagaのような学習コストを必要としない。


    • Promseとasync/awaitには学習コスト払うけど^^;

    • jsやる上で最低限の学習コストだと思ってる



  • redux-thunkやredux-promiseのようにactionsを汚さない


    • actionsは「reduserに何させるか」だけを考えてる



  • reduxがstateを管理するためだけの、ただの関数に成り下がる


    • わかりやすい



  • dispatchが副作用を起こさない


    • わかりやすい



  • action名に悩まない



    • 今までは副作用込みで、「reactから見てどんな振るまいか?」を意識して命名していた。
      reactで何が起こったか、で命名すればいいだけかも。

    • 「reducerに何をさせるか?」だけを考えて命名できるようになった。


      • 例) SET_${state名}



    • 命名しやすいは正義^^



  • connectするmapDispatchToPropsのメソッド名に悩まない


    • on~かhandle~で統一できる

    • 命名しやすいはs



わかりやすいのが一番のメリット。「サーバーサイド寄りのエンジニアにも書いてほしい」っていう前提があったので、よりシンプルな実装を探していた。


経緯

すごくローカルな勉強会に言った時に教えてもらったことを、ほぼ受け売りで書いてる感あります。この記事。

「reactはstateを引数にとって、jsxを返すだけのただの関数。reduxはactionとstateを引数にとって、新しいstateを生むだけのただのreduce関数。どちらもすごくシンプル。副作用を持つべきじゃない。」

衝撃

そしてホワイトボードに描いたのがさっきのafterの図と大体同じ図。

衝撃

その現場ではreact-routerもreact-reduxも使わないらしい。シンプルイズベスト。

衝撃

その衝撃を受け、「でもreact-routerとreact-reduxは使いたいなぁ。ラクしたいなぁぐへへ」ってなって至ったのが、redux#bindActionCreatorsをやめることだった感じ。