ReactベースのTodo管理ページを自分なりに作ってみた件

Reactを勉強する機会を設けさせてもらえたため、最初の一歩を踏んだ際の気付きを雑多に記録する。
なお、環境はWSL（Windows10 Ubuntu）を利用している。

（※下記の手順では、永続的にインストール時の状態を保存できないため、コンソールを立ち上げる度にnvmでのNodeインストールのコマンド実行が必要になるので注意）

## １．Reactインストール
Reactでのアプリを作成するとして、JSなんでブラウザとReactのJSライブラリがあれば各種動作確認はできる（頑張れば）が、環境構築・開発ツール・動作確認など効率的に作業をすするために、まず最初にNodeをインストールしなくては。
（いつも思うのが、本当にやりたいことの前にいろいろ準備が必要なのが、`○○○○JS` 系の面倒にしか感じれないところ。慣れればそういうもんやなと思える）

### Nodeはnvmでインストール

NodeのインストールにはNVMを使う。
https://github.com/nvm-sh/nvm

```
curl -o- https://raw.githubusercontent.com/nvm-sh/nvm/v0.34.0/install.sh | bash
nvm install node
```

以上で、npmも使えるようになる。

### Reactアプリ作成のための準備

Reactアプリを作るには、それ用の作業場所や必要なライブラリを設置しなければならない。コーディングだけしたいので、それ用に準備されている先人のノウハウに頼る。
Reactアプリを立ち上げるには、Nodeを利用する。

Windows上で、どこにファイルを保存するか決めて、作業場所にWSL上で移動した後、
以下ののコマンドを実行する。

```
npm install -g create-react-app
create-react-app react-todo
```

以上で、`react-todo`というサブディレクトリに、Reactアプリを作成するために最低限のファイル類が設置される。

正常に設置が完了されていれば、
以下のコマンドを実行することで、Nodeが立ち上がって、Reactで表示されたページがデフォルトブラウザで表示される。

```
cd react-todo
npm start
```

App.jsで画面を表示している。App.jsをvimやエディタで編集すれば自動更新でブラウザ側のページも更新される

なにか、Moduleを追加して、別機能を実装したいなどとなった場合は、以下のコマンドを叩いて、Moduleを追加すればいい。

```
npm install <追加したいModule名をカンマ区切り> --save
```

### この時点の実装内容を見たい場合は以下のGitコマンドを叩く

```
git clone https://github.com/abikoka/todo-react-mlab.git
git checkout -f secstion.1
```


## ２．Todo管理画面のHTML作成と静的な画面表示処理の実装

まず、どんな仕組みをどんな見た目で作成していくか、大まかに決めるためHTMLとCSSだけ作成

### 一覧表示のスタイル

一覧のところは、TABLE要素ではなくて、DIV要素でCSSのFlex表示を使ってみる。

ただ、削除ボタンのセル要素を「10%」幅にしてるけど、
これだと、幅広い表示のときに削除ボタンエリアが余計に大きく見えてダサい。
Todo表示エリアを%指定で、削除エリアをpixel指定にすると、幅が小さいときに期待通りにならない。こういうときはどうするのが妥当なのか。。。

それから削除ボタンを、縦の中央に寄せたいがFlexを使っているとtable-cellが使いづらいので、一旦padding指定で下にずらした。

### この時点の実装内容を見たい場合は以下のGitコマンドを叩く

```
git clone https://github.com/abikoka/todo-react-mlab.git
git checkout -f secstion.2
```


## ３．登録処理の作成

### 登録処理の実装

登録処理は、handleSubmitというメソッドを追加して、タイトルと備考を指定して、追加できるようになっている。特段難しいことはしていない。

大事なことは、Reactの同期処理の根幹となるsetStateメソッドを使って、Todo情報が追加されたリストデータと件数を更新。
こうしておけば、一覧の実装後にすぐに動作を確認できる。

まだ、一覧処理はつくっていないため実装時の登録処理の結果確認は、console.logで確認できるように記述し、追加されていることをブラウザの開発者ツールのコンソールで確認した。

### （臨時対応）Todoデータは、MongoDB(mlab.com) へ保存

postメソッドを呼び出している行があるが、
本当にやりたかったことが、このようなRESTful API を介して、CRUD処理を作ること。

今回は、作業を簡便化するためにmlab.comを使った。ただし、現在mlab.comは新規アカウント登録を行っていないため、mlabアカウントがない状態でこのサンプルコードを利用する場合は別途APIサーバーを自前で立ててほしい。

本来なら、環境変数からAPI keyを埋め込む形が望ましい。
MongoDB Atlasは、RESTful API経由のデータ操作は許可されていなかったのであきらめた。

### React の保存処理の流れを知る

