Skip to content

Instantly share code, notes, and snippets.

@clshortfuse
Created March 2, 2021 17:22
Show Gist options
  • Save clshortfuse/80b02f8f8a0c2abcb900aa23fd83c02e to your computer and use it in GitHub Desktop.
Save clshortfuse/80b02f8f8a0c2abcb900aa23fd83c02e to your computer and use it in GitHub Desktop.
fetch() operations
export class NetworkError extends Error {
/**
* @param {string} message
* @param {number} status
*/
constructor(message, status) {
super();
this.status = status;
}
}
/** @type {(error: Error|NetworkError|any) => void} */
let errorHandler = null;
/**
* @param {(error: Error|NetworkError|any) => Promise<any>} fn
* @return {void}
*/
export function setDefaultErrorHandler(fn) {
errorHandler = fn;
}
/**
* @param {Error|NetworkError|any} error
* @return {void}
*/
export function onPostError(error) {
if (errorHandler) {
errorHandler(error);
return;
}
throw error;
}
/**
* @param {string} url
* @param {Object=} data
* @param {Object} options
* @param {number=} options.timeout Timeout in milliseconds
* @param {string=} options.format response format
* @param {boolean=} options.credentials response format
* @param {Object<string,string>=} options.headers headers
* @return {Promise<any>}
*/
export function postJson(url, data = {}, options = { timeout: 60000, format: 'json', headers: {} }) {
/** @type {RequestInit} */
const fetchOptions = {
method: 'POST',
credentials: options.credentials === false ? 'omit' : 'include',
mode: 'cors',
headers: {
'Content-Type': 'application/json',
...options.headers,
},
body: JSON.stringify(data),
};
const promise = fetch(url, fetchOptions).then((response) => {
if (response.status >= 400) {
const err = new NetworkError(response.statusText, response.status);
err.status = response.status;
throw err;
}
if (response.status === 200) {
if (options.format === 'string') {
return response.text();
}
return response.json();
}
if (response.status === 204) {
if (options.format === 'string') {
return '';
}
return {};
}
// No content
return null;
});
if (options.timeout) {
return timeoutPromise(options.timeout, promise);
}
return promise;
}
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment