-
Notifications
You must be signed in to change notification settings - Fork 0
/
Copy pathindex.ts
83 lines (69 loc) · 1.66 KB
/
index.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
/* eslint-disable import/no-unused-modules */
const OK = 200
/** Request options */
export interface RequestOptions extends Omit<RequestInit, 'body'> {
/** Request query params */
query?: Record<string, string>
/** Request body */
body?: Record<string, any> | BodyInit | null
/** Request timeout (ms) */
timeout?: number
}
/** Request */
export async function request<T>(
url = '',
requestOptions: RequestOptions = {}
): Promise<T> {
const {
method = 'get',
query = {},
body,
timeout,
headers,
...options
} = requestOptions
const requestInit: RequestInit = {
method,
...options,
headers: {
'Content-Type': 'application/json',
...headers
}
}
let requestUrl = url
if (query) {
const queryString = new URLSearchParams(query).toString()
if (queryString) {
requestUrl += `?${queryString}`
}
}
if (body) {
requestInit.body =
body instanceof FormData || typeof body === 'string'
? body
: JSON.stringify(body)
}
if (timeout != null) {
const controller = new AbortController()
requestInit.signal = controller.signal
window.setTimeout(() => controller.abort(), timeout)
}
const response = await fetch(requestUrl, requestInit)
if (response.status !== OK) {
throw new Error(
`Failed to fetch: ${response.status} ${response.statusText}`
)
}
return response.json()
}
/** Request factory */
export function createRequest(
url = '',
options: RequestOptions = {}
): typeof request {
return <T>(endpoint = '', requestOptions: RequestOptions = {}) =>
request<T>(url + endpoint, {
...options,
...requestOptions
})
}