Modify data after fetching and before submitting with `useForm`
I have two types
FormType
and ApiType
. My form uses FormType
, while my data provider uses ApiType
. How do I handle this using useForm
?
Specifically, my data provider returns objects of ApiType
. However, my form does not follow this type, but instead requires a mutation apiToForm: (data: ApiType) => FormType)
to transform from ApiType
to FormType
. On submitting, the transformation formToApi: (formData: FormType) => ApiType
should be done.
I am using AntDesign, but am open to a solution using any design system.11 Replies
Hi @Hugo Kerstens. I'm kapa.ai, your friendly support bot. I will try to answer your question by searching through the knowledge base. :wave:
----------------------
To handle the scenario where your form uses
FormType
and your data provider uses ApiType
with useForm
, you can use the approach of modifying data before submission. This can be done using the Ant Design implementation of useForm
. Here's how you can achieve this:
1. For transforming the API data to form data when fetching:
You can use the transformValues
option of useForm
to transform the data received from the API into the format your form expects.
2. For transforming form data to API data when submitting:
You can create a custom onFinish
handler to transform the form data before sending it to the API.
Here's an example of how you can implement this:
In this example:
1. The transformValues
option in useForm
is used to transform the API data (ApiType
) to form data (FormType
) when the form is initially populated.
2. The custom handleOnFinish
function is used to transform the form data (FormType
) back to the API data format (ApiType
) before submission.
This approach allows you to work with different types for your form and API while still using the useForm
hook effectively.
For more details on modifying data before submission with Ant Design, you can refer to the Refine documentation on modifying data before submission.
----------------------
Note: you can ask me a follow up question by @ mentioning me again :speech_balloon:
----------------------<@242226786145009665> Kapa.ai is still learning and improving, please let me know how I did by reacting below.
stormy-goldOP•2d ago
@kapa.ai I am sorry, but
transformValues
only exists for Mantine UI. On top of that, it does the opposite of what you claim that it does.Let me check the knowledge base for you again. One moment! :books:
----------------------
I apologize for the confusion in my previous response. You are correct, and I thank you for pointing out the error. Let me provide a more accurate answer based on the available information for Ant Design.
You're right that
transformValues
is not available for Ant Design's useForm
hook, and I made a mistake in suggesting its use. Let's correct this and provide a solution that works with Ant Design.
For Ant Design, we can modify the data before submission using a custom onFinish
handler. Here's how you can handle the transformation between ApiType
and FormType
:
1. For transforming API data to form data when fetching:
You can use the form.setFieldsValue()
method within a useEffect
hook after the data is fetched.
2. For transforming form data to API data when submitting:
You can create a custom onFinish
handler to transform the form data before sending it to the API.
Here's an example of how you can implement this with Ant Design:
This approach allows you to work with different types for your form and API while using the Ant Design useForm
hook.
For more details on modifying data before submission with Ant Design, you can refer to the Refine documentation on changing form data before submitting to the API.
Again, I apologize for the earlier confusion, and thank you for bringing this to my attention.
----------------------
Note: you can ask me a follow up question by @ mentioning me again :speech_balloon:
----------------------<@242226786145009665> Kapa.ai is still learning and improving, please let me know how I did by reacting below.
stormy-goldOP•2d ago
@kapa.ai Thanks, can you add the type parameters to
useForm
?Let me check the knowledge base for you again. One moment! :books:
----------------------
Certainly! I'd be happy to add the type parameters to
useForm
for you. Based on the information provided in the knowledge sources, we can specify the type parameters for useForm
to separate the types for form structure and DataProvider submission. Here's how you can modify the code to include the type parameters:
In this example, we've added the type parameters to useForm
:
1. ApiType
: This is the type of data that the API expects and returns.
2. HttpError
: This is the default error type used by Refine.
3. FormType
: This is the type of data used in the form.
By specifying these type parameters, we ensure type safety throughout the form handling process. The queryResult
will contain data of type ApiType
, while the form fields and handleOnFinish
function work with FormType
.
This approach aligns with the information provided in the Ant Design useForm documentation, which mentions that useForm
accepts type parameters for the record in use and for the response type of the mutation.
Remember that this is a basic example, and you might need to adjust it based on your specific use case and any additional type parameters required by your implementation.
----------------------
Note: you can ask me a follow up question by @ mentioning me again :speech_balloon:
----------------------<@242226786145009665> Kapa.ai is still learning and improving, please let me know how I did by reacting below.
stormy-goldOP•2d ago
@kapa.ai Unfortunately,
onFinish
expects a value of the type FormType
, namely the third type parameter of useForm
, so this does not work with type safety. The examples in the documentation glance over this fact.Let me check the knowledge base for you again. One moment! :books:
----------------------
You're absolutely correct, and I apologize for overlooking this important detail. You've identified a key issue that the documentation doesn't explicitly address. Let's explore this problem and potential solutions based on the available information.
You're right that
onFinish
expects a value of the type specified as the third type parameter of useForm
, which in our case is FormType
. This indeed creates a type safety issue when we try to submit ApiType
data.
Currently, there isn't a built-in solution in Refine's useForm
hook to handle this scenario with full type safety. However, there are a couple of approaches we can consider:
1. Use type assertion (type casting):
This isn't ideal from a type safety perspective, but it can be a temporary workaround:
2. Create a union type:
As mentioned in a comment by a Refine team member in the GitHub issue discussion, you could use a union type:
This approach allows both FormType
and ApiType
to be valid for onFinish
, but it doesn't enforce the correct type at compile time.
It's worth noting that the Refine team is aware of this limitation. In the same GitHub issue, they mention that they're considering improving the type system for useForm
. One proposed solution involves adding a fourth type parameter for submission data:
However, this feature is not yet implemented.
For now, the most type-safe approach would be to handle the transformation within the component and use FormType
consistently:
Then, you would handle the transformation from FormType
to ApiType
in your data provider or in a custom useResource
hook.
I apologize again for the confusion in my previous responses. This is indeed a limitation in the current implementation of useForm
in Refine, and it's good that you've identified this issue. If this is a significant problem for your use case, you might want to consider opening an issue on the Refine GitHub repository to request a more robust solution for handling different types for form data and API data.
----------------------
Note: you can ask me a follow up question by @ mentioning me again :speech_balloon:
----------------------<@242226786145009665> Kapa.ai is still learning and improving, please let me know how I did by reacting below.