『状態管理』ってなんですか?

November 07, 2020

謎ワード『状態管理』

Flutterについて調べはじめた初心者が2日目あたりに遭遇する謎ワード『状態管理』。

しかも、ググって出てきた100いいね超えの良さそうなドヤ記事に書いてある内容も 半年ごとぐらいに「もっといいヤツ」が登場してオワコン化しているっぽくて、 今から始めたいんですけど、どれですか、、、ね??状態。。。

で、チュートリアルやりつつ、実際のコード書きつつ、その「ジョウタイカンリ」を調べて、 数週間後の今(2020-11-08)の理解のメモ。

問題はなにか? なにがそんなにむずかしいの??

FlutterはUIをつくるお仕事がメインです。WidgetというUI部品のツリー構造をつくるとiPhoneとAndroidのアプリの画面ができちゃう。それだけ。

UIの裏側で動くロジック(サーバにAPIゲットしたり、画像ダウンロードしたり、AIがディープラーニングしたりするなど)を書くところや、その仕組み、 フレームワークはなにも用意されていなくて、好きなようにつくるなり、パクるなりしてやってねということになっている。 Railsおじさんにはどこに何書いていいかぜんぜんわからないようになっている。

flutter createで生成されるアプリの雛形(StatefulWidgetの(Stateの)メンバ変数にintを保持していてボタンを押すと数字が増えるやつ) を元にして、俺が考えた最強のアプリ作っていくとすると、 このStateにどんどん変数が増えるのか?APIにgetするのをonTapに・。。ってのはすぐ無理が見えるので、

「FlutterのWidgetを構築するコード」と「ビジネスロジックのコード」をきれいに分けたい、整理したい。

となる。

「データ(=状態)」を「画面に表示」したい

Flutterにおいて「画面に表示」とはWidgetツリーをつくること。

Widgetツリーをつくるコードは、

  • child,childrenで子を連ねていく
  • Widgetを返すbuildコールバックメソッド

が主原料になっていて、

  • なにものかから「build」が呼ばれる
  • buildの中で最新のデータを使った最新のWidgetを作り直す
  • なにものかが、画面に最新のデータを表示する

という風なピタゴラ装置になっている。

画面を更新したかったら、buildが呼ばれるように仕向ければいいんだけど、そのへんを手作業でやるのはきっとややこしいので、

「データ(=状態)」が変わったら(buildが自動的に呼ばれて)「画面の表示」も『自動的に変わる仕組み』がほしい。

となる。

— データはいつ変わるのか? — データはどこにあるのか? — データを変えるのはだれ?

あたりが、アプリそれぞれで違ってきてややこしいとこなんだけど、 このあたりを上手に整理吸収できたらよくない?かっこよくない??

じゃあ、

  • データが変わったらWidget(のあたり)に通知するようにしよう
  • 通知を受け取ったらWidgetを再構築して表示を更新することにしよう

というアイデアが、Flutter初心者殺し謎ワード『状態管理』テクノロジーが解決する画期的ソリューションなのです。 あ、これ Virtual DOM のときにみたやつっぽい。

いろんな『状態管理』

https://flutter.dev/docs/development/data-and-backend/state-mgmt/options

ここにしっかり全部リストされているけども、結論から逆に歴史をたどって調べたメモ。

BLoC

  • Widgetとビジネスロジック間はStreamでつなごう
  • ビジネスロジック側にView側都合なコード入れないでね(そりゃそうだ)
  • Streamか・・・面倒ぽくないかい?しらないけど。

Scoped Model

  • ツリーの上の方に「モデル」を置いておいて、
  • その配下から「モデル」アクセスできるようにしよう
  • 「モデル」のデータが変わったら、使ってるWidget再構築しますね(たぶんここが雑でリビルド多すぎどうのこうの問題なんじゃないか)

Provider

  • Widget(buildの中やUI操作のコールバックあたり)からビジネスロジック(=のクラスのインスタンス)を見つける仕組み
  • なんとかNotifier群。変わったらnotifyするわかりやすいのから、Stream、Futureなど変わる系のものならなんでも対応的な?
  • readとwatch(とchange)を上手に使ってリビルド多すぎ問題に対応可能

Riverpod

  • Flutter(InheritedWidgetなど)に依存しないように作り直したProvider相当のもの

結論 Riverpod

進化の到達点である、Riverpodで遊んでおこう。だって今からやる人は古いのとの違いがわからないよ。 (半年後はまたその時考える)

でも、まだまだ便利になる余地があるきがします。 いろいろな背景知識なしで、もっとゆるふわにアプリが作れるように進化するはず。


Profile picture

Written by takeru You should follow them on Twitter