@elastic-suite/gally-admin-components
Version:
Components package for gally admin BO
99 lines (90 loc) • 2.36 kB
text/typescript
import {
Dispatch,
SetStateAction,
useCallback,
useEffect,
useState,
} from 'react'
import Router from 'next/router'
import { useTranslation } from 'next-i18next'
import {
AuthError,
IFetch,
IGraphqlApi,
ILoadResource,
LoadStatus,
fetchGraphql,
isError,
storageRemove,
tokenStorageKey,
} from '@elastic-suite/gally-admin-shared'
import { useLog } from './useLog'
export function useApiGraphql(secure = true): IGraphqlApi {
const { i18n } = useTranslation('common')
const log = useLog()
const { t } = useTranslation('alert')
return useCallback(
async <T extends object>(
query: string,
variables?: Record<string, unknown>,
options?: RequestInit
) => {
try {
const json = await fetchGraphql<T>(
i18n.language,
query,
variables,
options,
secure
)
return json
} catch (error) {
if (secure && error instanceof AuthError) {
storageRemove(tokenStorageKey)
Router.push('/login')
log(t('Expired JWT Token'))
} else {
log(error)
}
return { error }
}
},
[i18n.language, log, secure, t]
)
}
export function useGraphqlApi<T extends object>(
query: string,
variables?: Record<string, unknown>,
options?: RequestInit,
conditions = true
): [IFetch<T>, Dispatch<SetStateAction<T>>, ILoadResource] {
const graphqlApi = useApiGraphql()
const [response, setResponse] = useState<IFetch<T>>({
status: LoadStatus.IDLE,
})
const updateResponse = useCallback((data: SetStateAction<T>): void => {
setResponse((prevState) => ({
...prevState,
data: data instanceof Function ? data(prevState.data) : data,
}))
}, [])
const load = useCallback(() => {
if (conditions) {
setResponse((prevState) => ({
data: prevState.data,
status: LoadStatus.LOADING,
}))
graphqlApi<T>(query, variables, options).then((json) => {
if (isError(json)) {
setResponse({ error: json.error, status: LoadStatus.FAILED })
} else {
setResponse({ data: json, status: LoadStatus.SUCCEEDED })
}
})
}
}, [conditions, graphqlApi, options, query, variables])
useEffect(() => {
load()
}, [load])
return [response, updateResponse, load]
}