Form要素のonSubmitに、クロージャーのhandleSubmitをbind？実装？する。
これで、Submitボタン要素がクリックされると、handleSubmitが実行されるようになった。
このようなReactのイベント実装の仕組みがいまいちわかっていない。

### この時点の実装内容を見たい場合は以下のGitコマンドを叩く

```
git clone https://github.com/abikoka/todo-react-mlab.git
git checkout -f secstion.3
```

## ４．一覧の表示作成

登録したデータを表示するための一覧だが、処理には「初期データの表示」と「登録後の追加」という大きく2種類の処理に分かれる。
すべて非同期処理なので、サーバーサイドで実装するようにControllerにDB取得してデータをアサインする流れを書くだけでは済まない。

### 初期データの表示処理

コンポーネントに分かれて処理が非同期で動作するため、初期データもコンポーネントが評価されて追加されたタイミングで取得して表示されるようにする必要がある。そのために、componentDidMountというメソッドをオーバーライドする。

### 静的なリスト表示を動的にする

　まず、静的なHTMLで記述されていたところを削除して、TodoListクラスでrenderされるようになおす。リスト情報は、Appクラスで全部取得させる形で今回実装するため格納先となるstate.todosを参照してTodoListクラスに引き渡している。

　TodoListクラスは、リストエリアをrenderで出力するだけを担う。個々のTodo情報は、表示に必要な情報をTodoタグ属性で引き渡している。
　Todoクラス側のrenderメソッドに、一個のTodoを出力する際に必要なHTMLを移設して、各Todo情報の属性値を出力できるように改修。

Todo情報の登録時にsetStateを呼び出しているのため、以上の実装で、登録処理後にサクッと一覧の一番上に登録したTodo情報が追加されるはず。

そして、ブラウザをリロードしても、情報は消えずに再表示される。

### この時点の実装内容確認

```
git clone https://github.com/abikoka/todo-react-mlab.git
git checkout -f secstion.4
```


## ５．ステータス変更処理の作成

実際の作業が終わったら、該当のTodo情報を「完了へ」のボタンを押して、作業完了を記録できるようにする。

### 状態更新用のクロージャー処理を実装

更新処理は、setTodoStatusメソッドに、該当Todo情報を更新させるRESTのPUT送信処理を記載して実現。差分更新はできないため該当Todo情報を全部送っている。
完了状態かどうかを判断できるように、Todo情報行の背景色をグレーにして、状態を可視化。

### ステータス更新のイベントの実装

各タスクに状態更新ボタンをトグル形式で配置しているの（トグルはユーザに混乱とか今回は気にしない）で、そのボタンのイベント発火で、setTodoStatusが実行されるようにする。
処理はApp.jsに実装、callはTodo.js側に実装できるようにTodoList.js経由で引き継ぐ。


### この時点の実装内容確認

```
git clone https://github.com/abikoka/todo-react-mlab.git
git checkout -f secstion.5
```

## ６．削除処理の作成

必要なTodo情報は削除したいので、もともと設置していた作削除ボタンを使って、削除処理の実装

### 削除処理を実装する

削除処理は、removeTodoメソッドに、該当タスク情報を更新させるRESTのDELETE送信処理を記載して実現しようとしたが、なぜかmlab.com側で許可されていなかったため論理削除で実現。
state.todsからも削除して、setStateメソッドにて反映

論理削除にしたことで、Todo作成時に削除状態フラグのカラムを追加して、GET時のクエリに削除状態が立っていない指定を追加

### この時点の実装内容確認

```
git clone https://github.com/abikoka/todo-react-mlab.git
git checkout -f secstion.6
```

## まとめ

各実装ステップに合わせてブランチを切っているので、
該当ステップ時点の実装内容を確認したい場合は、ブランチ名を指定してcheckoutしてください。

Reactは表示制御用のフレームワークなので、画面遷移などを実現させるには別途モジュールがいるため今回は一画面で全部実現できるように実装しています。
Reactの仕様に沿って各イベント発火時の処理を実装すれば、簡単に登録・表示・更新・削除の処理が連動できるのが、やっぱいい。

根幹の部分は別途勉強するとして、基本的な実装方法はこれでだいたい分かるはず。

## 参考

* [Reactの環境構築を最短で行う](https://qiita.com/mikan3rd/items/496a87fc8b76263d0a91)
* [mlab.com Data API](https://docs.mlab.com/data-api/)
* [A Simple CRUD Application On React + Redux + Axios + Nodejs REST API + MongoDB — Part II](https://medium.com/@raju.allen/a-simple-crud-application-with-login-on-react-redux-axios-nodejs-rest-api-mongodb-part-ii-376606eb67a7)
: