2018年は、reduxとeslintとflowとwebpackを捨ててみようと思う

2017年版と2018年版でwebアプリケーション作成時のreactの（マイ）ベストプラクティクスを以下のリポジトリに、まとめてみたので記事にしてみました。

* react-best-practices
 * https://github.com/wheatandcat/react-best-practices/tree/master


ちなみにタイトルは、その過程で2018年版に削除したpackageです（理由は後述）


# github
 * サンプルコードの内容は、ログイン/ログアウト + fetchした内容を画面に表示するだけです
    * （ただのサンプルなので、実装はハリボテです）

## 2017年版
 * https://github.com/wheatandcat/react-best-practices/tree/master/2017years

## 2018年版
 * https://github.com/wheatandcat/react-best-practices/tree/master/2018years

# 2017年版と2018年版で使用しているpackageの比較

## 2017年版で使用しているpackage
 * [react](https://github.com/facebook/react)
 * [redux](https://github.com/reactjs/redux)
 * [redux-saga](https://github.com/redux-saga/redux-saga)
 * [redux-localstorage](https://github.com/elgerlambert/redux-localstorage)
 * [recompose](https://github.com/acdlite/recompose)
 * [react-router](https://github.com/ReactTraining/react-router)
 * [styled-components](https://github.com/styled-components/styled-components)
 * [storybook](https://github.com/storybooks/storybook)
 * [eslint](https://github.com/eslint/eslint)
 * [prettier](https://github.com/prettier/prettier)
 * [flow-bin](https://github.com/facebook/flow)
 * [webpack](https://github.com/webpack)

## 2018年版で使用しているpackage
 * [react](https://github.com/facebook/react)
 * [typescript](https://github.com/Microsoft/TypeScript)
 * [react-router](https://github.com/ReactTraining/react-router)
 * [styled-components](https://github.com/styled-components/styled-components)
 * [storybook](https://github.com/storybooks/storybook)
 * [prettier](https://github.com/prettier/prettier)
 * [parcel](https://github.com/parcel-bundler/parcel)

## package差分
### keep
 * [react](https://github.com/facebook/react)
 * [react-router](https://github.com/ReactTraining/react-router)
 * [styled-components](https://github.com/styled-components/styled-components)
 * [storybook](https://github.com/storybooks/storybook)
 * [prettier](https://github.com/prettier/prettier)

### out
 * [redux](https://github.com/reactjs/redux)
 * [redux-saga](https://github.com/redux-saga/redux-saga)
 * [redux-localstorage](https://github.com/elgerlambert/redux-localstorage)
 * [recompose](https://github.com/acdlite/recompose)
 * [eslint](https://github.com/eslint/eslint)
 * [flow-bin](https://github.com/facebook/flow)
 * [webpack](https://github.com/webpack)

### in
 * [typescript](https://github.com/Microsoft/TypeScript)
 * [parcel](https://github.com/parcel-bundler/parcel)


# 解説
・・・という結果になったので、諸々のpackageについて解説、keep / out / inの理由に記載

## keepしたpackage
### [react](https://github.com/facebook/react)
 * これが無いとreactプロジェクトじゃないということで、次へ

### [react-router](https://github.com/ReactTraining/react-router)
 * URL: https://reacttraining.com/react-router/web/guides/philosophy
  * reactのルーティングライブラリ
  * 画面遷移が必要な場合は、ほぼ一択
  * ただ、URLパラメータ周りと不満があるのと、バージョンアップ時に破滅的な修正を入れてくることが、たまにきず

### [styled-components](https://github.com/styled-components/styled-components)
 * URL: https://www.styled-components.com/

```scala
import styled from "styled-components";

const Button = styled.a`
  display: inline-block;
  border-radius: 3px;
  padding: 0.5rem 0;
  margin: 0.5rem 1rem;
  width: 11rem;
  background: transparent;
  color: white;
  border: 2px solid white;
`

render(<Button>ログイン</Button>)
```

  * ↑みたいなコードで、jsに直接cssを書けるライブラリ

### [storybook](https://github.com/storybooks/storybook)
 * URL: https://storybook.js.org/
  * reactコンポーネントをサンドボックスで開発できるライブラリ

### [prettier](https://github.com/prettier/prettier)
 * URL: https://prettier.io/
  * JavaScriptのフォーマッター

## outしたpackage
### redux （+ 関連package） 
 * URL: https://redux.js.org/
  * reactで複雑な状態管理するとき使用するライブラリ

#### 削除したpackage一覧
 * [redux](https://github.com/reactjs/redux)
 * [redux-saga](https://github.com/redux-saga/redux-saga)
 * [redux-localstorage](https://github.com/elgerlambert/redux-localstorage)

#### 削除した理由
  * reduxが本来必要な箇所は、親子関係以外のレイヤーに存在するコンポーネント同士で連携するために必要なものだけど、その動作を実装する機会がほぼ無い
  * ~~というか、アクションしたコンポーネントに対して親子関係以外のコンポーネントが変更されるデザインの方に疑問持った方が良いと思う~~
  * 管理するactionやstoreの値が増えた時のパフォーマンス調整が難しい

#### 2018年版での代替え
  * 2018年版ではコンポーネント内でfetchしてstateに入れるだけのシンプルな実装に変更
    * 実装: [https://github.com/whe.../Connected.tsx#L23-L43](https://github.com/wheatandcat/react-best-practices/blob/master/2018years/src/components/Pages/Welcome/Table/Connected.tsx#L23-L43)
  * また認証のtokenの取得などグローバルに使用したい処理については「contextTypes」で取得できるように実装
    * 定義: [https://github.com/whe.../Auth.js#L6-L14](https://github.com/wheatandcat/react-best-practices/blob/master/2018years/src/containers/Auth.js#L6-L14)
    * 取得: [https://github.com/whe.../Connected.tsx#L24](https://github.com/wheatandcat/react-best-practices/blob/master/2018years/src/components/Pages/Welcome/Table/Connected.tsx#L24)

### [recompose](https://github.com/acdlite/recompose)
 * コンポーネントにHOCを実装をサポートするライブラリです

#### 削除した理由
 * （ライブラリ自体は良いものなので、個人的には推したい気持ちをありますが。。。）
 * ライブラリの性質上、普及率がそこまで高くないのでwebアプリケーション作成には適していないと判断して削除
 * 複雑なreactコンポーネントモジュールを作る時には、ガンガン使っていきたいところ

### [eslint](https://github.com/eslint/eslint)
 * URL: https://eslint.org/
  * JavaScriptのLintライブラリ

#### 削除した理由
 * 運用が難しい
 * 細かくルール設定が出来すぎてしまう
 * prettierとケンカする
 * 「eslint-disable」を使い出すとソースコードがカオスになる
 * 以下のような共有設定を入れ始めると、大して意味の無い縛りに悩まされる
    * https://www.npmjs.com/package/eslint-config-airbnb
    * https://www.npmjs.com/package/eslint-config-standard

#### 2018年版での代替え
 * コード整理の役割は、prettierのみに任せる形に変更
 * [prettier-eslint](https://github.com/prettier/prettier-eslint)での併用も考えたが、eslintは「細かくルール設定が出来すぎてしまう」問題 + それを「eslint-disable」で簡単に無効にできてしまう問題があるので不採用

### [flow-bin](https://github.com/facebook/flow)
 * URL: https://flow.org/
    * javascriptで型定義をできるするライブラリ
  
#### 削除した理由
 * 重い
 * バージョンアップで破滅的な仕様変更が頻繁に行われる
 * atomとVSCodeのプラグインがイマイチ
 * [flow-typed](https://github.com/flowtype/flow-typed)で管理している型定義のバージョン管理が難しい
 * ~~よく分からないけど型に「*」を入力すると定義checkを突破できてしまう~~

#### 2018年版での代替え
 * 型定義したいなら、素直にTypeScriptを使えば良くないか？と思ったので変更

### [webpack](https://github.com/webpack)
 * jsコードのbuildツール

#### 削除した理由
 * webpackには不満は無いが、[create-react-app](https://github.com/facebook/create-react-app)をejectしないと、TypeScriptをサポートできないので、巻き添えで削除

## inしたpackage

### [TypeScript](https://github.com/Microsoft/TypeScript)
 * JavaScriptに静的型付けが行えるプログラミング言語。

#### 追加した理由
 * 上記で記載しているが、[flow-bin](https://github.com/facebook/flow)の代替えで追加
 * エディターとの相性が良い（VScode、atom共に）
 * webpackやparcelを使えば、jsコードに対してもフラットにimportがexportができるので部分的にTypeScriptを使用することも可能なので実装へのハードルが低い

### [parcel](https://github.com/parcel-bundler/parcel)
 * URL: https://parceljs.org/
    * webpackと似たようなbuildツール。webpack.config.jsのような設定ファイルが必要ない

#### 追加した理由
 * 上記に記載しましたが、[create-react-app](https://github.com/facebook/create-react-app)をejectしないと、TypeScriptをサポートできないので、TypeScriptをサポートしてくれているparcelを採用
 * まだ、時期尚早感はあるが、今のところは困ることも無い程度には使えている

# 総評 

## 2017年版→2018年版になって得られたもの
 * エディターが快適に動作するようになった（主にflow-binのプラグイン重かったので）
 * 全体のコードが1/3程度削減（主にredux関連コードがなくなったため）
 * redux系の複雑なロジックが無くなり、直感的な実装にしたのでコードが読やすくなった（はず）
 * 稀に出現する「eslint-disable」から解放された

## 2017年版→2018年版になって失ったもの
 * eslintの「[rules/no-unused-vars](https://eslint.org/docs/rules/no-unused-vars):(未使用の変数をcheck)」などの有用な設定が使えなくなった
 * webpack時に比べると、parcelはエラー表示系の機能が不足している