在使用 Mobx Persist Store 时将 MobX 与 React Context 一起使用?

Use MobX with React Context while using Mobx Persist Store?

原来我在React.createContext()

里面用的是new CounterStore

context.ts

import React from 'react'
import { stores, PersistState, CounterStore } from '@/store/index'
import type { ICounterStore } from '@/types/index'

export const FrameItContext = React.createContext<ICounterStore>(new CounterStore())
export const useCounterStore = () => React.useContext(FrameItContext)

然后我开始在我的应用程序中使用 Mobx Persist Store

persist.ts

import { persistence, StorageAdapter } from 'mobx-persist-store'
import { CounterStore } from '@/store/index'

const read = (name: string): Promise<string> =>
    new Promise((resolve) => {
        const data = localStorage.getItem(name) || '{}'
        console.log('got data: ', data)
        resolve(data)
    })

const write = (name: string, content: string): Promise<Error | undefined> =>
    new Promise((resolve) => {
        localStorage.setItem(name, content)
        console.log('write data: ', name, content)
        resolve(undefined)
    })

export const PersistState = persistence({
    name: 'CounterStore',
    properties: ['counter'],
    adapter: new StorageAdapter({ read, write }),
    reactionOptions: {
        // optional
        delay: 2000,
    },
})(new CounterStore())

并且我更改了我的代码以使用 PersistState 而不是 new CounterStore()

context.ts

import React from 'react'
import { stores, PersistState, CounterStore } from '@/store/index'
import type { ICounterStore } from '@/types/index'

export const FrameItContext = React.createContext<ICounterStore>(PersistState)
export const useCounterStore = () => React.useContext(FrameItContext)

它只记录 got data: {} 到控制台。 write 函数永远不会被调用。

我做错了什么吗?

巧合的是,Codesandbox 上的一个简单的计数器示例工作得很好 → https://codesandbox.io/s/mobx-persist-store-4l1dm

上面的示例适用于简单的 Chrome 扩展程序或 Web 应用程序,但似乎不适用于我的特定应用程序,因此我编写了一个保存到 LocalStorage 的手动实现。

在商店中使用 toJSON() 来跟踪应保存哪些属性:

toJSON() {
    const { color, counter } = this
    return {
        color,
        counter,
    }
}

并在 constructor() 下方添加 localStorage 逻辑。首先,检查 localStorage 是否包含最新值 & return 如果有的话。

如果没有保存,就保存在localStorage里面。

constructor() {
    ...
    const name = "CounterStore"
    const storedJson = localStorage.getItem(name)
    if (storedJson) Object.assign(this, JSON.parse(storedJson))
    autorun(() => {
        localStorage.setItem(name, JSON.stringify(this))
    })
}

Codesandbox → https://codesandbox.io/s/mobx-persist-store-manual-implementation-vm38r?file=/src/store.ts