带你了解并使用Recoil状态管理

314 阅读2分钟

知识点:

  • Recoil是什么? 一个React状态管理库
  • Recoil是FaceBook开发的状态管理库, 目标是做一个高性能的状态管理库,并且可以使用React内部的调度机制,包括会支持并发模式
  • 数据流图: 派生数据和异步查询均采取纯函数和高效的订阅方式实现
  • 应用程序全局监听: 通过监听应该程序中所有状态的变化来实现持久化存储,路由, 时间旅行调试或撤销,并且不会影响代码拆分

Recoil API

  • useRecoilState 当组件需要读写状态的时候,用到这个hook
import { useRecoilState } from 'recoil'
import { textState } from './store/index'

function HomePage(props){
    return <div>
    <TextInput />
    <CharacterCount />
    </div>
}

function TextInput(props) {
    
    const [text, setText] = useRecoilState(textState)
    
    const onChange = (e) => {
        setText(e.target.value)
    }

    return <div>
        <input type='text' value={text} onChange={onChange}/>
    </div>
}
  • useRecoilValue 当一个组件不需要写入state的时候,使用这个hook
import { useRecoilState } from 'recoil'
import { textState, charCountState } from './store/index'

function HomePage(props){
    return <div>
    <TextInput />
    <CharacterCount />
    </div>
}

function TextInput(props) {
    
    const [text, setText] = useRecoilState(textState)
    
    const onChange = (e) => {
        setText(e.target.value)
    }

    return <div>
        <input type='text' value={text} onChange={onChange}/>
    </div>
}

function CharacterCount(props) {
    
    const count = useRecoilValue(charCountState)

    return <div>
        {count}
    </div>
}

  • useSetRecoilState 返回一个setter函数, 用来更新可写 Recoil state的值, 状态变化不会导致组件重渲染,当一个组件需要写入而不需要读取state时, 使用此hook
  • RecoilRoot
import { RecoilRoot } from 'recoil'
import HomePage from './pages/HomePage'

export default function App() {
    return (
        <RecoilRoot>
            <HomePage />
        </RecoilRoot>
    )
}
  • atom 一个atom代表一个状态,atom可在任意组件中进行读写,读取atom值的组件隐式订阅了该atom 在需要向atom 读取或写入的组件中, 应该使用 useRecoilState()
import { atom } from 'recoil'

export textState = atom({
    key: 'textState',
    default: ''
})
  • selector 这是一个派生状态,派生状态是状态的转换 你可以将派生状态视为将状态传递给以某种方式修改给定状态的纯函数的输出
import { atom, selector } from 'recoil'

export const textState = atom({
    key: 'textState',
    default: ''
})

export const charCountState = selector({
    key: 'charCountState',
    get: ({get}) => {
        const text = get(textState)
        
        return text
    }
})