react-hooks
react-hooks copied to clipboard
Need promise associated with `request` of `useRequestCall` to track task status outside
https://github.com/ecomfe/react-hooks/blob/8d89a72ea22b6591b9cb226e8378e8ba7cc1e1c2/packages/request/src/index.ts#L104-L107
Usage:
function DeleteButton ({segmentId, refresh}) {
const [delete, {pending}] = useRequestCallback(deleteSegment, {segmentId});
const onClick = async () => {
if (await confirm(message)) {
await delete(); // <--- promise to be awaited to ensure task is settled.
refresh();
}
};
return <button disabled={pending} onClick={onClick}>删除</button>;
}
We're not going to add this because it is a potential breaking change, such as it can produce extra warning for no-floating-promise
lint rules
On the other side, we are planning a next version of useRequest
to address all current issues, including:
- A way simpler implement by cut off the ability to cache unreached responses
- A
useRequestDynamic
likeuseRequestCallback
but to allow users pass dynamic params to returningrequest
function - Return
Promise<void>
onuseRequestDynamic
- A
onAccept
callback option to allow extra logic when a response is accepted over race condition - A set of resilient types, no chance to access undefined
data
property on pending or state without defining adefaultValue
option - A
throwError
option to work with error boundaries more friendly
Here is a set of upcoming useRequestDynamic
definition:
export type Async<I, O> = (params: I) => Promise<O>;
interface OptionsBase<I, O> {
onAccept?: (result: O, params: I) => void;
}
export interface OptionsDefaultThrow<I, O> extends OptionsBase<I, O> {
defaultValue: O;
throwError: true;
}
export interface OptionsDefaultNoThrow<I, O> extends OptionsBase<I, O> {
defaultValue: O;
throwError?: false;
}
export interface OptionsNoDefaultThrow<I, O> extends OptionsBase<I, O> {
throwError: true;
}
export interface OptionsNoDefaultNoThrow<I, O> extends OptionsBase<I, O> {
throwError?: false;
}
export interface ResponseBase<I> {
params: I | undefined;
}
export interface PendingDefault<I, O> extends ResponseBase<I> {
state: 'pending';
data: O;
}
export interface PendingNoDefault<I> extends ResponseBase<I> {
state: 'pending';
}
export interface HasValue<I, O> extends ResponseBase<I> {
state: 'hasValue';
data: O;
}
export interface HasError<I> extends ResponseBase<I> {
state: 'hasError';
error: Error;
}
export type ResponseDefaultThrow<I, O> = PendingDefault<I, O> | HasValue<I, O>;
export type ResponseNoDefaultThrow<I, O> = PendingNoDefault<I> | HasValue<I, O>;
export type ResponseDefaultNoThrow<I, O> = PendingDefault<I, O> | HasValue<I, O> | HasError<I>;
export type ResponseNoDefaultNoThrow<I, O> = PendingNoDefault<I> | HasValue<I, O> | HasError<I>;
export type DefaultThrow<I, O> = [ResponseDefaultThrow<I, O>, Async<I, void>];
export type NoDefaultThrow<I, O> = [ResponseNoDefaultThrow<I, O>, Async<I, void>];
export type DefaultNoThrow<I, O> = [ResponseDefaultNoThrow<I, O>, Async<I, void>];
export type NoDefaultNoThrow<I, O> = [ResponseNoDefaultNoThrow<I, O>, Async<I, void>];
export type Response<I, O> = PendingDefault<I, O> | PendingNoDefault<I> | HasValue<I, O> | HasError<I>;
type State<I, O> = [Response<I, O>, Async<I, void>];
function useRequestDynamic<I, O>(api: Async<I, O>, options: OptionsDefaultThrow<I, O>): DefaultThrow<I, O>;
function useRequestDynamic<I, O>(api: Async<I, O>, options: OptionsNoDefaultThrow<I, O>): NoDefaultThrow<I, O>;
function useRequestDynamic<I, O>(api: Async<I, O>, options: OptionsDefaultNoThrow<I, O>): DefaultNoThrow<I, O>;
function useRequestDynamic<I, O>(api: Async<I, O>, options?: OptionsNoDefaultNoThrow<I, O>): NoDefaultNoThrow<I, O>;
Any progress?
We have ported the latest implement and tests, but still struggling to refine docs and demos.