ReactNativeアプリケーションの状態マネージャーとしてMobxを使用する
公開: 2022-03-10状態管理は、JavaScriptアプリケーション、特にReactおよびReactNativeアプリケーションの開発に不可欠な部分です。 このチュートリアルでは、状態管理にMobXライブラリを使用する方法を学習します。 コアコンセプト、いくつかのユースケースを理解し、簡単な例を作成します。
注:このチュートリアルを実行する際には、JavascriptとReactNativeの基本的な知識が非常に役立ちます。
ReactアプリケーションでのMobXの使用
状態は、コンポーネントが処理しているデータです。これは、コンポーネントが必要とするデータを保持し、コンポーネントが何をレンダリングするかを決定します。 状態管理は、状態が更新され、あるコンポーネントから別のコンポーネントに渡される方法を管理するプロセスです。 アプリケーション内のデータの監視と操作は困難な場合があり、それが状態管理ライブラリの必要性です。 アプリケーションのすべてのデータを処理することは、特にアプリケーションのサイズと複雑さが増す場合、少し気が遠くなる可能性があります。独自の状態管理ツールを構築することは、時間がかかるだけでなく困難です。そのため、状態管理ライブラリを使用することをお勧めします。
ただし、コンポーネントがレンダリングするデータは状態だけではなく、コンポーネントはそれに渡される小道具をレンダリングすることもできることを知っておくことが重要です。
状態管理のオプション
ReactNativeアプリケーションの状態管理ライブラリには次のものがあります。 React Context API、Redux、MobX、UnstatedNext。
これらの状態管理者にはそれぞれ長所と短所がありますが、個人的にはMobXをお勧めします。これは、その単純さ、最小限の定型コードです。コードを変更する必要がないためです。これは、MobXのコアがJavaScriptであり、JavaScriptに似ているためです。 それをサポートするためにアーキテクチャを変更する必要はありません(Reduxとは異なり、コンテキストはそれほどではありません)。
実際、これは非常に目に見えない抽象化であるため、多くの場合、 MobXコード(@ observable、 @ computerd 、 @ action 、 observerデコレーター)をすべて削除しても、コードはまったく同じように機能します(ただし、パフォーマンスの問題がいくつかあります)。 )そしてそれはグローバルな状態に限定されません。 これらは、ReactNativeアプリケーションに最適な状態マネージャーとしてMobXを使用する理由です。
MobXを状態マネージャーとして使用する際のいくつかの問題に注意することも重要ですが、その一部には、MobXの実装方法に関するルールの回避が含まれ、特に@actionsを使用せずにコンポーネントで直接状態を変更する場合、 @actions
のデバッグが困難になる可能性があります。パラメータ。
MobXとは何ですか?
公式ドキュメントによると、MobXは、関数型リアクティブプログラミングを透過的に適用することにより、状態管理をシンプルかつスケーラブルにする、戦闘でテストされたライブラリです。 MobXは、アプリケーションをスプレッドシートのように扱います。 ロジックは、アプリケーションの状態から派生できるものはすべて自動的に実行する必要があるというものです。
MobXのコア原則とコンセプト
MobXは、次の概念で他の州のマネージャーとの差別化を図っています。
1.状態
状態は、アプリケーションが保持するデータです。これは、おおよそそのメモリの内容全体です。 これは、コンポーネントにも当てはまります。
2.派生
MobXでは、相互作用なしで状態から派生できるものはすべて派生です。 派生の例は次のとおりです。
- ユーザーインターフェース、
- サーバーへの変更などのバックエンドアドオン。
MobXには、主に2つのタイプの派生があります。
- 計算値
計算された値は、ほとんどの場合、純粋関数を使用して現在の状態から導出できる値です。 - 反応
派生の反応は、アプリケーションの状態の変化の結果として発生する副作用です。 これらは計算値に似ていますが、新しい値を生成する代わりに、リアクションは、コンソールへの出力、ネットワークリクエストの作成、Reactコンポーネントツリーを段階的に更新してDOMにパッチを適用するなどの副作用を生成します。
MobXを使用する場合の基本的なルールは、現在の状態に基づいて値を作成するときに、計算された値を使用することです。
3.アクション
派生とは異なり、アクションはアプリケーションの状態を変更するコード、つまり状態を変更するコードです。 それらは状態を変更するものです。 MobXを使用すると、コードで明示的にすることができます。アクションは、ほとんどの場合、入力、バックエンドデータプッシュ、さらにはスケジュールされたイベントなどのユーザーイベントです。
アクションをよりよく理解するために、MobXドキュメントの例を見てみましょう。
class Ticker { @observable tick = 0 @action increment() { this.tick++ // 'this' will always be correct } } const ticker = new Ticker() setInterval(ticker.increment, 1000)
ここでは、初期値が0の@observable
ティックを設定します。次に、ティックが1秒ごとに行われると初期値を更新するアクションでもある関数インクリメントを作成しました。
MobXのオブザーバブル
MobXのオブザーバブルまたはオブザーバブル値は、ほとんどがJavaScriptプリミティブ、プレーンオブジェクト、クラス、配列、およびマップです。 これらは主に、最初にobservableを宣言して値を追加し、次に以下に示すように@observableを追加して呼び出すことで使用されます。
observable(value) @observable classProperty = value
MobXでのストアアーキテクチャアプローチ
MobXの主要なアーキテクチャには、サービス、ストア、ビューモデル、コンテナなどのパーツとアイデアが含まれています。これらの一部については、以下で説明します。
- サービス
これは通常、コンテナから呼び出される関数です。 APIからデータを取得し、ストアに追加するために使用できます。 - 店
名前が示すように、これはアプリケーションによって使用される状態の中心的な場所です。 通常、MobXでは、これらには、オブザーバブル、変数、アクション、および計算されたプロパティが含まれます。 - 容器
これはservice
を呼び出し、ビューモデルからビューコンポーネントにReactプロップとしてデータを配置します(@observer
デコレータでマークする必要があります)。
ReactおよびネイティブアプリケーションのMobX
学習目的で、このチュートリアルでは、ユーザーがリストアイテムを追加、表示、および削除できるようにする簡単なリストアプリを作成します。 このアプリケーションでは、MobXを状態マネージャーとして使用して、リストを追加したり、更新したり、アプリの状態から削除したりします。 ただし、JavaScriptとReactの基本的な概念をすでに理解していることに注意することが重要です。
それ以上の苦労なしに、始めましょう!
環境のセットアップ
MobXとは何か、そしてそれがどのように機能するかがわかったので、プロジェクトの設定について説明します。
まず、次のようなプロジェクトを作成し、端末に次のコードを記述してプロジェクトを初期化します。
npx create-react-app listapp
上記のコードは、create-react-appパッケージを使用してベアReactアプリケーションを作成します。 プロジェクトディレクトリに移動します。
cd listapp
このアプリには、次の3つのコンポーネントが必要です。
-
TitleInput
これには、プロジェクトのタイトルとリストを追加するための入力フォームが含まれます。 -
List
これは、ユーザーがリストを追加できるようにする入力フォームになります。 リストアイテムを追加するための追加ボタンがあります。 -
ListsDisplay
このコンポーネントは、すべてのユーザーリストアイテムと、ユーザーがリストアイテムを追加したときに自動的に生成される削除ボタンを表示します。
Store.jsを使用して、Reduxと同様にアプリの状態とそれを変更するメソッドを含めます。 それらが何に使用されるかを概説しましょう。
-
mobx
これは、このプロジェクトで使用する状態マネージャーです。 -
mobx-react
これは、MobXの公式のReactバインディングです。 -
bootstrap
プロジェクトのスタイル設定には、ブートストラップバージョン4.5を使用します。 -
uuid
これは、リストを削除するためのキーを自動的に作成するために使用されます。
それが終わったら、先に進んでこれらのパッケージをインストールしましょう。 私はそれらをyarnで行われるnpmの代替でインストールします:
yarn add mobx mobx-react [email protected] uuid
パッケージがインストールされたら、ターミナルで以下のコードを実行して、アプリを開発モードで起動します。
yarn start
AppStoreのセットアップ
プロジェクトのストアを作成しましょう。 まず、プロジェクトのルートディレクトリにListStoreというファイルを作成します。これは、アプリの状態の中心的な場所になります。
このアプリでは、他のアプリコンポーネントで使用するときに繰り返さないように、 ListStoreを作成する必要があります。
/*** src/Store.js ***/ import { observable, action, computed } from "mobx"; import { v4 } from "uuid"; export class List { @observable value @observable done constructor (value) { this.id = v4() this.value = value } } export class ListStore { @observable lists = [] @observable filter = "" @action addList = (value) => { this.lists.push(new List(value)) } @action deleteList = (list) => { this.lists = this.lists.filter(t => t !== list) } @computed get filteredLists () { const matchCase = new RegExp(this.filter, "i") return this.lists.filter(list=> !this.filter || matchCase.test(list.value)) } }
上記のコードでは、 mobx
から3つの関数をインポートしました。
-
observable
これは、状態が変化した場合に更新できる変数を保持します。 -
action
アプリケーションの状態を変更するために使用されます。 -
computed
既存の状態または他の計算された値から導出できる値は、状態が変更された後に変更されます。
クラスList
には、 done
される2つのオブジェクト値と、アプリの初期状態と変更の場合の変更を保持するvalue
があります。
新しいリストでキーを自動的に作成して、リストが作成されると自動的に削除ボタンを取得できるようにします。ここでは、uuidを使用してアプリケーションでキーを自動的に作成します。
次に、 .push()
メソッドを使用してクリックするとリストを追加するaddList
関数を追加し、@ observablelists配列で既に作成した配列にリストをプッシュし@observable lists
。
deleteList
関数は、ユーザーが削除したいアイテムであると想定されるプロパティとしてList
を受け入れます。 次に、選択したアイテムを削除した後、 this.Lists
の値を新しい配列に設定します。
addLists
とdeleteList
はどちらも、変更が加えられたときにアプリの状態を変更するため、アクションです。
MobXストアの初期化
次のリストは、 App.jsにストアをインポートし、プロジェクトで使用することです。
import React from 'react'; import Navbar from "./components/navbar"; import ListDisplay from "./components/ListDisplay"; import {ListStore} from './ListStore'; function App() { const store = new ListStore() return ( <div> <Navbar store={store}/> <ListDisplay store={store}/> </div> ); } export default App;
ここでは、 TitleInputコンポーネントとListDisplayコンポーネントをインポートしました。 次に、 App.js
でストアを初期化して、 TitleInputコンポーネントとListDisplayコンポーネントに小道具として渡すことができるようにしました。
通常、他のコンポーネントで作業していないため、これはエラーをスローします。それでは、それを実行しましょう。 ListDisplay
コンポーネントを構築してみましょう。
ListDisplay
このコンポーネントは、追加されたすべてのリストを表示し、新しいリストが追加されると自動的に削除ボタンを生成します。
import React from 'react' import List from "./List"; import { observer } from 'mobx-react'; function ListDisplay(props) { const { deleteList, filteredLists } = props.store return ( <div> <div className="container"> {filteredLists.map(list => ( <List key={list.id} list={list} deleteList={deleteList} /> ))} </div> </div> ) } export default observer(ListDisplay)
このコンポーネントでは、関数ListDisplay
を作成してオブザーバーにしました。また、ストアからlist
関数とdeletelist
関数を分解しました。これにより、オブジェクトの小道具として渡すのが簡単になりました。
次に、 filteredLists
を介してマップしてリストを返します。次に、返されたアイテムを小道具としてListコンポーネントに渡すことにより、個々のリストを作成する際に使用します。
完了すると、コンポーネントは次のようになり、リストが追加されます。
次に、 ListコンポーネントとTitleInputコンポーネントを追加します。
リストコンポーネント
他のコンポーネントと同様に、 List
コンポーネントは、ストアが変更を監視できるように、リストをオブザーバーとしてエクスポートします。
import React from 'react' import { observer } from 'mobx-react' function List(props) { return ( <div className="card"> <div className="card-body"> <div className="d-flex justify-content-between align-items-center"> <p className={`title ${props.list.done ? "text-secondary" : ""}`}> {props.list.value} </p> <div> <button onClick={props.deleteList.bind(this, props.list)} className="btn btn-danger font-weight-bold py-2 px-5 ml-2"> Delete </button> </div> </div> </div> </div> ) } export default observer(List)
ブートストラップを使用して、 divs
の最初のセットにカードを作成し、削除アイコンをアプリの右側に移動するように配置しました。 まず、 list
を処理するカードコンポーネントを作成し、次に削除button
のボタンタグを作成しました。このタグは、この2つのオブジェクトを受け入れ、リストに小道具を渡します。これをクリックすると、選択したリストアイテムがリストから削除されます。ページ内のリスト。
次は、リストを追加するための入力フォームとプロジェクトのタイトルを含むTitleInputです。
TitleInput
他のプロジェクトと同様に、コンポーネントがアプリストアから小道具を受け入れることができるように@observer
関数を追加します。
import React, { useState } from 'react' import { observer } from 'mobx-react' function Navbar(props) { const [value, setValue] = useState("") const {addList} = props.store const prepareAddList = (e) => { e.preventDefault() addList(value) setValue("") } return ( <div className="container mt-3"> <h1 className="title">List App</h1> <form onSubmit={prepareAddList} className="form-group"> <div className="row ml-lg-2"> <input className="form-control-lg col-12 col-lg-9 col-sm-12 mr-3 border border-secondary" value={value} type="text" onChange={(e) => setValue(e.target.value)} placeholder="Enter list" /> <button className="col-lg-2 col-5 col-sm-5 mt-2 mt-lg-0 mt-sm-2 btn btn-lg btn-success font-weight-bold"> Add to List </button> </div> </form> </div> ) } export default observer(Navbar)
まず、初期状態を初期化しました。 React Hooksを使用して、 values
と呼ばれる初期状態を追加し、空の文字列に設定しました。 これを使用して、入力フィールドに入力された値を保持します。 React Hooksの詳細については、DavidAbiodunによるこの記事をご覧ください。
次に、リストをストアaddList
に追加するためのオブジェクトを呼び出し、アプリストアから小道具として渡しました。
次に、入力フォームのイベントオブジェクトを受け入れる関数preparedAddList
を作成しました。また、クリック時にリストを手動で追加するためのボタンも追加しました。
ほぼ完了したら、次を実行してプロジェクトサーバーを再起動する必要があります。
yarn start
そして、 TitleInput
は次のようになります。
これですべてのアプリコンポーネントが完成したので、 App.js
でアセンブルしましょう。 これを行うには、コンポーネントtitleInput
とListDisplay
をインポートする必要があります。 また、Storeコンポーネントからストアをインポートする必要があります。
MobXがアプリで機能するためには、アプリと個々のコンポーネントの小道具としてMobXストアを渡し、ストアのプロパティと機能を取得する必要があります。
import React from 'react'; import Navbar from "./components/navbar"; import ListDisplay from "./components/ListDisplay"; import {ListStore} from './ListStore'; function App() { const store = new ListStore() return ( <div> <Navbar store={store}/> <ListDisplay store={store}/> </div> ); } export default App;
完了すると、アプリは次のようになります。
結論
MobXは、特にReactベースのアプリケーション向けの優れた状態マネージャーであり、リストアプリを構築し、MobX、状態、派生、およびアクションの基本概念を学習しました。 このアプリの動作バージョンはここで見つけることができます:
状態の管理を含む次のアプリケーションでMobXを使用することで、これをさらに進めることができます。 あなたが思いついた新しいことを見てみたいです。 以下のリファレンスで、MobXおよび状態管理アプリケーションの詳細を読むことができます。
リソースとリファレンス
- 「ReactNativewith MobX —はじめに」Nader Dabit、Medium
- 「概念と原則」MobX(公式ドキュメント)
- 「Reactフックのベストプラクティス」、Adeneye David Abiodun、Smashing Magazine