Create a Request, Stringify a Request into JSON, Hydrate JSON back into a Request
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
// @ts-check | |
/** Creates a new Request. */ | |
export const create = /** @type {(input: RequestInfo | URL, init?: RequestInit) => Request} */ ( | |
(input, config = any) => new Request(input, config) | |
) | |
/** Stringifies a Request into JSON. */ | |
export const stringify = /** @type {(request: Request) => Promise<StringifiedRequest>} */ (async (request) => { | |
/** URL of the request. */ | |
const input = request.url | |
/** Configuration of the request. */ | |
const config = /** @type {StringifiedRequestConfig} */ ({}) | |
// assign any unique configuration from the request | |
for (const name in defaultRequest) { | |
if (request[name] !== defaultRequest[name]) { | |
config[name] = request[name] | |
} | |
} | |
// assign any headers from the request | |
config.headers = Object.fromEntries(request.headers) | |
// assign any body from the request | |
if (!request.bodyUsed) { | |
/** Blob retreived from the request. */ | |
const blob = await request.clone().blob() | |
// serialize the type and array of the blob | |
/** @type {[ string, number[] ]} */ | |
config.body = [ | |
blob.type, | |
[ | |
...new Uint8Array( | |
await blob.arrayBuffer() | |
) | |
] | |
] | |
} | |
return [ input, config ] | |
}) | |
/** Hydrates JSON back into a Request. */ | |
export const hydrate = /** @type {(json: StringifiedRequest) => Request} */ ( | |
([ input, options ]) => new Request( | |
input, | |
{ | |
...options, | |
body: options.body ? new Blob([ | |
new Uint8Array(options.body[1]) | |
], { | |
type: options.body[0] | |
}) : null, | |
} | |
) | |
) | |
const defaultRequest = { | |
method: 'GET', | |
referrer: 'about:client', | |
/** @type {ReferrerPolicy} */ | |
referrerPolicy: '', | |
/** @type {RequestMode} */ | |
mode: 'cors', | |
/** @type {RequestCredentials} */ | |
credentials: 'same-origin', | |
/** @type {RequestCache} */ | |
cache: 'default', | |
/** @type {RequestRedirect} */ | |
redirect: 'follow', | |
integrity: '', | |
keepalive: false, | |
} | |
const any = /** @type {any} */ (null) | |
/** @typedef {typeof defaultRequest & { headers: { [name: string]: string }, body: [ string, number[] ] | null }} StringifiedRequestConfig */ | |
/** @typedef {[ string, StringifiedRequestConfig ]} StringifiedRequest */ |
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment