かえるの井戸端雑記

開発日誌的な記事だったり備忘録だったり。まとめ記事と言うよりは、七転八倒の様子を小説みたいに読んで眺めてもらえればと。

Redux DevToolsとの連携

少しおさらい

前回の最後の方に紹介した。Redux DevToolsだけど、このままだとちょっと嬉しくない。

frogwell.hatenablog.jp

何が嬉しくないってRedux DevToolsに問題があるわけじゃなくて、この書き方だと常にRedux DevToolsが機能してしまうという点。さすがに配布versionにはいれなくていいと思うのです。

というわけでうまく切り分けてみようと思う。

directoryを整理

ちょっとdirectory構成を変更。/route以下に直接bundleのindexとなるjsxを配置することにした。

.
├── Makefile
├── config
│   ├── entry.js
│   ├── webpack-dev.config.js
│   ├── webpack-production.config.js
│   └── webpack.config.js
├── package.json
├── pages
│   └── index.html
└── src
    ├── components
    │   ├── HelloWorld
    │       └── index.jsx
    └── route
        └── test.jsx

当然/config/entry.jsも修正。

const path = require('path');
const entry = {
      test: path.resolve(__dirname, '../src/route', "test.jsx"),
};
module.exports = entry;

余計なところが消えた気分に浸れる。実際消えている。はず。

develop modeの時だけonにする条件分岐をいれたい

いじるのはここ。

const initialState = {
  value: null,
};
const store = createStore(
  formReducer,
  initialState,
  window.__REDUX_DEVTOOLS_EXTENSION__ && window.__REDUX_DEVTOOLS_EXTENSION__()
);

何か無いかなあと探してみる。

qiita.com

ふむ。process.env.NODE_ENV === "production"というものがあるのか。で、これはbuildするときにNODE_ENVとかで定義している、と。

あーなんかあった気がする。NODE_ENVの定義で分岐するというやつ。

あ。そもそも/config/ webpack-production.config.jsで使ってた。

  plugins: [
    new webpack.DefinePlugin({
      'process.env.NODE_ENV': JSON.stringify('production')
    }),
    new webpack.optimize.UglifyJsPlugin({
      compress: {
        warnings: false
      }
    })
  ]

mae.chab.in

これを使うと以下のような感じでproductionでないときは消せるのか。

if (process.env.NODE_ENV !== 'production') {
  console.log('development only')
}

良いことを聞いた。とするとこれでいいかな。

if (process.env.NODE_ENV !== 'production') {
  const store = createStore(
    formReducer,
    initialState,
    window.__REDUX_DEVTOOLS_EXTENSION__ && window.__REDUX_DEVTOOLS_EXTENSION__()
  );
}else{
  const store = createStore(
    formReducer,
    initialState
  );
}

……scopeが美しくない。でもまずは動くかどうかの確認だ。

test.jsx:71 Uncaught ReferenceError: store is not defined

駄目であったか。まあconstだからな。むしろ良い。こうなってくれると安心できる。さて修正。三項演算子でいいか。

const store = createStore(
  formReducer,
  initialState,
  (process.env.NODE_ENV !== 'production') ? window.__REDUX_DEVTOOLS_EXTENSION__ && window.__REDUX_DEVTOOLS_EXTENSION__() : undefined
);

さらに美しくないけどこっちは動いた。undefined……まあいいけど……。

createStoreの定義をちゃんと見てみたいなこれ。こういう入力していいのか。たぶんargsで取ってるんだろうけど。

createStore

createStore · Redux

createStore(reducer, [preloadedState], [enhancer])

んなこたぁなかったぜ。

ああ。ふうん。へぇ。enhancerってなんだろ。

[enhancer] (Function): The store enhancer. You may optionally specify it to enhance the store with third-party capabilities such as middleware, time travel, persistence, etc. The only store enhancer that ships with Redux is applyMiddleware().

middlewareを使ってstoreを拡張できると。そりゃdevtoolsみたいなものが入るわけだ。

github.com

今気づいたけどBasic StoreではpreloadedStateをcomment outしてるわ。enhancerじゃないの?

Note that preloadedState argument is optional in Redux' createStore.

ああ別に問題なさそう。sourceも無事通過しているので動作はこれでよし。

じゃあenhancerって何っていうのをもう少し調べてみよう。

enhancer

qiita.com

applyMiddlewareは、redux-promiseやredux-thunkなどのMiddlewareを適用するのに使う関数。applyMiddlewareを使うことでdispatch関数をラップし、actionがreducerに到達する前にmiddlewareがキャッチできるようにする。

enhancerはcreateStoreを引数に受け取って、ラップしたcreateStoreを返す関数。applyMiddlewareの場合、ラップしたdispatch関数を持つstoreを生成するためのcreateStoreを返す。

へぇー。楽しそう。なんか作ってみたい。

memo

githubへの反映などは週末に。