Cancellable requests
You can cancel requests with AbortControllers.
Automatic cancellation
Requests are automatically cancelled if their timeout is exceeded (by default 5 seconds).
When using query.refetch()
, ongoing requests are cancelled.
Defining a timeout
You can set an timeout delay for all resources in your core provider.
function MyWrapper() { return <XSWR.CoreProvider timeout={5000}> <MyAwesomeApp /> </XSWR.CoreProvider>}
Or you can set an timeout delay for some resource.
function getHelloSchema() { return getSingleSchema<Hello>("/api/hello", fetchAsJson, { timeout: 5000 })}
Preparing your fetcher for abortion
You have to prepare your fetcher for abortion in order to abort it on the fly.
You can pass the AbortSignal to your fetcher (e.g. fetch) in order to cancel the request and throw an error when the signal is triggered.
The signal will be passed in the second parameter of your fetcher (FetcherMore
).
async function fetchAsJson<T>(url: string, more: FetcherMore<T>) { const { signal } = more const res = await fetch(url, { signal }) if (!res.ok) { const error = new Error(await res.text()) return { error } } const data = await res.json() as T return { data }}
You can then ignore AbortErrors in your components.
if (isAbortError(query.error)) // do not display the errorelse // display the error
Aborting using query.aborter
By default, an aborter is created and passed to your query for each request.
You can use query.aborter.abort
to abort the ongoing request, or query.aborter.signal
to check the signal.
const mydata = useMyData()const { aborter } = mydatareturn <button onClick={aborter.abort}> Abort<button />
Note: query.aborter
is undefined
is there is no ongoing request.
Note: query.aborter
will only be available after a render, use a custom aborter with a ref if you want instant access.
Aborting using custom aborter
For more control, you can create your own aborter and store it wherever you like (e.g. is a useRef) and trigger it whenever you like.
function Component() { const mydata = useMyData() const { fetch } = mydata const syncAborter = useRef<AbortController>() const fetchWithAborter = useCallback(() => { const aborter = new AbortController() fetch(aborter) // your aborter will be available instantly syncAborter.current = aborter }, []) return <>...</>}
Note: query.aborter
will be set to your custom aborter, even for other components in the tree.