719 words
4 minutes
Recoilに代わるJotaiの使い方が何もわからん

背景#

TypeScript + React + Viteでウェブアプリを作っているのですが、管理クラスのようなものが必要になりました。

class Application {
  readonly version: string
  private _theme: 'dark' | 'light'

  get theme(): 'dark' | 'light' {
    return this._theme
  }

  changeTheme = () => {
    this._theme = this._theme === 'dark' ? 'light' : 'dark'
  }
}

上は大雑把な感じですが、こういうのを作ったときにApplicationのクラスの何かの要素が変化したときにコンポーネントの再レンダリングをして欲しいわけです。

ところがクラスは参照渡ししかしない上にクラスのプロパティが変化してもReactはクラスのインスタンスが変化したとは検知してくれません。

よって、これはchangeThemeを呼び出してthis._themeを変更してもApplicationクラスのインスタンスが変わったと認識してくれないので表示は全く変わりません。

これが困るのでなんとかしたいというわけですね。

SwiftUIの場合#

SwiftUIもReactと同じように宣言型のフレームワークなので同様の問題がありました。

フレームワーク状態管理クラス管理
SwiftUI@State@Observable
ReactuseState-
Jotaiatom-

ところがSwiftUIの場合にはクラス自体に@Observableを宣言して、プロパティの変化をチェックしたい場合に@Publishedをつけることでクラスのプロパティが変化したことをSwiftUIのフレームワークに通知する仕組みがありました。

ところがReactにはデフォルトでその機能はないようで、この時点で結構困ります。

ログインフォームくらいであればユーザー名とパスワードを管理すればいいだけなので@StateuseStateで十分なのですがアプリの設定などであればたくさんのプロパティが必要なので、それらを必要とするコンポーネントで何回も呼び出していると流石にめんどくさいです。

また、クラスの場合にはプロパティAとプロパティBが密結合になっている場合があるので、別のStateで管理すると表示上の非同期を招きかねません。

SwiftUIの場合にはより単純なクラスの状態管理として@Observationもあったりします

@Observableの欠点#

じゃあSwiftUIの@Observableは便利なのかというとそうではない一面もあります。

というのも、クラス自体を@Observableとして宣言しないといけないので、外部のライブラリが使っているクラスはラッパーを作るなり拡張クラスを作らないとObservableに対応させることができません。この時点で結構めんどくさいです。

まあSwiftUIの愚痴はどうでもいいです、ぶっちゃけそんなに困っていません。困っているのはReactです。

Jotaiを理解せよ#

Recoilに代わるJotaiの使い方が何もわからん
https://fuwari.vercel.app/posts/2025/01/jotai/
Author
tkgling
Published at
2025-01-25