logaretm / villus

🏎 A tiny and fast GraphQL client for Vue.js
https://villus.dev
MIT License
790 stars 31 forks source link

Testing Pinia-Store #211

Closed JarvisH closed 3 months ago

JarvisH commented 3 months ago

When testing a single Pinia-Store outside of a component, the Villus client is not found. All standard component tests using createTestingPinia() work just fine.

Using this code to inject the Villus client:

const pinia = createPinia()
app.provide(VILLUS_CLIENT, createClient(someConfig))
app.use(pinia)
setActivePinia(pinia)
const store = useSomeStore()

vue.getCurrentInstance() returns null and the client is not injected even though it is available.

function resolveClient() {
      const vm = vue.getCurrentInstance();
      // Uses same component provide as its own injections
      // Due to changes in https://github.com/vuejs/vue-next/pull/2424
      let client = vm && vue.inject(VILLUS_CLIENT, resolveInternalInjection(vm, VILLUS_CLIENT));
      if (client)
          setActiveClient(client);
      client = getActiveClient();
      if (client === null || client === undefined) {
          throw new Error('Cannot detect villus Client, did you forget to call `useClient`? Alternatively, you can explicitly pass a client as the `manualClient` argument.');
      }
      return client;
}

Is there a way to achieve this, or is some testing-util needed where a dummy-component is mounted?

logaretm commented 3 months ago

Try using createClient as a Vue app plugin.

If that doesn't work you can also import setActiveClient that is similar to pinias but the plugin method is doing that already under the hood so it should work for you.

import { setActiveClient, createClient } from 'villus';
const client = createClient(someConfig);

app.use(client);
// or
setActiveClient(client);
JarvisH commented 3 months ago

Thank you so much, app.use(client) did the trick. For anyone else interested, this is the final setup for testing a Pinia-Store that uses Villus composables:

beforeEach(() => {
  const app = createApp({})
  const pinia = createPinia()
  app.use(pinia)
  app.use(client)
  setActivePinia(pinia)
})