Skip to content

Commit 3a594a5

Browse files
committed
feat: whileFetching - new loader argument
chore: Refactored useCallback into a simple cache
1 parent 741bf23 commit 3a594a5

File tree

6 files changed

+58
-11
lines changed

6 files changed

+58
-11
lines changed

README.md

+11
Original file line numberDiff line numberDiff line change
@@ -131,6 +131,17 @@ Make sure you call the second argument as a component, not a function:
131131
}
132132
```
133133

134+
**whileFetching**?:
135+
136+
```typescript
137+
{
138+
append?: (props: P, data?: R) => ReactElement;
139+
prepend?: (props: P, data?: R) => ReactElement;
140+
}
141+
```
142+
143+
By using this instead of `onFetching`, you ensure that you don't reset the internal state of the component while fetching.
144+
134145
## withLoader
135146

136147
Wraps a component to provide it with loader data.

package.json

+1-1
Original file line numberDiff line numberDiff line change
@@ -1,6 +1,6 @@
11
{
22
"name": "@ryfylke-react/rtk-query-loader",
3-
"version": "0.3.3",
3+
"version": "0.3.31",
44
"description": "Lets you create loaders that contain multiple RTK queries.",
55
"main": "./dist/cjs/index.js",
66
"module": "./dist/esm/index.js",

src/RTKLoader.tsx

+15-1
Original file line numberDiff line numberDiff line change
@@ -10,6 +10,10 @@ type Props<T> = {
1010
error: FetchBaseQueryError | SerializedError
1111
) => React.ReactElement;
1212
onFetching?: React.ReactElement;
13+
whileFetching?: {
14+
append?: React.ReactElement;
15+
prepend?: React.ReactElement;
16+
};
1317
loader?: React.ReactElement;
1418
};
1519

@@ -30,7 +34,17 @@ export function RTKLoader<T>(
3034
return props.onFetching;
3135
}
3236
if (props.query.data !== undefined) {
33-
return props.onSuccess(props.query.data);
37+
return (
38+
<>
39+
{props.query.isFetching
40+
? props.whileFetching?.prepend ?? null
41+
: null}
42+
{props.onSuccess(props.query.data)}
43+
{props.query.isFetching
44+
? props.whileFetching?.append ?? null
45+
: null}
46+
</>
47+
);
3448
}
3549
return <React.Fragment />;
3650
}

src/createLoader.ts

+1
Original file line numberDiff line numberDiff line change
@@ -50,6 +50,7 @@ export const createLoader = <
5050
onLoading: createLoaderArgs.onLoading,
5151
onError: createLoaderArgs.onError,
5252
onFetching: createLoaderArgs.onFetching,
53+
whileFetching: createLoaderArgs.whileFetching,
5354
queriesArg: createLoaderArgs.queriesArg,
5455
extend: function <
5556
QRUb extends readonly Types.UseQueryResult<unknown>[],

src/types.ts

+7
Original file line numberDiff line numberDiff line change
@@ -85,6 +85,11 @@ export type WithLoaderArgs<
8585
A = never
8686
> = Loader<P, R, A>;
8787

88+
type WhileFetchingArgs<P extends unknown, R extends unknown> = {
89+
prepend?: (props: P, data?: R) => ReactElement;
90+
append?: (props: P, data?: R) => ReactElement;
91+
};
92+
8893
export type CreateLoaderArgs<
8994
P extends unknown,
9095
QRU extends readonly UseQueryResult<unknown>[],
@@ -102,6 +107,7 @@ export type CreateLoaderArgs<
102107
props: P,
103108
renderBody: () => ReactElement
104109
) => ReactElement;
110+
whileFetching?: WhileFetchingArgs<P, R>;
105111
};
106112

107113
export type Loader<
@@ -121,6 +127,7 @@ export type Loader<
121127
props: P,
122128
renderBody: () => ReactElement
123129
) => ReactElement;
130+
whileFetching?: WhileFetchingArgs<P, R>;
124131
extend: <
125132
QRUb extends readonly UseQueryResult<unknown>[],
126133
Pb extends unknown = P,

src/withLoader.tsx

+23-9
Original file line numberDiff line numberDiff line change
@@ -10,21 +10,20 @@ export const withLoader = <
1010
Component: Types.ComponentWithLoaderData<P, R>,
1111
args: Types.WithLoaderArgs<P, R, A>
1212
): Types.Component<P> => {
13-
return (props: P) => {
13+
let CachedComponent: Types.ComponentWithLoaderData<P, R>;
14+
const LoaderComponent = (props: P) => {
1415
const useLoaderArgs = [];
1516
if (args.queriesArg) {
1617
useLoaderArgs.push(args.queriesArg(props));
1718
}
1819
const query = args.useLoader(
1920
...(useLoaderArgs as Types.OptionalGenericArg<A>)
2021
);
21-
22-
const ForwardedComponent = React.useCallback(
23-
React.forwardRef(
22+
if (!CachedComponent) {
23+
CachedComponent = React.forwardRef(
2424
Component as React.ForwardRefRenderFunction<R, P>
25-
) as unknown as Types.ComponentWithLoaderData<P, R>,
26-
[]
27-
);
25+
) as unknown as Types.ComponentWithLoaderData<P, R>;
26+
}
2827

2928
return (
3029
<RTKLoader
@@ -41,13 +40,27 @@ export const withLoader = <
4140
: undefined
4241
}
4342
onSuccess={(data) => (
44-
<ForwardedComponent {...props} ref={data} />
43+
<CachedComponent {...props} ref={data} />
4544
)}
45+
whileFetching={
46+
args.whileFetching
47+
? {
48+
prepend: args.whileFetching?.prepend?.(
49+
props,
50+
query?.data
51+
),
52+
append: args.whileFetching?.prepend?.(
53+
props,
54+
query?.data
55+
),
56+
}
57+
: undefined
58+
}
4659
onFetching={args?.onFetching?.(
4760
props,
4861
query.data
4962
? () => (
50-
<ForwardedComponent
63+
<CachedComponent
5164
{...props}
5265
ref={query.data as R}
5366
/>
@@ -57,4 +70,5 @@ export const withLoader = <
5770
/>
5871
);
5972
};
73+
return LoaderComponent;
6074
};

0 commit comments

Comments
 (0)