Movatterモバイル変換


[0]ホーム

URL:


Skip to content

Navigation Menu

Sign in
Appearance settings

Search code, repositories, users, issues, pull requests...

Provide feedback

We read every piece of feedback, and take your input very seriously.

Saved searches

Use saved searches to filter your results more quickly

Sign up
Appearance settings

[Form] Introduce validation events#47210

New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to ourterms of service andprivacy statement. We’ll occasionally send you account related emails.

Already on GitHub?Sign in to your account

Open
Seb33300 wants to merge4 commits intosymfony:7.4
base:7.4
Choose a base branch
Loading
fromSeb33300:form-validate-events

Conversation

Seb33300
Copy link
Contributor

@Seb33300Seb33300 commentedAug 6, 2022
edited
Loading

QA
Branch?6.2
Bug fix?no
New feature?yes
Deprecations?no
TicketsFix#47046
LicenseMIT
Doc PRsymfony/symfony-docs#17229

Inspired from#38479 (@alcaeus, I coud not reuse your commit because you deleted your branch)

With some changes:

  • I removed the BC break
  • form.pre_validate andform.post_validate events are triggered individually to all Form items, not only the to the root form (same as all others existing form events)

Regarding the second point, for example, when working with nested forms, if theform.post_validate event is attached to a child form:

  • $event->getForm()->isValid() will return the validity for the current form item only (the nested one)
  • If you want to check if the entire form is valid form a nested form, you will have to check the root form:$event->getForm()->getRoot()->isValid()

Usage example:

Thy are working in the same way as existing form events work.

