kodadot/nft-gallery

View on GitHub
composables/useGraphql.ts

Summary

Maintainability
A
1 hr
Test Coverage
import type { ComputedRef } from 'vue'
import resolveQueryPath from '@/utils/queryPathResolver'

interface DoFetchParams {
  variables?: Record<string, unknown>
}

type UseGraphqlParams<T> = {
  queryPrefix?: string
  queryName: string
  clientName?: string | ComputedRef<string>
  variables?: Record<string, unknown> | ComputedRef<Record<string, unknown>>
  disabled?: ComputedRef<boolean>
  data?: Ref<T | undefined>
  error?: Ref<unknown>
  loading?: Ref<boolean>
}

export default function<T = unknown>({
  queryPrefix = '',
  queryName,
  clientName = '',
  variables = {},
  disabled = computed(() => false),
  data = ref<T>(),
  error = ref(),
  loading = ref(true),
}: UseGraphqlParams<T>) {
  const { client: clientPrefix } = usePrefix()
  const { $consola } = useNuxtApp()

  const prefix = queryPrefix || clientPrefix.value
  const client = clientName || clientPrefix.value

  async function doFetch({
    variables: extraVariables = {},
  }: DoFetchParams = {}) {
    const query = await resolveQueryPath(prefix, queryName)

    try {
      loading.value = true
      const { data: result } = await useAsyncQuery<T>({
        query: query.default,
        variables: {
          ...variables,
          ...extraVariables,
        },
        clientId: isRef(client) ? String(client.value) : client,
      })
      data.value = result.value
    }
    catch (err) {
      ;(error.value as unknown) = err
      dangerMessage(`${err as string}`)
      $consola.error(err)
    }
    finally {
      loading.value = false
    }
  }

  async function refetch(variables: Record<string, unknown> = {}) {
    await doFetch({
      variables,
    })
  }

  if (!disabled.value) {
    if (isRef(variables)) {
      watchEffect(() => doFetch())
    }
    else {
      doFetch()
    }
  }

  return {
    data: data,
    error,
    refetch,
    loading,
  }
}