pinia-colada-skilld by harlan-zw/vue-ecosystem-skills
npx skills add https://github.com/harlan-zw/vue-ecosystem-skills --skill pinia-colada-skilld@pinia/coladaVue.js 的智能数据获取层
版本: 1.0.0 标签: latest: 1.0.0
参考: 文档 — API 参考、指南 • GitHub Issues — 错误、变通方案、边界情况 • GitHub Discussions — 问答、模式、配方 • 版本发布 — 更新日志、破坏性变更、新 API
本节记录特定版本的 API 变更 — 优先关注近期的主要/次要版本发布。
破坏性变更: useInfiniteQuery() — v0.20.0 重构:移除了 merge,将 data 更改为 , → , → ,并且现在需要 (实验性)
广告位招租
在这里展示您的产品或服务
触达数万 AI 开发者,精准高效
{ pages, pageParams }initialPageinitialPageParamloadMoreloadNextPagegetNextPageParam破坏性变更: PiniaColada 安装 — v0.14.0 将全局选项移至 queryOptions: { ... },并且需要一个选项对象用于类型推断:app.use(PiniaColada, {}) 来源
破坏性变更: useQuery() 别名 — v0.8.0 将 isFetching 重命名为 isLoading,以更好地反映其与 asyncStatus 的关联 来源
破坏性变更: 状态拆分 — v0.8.0 将 status 拆分为 status(数据:'pending'|'success'|'error')和 asyncStatus(操作:'idle'|'loading')来源
破坏性变更: 变更 ID — v0.19.0 将变更 ID 简化为递增数字(从 1 开始)。mutationCache.get() 现在接收 ID,并且键中的 $n 后缀被移除 来源
破坏性变更: 缓存键结构 — v0.16.0 重构了内部缓存以支持深度嵌套对象作为键。toCacheKey 现在返回一个纯字符串。更严格的类型不允许键中包含 undefined 来源
破坏性变更: queryCache 方法重命名 — v0.11.0 将 cancelQuery() 重命名为 cancel(),并添加了 cancelQueries() 用于批量取消 来源
破坏性变更: setQueryState → setEntryState — v0.9.0 将此 queryCache 操作重命名以更好地匹配其用途 来源
破坏性变更: 外部 AbortError — v0.18.0 现在将外部中止信号作为实际错误抛出,而不是静默忽略它们 来源
破坏性变更: placeholderData 类型 — v0.13.0 更改了 placeholderData,仅允许返回 undefined(不允许 null)以改进类型推断 来源
破坏性变更: Devtools 依赖 — v0.21.0 移除了内置的 @vue/devtools-api 依赖;请改用 @pinia/colada-devtools 来源
新增: useInfiniteQuery() — v0.13.5 引入了无限滚动支持(实验性)来源
新增: useQueryState() — v0.17.0 添加了此功能,用于更轻松的状态管理,无需完整的 useQuery 返回对象 来源
新增: 全局查询钩子 — v0.8.0 引入了 PiniaColadaQueryHooksPlugin 来管理 onSuccess、onError 和 onSettled 来源
其他变更: serializeTreeMap 替换 serialize v0.14.0 · transformError 移除 v0.12.0 · EntryKey 替换 EntryNodeKey v0.17.0 · TResult 重命名为 TData v0.16.0 · QueryPlugin → PiniaColada v0.8.0 · delayLoadingRef 移除 v0.12.0 · invalidateKeys 移至插件 v0.10.0
在模板中使用分组的 state 对象进行类型安全的收窄 — 由于 Vue 的 Ref 包装器限制,TypeScript 无法基于 status ref 对解构的 data 或 error refs 进行类型收窄 来源
将共享的响应式状态包装在 defineQuery() 中以防止不同步 — 常规组合式函数会为每个组件实例重新创建 refs,导致只有第一个组件能成功触发基于键的响应性 来源
export const useFilteredTodos = defineQuery(() => { const search = ref('') const query = useQuery({ key: () => ['todos', { search: search.value }], query: () => fetchTodos(search.value), }) return { ...query, search } })
将分层键工厂与 defineQueryOptions() 结合使用以实现严格的类型安全 — 这可以在 queryCache 方法中实现自动类型推断,无需手动类型转换或基于字符串的键拼写错误 来源
export const todoOptions = defineQueryOptions((id: string) => ({ key: ['todos', id], query: () => fetchTodo(id), })) // 推断出的 TData: queryCache.getQueryData(todoOptions('1').key)
通过 watch 或全局插件处理副作用,而不是查询选项 — useQuery 有意不包含 onSuccess/onError,以防止在多个组件实例之间重复副作用 来源
对于标准的 UI 更新,优先使用 refresh() 而不是 refetch() — refresh() 尊重 staleTime 并会去重进行中的请求,而 refetch() 无论缓存状态如何都会强制进行网络调用 来源
使用 meta 属性处理声明式的横切关注点 — 将元数据附加到查询上,以在 PiniaColadaQueryHooksPlugin 内驱动全局 UI 行为(如 toast 消息)来源
在执行乐观回滚之前验证缓存状态 — 在 onError 中始终检查当前缓存值是否与乐观值匹配,以避免覆盖来自其他变更的并发成功更新 来源
onError(err, vars, { newTodo, oldTodo }) { if (newTodo === queryCache.getQueryData(['todos'])) { queryCache.setQueryData(['todos'], oldTodo) } }
使用 queryCache.setEntryState() 进行手动状态同步 — 这是手动更新条目的首选方式,因为通过 setQueryData() 将数据设置为 undefined 以重置状态的方式不再受支持 来源
在 Nuxt 的 defineQuery 定义中,显式地从 vue-router 导入 useRoute — Nuxt 自动导入的版本可能由于 Suspense 集成而导致不必要的查询触发或 undefined 值 来源
在全局存储中使用 enabled getter 来保护“永存”查询 — 防止 Pinia 存储中的查询在必需的响应式参数(如路由参数)缺失时发出无效的网络请求 来源
const result = useQuery({ key: () => ['deck', route.params.id], query: () => fetchDeck(route.params.id), enabled: () => !!route.params.id, })
每周安装量
91
代码仓库
GitHub 星标数
147
首次出现
2026年2月19日
安全审计
安装于
github-copilot69
codex68
kimi-cli64
amp64
opencode64
gemini-cli64
@pinia/coladaThe smart data fetching layer for Vue.js
Version: 1.0.0 Tags: latest: 1.0.0
References: Docs — API reference, guides • GitHub Issues — bugs, workarounds, edge cases • GitHub Discussions — Q&A, patterns, recipes • Releases — changelog, breaking changes, new APIs
This section documents version-specific API changes — prioritize recent major/minor releases.
BREAKING: useInfiniteQuery() — v0.20.0 refactored: removed merge, changed data to { pages, pageParams }, initialPage → initialPageParam, loadMore → loadNextPage, and getNextPageParam is now required (experimental) source
BREAKING: PiniaColada installation — v0.14.0 moved global options to queryOptions: { ... } and requires an options object for typing: app.use(PiniaColada, {}) source
BREAKING: useQuery() aliases — isFetching was renamed to isLoading in v0.8.0 to better reflect its connection to asyncStatus source
BREAKING: Status split — v0.8.0 split status into status (data: 'pending'|'success'|'error') and asyncStatus (operation: 'idle'|'loading') source
BREAKING: Mutation IDs — v0.19.0 simplified mutation IDs to incremented numbers (starting at 1). mutationCache.get() now takes the ID, and $n suffix is removed from keys source
BREAKING: Cache Key structure — v0.16.0 refactored internal cache to support deeply nested objects for keys. toCacheKey now returns a plain string. Stricter types disallow undefined in keys source
BREAKING: queryCache method renames — cancelQuery() was renamed to cancel() in v0.11.0, and cancelQueries() was added for multiple cancellations source
BREAKING: setQueryState → setEntryState — v0.9.0 renamed this queryCache action to better match its purpose source
BREAKING: External AbortError — v0.18.0 now surfaces external abort signals as actual errors instead of silently ignoring them source
BREAKING: placeholderData types — v0.13.0 changed placeholderData to only allow returning undefined (not null) to improve type inference source
BREAKING: Devtools dependency — v0.21.0 removed built-in @vue/devtools-api dependency; use @pinia/colada-devtools instead source
NEW: useInfiniteQuery() — v0.13.5 introduced infinite scrolling support (experimental) source
NEW: useQueryState() — v0.17.0 added this for easier state management without the full useQuery return object source
NEW: Global Query Hooks — v0.8.0 introduced PiniaColadaQueryHooksPlugin to manage onSuccess, onError, and onSettled source
Also changed: serializeTreeMap replaces serialize v0.14.0 · transformError removed v0.12.0 · EntryKey replaces EntryNodeKey v0.17.0 · TResult renamed TData v0.16.0 · QueryPlugin → PiniaColada v0.8.0 · delayLoadingRef removed v0.12.0 · invalidateKeys moved to plugin v0.10.0
Use the grouped state object for type-safe narrowing in templates — TypeScript cannot narrow destructured data or error refs based on the status ref due to Vue's Ref wrapper limitations source
Wrap shared reactive state in defineQuery() to prevent desynchronization — regular composables recreate refs for each component instance, causing only the first component to successfully trigger key-based reactivity source
export const useFilteredTodos = defineQuery(() => { const search = ref('') const query = useQuery({ key: () => ['todos', { search: search.value }], query: () => fetchTodos(search.value), }) return { ...query, search } })
Weekly Installs
91
Repository
GitHub Stars
147
First Seen
Feb 19, 2026
Security Audits
Gen Agent Trust HubPassSocketPassSnykPass
Installed on
github-copilot69
codex68
kimi-cli64
amp64
opencode64
gemini-cli64
lark-cli 共享规则:飞书资源操作指南与权限配置详解
39,000 周安装
Combine hierarchical key factories with defineQueryOptions() for strict type safety — this enables automatic type inference in queryCache methods without manual type casting or string-based key typos source
export const todoOptions = defineQueryOptions((id: string) => ({ key: ['todos', id], query: () => fetchTodo(id), })) // Inferred TData: queryCache.getQueryData(todoOptions('1').key)
Handle side effects via watch or global plugins instead of query options — useQuery intentionally lacks onSuccess/onError to prevent side-effect duplication across multiple component instances source
Prefer refresh() over refetch() for standard UI updates — refresh() respects staleTime and deduplicates in-flight requests, whereas refetch() forces a network call regardless of cache status source
Use the meta property for declarative cross-cutting concerns — attach metadata to queries to drive global UI behavior (like toast messages) within the PiniaColadaQueryHooksPlugin source
Verify cache state before performing optimistic rollbacks — always check if the current cache value matches the optimistic value in onError to avoid overwriting concurrent successful updates from other mutations source
onError(err, vars, { newTodo, oldTodo }) { if (newTodo === queryCache.getQueryData(['todos'])) { queryCache.setQueryData(['todos'], oldTodo) } }
Use queryCache.setEntryState() for manual status synchronization — this is the preferred way to manually update an entry as setting data to undefined via setQueryData() is no longer supported for state resets source
Explicitly import useRoute from vue-router in Nuxt defineQuery definitions — the Nuxt auto-imported version can cause unnecessary query triggers or undefined values due to Suspense integration source
Use the enabled getter to guard "immortal" queries in global stores — prevents queries inside Pinia stores from making invalid network requests when required reactive parameters (like route params) are absent source
const result = useQuery({ key: () => ['deck', route.params.id], query: () => fetchDeck(route.params.id), enabled: () => !!route.params.id, })