Skip to content

Commit 8c51625

Browse files
author
Ruben van Leeuwen
committed
2059: Adds formData storage property
1 parent e250e43 commit 8c51625

File tree

2 files changed

+41
-0
lines changed

2 files changed

+41
-0
lines changed

frontend/packages/pydantic-forms/src/core/PydanticFormContextProvider.tsx

Lines changed: 34 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -34,6 +34,7 @@ import {
3434
import {
3535
Locale,
3636
PydanticFormContextProps,
37+
PydanticFormFieldDataStorage,
3738
PydanticFormFieldType,
3839
PydanticFormInitialContextProps,
3940
PydanticFormSchemaRawJson,
@@ -242,6 +243,38 @@ function PydanticFormContextProvider({
242243
setHasNext(false);
243244
}, [emptyRawSchema]);
244245

246+
const fieldDataStorageRef = useRef<Map<string, Map<string, unknown>>>(
247+
new Map(),
248+
);
249+
250+
/*
251+
A field might load a list of options from a remote source, load some more and do some logic based on the selection
252+
and only store the final selected id in the form submission data. This method allows to store these intermediate
253+
values to be able to restore the field state when navigating back to it or when errors occur.
254+
*/
255+
const pydanticFormFieldDataStorage: PydanticFormFieldDataStorage = {
256+
has: (fieldId: string, key: string | number) => {
257+
if (
258+
fieldDataStorageRef.current &&
259+
fieldDataStorageRef.current.has(fieldId)
260+
) {
261+
const fieldStorage = fieldDataStorageRef.current.get(fieldId);
262+
return fieldStorage?.has(key.toString()) ?? false;
263+
}
264+
return false;
265+
},
266+
get: (fieldId: string, key: string | number) => {
267+
const fieldData = fieldDataStorageRef?.current?.get(fieldId);
268+
return fieldData?.get(key.toString());
269+
},
270+
set: (fieldId: string, key: string | number, value: unknown) => {
271+
fieldDataStorageRef.current.set(
272+
fieldId,
273+
new Map([[key.toString(), value]]),
274+
);
275+
},
276+
};
277+
245278
const PydanticFormContextState = {
246279
// to prevent an issue where the sending state hangs
247280
// we check both the SWR hook state as our manual state
@@ -272,6 +305,7 @@ function PydanticFormContextProvider({
272305
formInputData,
273306
hasNext,
274307
initialData,
308+
pydanticFormFieldDataStorage,
275309
};
276310

277311
// a useeffect for whenever the error response updates

frontend/packages/pydantic-forms/src/types.ts

Lines changed: 7 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -47,6 +47,12 @@ export type PydanticFormControlledElementProps = Omit<
4747
export type PydanticFormControlledElement =
4848
React.JSXElementConstructor<PydanticFormControlledElementProps>;
4949

50+
export type PydanticFormFieldDataStorage = {
51+
set: (fieldId: string, key: string | number, value: unknown) => void;
52+
has: (fieldId: string, key: string | number) => boolean;
53+
get: (fieldId: string, key: string) => unknown;
54+
};
55+
5056
export interface PydanticFormContextProps {
5157
isLoading: boolean;
5258
isSending: boolean;
@@ -71,6 +77,7 @@ export interface PydanticFormContextProps {
7177
hasNext: boolean;
7278
formInputData: object[];
7379
initialData: FieldValues;
80+
pydanticFormFieldDataStorage: PydanticFormFieldDataStorage;
7481
}
7582

7683
export enum PydanticFormState {

0 commit comments

Comments
 (0)