Zustand是什么

Zustand 是一个为 React 运用程序规划的开源状况办理库,它旨在供给一种简略、轻量级且易于运用的方法来办理运用程序的状况。它是由 Max Stoiber 创立的,并且得到了社区的广泛支撑和运用。

Zustand 的中心思维是将状况办理与组件分离,然后使得状况办理愈加集中化,一起坚持了 React 的响应性和组件的可重用性。它供给了一种简略的 API,使得开发者能够轻松地在运用程序中的任何地方拜访和修改状况。 运用 Zustand,开发者能够经过创立一个 store 来存储和办理运用程序的状况。这个 store 是经过调用 createStore 方法并传入一个包括状况和操作的 object 来创立的。

Zustand 与其他状况办理库 如 Redux 和 MobX 比较有什么优势?

Zustand 是一个为 React 运用程序规划的状况办理库,与其他流行的状况办理库如 Redux 和 MobX 比较,它供给了一些共同的优势和特性。以下是 Zustand 相对于 Redux 和 MobX 的一些首要优势:

1. 简略性和易用性

Zustand 供给了一个十分简略和直观的 API,使得开发者能够轻松地创立和办理状况。与 Redux 比较,Zustand 不需求界说杂乱的 reducer、action 类型和 action 创立器。与 MobX 比较,Zustand 避免了运用装饰器和 Proxy,使得代码愈加直观和易于了解。

2. 集成和兼容性

Zustand 与 React 的集成十分紧密,它利用了 React 的上下文和钩子体系来供给状况办理功用。这意味着在运用 React 运用程序时,Zustand 能够无缝地与现有的组件和钩子一起作业。此外,Zustand 还支撑 React Concurrent 形式,确保在最新的 React 版别中也能正常作业。

3. 功用优化

Zustand 经过自动缓存状况值来减少不必要的组件烘托,然后进步功用。它还处理了 Redux 中的“死节点”问题,即在某些情况下,子组件或许无法正确更新的问题。此外,Zustand 经过运用 React 的上下文和钩子体系,避免了 Context loss 问题,这在某些杂乱的组件结构中或许会出现。

4. 中间件支撑

Zustand 支撑大量的中间件,如 Immer、Redux 中间件等,这使得开发者能够根据需求轻松地扩展 Zustand 的功用。这些中间件能够协助处理不行变状况的更新、异步操作等杂乱场景。

5. 状况同享和拜访

Zustand 使得在运用程序的任何地方同享和拜访状况变得十分简略。开发者能够运用 useStore 钩子来获取和更新状况,而不需求经过多层的组件传递 props 或许运用 React Context。

6. 调试和开发体会

Zustand 供给了良好的调试体会,它与 Redux DevTools 兼容,使得开发者能够轻松地查看和调试状况改变。此外,Zustand 还供给了一些内置的调试功用,如 useDebugValue 钩子,能够协助开发者更好地了解状况的改变。

7. 灵活性和可扩展性

Zustand 答应开发者经过自界说钩子和中间件来扩展其功用。这意味着开发者能够根据项目的具体需求来定制状况办理的行为,然后获得更高的灵活性和可扩展性。

总的来说,Zustand 经过其简略、高效和与 React 紧密集成的特性,为 React 运用程序的状况办理供给了一个优异的处理方案。它的易用性、功用优化、中间件支撑和良好的调试体会使其成为了许多开发者在构建 React 运用程序时的首选状况办理库。

怎么运用Zustand

1. 装置 Zustand

首要,你需求装置 Zustand 库。能够经过 npm 或 yarn 来装置:

npm install zustand
# 或许
yarn add zustand

2. 创立一个 store

运用 create 方法创立一个新的 Zustand store。store 是状况的容器,你能够在其中界说状况和与之相关的操作。

import create from 'zustand'
const useStore = create(set => ({
  count: 0,
  increment: () => set(state => ({ count: state.count + 1 })),
  decrement: () => set(state => ({ count: state.count - 1 })),
}))

3. 在组件中运用 store

在你的 React 组件中,运用 useStore 钩子来拜访和更新 store 中的状况。

import { useStore } from './store'
function Counter() {
  const { count, increment, decrement } = useStore()
  return (
    <div>
      <h2>Counter: {count}</h2>
      <button onClick={increment}>Increment</button>
      <button onClick={decrement}>Decrement</button>
    </div>
  )
)

高级特性

运用中间件

Zustand 支撑中间件,你能够运用它来处理异步操作、完成不行变性等。

import create from 'zustand'
import { immer } from 'immer'
const useStore = create(
  immer(set => ({
    items: [],
    addItem: (item) => set(produce((draft) => { draft.items.push(item) })),
  })),
  { middleware: [immer] }
)

与 React Context 集成

Zustand 能够与 React Context 集成,使得在组件树中同享状况愈加简略。

import { createContext, useContext } from 'react'
import { useStore } from './store'
const StoreContext = createContext(null)
function App() {
  const store = useStore()
  return (
    <StoreContext.Provider value={store}>
      {/* 运用程序的其他部分 */}
    </StoreContext.Provider>
  )
}
function Component() {
  const store = useContext(StoreContext)
  // 运用 store ...
}

