CtrlK
BlogDocsLog inGet started
Tessl Logo

tessl/npm-tanstack--vue-query

Hooks for managing, caching and syncing asynchronous and remote data in Vue

Pending
Overview
Eval results
Files

plugin-setup.mddocs/

Plugin & Setup

Vue plugin for installing TanStack Query with global configuration, dependency injection, and lifecycle management for both Vue 2 and Vue 3 applications.

Capabilities

VueQueryPlugin

Main Vue plugin for setting up TanStack Query in your application.

/**
 * Vue plugin for installing TanStack Query
 * Provides QueryClient via Vue's dependency injection system
 */
interface VueQueryPlugin {
  install(app: any, options?: VueQueryPluginOptions): void;
}

interface VueQueryPluginOptions {
  queryClient?: QueryClient;
  queryClientConfig?: QueryClientConfig;
  queryClientKey?: string;
  enableDevtoolsV6Plugin?: boolean;
  clientPersister?: ClientPersister;
  clientPersisterOnSuccess?: (client: QueryClient) => void;
}

type ClientPersister = (client: QueryClient) => [() => void, Promise<void>];

interface QueryClientConfig {
  queryCache?: QueryCache;
  mutationCache?: MutationCache;
  defaultOptions?: DefaultOptions;
}

Usage Examples:

// Vue 3 setup
import { createApp } from 'vue';
import { VueQueryPlugin, QueryClient } from '@tanstack/vue-query';
import App from './App.vue';

const app = createApp(App);

// Basic setup with default configuration
const queryClient = new QueryClient();
app.use(VueQueryPlugin, { queryClient });

// Advanced setup with custom configuration
const queryClient = new QueryClient({
  defaultOptions: {
    queries: {
      staleTime: 1000 * 60 * 5,    // 5 minutes
      gcTime: 1000 * 60 * 30,      // 30 minutes
      retry: 3,
      refetchOnWindowFocus: false,
      refetchOnReconnect: 'always',
    },
    mutations: {
      retry: 1,
      throwOnError: true,
    },
  },
});

app.use(VueQueryPlugin, {
  queryClient,
  enableDevtoolsV6Plugin: true,
});

app.mount('#app');

// Vue 2 setup with Composition API
import Vue from 'vue';
import VueCompositionAPI from '@vue/composition-api';
import { VueQueryPlugin, QueryClient } from '@tanstack/vue-query';
import App from './App.vue';

Vue.use(VueCompositionAPI);

const queryClient = new QueryClient();
Vue.use(VueQueryPlugin, { queryClient });

new Vue({
  render: h => h(App),
}).$mount('#app');

// Setup with configuration object instead of client instance
app.use(VueQueryPlugin, {
  queryClientConfig: {
    defaultOptions: {
      queries: {
        staleTime: 1000 * 60 * 10,
        retry: 2,
      },
    },
  },
  enableDevtoolsV6Plugin: process.env.NODE_ENV === 'development',
});

// Multiple client setup with keys
const mainClient = new QueryClient();
const analyticsClient = new QueryClient();

app.use(VueQueryPlugin, { 
  queryClient: mainClient,
  queryClientKey: 'main' 
});

app.use(VueQueryPlugin, { 
  queryClient: analyticsClient,
  queryClientKey: 'analytics' 
});

// Usage in components with multiple clients
export default {
  setup() {
    const mainClient = useQueryClient('main');
    const analyticsClient = useQueryClient('analytics');
    
    // Use different clients for different purposes
    const { data: userData } = useQuery({
      queryKey: ['user'],
      queryFn: fetchUser,
    }, mainClient);
    
    const { mutate: trackEvent } = useMutation({
      mutationFn: trackAnalyticsEvent,
    }, analyticsClient);
    
    return { userData, trackEvent };
  }
};

Client Persistence

Setup for persisting query client state across application restarts.

/**
 * Client persister function type for state persistence
 * @param client - QueryClient instance to persist
 * @returns Tuple of [unmount function, ready promise]
 */
type ClientPersister = (client: QueryClient) => [() => void, Promise<void>];

Usage Examples:

import { VueQueryPlugin, QueryClient } from '@tanstack/vue-query';
import { persistQueryClient } from '@tanstack/query-persist-client-core';
import { createSyncStoragePersister } from '@tanstack/query-sync-storage-persister';

// Create persister
const persister = createSyncStoragePersister({
  storage: window.localStorage,
  key: 'vue-query-cache',
});

// Setup client persistence
const queryClient = new QueryClient({
  defaultOptions: {
    queries: {
      gcTime: 1000 * 60 * 60 * 24, // 24 hours
    },
  },
});

app.use(VueQueryPlugin, {
  queryClient,
  clientPersister: (client) => {
    return persistQueryClient({
      queryClient: client,
      persister,
      maxAge: 1000 * 60 * 60 * 24, // 24 hours
    });
  },
  clientPersisterOnSuccess: (client) => {
    console.log('Query cache restored from storage');
  },
});

// Custom persister implementation
const customPersister = (client) => {
  let intervalId;
  
  // Restore from storage
  const storedState = localStorage.getItem('query-cache');
  if (storedState) {
    const parsedState = JSON.parse(storedState);
    client.setQueriesData({}, parsedState);
  }
  
  // Save to storage periodically
  intervalId = setInterval(() => {
    const state = client.getQueriesData({});
    localStorage.setItem('query-cache', JSON.stringify(state));
  }, 30000); // Save every 30 seconds
  
  const unmount = () => {
    clearInterval(intervalId);
  };
  
  const ready = Promise.resolve();
  
  return [unmount, ready];
};

