vee-validate
vee-validate copied to clipboard
Multiple independent forms on a single page
I'm using v4 with the composition api. I don't quite understand how the useForm
and useField
functions relate to each other.
Currently I'm having multiple small forms on the same page, each with a few fields, maybe even sharing an input field with the same name. I would expect to be able to define some kind of context (a form html element reference?) to be able to set some initial values.
Or do I need to split this page up in sub components to achieve this?
This is one of the inherited issues with the composition API in general, not specific to vee-validate.
Typically you need to split them up into multiple smaller components, or turn to the <Field/>
or <Form/>
components as they are ideal for these scenarios.
In the early Alphas I experimented with explicit forms, where you would pass the form
object to the useField
to designate it as part of that form, maybe I can bring it back with some enhancements.
Thanks @logaretm! Even though splitting up in to smaller components is a better approach and a good practice, it doesn't feel right to be forced to do so.
When I started with the composition API approach, it felt like magic how initialValues is passed to inputs associated with the useForm function. I definitely would favor some (optional?) explicit binding to make things clear and more understandable.
By the way, thanks for all the support and effort you put into this library! My question has been answered, shall I close this issue or do you want it open for future reference?
it doesn't feel right to be forced to do so
I share your sentiment here, basically this was possible in previous alphas:
const form1 = useForm();
const form2 = useForm();
const field = useField('somefield', undefined, {
form: form1
});
But didn't like the style because it would encourage doing messy setup functions.
shall I close this issue or do you want it open for future reference?
Let's keep it open for now, I plan to experiment with some ideas for this.
I just realized you can't have a main Form, with many nested Form's and have the ability to validate all of them at once (the main Form). I have a component, with many sub-components with their own <Form>. I can't validate the parent <Form> if there are nested <Form>'s. Will this be possible in the future? Version 1-3 you were able to do this.
@Speedy059 That's a different use case, in v4 I have no intention to introduce nested forms as maintaining that heap of crap was very consuming in v2 and v3.
I never actually used scopes in v2 or nested observers in v3 which made me re-evaluate their usefulness for v4, what you are looking to do is aggregate form information and stitch them together, which can be easily done in user-land with the composition API.
Check the issue here which discussed this briefly
@logaretm I use multiple fields on a page in separate sub-components with useField. When validation error occurs and the input field is empty then something weird happen - an error message from different neighbouring component is displayed which shouldn't happen as they are independent from each other. They have different names and all the composition functions I use in setup() are originating from useField. Is this a bug, or I'm doing something wrong?
@JoJk0 Without a minimal example it would hard to tell you what's going on, but the way useField
works is that it searches for the nearest form context created by either useForm
or <Form />
in the parent hierarchy, which what might be happening on your end.
@logaretm would be good to mention in the documentation that using multiple userForm()
in a single component will not work atm (just spent some time figuring out why my validation was not working...).
Will put my forms in separate components for the time being.
Is there a solution for this? My setup is:
<parent>
<child>
<form2>
</form2>
</child>
<form>
</form>
</parent>
The child's fields are automatically added to Form in the parent, what can I do to prevent this?
Pretty common use-case, a form, and then a modal on the page with it's own form, the traversal should only be searching direct parents? Not uncles or siblings?
@logaretm I understand not wanting to mess with a config object on top of useField in your example as it does seem messy
const form1 = useForm();
const form2 = useForm();
const field = useField('somefield', undefined, {
form: form1
});
But maybe it would be possible to expose a useField
function from useForm
that always has the context of that form? I'm not sure how it works under the hood.
const form1 = useForm();
const form2 = useForm();
const field = form1.useField('somefield')
@DoubleJ-G Thanks for the suggestion, your suggested API has another benefit as it allows for typing the field name as mentioned here #3375
This is something to do for 4.6
probably.
Hi @logaretm , looking forward to find this feature in next release.
A couple of updates on this:
- Using
useField
to create models should no longer be encouraged since this isn't its intended use case but I will work on adding logic to allow for this. - New API is already merged on
main
which exposes a similar function calleduseFieldModel
on the Form context object.
const form1 = useForm();
const form2 = useForm();
const [email, password] = form1.useFieldModel(['email', 'password']);
const [firstName, lastName] = form1.useFieldModel(['firstName', 'lastName']);
The useFieldModel
will be the recommended way if you plan to use v-model
instead of creating field components with useField
.
Hi @logaretm, i set validationSchema, validateOnMount false to form and useFieldModel, it will validate fields at updated hook then display errors, is it possible to prevent validate when form initial mounted? My link is below.
https://stackblitz.com/edit/vee-validate-v4-starter-composition-example-tcdkkt?file=src%2FApp.vue
Many thanks.
@logaretm nice!
Small detail: you probably want to show that firstName
and lastName
can be managed by form2
(your example uses form1
).
const [firstName, lastName] = form2.useFieldModel(['firstName', 'lastName']);