-
Notifications
You must be signed in to change notification settings - Fork 9
Expand file tree
/
Copy pathapi.ts
More file actions
122 lines (112 loc) · 4.62 KB
/
Copy pathapi.ts
File metadata and controls
122 lines (112 loc) · 4.62 KB
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
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
import { toast } from '@datagouv/components-next'
export default defineNuxtPlugin({
async setup(nuxtApp) {
const config = useRuntimeConfig()
const token = useToken()
const cookie = useRequestHeader('cookie')
const route = useRoute()
const { t, locale } = useTranslation()
const publicApiBase = config.public.apiBase as string
// Only set on the server (private runtimeConfig keys aren't exposed to the client).
const privateNetworkApiBase = (config.apiBasePrivateNetwork as string) || ''
const makeApi = (apiOptions: { sendJson: boolean, redirectOn404: boolean }) => {
return $fetch.create({
baseURL: publicApiBase,
onRequest(context) {
const { options } = context
// On the server, route requests through the private-network API base (when configured)
// so SSR doesn't go over the public internet. ofetch runs onRequest before applying
// baseURL, so rewriting the (absolute) request here makes baseURL a no-op server-side.
if (import.meta.server && privateNetworkApiBase && typeof context.request === 'string') {
context.request = toServerApiUrl(context.request, publicApiBase, privateNetworkApiBase)
}
if (apiOptions.sendJson) {
options.headers.set('Content-Type', 'application/json')
}
options.headers.set('Accept', 'application/json')
options.credentials = 'include'
if (config.public.devApiKey) {
options.headers.set('X-API-KEY', config.public.devApiKey)
}
if (token.value) {
options.headers.set('Authentication-Token', token.value)
}
if (cookie) {
options.headers.set('Cookie', cookie)
}
if (locale) {
if (!options.query) {
options.query = {}
}
options.query['lang'] = locale
}
},
async onResponseError({ response, options }) {
if (response.status === 404) {
if (apiOptions.redirectOn404) {
await nuxtApp.runWithContext(() => showError({ statusCode: 404, statusMessage: 'Page Not Found', fatal: true }))
}
else {
// We don't want to show the toast for default 404 Flask response
return
}
}
if (response.status === 401) {
if (response._data?.response && typeof response._data.response === 'object' && response._data.response?.reauth_required === true) {
await nuxtApp.runWithContext(() => navigateTo({ path: '/verify', query: { next: route.fullPath } }))
}
else {
await nuxtApp.runWithContext(() => navigateTo({ path: '/login', query: { next: route.fullPath } }))
}
}
if (response.status === 429) {
toast.error(t('Erreur API 429 : trop de requêtes. Veuillez réessayer plus tard.'))
return
}
if (response.status === 403) {
toast.error(t('Erreur API 403 : accès interdit.'))
return
}
let message = ''
if (response._data) {
try {
if ('error' in response._data) {
message = response._data.error
}
else if ('message' in response._data) {
message = response._data.message
}
else if ('errors' in response._data && typeof response._data.errors === 'object') {
message = Object.entries(response._data.errors).map(([key, value]) => `${key}: ${value}`).join(' ; ')
}
else if ('response' in response._data && 'errors' in response._data.response && Array.isArray(response._data.response.errors)) {
message = response._data.response.errors.join(' ; ')
}
}
catch (e) {
console.error(e)
}
}
if (options?.method && ['POST', 'PUT', 'PATCH'].includes(options.method) && response.status === 400) {
toast.error(t(`Le formulaire contient des erreurs. ${message}`))
return
}
if (message) {
toast.error(message)
}
else {
toast.error(t(`L'API a retourné une erreur inattendue`))
}
},
})
}
// Expose to useNuxtApp().$api
return {
provide: {
api: makeApi({ sendJson: true, redirectOn404: false }),
fileApi: makeApi({ sendJson: false, redirectOn404: false }),
apiWith404: makeApi({ sendJson: true, redirectOn404: true }),
},
}
},
})