app.use(VueQueryPlugin, {
  queryClient,
  clientPersister: customPersister,
});

DevTools Integration

Setup for Vue DevTools integration to inspect query state.

interface VueQueryPluginOptions {
  enableDevtoolsV6Plugin?: boolean;
}

Usage Examples:

import { VueQueryPlugin, QueryClient } from '@tanstack/vue-query';

// Enable devtools in development
app.use(VueQueryPlugin, {
  queryClient: new QueryClient(),
  enableDevtoolsV6Plugin: process.env.NODE_ENV === 'development',
});

// Conditional devtools setup
const isDevelopment = import.meta.env.DEV;
const enableDevtools = isDevelopment && window.__VUE_DEVTOOLS_GLOBAL_HOOK__;

app.use(VueQueryPlugin, {
  queryClient: new QueryClient(),
  enableDevtoolsV6Plugin: enableDevtools,
});

SSR Setup

Server-side rendering configuration for Nuxt.js and other SSR frameworks.

Usage Examples:

// Nuxt 3 plugin setup
// plugins/vue-query.client.ts
import { VueQueryPlugin, QueryClient, hydrate, dehydrate } from '@tanstack/vue-query';

export default defineNuxtPlugin((nuxtApp) => {
  const queryClient = new QueryClient({
    defaultOptions: {
      queries: {
        staleTime: 1000 * 60 * 5,
      },
    },
  });

  // Hydrate on client
  if (process.client) {
    const dehydratedState = nuxtApp.ssrContext?.nuxt?.data?.vueQueryState;
    if (dehydratedState) {
      hydrate(queryClient, dehydratedState);
    }
  }

  nuxtApp.vueApp.use(VueQueryPlugin, { queryClient });

  return {
    provide: {
      queryClient,
    },
  };
});

// Server-side data fetching
// server/api/ssr-data.ts
export default defineEventHandler(async (event) => {
  const queryClient = new QueryClient();
  
  // Prefetch data on server
  await queryClient.prefetchQuery({
    queryKey: ['posts'],
    queryFn: () => $fetch('/api/posts'),
  });
  
  // Dehydrate for client
  const dehydratedState = dehydrate(queryClient);
  
  return {
    dehydratedState,
  };
});

// Vite SSR setup
// entry-server.js
import { createApp } from 'vue';
import { VueQueryPlugin, QueryClient, dehydrate } from '@tanstack/vue-query';
import { createSSRApp } from 'vue';

export async function render(url, manifest) {
  const app = createSSRApp(App);
  const queryClient = new QueryClient();
  
  app.use(VueQueryPlugin, { queryClient });
  
  // Prefetch critical data
  await queryClient.prefetchQuery({
    queryKey: ['user'],
    queryFn: fetchCurrentUser,
  });
  
  const html = await renderToString(app);
  const state = dehydrate(queryClient);
  
  return { html, state };
}

// entry-client.js
import { createApp } from 'vue';
import { VueQueryPlugin, QueryClient, hydrate } from '@tanstack/vue-query';

const app = createApp(App);
const queryClient = new QueryClient();

// Hydrate with server state
if (window.__INITIAL_STATE__) {
  hydrate(queryClient, window.__INITIAL_STATE__.queryState);
}

app.use(VueQueryPlugin, { queryClient });
app.mount('#app');

Types

// Plugin configuration
interface VueQueryPluginOptions {
  queryClient?: QueryClient;
  queryClientConfig?: QueryClientConfig;
  queryClientKey?: string;
  enableDevtoolsV6Plugin?: boolean;
  clientPersister?: ClientPersister;
  clientPersisterOnSuccess?: (client: QueryClient) => void;
}

// Configuration interfaces
interface QueryClientConfig {
  queryCache?: QueryCache;
  mutationCache?: MutationCache;
  defaultOptions?: DefaultOptions;
}

interface DefaultOptions {
  queries?: QueryObserverOptions & ShallowOption;
  mutations?: MutationObserverOptions & ShallowOption;
  hydrate?: HydrateOptions['defaultOptions'];
  dehydrate?: DehydrateOptions;
}

// Persister types
type ClientPersister = (client: QueryClient) => [() => void, Promise<void>];

// Hydration types
interface DehydrateOptions {
  shouldDehydrateQuery?: (query: Query) => boolean;
  shouldDehydrateMutation?: (mutation: Mutation) => boolean;
}

interface HydrateOptions {
  defaultOptions?: DefaultOptions;
  mutations?: Array<MutationOptions>;
  queries?: Array<QueryOptions>;
}

interface DehydratedState {
  mutations: Array<DehydratedMutation>;
  queries: Array<DehydratedQuery>;
}

interface DehydratedQuery {
  queryHash: string;
  queryKey: QueryKey;
  state: QueryState;
}

interface DehydratedMutation {
  mutationKey?: MutationKey;
  state: MutationState;
}

Install with Tessl CLI

npx tessl i tessl/npm-tanstack--vue-query

docs

helpers.md

index.md

mutations.md

plugin-setup.md

queries.md

query-client.md

status-utilities.md

tile.json