iOS で Flux アーキテクチャの恩恵を受け、リアクティブかつ一方向のデータフローをサポートするための Framework で、これによって シンプルで処理を追いやすくかつ、Testableなアプリ設計を構築することができるようになります。
ReactorKit の恩恵
-
Testability
- ビジネスロジックを View から完全に分離することで、
View
とReactor
をそれぞれテストすることが可能になります。
- ビジネスロジックを View から完全に分離することで、
-
Start Small
- ReactorKit はアプリ全体に単一のアーキテクチャを適用する必要がなく、最小で1ViewController からアーキテクチャを導入できるため、プロジェクトの途中から導入する場合でも細かいステップを踏んでいくことができます。
-
Less Typing
- ReactorKit は複雑なコードを回避できるので、導入時コードの記述量を少なく済ませることができます。
また、他のアーキテクチャなどと比較して規約が比較的カッチリと決まっているため、指針をチームに依存させずに開発を進めることができます。
基本的な考え方
- Action
- ユーザインタラクションを抽象化したもので、それぞれのインタラクションを Reactor クラスにオブジェクトとして定義します。
フォローする
やページングする
などのインタラクションを表現します。
- ユーザインタラクションを抽象化したもので、それぞれのインタラクションを Reactor クラスにオブジェクトとして定義します。
- Reactor
- ビジネスロジックを担い View の状態管理をする役割があります。Reactor と View の関係は 1:1 になります。Reactor を担うクラスは
Reactor
プロトコルに準拠し、このクラスにはUIKit
を import しないようにします。
- ビジネスロジックを担い View の状態管理をする役割があります。Reactor と View の関係は 1:1 になります。Reactor を担うクラスは
- State
- View の状態を抽象化したもので、Reactor クラスにそれぞれの状態をオブジェクトとして定義します。
フォローしているか
や投稿のコレクション
の内容などを表現します。
- View の状態を抽象化したもので、Reactor クラスにそれぞれの状態をオブジェクトとして定義します。
- View
- 現在の
State
を描画し、ユーザからのインタラクションをAction
としてReactor
に渡す役割を担っています。このレイヤーにはView
というプロトコルと、Storyboard で UIViewController を扱う場合などに使用するStoryboardView
というプロトコルが用意されています。
- 現在の
データの流れ
ReactorKit でのデータの流れは下記のような感じです。また、Service レイヤーには API 実行や Local DB からのデータの取得など、Action の通知を受けて処理するべき副作用のロジックなどを追加します。
Action → Reactor → State → View → ....Action
Reactor には、mutate と reduce の2つの関数が存在し、それぞれの役割は下記のような感じです。
-
Mutation
- Action を元に
mutate
関数で生成される具体的な状態の変更方法を抽象化したものです。これはオブジェクトとして Reactor クラスに定義する必要があり、定義しない場合は Action オブジェクトが Mutation として扱われます。また、Mutation は Reactor 内部に閉じ込められたオブジェクトなので、View からは参照されません。
- Action を元に
-
mutate
- Reactor が受け取った Action を元に処理を行い、Observable として Mutation を返却します。
-
reduce
- mutate 関数で返された Mutation を元に新しい State を作成し、返却します。
テストについて
テストは基本的には下記の3点を抑えることによって動作を担保できます。詳しくはこちらに記載されています。
View
- ユーザインタラクションで Action が正常に通知されているか
- State の変更時に View が更新されるか
Reactor
- Action 取得時に State が更新されるか