GraphQL in Vue3 using Apollo

ยท

2 min read

Today I am going to show you how to use GraphQL in a Vue3 web application.

To keep this blog post simple and focused on the topic only, I will assume that you know how to create a Vue 3 app using the composition API and what GraphQL is.

First of all we need to install the following packages:

npm install --save @apollo/client @vue/apollo-composable @vue/composition-api graphql graphql-tag react vue@3.0.11 --legacy-peer-deps

As you might have noticed, we need to install react as it's a dependency of the Apollo client. The --legacy-peer-deps will allow us to install @vue/composition-api as it's a dependency of @vue/apollo-composable. And at the time of writing, vue@3.1.2 is not working properly with Apollo so we need to install vue@3.0.11.

At this point we are half way through the finish.

We now need to initialize the Apollo plugin and I like it to organize it this way:

Create a new folder called Plugins and inside create this file useApolloPlugin.js:

import { ApolloClient, InMemoryCache } from '@apollo/client'

const apolloClient = new ApolloClient( {
    uri: 'https://yourservicedomain.com/graphql',
    cache: new InMemoryCache(),
    headers: {
        "Authorization": "Bearer TO_ADD_FOR_TESTING_PURPOSES"
    }
} )

export default apolloClient

In your app.js file write the following:

import { createApp, h } from 'vue'
import { provideApolloClient } from '@vue/apollo-composable'
import apolloClient from '@/Plugins/useApolloPlugin'

const app = createApp( {
    setup () {
        provideApolloClient( apolloClient )
    },
    ...
} )

To simplify the GraphQL fetch handling process, I create a file in GraphQL/index.js with the following content:

import { useQuery, useResult } from '@vue/apollo-composable'
import { watch } from 'vue';

export default {
    runQuery ( query, model ) {
        const { result } = useQuery( query )

        watch(useResult( result, []), data => {
            model.value = data
        })
    }
}

The above file will send the query and once we have a result, will set the value on the given reactive variable model.

We can now start using Apollo to fetch queries, and this is how I like to do it:

<template>
    <AppLayout>
        <button @click="fetchItems">Fetch items</button>
        <div v-for="item in items" :key="item.id">
            {{ item }}
         </div>
    </AppLayout>
</template>

<script>
import { ref } from 'vue'
import { gql } from 'graphql-tag'
import GraphQL from '@/GraphQL'

export default {
    setup () {
        let items = ref( [] )

        const fetchItemsQuery = gql`
            query ItemsList {
                items  {
                    id
                    name
                }
            }
        `

        const fetchItems = () => GraphQL.runQuery( fetchItemsQuery, items )

        return {
            spaces,
            fetchItems
        }
    }
}
</script>