-
Notifications
You must be signed in to change notification settings - Fork 26.2k
Calling setValidators on a form control when control is nested as a component in form causes ExpressionChangedAfterItHasBeenCheckedError #18004
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 our terms of service and privacy statement. We’ll occasionally send you account related emails.
Already on GitHub? Sign in to your account
Comments
Can you make a minimal reproduction to show your issue? Here's a plunkr to get your stared: https://plnkr.co/edit/tpl:AvJOMERrnz94ekVua0u5 |
It turns out this is happening for one nested form component where it wasn't happening before nesting. For instance I'm passing in the formGroup via an input. What's special about this component is that is makes use of ngDefaultControl [(ngModel)]="rE.formattedDate" and when I set [Validators.required] in the parent form and change the input value the feedback loop starts. For now I've found a temporary fix by putting *ngIf="true" on the nested component which contains the component using ngDefaultControl and I can still use the validators. I think it's interesting this worked when not nested. I wonder if I should rewrite the component to not use ngDefaultControl [(ngModel)] or if this is even a bug. BTW this seems to complicated to put in a plunker but I'll take a look to see if that's feasible. |
Hi @rmanuel200 Please let me know if my my assumption is the case! best, |
We're experiencing a related issue: ExpressionChangedAfterItHasBeenCheckedError is always thrown for a very simple reactive form, if the input is on a lower template hierarchy level (defined by
The reason for the error being thrown is that change detection evaluates the The workaround is to bring the error div onto the same level as the input by adding just another |
I was able to trigger the ExpressionChangedAfterItHasBeenCheckedError with form validators error in this plunker using a simpler example with a mutable object: https://plnkr.co/edit/MtAvKgSnudA1Lk7WEVL2?p=preview. We are passing in [formGroup] through inputs on many forms and this problem wasn't happening prior. Please inform if this is something that's fixable. |
I am facing the same issue with the nested form components. |
Facing same issue. Here's a very simple repro that only uses nested reactive form and ng-if. |
Also reproduced: https://plnkr.co/edit/lODxTJN8qy4s5YaC1JZD?p=preview |
In my case, I can't try *ngIf.
|
Work around my issue like this |
Same issue when trying to setValidators inside a nested reactive forms component. To clarify the above In the Parent template, add a
@jasonzhang2022 's solution w/o messing w/the template would be nice, but didn't work for me. A bit more context would be helpful. |
any update on this issue? I am experiencing the same issue now that I'm trying to make some nested reactive forms. |
Just to add what I'm seeing from my tests, I was only seeing the issue if the form's validity changed below the 2nd level of components, i.e. the 3rd level or lower.
Here
|
Just stumbled upon this issue and it is reaaaaaally nasty one, I know that it will not matter in production but in dev env is really a show stopper. A workaround for us was setting the component that holds the form to use OnPush detection strategy. |
+1 |
helped me |
@renehamburger thank you so much 🙏 for clarifying that. I've encountered that issue plenty of times thinking I was doing something wrong and turns out... not really (?). At least from the point of view of CD. |
Spent a bit of time refining this one .. hopefuly helps someone
|
I ran change detection manually in the ngAfterViewInit() {
this.cdRef.detectChanges();
} The reason is that that hook is executed after the view AND the child views are initialized and thus the validators from the child component should be in place at that point. |
The issue is still here. Fix (hack) by @renehamburger works fine. |
do you have a more complete code example... i have just been ignoring the errors 😒 |
While it is good to know that there are work-arounds like manual change detection this issue should be handled by the framework. |
when is this going to be fixed? Im still having issues with this |
this error poped after upgrade to ivy ExpressionChangedError on form.valid with following structure `<custom-comp formGroup="form" [isValid]="(form.statusChanges | async) == 'VALID'"> <nested1 formControlName="nested1> <nested2 formControlName="nested2> <button [disabled]="!((form.statusChanges | async) == 'VALID') || loading"
workaround: replace form.valid with (form.statusChanges | async) == 'VALID' |
I'm having the same issue. :( |
I'm submitting a ...
Current behavior
Calling setValidators on a form control when control is nested as a component in form causes ExpressionChangedAfterItHasBeenCheckedError. Otherwise nesting formControls in components seems to work fine.
Expected behavior
When calling myform.controls["my_control"].setValidators([Validators.required]); in a nested component of a reactive form I would expect no errors to occur, especially ExpressionChangedAfterItHasBeenCheckedError
Minimal reproduction of the problem with instructions
What is the motivation / use case for changing the behavior?
Please tell us about your environment
The text was updated successfully, but these errors were encountered: