Posting my wrapper for a native fetch()
API:
const API_URL: string = process.env.YOUR_ENV_NAME || 'https://example.com';
export default async <T, B>(
url: string,
method = 'get',
body: B | undefined = undefined,
headers = {}
): Promise<T | { error: string }> => {
const controller = new AbortController();
try {
const res = await fetch(`${API_URL}${url}`, {
method: method.toUpperCase(),
signal: controller.signal,
body: typeof body === 'object' ? JSON.stringify(body) : undefined,
mode: 'cors',
headers: {
'Content-type': 'application/json',
...headers
}
});
if (!res.ok) {
const error = await res.json();
return { error: error.code };
}
return await res.json();
} catch (err) {
return { error: err };
} finally {
controller.abort();
}
};
And we can use it this way:
const result = await api<IResponse, IBody>('url', 'post', { name: 'asd' });
if (result.error) {
// handle error;
} else {
// handle successful response
}
We can type our response as 1st type argument, and body as 2nd.
I wrote it to use in my React app. Improvements of this code snippet are welcome!
Top comments (7)
Hey, very nice! A few remarks:
method
should be an enum, otherwise typos are welcome (path
instead ofpatch
for example);body
shouldn't be allowed onget
requests.There are very minor things, no deal-breakers. Great job!
Thank you for your tips, definitely need to improve this.
POST is OK, but GET shouldn't have a response body. You should use querystrings.
Yeah, that's why i set body to
undefined
by default, when calling this wrapper you also can omit a body.You still have
application/json
header, which is affected by CORS.Now, my goto is
axios
, which auto-detect body typeapplication/json
application/x-www-form-urlencoded
Axios also allowes
raise_for_status
anderror
interceptors.However,
axios
uses XMLHttpRequest. Not sure if this matters.Well, i've used axios with Vue a lot, it's more convenient, tbh. But it's an additional dependency, also they are not actively working on currently stalled issues in their repo. Axios has many neat features built-in. But i wonder about the future of this project.
Nice !
For those who want a wrapper around fetch there is Ky ;)