-
Notifications
You must be signed in to change notification settings - Fork 16
/
Copy pathgraphql.ts
83 lines (70 loc) · 2.66 KB
/
graphql.ts
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
import { GraphQLClient, type RequestDocument } from 'graphql-request'
import { useRuntimeConfig } from '#imports'
import type { ErrorCode, ServerErrorResponse, ServerResponse } from '~/typedefs/serverResponse'
// eslint-disable-next-line
export let gqlClient: GraphQLClient
export const initializeGqlClient = () => {
if (gqlClient) {
return gqlClient
}
let apiURL
const useLocalApi = useRuntimeConfig().public.NUXT_USE_LOCAL_API as string | undefined
if (useLocalApi) {
apiURL = 'http://127.0.0.1:4000'
} else {
apiURL = 'https://api.findadoc.jp'
}
const client = new GraphQLClient(apiURL)
gqlClient = client
}
export const graphQLClientRequestWithRetry = async <T>(
gqlClientRequestFunction: (
queryOrMutation: RequestDocument,
variables?: unknown
) => Promise<T>,
queryOrMutation: RequestDocument,
variables: unknown,
retryOptions?: graphQLClientRequestWithRetryOptions
): Promise<ServerResponse<T>> => {
let attempts = 0
const retryAmount = retryOptions?.retryAmount || 3
const requestTimeoutInMilliseconds = retryOptions?.requestTimeoutInMilliseconds || 5000
const executeGQLClientRequest = async (): Promise<ServerResponse<T>> => {
try {
const data = await gqlClientRequestFunction(queryOrMutation, variables)
return { data, errors: [], hasErrors: false }
} catch (error) {
if (attempts < retryAmount) {
attempts++
if (attempts > 1) {
await new Promise(resolve => setTimeout(resolve, requestTimeoutInMilliseconds))
}
return executeGQLClientRequest() // retry request
}
// This is a consistent error messaging no matter the type of query or mutation
console.error(`There was an error executing the request: ${error}`)
const serverError = error as ServerErrorResponse
// This map transforms errors if they exist
const errors = serverError.response?.errors?.map(errorResponse => ({
message: errorResponse.message,
fieldWithError: errorResponse.locations,
code: errorResponse.extensions.code as ErrorCode
})) || []
return { data: {} as T, errors, hasErrors: true }
}
}
return executeGQLClientRequest()
}
export interface graphQLClientRequestWithRetryOptions {
requestTimeoutInMilliseconds?: number
retryAmount?: number
}
export interface gqlMutation<T> extends gqlRequest {
variables: {
input: T
}
}
export interface gqlRequest {
query: string
variables: unknown
}