监听状况改变

你能够订阅 store 的改变,以便在状况改变时履行某些操作。

const unsubscribe = useStore.subscribe(() => {
  console.log('State changed!')
})
// 当不再需求监听时,撤销订阅
unsubscribe()

整理和毁掉 store

在某些情况下,你或许需求整理或毁掉 store。Zustand 供给了 destroy 方法来完成这一点。

const store = useStore()
// 当组件卸载时,整理 store
store.destroy()

运用自界说钩子

你能够创立自界说钩子来封装 store 的某些操作,使得在组件中运用愈加方便。

const useIncrement = () => useStore(state => state.increment)
function Button() {
  const increment = useIncrement()
  return <button onClick={increment}>Increment</button>
}

处理异步操作

Zustand 答应你处理异步操作,并在操作完成后更新状况。

const useStore = create(set => ({
  data: null,
  loading: false,
  error: null,
  fetchData: async () => {
    set(state => ({ loading: true }))
    try {
      const response = await fetch('/api/data')
      const data = await response.json()
      set(state => ({ data, loading: false }))
    } catch (error) {
      set(state => ({ error, loading: false }))
    }
  },
}))

经过这些根本步骤和高级特性,能够开始在 React 运用程序中运用 Zustand 来办理状况。

Zustand 的规划旨在供给一种简略、高效且易于了解的方法来处理状况,无论是对于新手仍是有经历的开发者,都是一个很好的状况办理库。

我的上一篇文章两种最简略的方法教会你怎么完成前端一键换肤!其实能够运用状况办理来办理大局的主题样式,然后再合作zustand的耐久化插件persist来完成一键换肤的功用,这样改写之后也不会丢失状况了

persist耐久化的用法

Zustand 的耐久化插件是一个强大的功用,它答应你将状况保存在客户端的 localStoragesessionStorage 中。这意味着即便在页面改写或关闭后,状况也能够被保存和康复。这个功用对于那些需求耐久保存用户操作的场景十分有用,比方表单数据、用户偏好设置等。

怎么运用耐久化插件

要运用 Zustand 的耐久化功用,你需求先从 zustand 库中导入 persist 中间件。然后,你能够将这个中间件运用到你的 store 创立函数中。

以下是一个简略的比如,展示了怎么运用 persist 中间件来耐久化一个 store 中的状况:

import create from 'zustand'
import { persist } from 'zustand/middleware'
// 界说你的 store 结构和操作
const useSettingsStore = create(
  persist(
    (set) => ({
      theme: 'light',
      setTheme: (theme) => set((state) => ({ theme })),
    }),
    {
      // 耐久化装备项
      key: 'settings', // localStorage 中的 key 值
      whitelist: ['theme'], // 只耐久化 theme 状况
      blacklist: [], // 不耐久化任何状况
      debug: false, // 是否在控制台输出调试信息
    }
  )
)
// 现在你能够在组件中运用 useSettingsStore 钩子来拜访和修改状况
// 状况改变后,它将自动保存到 localStorage 中

在上面的代码中,咱们创立了一个名为 useSettingsStore 的 store,其中包括一个 theme 状况和一个 setTheme 操作。咱们运用 persist 中间件来耐久化这个 store,并设置了 key'settings',这样 localStorage 中就会有一个与之对应的键值对。

耐久化装备项

persist 中间件承受一个装备目标,你能够在这个目标中界说耐久化的行为:

  • key: 存储在 localStoragesessionStorage 中的键名。
  • whitelist: 一个数组,指定哪些状况应该被耐久化。只要包括在数组中的状况才会被保存。
  • blacklist: 一个数组,指定哪些状况不该该被耐久化。这是一个取反的 whitelist
  • debug: 一个布尔值,假如设置为 true,则会在控制台输出额定的调试信息。

自界说耐久化中间件

假如你需求更细粒度的控制或许想要创立自己的耐久化逻辑,你能够经过创立自界说中间件来完成。例如,你能够创立一个中间件来处理特定的存储逻辑或许在耐久化前后履行额定的操作。

const myCustomPersist = (set, get, store) => {
  // 自界说耐久化逻辑
  const originalSet = store.setState
  store.setState = (update, ...args) => {
    // 在更新状况之前或之后履行一些操作
    const result = originalSet(update, ...args)
    // 耐久化状况
    // ...
    return result
  }
}
// 运用自界说耐久化中间件
const useCustomStore = create(
  myCustomPersist(
    set => ({
      // 状况和操作
    })
  )
)

经过运用 Zustand 的耐久化插件,你能够轻松地将状况保存在客户端存储中,然后供给更好的用户体会和更健壮的运用程序状况办理。这个功用特别适用于那些需求跨会话或页面改写坚持状况的场景。

总结

以上便是zustand的全部用法了。已经简略论述了一下为什么要选zustand而不是持续用redux。