sindresorhus / fetch-extras

Useful utilities for working with Fetch
MIT License
67 stars 0 forks source link

`withTimeout` #1

Open sindresorhus opened 1 month ago

sindresorhus commented 1 month ago

Would be useful to have a function to easily get timeout for a fetch function.

import {withTimeout} from 'fetch-extras';

const fetchWithTimeout = withTimeout(fetch, 5000);

const response = await fetchWithTimeout('/api');
const data = await response.json();

POC (untested):

export function withTimeout(fetchFunction, timeout) {
    return async (urlOrRequest, options = {}) => {
        const providedSignal = options.signal ?? (urlOrRequest instanceof Request && urlOrRequest.signal);
        const signal = AbortSignal.any([providedSignal, AbortSignal.timeout(timeout)].filter(Boolean));
        return fetchFunction(urlOrRequest, {...options, signal});
    };
}

Feedback wanted


If this one works out, I imagine we could have more.

const superFetch = withHttpError(withTimeout(fetch, 5000));

const response = await superFetch('/api');
const data = await response.json();

Alternative API:

const betterFetch = createFetch(
    fetchTimeout(5000),
    fetchRetry(3)
);

const response = await betterFetch('/api');
const data = await response.json();
sindresorhus commented 1 month ago

// @fregante

fregante commented 1 month ago

fetchWithTimeout

I think if you need a reusable function, there's already ky. Timeouts on their own are easy:

const response = fetch('/api', {signal: Abort.timeout(5000)})
sindresorhus commented 1 month ago

I think if you need a reusable function, there's already ky.

You could use that argument on the utilties already here too. Could just use Ky. The point is that this package is composable. You take only what you need.


Timeouts on their own are easy:

Sure, but usually you also want to pass in your own signal, and then it's more difficult.

fregante commented 1 month ago

You could use that argument on the utilties already here too

throwIfHttpError is not 4-tokens long, , {signal: AbortSignal.timeout(5000)} is

this package is composable

👍

I thought it was more like a utilities package like uint8array-extras than a build-your-own-ky

Sure, but usually you also want to pass in your own signal, and then it's more difficult.

A bit, yes

- const fetchWithTimeout = withTimeout(fetch, 5000);
- fetchWithTimeout('/api', {signal: mySignal})
+ fetch('/api', {signal: AbortSignal.any([yourOwn, AbortSignal.timeout(5000)]))