Recoil

Reduxよりシンプルに扱えるステート管理ツールです。
ただし、ブラウザリロードするとリセットされてしまうので永続化は別途設定する必要があります。

・1. Recoilのインストール

yarn add recoil @types/recoil

知っておくといい概念

Recoliには大きく2つの概念があります。
AtomとSelectorです。
Atomは状態を管理します。状態の保持と状態の更新ができます。
SelectorはAtomで管理している状態を加工して取得することができます。

引用 : https://bit.ly/3Si4otw

・2. データストアの作成

認証に関するデータストアを以下のファイル名で作成してみます

src/Recoil/atoms/Auth.ts

import { atom } from 'recoil';

export interface Auth {
  displayName: string | null;
  email: string | null;
  isLogined: boolean;
  isAuthChecked: boolean;
}

const initialAuth: Auth = {
  displayName: null,
  email: null,
  isLogined: false,
  isAuthChecked: false,
};

export const authState = atom({
  key: 'auth',
  default: initialAuth,
})

・3. RecoilRoot の設置

import { RecoilRoot } from 'recoil';
<RecoilRoot>
  <App />
</RecoilRoot>

・4.値の取得

useRecoilState  : 1. 値の取得とSetter取得
useRecoilValue  : 2. 値の取得のみ
useSetRecoilState : 3. Setterのみ(useSetRecoilStateはあくまでSetter関数だけなので、Stateの値自体を参照していない限りComponentにはRe-Renderが走らない)

1. useRecoilState ( 値の取得と更新 )

import { myState } from "../recoil/atoms/myState"; // 自分で作成したRecoilState
import { useRecoilState } from 'recoil'
const [recoilAuth, setRecoilAuth] = useRecoilState(myState);

2. useRecoilValue ( 値の取得のみ )

import { myState } from "../recoil/atoms/myState"; // 自分で作成したRecoilState
import { useRecoilValue } from 'recoil'
  const recoilAuth = useRecoilValue(myState);    // 値のみ

3. useSetRecoilState ( setterのみ )

import { myState } from "../recoil/atoms/myState"; // 自分で作成したRecoilState
import { useSetRecoilState } from 'recoil'
// 関数コンポーネントのトップに記述
const setRecoilAuth = useSetRecoilState(myState);   // setterのみ(Re-Renderしない)
// recoil へ保存
setRecoilAuth({
	displayName: "hogehoge",
	email: "fugafuga@test.local",
	isLogined: true,
})

● Next.js + nookies を使ってRecoilのステートの永続化設定する(Cookie に保存する場合)

https://zenn.dev/someone7140/articles/8a0414a0236142

注意 : parseCookies では http only な Cookie は 取得できません。

● recoil-persist を使ってRecoilのステートの永続化設定する(localStorage, sessionStorage に保存する場合)

recoil-persistはデフォルトだとlocalStorageに保存されますが storageオプションを設定することで任意のStorageを利用することができます。

yarn add recoil-persist

例 : src/recoil/atoms/authState.tsx

import { recoilPersist } from 'recoil-persist'
const { persistAtom } = recoilPersist({
  key: 'recoil-persist',
  storage: sessionStorage,
});
export const authState = atom({
  key: 'authState',
  default: initialAuth,
  effects_UNSTABLE: [persistAtom],  // この行を追加
})

注意 : ログインしているかどうかの情報はにローカルストレージやセッションストレージには保存しないようにしましょう。 (サーバー側に情報を持たせるべきです)

● Recoil の selector (getter , setter )

ざっくり言うとゲッターとセッターです。
次のように使用します

import { selector } from 'recoil'
import { authState } from '../atoms/Auth'

/**
 * ユーザの認証状態を取得するrecoilセレクター
 * @example : const isAuthenticated = useRecoilValue(isAuthenticatedSelector);
 */
export const isAuthenticatedSelector = selector({
  key: 'authSelector',
  get: ({ get }) => {
    const state = get(authState)

    return state.isLogined === true
  }
})

● Recoil を さらに便利にする Atom Effects

https://recoiljs.org/docs/guides/atom-effects/

effects に atom 初期化時に1度だけ実行される Atom Effects を記述することができます。
return で クリーンアップ関数を記述します
何かの値を監視する関数をここに登録しておいて自動的にステート変更させる。といった使い方ができます

export const authState = atom({
  key: 'auth',
  default: authInitialValues,
  effects: [
    () => {
      alert('atom effect 1')

      // クリーンアップ関数
      return () => {
        alert('atom effect cleanup 1')
      }
    }
  ]
})

引数

setSelf: 自分自身の値を更新するための関数
onSet: 値の変更があるたびに引数に入れたコールバック関数を実行する

など、全ての引数は https://recoiljs.org/docs/guides/atom-effects/ を参照

React, Recoilでカスタムフックを作ってRecoilを隠匿する](https://zenn.dev/tokiya_horikawa/articles/89830f78a6dd57)

No.2140
10/12 16:32

edit