译零 TransZero · TanStack Query v4 中文文档
主站

概览

@tanstack/solid-query 包提供了一级 API,用于在 SolidJS 中使用 TanStack Query。

例子

TypeScript
1import {2  QueryClient,3  QueryClientProvider,4  createQuery,5} from "@tanstack/solid-query";6import { Switch, Match, For } from "solid-js";7 8const queryClient = new QueryClient();9 10function Example() {11  const query = createQuery(() => ["todos"], fetchTodos);12 13  return (14    <div>15      <Switch>16        <Match when={query.isLoading}>17          <p>Loading...</p>18        </Match>19        <Match when={query.isError}>20          <p>Error: {query.error.message}</p>21        </Match>22        <Match when={query.isSuccess}>23          <For each={query.data}>{(todo) => <p>{todo.title}</p>}</For>24        </Match>25      </Switch>26    </div>27  );28}29 30function App() {31  return (32    <QueryClientProvider client={queryClient}>33      <Example />34    </QueryClientProvider>35  );36}

可用的函数

Solid Query 提供了一些有用的原语及函数,使得在 SolidJS 中操作并管理服务器状态变得非常容易。

  • createQuery
  • createQueries
  • createInfiniteQueries
  • createMutation
  • useIsFetching
  • useIsMutating
  • useQueryClient
  • QueryClient
  • QueryClientProvider

Solid Query & React Query 之间的主要差异

Solid Query 提供了一个与 React Query 类似的 API,但有一些关键的区别需要注意。

  • 为了保持状态的可响应性,在使用 createQuery、createQueries、createInfiniteQuery 及 useIsFetching 时,查询键值必须包裹在一个函数内:
TypeScript
1// ❌ react version2useQuery(["todos", todo], fetchTodos);3 4// ✅ solid version5createQuery(() => ["todos", todo()], fetchTodos);
  • 如果你在<Suspense>组件内访问和查询数据,Suspense 就能开箱即用:
TypeScript
1import { For, Suspense } from "solid-js";2 3function Example() {4  const query = createQuery(() => ["todos"], fetchTodos);5  return (6    <div>7      {/* ✅ 将触发正确的 loading,因为是在 suspense 中访问数据 */}8      <Suspense fallback={"Loading..."}>9        <For each={query.data}>{(todo) => <div>{todo.title}</div>}</For>10      </Suspense>11      {/* ❌ 不会触发 loading,因为是在 suspense 外访问数据. */}12      <For each={query.data}>{(todo) => <div>{todo.title}</div>}</For>13    </div>14  );15}
  • Solid Query 的原语(如createX)不支持解构操作。这些函数的返回值是一个 store(译注:不清楚 Solid 中 store 的正式名称),它们的属性在内部被追踪,以支持 SolidJS 的响应式写法:
TypeScript
1import {2  QueryClient,3  QueryClientProvider,4  createQuery,5} from "@tanstack/solid-query";6import { Match, Switch } from "solid-js";7 8const queryClient = new QueryClient();9 10export default function App() {11  return (12    <QueryClientProvider client={queryClient}>13      <Example />14    </QueryClientProvider>15  );16}17 18function Example() {19  // ❌ react version -- 支持解构,因为 react 内部未处理响应式的属性20  // const { isLoading, error, data } = useQuery(['repoData'], () =>21  //   fetch('https://api.github.com/repos/tannerlinsley/react-query').then(res =>22  //     res.json()23  //   )24  // )25 26  // ✅ solid version -- 不支持解构,因为 solid 以此完成响应式编程27  const query = createQuery(28    () => ["repoData"],29    () =>30      fetch("https://api.github.com/repos/tannerlinsley/react-query").then(31        (res) => res.json()32      )33  );34 35  // ✅ 在响应式UI的上下文中访问数据36  return (37    <Switch>38      <Match when={query.isLoading}>Loading...</Match>39      <Match when={query.isError}>Error: {query.error.message}</Match>40      <Match when={query.isSuccess}>41        <div>42          <h1>{query.data.name}</h1>43          <p>{query.data.description}</p>44          <strong>👀 {query.data.subscribers_count}</strong>{" "}45          <strong>✨ {query.data.stargazers_count}</strong>{" "}46          <strong>🍴 {query.data.forks_count}</strong>47        </div>48      </Match>49    </Switch>50  );51}
  • 如果你希望查询的配置项内容是响应式的,你需要使用对象访问器(getter/setter)的语法来传递它们。可能在一开始会看着比较奇怪,但它确实是更加符合 Solid 习惯的(idiomatic) Solid 代码:
TypeScript
1import {2  QueryClient,3  QueryClientProvider,4  createQuery,5} from "@tanstack/solid-query";6import { createSignal, For } from "solid-js";7 8const queryClient = new QueryClient();9 10function Example() {11  const [enabled, setEnabled] = createSignal(false);12  const query = createQuery(() => ["todos"], fetchTodos, {13    // ❌ 直接单独传递选项不是响应式的14    // enabled: enabled(),15 16    // ✅ 传递一个对象访问器的是响应式的17    get enabled() {18      return enabled();19    },20  });21 22  return (23    <div>24      <Switch>25        <Match when={query.isLoading}>26          <p>Loading...</p>27        </Match>28        <Match when={query.isError}>29          <p>Error: {query.error.message}</p>30        </Match>31        <Match when={query.isSuccess}>32          <For each={query.data}>{(todo) => <p>{todo.title}</p>}</For>33        </Match>34      </Switch>35      <button onClick={() => setEnabled(!enabled())}>Toggle enabled</button>36    </div>37  );38}39 40function App() {41  return (42    <QueryClientProvider client={queryClient}>43      <Example />44    </QueryClientProvider>45  );46}
  • 错误可以用 SolidJS 本身的 ErrorBoundary 组件来捕获和重置。在 Solid Query 中不需要 QueryErrorResetBoundary。

  • 由于属性的跟踪是由 Solid 的 fine grained reactivity 处理,因此不需要如 notifyOnChangeProps 之类的配置项

本页为 TanStack Query 文档(Solid 版)的非官方中文翻译,原文由上游团队维护,遵循 MIT 许可。 译文如有偏差,以英文原文为准。

本页译文取自社区中文版 react-query-web-i18n(MIT),非本站翻译,已停止更新,内容可能与当前 API 有出入。

译自上游 (未记录版本)