この記事は
- Reactで状態管理ツールを使ってみたい。
- でも学習コストが高くて難しそう。
そのように感じている人向けに、Recoilの使い方をまとめたものになっています。
筆者はReduxという類似ツールを使ったことがありますが、「圧倒的にRecoilは簡単」 だと思っています!
状態管理ツールの選定に迷っている人、Recoil
の利用を考えてみてはいかがでしょうか!!
Recoilってなに?
Reactの提供元であるMeta(FaceBook)が開発中の新しい状態管理ライブラリです。
ReduxやReactQueryの立ち位置のライブラリになります!
2022年2月時点ではプレリリース状態(v0.6.1)となっていますが、作っているのがReactの生みの親ですので状態管理ライブラリとして標準利用される可能性大だと思っています。
実装
それでは早速書いていきましょう!
まず初めに
Next.jsやRecoilなど必要なライブラリをインストールします。
まず最初にNext.js
のインストール。
npx create-next-app nextjs-recoil
作成されたnextjs-recoilディレクトリ
の中身をルートディレクトリに持ってきます。
(ちょっと見栄えが悪いので..)
こんな感じに移動させてください!
.
├── LICENSE
├── README copy.md
├── README.md
├── next.config.js
├── node_modules
├── package-lock.json
├── package.json
├── pages
├── public
└── styles
今回のメインのRecoil
をインストールします。
npm install --save recoil
Recoilを有効化
RecoilはRecoilRoot
で囲ったコンポーネント内で利用できます。
公式ではルートコンポーネントに配置するのを推奨しているようですので/pages/_app.js
に配置しましょう。
import { RecoilRoot } from 'recoil';
function MyApp({ Component, pageProps }) {
return (
<RecoilRoot>
<Component {...pageProps} />
</RecoilRoot>
)
}
export default MyApp
これだけの設定でRecoilを利用できるようになります!
(めちゃめちゃ簡単ですね...!)
Next.js
を起動させましょう。
npm run dev
Atomって何?
RecoilではAtom
という単位で、各状態の管理を行うことができます。
以下のようなAtom
を作成することで、異なるページ間の状態管理をすることができます。
Atomの基本形
const todoState = atom({
key: "todo", // 一位のキー名
default: ["todo1"], // 初期値
});
- key: 作成したAtomに付与する一位のキー名(重複不可)
- default: Atomの初期値
データを表示・更新させる
今回は簡単なTodoアプリを作成するので、Todoの状態を管理するAtom
を作成します。
/recoil/todo.js
にAtom
を作成し、どのディレクトリでも利用できるようexport
しておきましょう。
import { atom } from "recoil";
//todo Atom
export const todoState = atom({
key: "todo",
default: ["todo1"]
});
先ほど作成したAtom
を早速表示させましょう。
Recoilは基本的にReactHooksを用いて状態の操作を行います。
データを編集する場合は、useRecoilState()
を利用します。
useRecoilState()の基本形
//const [Atomの状態変数, Atomを更新する関数] = useRecoilState(対象のAtom)
const [todoList, setTodoList] = useRecoilState(todoState)
- 1つ目の要素:
Atom
の現在の値 - 2つ目の要素:
Atom
の現在の値を更新するための関数
今回はこのような形で/pages/index.js
に実装します。
import { useState } from "react"
import { useRecoilState } from "recoil";
import { todoState } from "../recoil/todo"
export default function Home() {
// TodoのAtomを呼び出し
const [todoList, setTodoList] = useRecoilState(todoState)
const [todo, setTodo] = useState("")
const handleChange = (e) =>{
setTodo(e.target.value)
}
// Todoリストを更新する
const pushTodo = (newTodo) => {
setTodoList([...todoList, newTodo])
setTodo("")
}
return (
<div>
<p>todo list</p>
<ul>
{todoList.length && todoList.map((v, i) => (
<li key={i}>{v}</li>
))}
</ul>
<div>
<input type="text" value={todo} onChange={handleChange} />
<button onClick={() => pushTodo(todo)}>
add Todo
</button>
</div>
</div>
)
}
localhost:3000 にアクセスするとTodoアプリができていると思います!
[Tips]
RecoilにはuseRecoilValue()
というデータ表示のみ行うHooksと、useSetRecoilState()
という状態の更新のみを行うHooksも用意されています。
useRecoilValue()
はあまり使わないかもですが、useSetRecoilState()
は是非活用して欲しいです!
Reactのパフォーマンス向上には、データの再レンダリングを少なくすることが重要になります。
useSetRecoilState()
を利用することで、不要なレンダリング防止に繋がります。
状態の更新のみを行う場合は、積極的に使っていきましょう!!
// Todo Atomのデータ表示のみを行う場合、こんな感じ
const todoList = useRecoilValue(todoState)
// Todo Atomのデータ更新のみを行う場合、こんな感じ
const setTodoList = useSetRecoilState(todoState)
最後に
次回はRecoilのSelector
について書きたいと思います!
今回利用したコードはこちらになります!(不要なファイルは削除してあります。)
https://github.com/takusan64/nextjs-recoil