mirror of
https://github.com/pockethost/pockethost.git
synced 2025-11-28 08:11:01 +00:00
chore: improve tryFetch documentation and handling
This commit is contained in:
parent
3bb058762a
commit
a76566002d
@ -1,50 +1,64 @@
|
|||||||
import { LoggerService } from '@pockethost/common'
|
import { LoggerService } from '@pockethost/common'
|
||||||
import fetch from 'node-fetch'
|
import fetch, { Response } from 'node-fetch'
|
||||||
import { AsyncContext } from './AsyncContext'
|
|
||||||
|
|
||||||
export const TRYFETCH_RETRY_MS = 50
|
export const TRYFETCH_RETRY_MS = 50
|
||||||
|
|
||||||
export type Config = Required<AsyncContext> & {
|
export type Config = {
|
||||||
preflight: () => Promise<boolean>
|
preflight: () => Promise<boolean>
|
||||||
retryMs: number
|
retryMs: number
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
*
|
||||||
|
* @param url The URL to fetch
|
||||||
|
* @param config { preflight: ()=>Promise<boolean>, retryMs: number}
|
||||||
|
* @returns Promise<Response>
|
||||||
|
*
|
||||||
|
* tryFetch will contiously try to fetch a URL every `retryMs`, with an optinoal `preflight`.
|
||||||
|
* If `preflight` is specificed, it must resolve to `true` before tryFetch
|
||||||
|
* will attempt to fetch the URL. If `preflight` resolves to `false`, tryFetch
|
||||||
|
* will delay by `retryMs` and then check again. If `preflight` rejects,
|
||||||
|
* then tryFetch rejects and exits.
|
||||||
|
*
|
||||||
|
* Note: tryFetch exits ONLY on success or a rejected preflight.
|
||||||
|
*/
|
||||||
export const tryFetch = async (url: string, config?: Partial<Config>) => {
|
export const tryFetch = async (url: string, config?: Partial<Config>) => {
|
||||||
const { logger, preflight, retryMs }: Config = {
|
const { preflight, retryMs }: Config = {
|
||||||
logger: LoggerService().create(`tryFetch`),
|
|
||||||
preflight: async () => true,
|
preflight: async () => true,
|
||||||
retryMs: TRYFETCH_RETRY_MS,
|
retryMs: TRYFETCH_RETRY_MS,
|
||||||
...config,
|
...config,
|
||||||
}
|
}
|
||||||
const _logger = logger.create(`tryFetch`)
|
const logger = LoggerService().create(`tryFetch`).breadcrumb(url)
|
||||||
const { dbg } = _logger
|
const { dbg } = logger
|
||||||
return new Promise<void>((resolve, reject) => {
|
return new Promise<Response>((resolve, reject) => {
|
||||||
const tryFetch = async () => {
|
const again = () => setTimeout(_real_tryFetch, retryMs)
|
||||||
|
const _real_tryFetch = async () => {
|
||||||
if (preflight) {
|
if (preflight) {
|
||||||
dbg(`Checking preflight`)
|
|
||||||
try {
|
try {
|
||||||
|
dbg(`Preflight: CHECK`)
|
||||||
const shouldFetch = await preflight()
|
const shouldFetch = await preflight()
|
||||||
if (!shouldFetch) {
|
if (!shouldFetch) {
|
||||||
reject(new Error(`failed preflight, aborting`))
|
dbg(`Preflight: NOT READY`)
|
||||||
|
again()
|
||||||
return
|
return
|
||||||
}
|
}
|
||||||
|
dbg(`Preflight: READY`)
|
||||||
} catch (e) {
|
} catch (e) {
|
||||||
reject(new Error(`preflight threw error, aborting`))
|
dbg(`Preflight: ABORT`)
|
||||||
|
reject(e)
|
||||||
return
|
return
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
try {
|
try {
|
||||||
dbg(`Trying to fetch ${url} `)
|
dbg(`Fetch: START`)
|
||||||
const res = await fetch(url)
|
const res = await fetch(url)
|
||||||
dbg(`Fetch ${url} successful`)
|
dbg(`Fetch: SUCCESS`)
|
||||||
resolve()
|
resolve(res)
|
||||||
} catch (e) {
|
} catch (e) {
|
||||||
dbg(
|
dbg(`Fetch: ERROR: trying again in ${retryMs}ms | ${e}`)
|
||||||
`Could not fetch ${url}, trying again in ${retryMs}ms. Raw error ${e}`,
|
again()
|
||||||
)
|
|
||||||
setTimeout(tryFetch, retryMs)
|
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
tryFetch()
|
_real_tryFetch()
|
||||||
})
|
})
|
||||||
}
|
}
|
||||||
|
|||||||
Loading…
x
Reference in New Issue
Block a user