class MyFormTypeextends AbstractType{publicfunctionbuildForm(FormBuilderInterface$builder,array$options):void    {$builder            ->addEventListener(ValidatorFormEvents::PRE_VALIDATE,function (FormEvent$event) {// ...            })            ->addEventListener(ValidatorFormEvents::POST_VALIDATE,function (FormEvent$event) {$event->getForm()->isValid();// Check if current form item is valid$event->getForm()->getRoot()->isValid();// Check if entire form is valid            })        ;    }}

Why are those events required?
Can't we just add aPOST_SUBMIT event with a lower priority than the validation event?

Yes, this solution can work, but ONLY on the root form.
Because the validation of the form is triggered only by the root form, and events are triggered individually on all form items, starting from ancestors and ending by the root form.
This means, we currently have no way to know if a nested form is valid when attaching a POST_SUBMIT event on it.

d-ph and artyuum reacted with thumbs up emojisilasjoisten reacted with hooray emojiLustmored reacted with heart emojisilasjoisten reacted with rocket emoji
@Seb33300
Copy link
ContributorAuthor

In case you want to review, I saw you participated to the previous PR
@d-ph@silasjoisten

@d-ph
Copy link

d-ph commentedAug 7, 2022
edited
Loading

Hi.

Just wanted to say that I'm happy to see this feature gaining traction, and looking forward to seeing it in the stock Symfony code. Unfortunately, it's unlikely I'd review the PR in depth, however I did skim through the change, and it looks good to me.

May I ask a quick question though, just to double-check: Given the following case:

  1. A root formfoo listening on the postValidate event.
  2. A child formfooChild also listenting on the postValidate event.
  3. The formfoo is being submitted.

Then:

  1. fooChild's postValidate is going to be called first, and thenfoo's postValidate is going to be called second. I.e. The new events are dispatched recursively, deepest child form first?
  2. IffooChild adds a new FormError on itself in the postValidate listener, thefoo's postValidate listener will be able to see that there are validation errors by calling either:$event->getForm()->isValid(), or$event->getForm()->get('fooChild')->isValid()?

Thanks.


Btw Seb33300 search for "->idValid(" on this page and consider correcting the typos, because it takes a few seconds to conclude that it's a typo. Cheers.

@Seb33300
Copy link
ContributorAuthor

Seb33300 commentedAug 7, 2022
edited
Loading

@d-ph typo fixed. Thanks.

POST_VALIDATE event happens AFTER the form validation has been processed ON ALL form items.

  1. Yes, child form event will be dispatched first. The root form event will be the last one to be dispatched. (same order as others form events)

  2. Yes, you can add a new error to the form using$event->getForm()->addError() inside this event. If you do so, the form will be considered invalid after that. When the event will be propagated to parent form, the parent form will also be considered as invalid. Because a form is valid only if all his children are valid.

d-ph reacted with thumbs up emoji

Copy link
Member

@ycerutoyceruto left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others.Learn more.

Thanks for this proposal. I've now a better idea about the problem to solve after reading your code and description. I left you one comment to improve the implementation based on your approach and the other two are mainly consistency-related concerns.

I'm wondering if dispatching these new events inside theFormValidator makes more sense, is more accurate, and simplifies the implementation too (as the collection of the form tree won't be needed).

Although I've to admit that I'm not entirely sure how useful this feature is or if we are opening the door to the writing of something completely detached from the Form context.

if ($form->isRoot()) {
$this->dispatchEvents(ValidatorFormEvents::PRE_VALIDATE);
Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others.Learn more.

I like the goal of this new event but the dispatching moment is a bit confusing to me. If I create a listener in a nested form type, I expect the event to be received just before the current form is validated inFormValidator and not before the whole validation process of all forms in the tree is started.

The meaning is different in this case from other events.

Copy link
ContributorAuthor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others.Learn more.

To be consistant with POST_VALIDATE event, I decided to dispatch it before the validation of the entire form start.
(see my other comment to know why POST_VALIDATE is dispatched after all form items are validated)

@@ -50,6 +64,24 @@ public function validateForm(FormEvent $event)

$this->violationMapper->mapViolation($violation, $form, $allowNonSynchronized);
}

$this->dispatchEvents(ValidatorFormEvents::POST_VALIDATE);
Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others.Learn more.

I understand that child forms can check easily whether their parent is valid or not, but I have the same confusion about the right moment this event is being dispatched. They are not done just after the current form is validated but when the whole validation process is finished for all forms.

Copy link
ContributorAuthor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others.Learn more.

This is the main purpose of this PR, to be able to know if the entire form is valid or not.
That's why the POST_VALIDATE event must be dispatched here.
If we dispatch the event just after the validation of the current item, we will only be able to know if the current item (and his parents) are valid.

Maybe we can introduce a 3rd event "VALIDATE" that could be dispatched just after the current form item is validated?

Copy link
ContributorAuthor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others.Learn more.

Or rename PRE/POST events by START/FINISH to avoid confusion?

@nicolas-grekasnicolas-grekas modified the milestones:6.2,6.3Nov 5, 2022
@lyrixx
Copy link
Member

I faced the same use case. I did not test this PR, but I think this can be a good feature 👍🏼

@nicolas-grekasnicolas-grekas modified the milestones:6.3,6.4May 23, 2023
@nicolas-grekasnicolas-grekas modified the milestones:6.4,7.1Nov 15, 2023
@xabbuhxabbuh modified the milestones:7.1,7.2May 15, 2024
@fabpotfabpot modified the milestones:7.2,7.3Nov 20, 2024
@fabpotfabpot modified the milestones:7.3,7.4May 26, 2025
Sign up for freeto join this conversation on GitHub. Already have an account?Sign in to comment
Reviewers

@94noni94noni94noni left review comments

@ycerutoycerutoyceruto left review comments

@silasjoistensilasjoistensilasjoisten left review comments

@xabbuhxabbuhAwaiting requested review from xabbuhxabbuh is a code owner

Assignees
No one assigned
Projects
None yet
Milestone
7.4
Development

Successfully merging this pull request may close these issues.

[Form] Addingvalid &invalid form events
10 participants
@Seb33300@d-ph@lyrixx@94noni@yceruto@silasjoisten@fabpot@nicolas-grekas@xabbuh@carsonbot

[8]ページ先頭

©2009-2025 Movatter.jp