From 27dfe272b34a48d5a9c78f44936feb41273c55ce Mon Sep 17 00:00:00 2001 From: arturovt Date: Thu, 20 Feb 2025 22:25:08 +0200 Subject: [PATCH] refactor(forms): tree-shake `_checkParentType` in production (#60041) In this commit, we move `_checkParentType` to a separate function to avoid a redundant prototype method in production. PR Close #60041 --- .../forms_reactive/bundle.golden_symbols.json | 2 +- packages/forms/src/directives/ng_model.ts | 23 ++++++-------- .../reactive_directives/form_control_name.ts | 31 ++++++++----------- .../reactive_directives/form_group_name.ts | 18 +++-------- 4 files changed, 28 insertions(+), 46 deletions(-) diff --git a/packages/core/test/bundling/forms_reactive/bundle.golden_symbols.json b/packages/core/test/bundling/forms_reactive/bundle.golden_symbols.json index 2b55062eb1d..2e1e607d9f7 100644 --- a/packages/core/test/bundling/forms_reactive/bundle.golden_symbols.json +++ b/packages/core/test/bundling/forms_reactive/bundle.golden_symbols.json @@ -222,7 +222,6 @@ "_bind", "_currentInjector", "_global", - "_hasInvalidParent", "_injectImplementation", "_isRefreshingViews", "_keyMap", @@ -411,6 +410,7 @@ "handleUnhandledError", "hasApplyArgsData", "hasInSkipHydrationBlockFlag", + "hasInvalidParent", "hasParentInjector", "hasTagAndTypeMatch", "hasValidator", diff --git a/packages/forms/src/directives/ng_model.ts b/packages/forms/src/directives/ng_model.ts index 083e35a66e7..80d35eed254 100644 --- a/packages/forms/src/directives/ng_model.ts +++ b/packages/forms/src/directives/ng_model.ts @@ -334,24 +334,11 @@ export class NgModel extends NgControl implements OnChanges, OnDestroy { private _checkForErrors(): void { if ((typeof ngDevMode === 'undefined' || ngDevMode) && !this._isStandalone()) { - this._checkParentType(); + checkParentType(this._parent); } this._checkName(); } - private _checkParentType(): void { - if (typeof ngDevMode === 'undefined' || ngDevMode) { - if ( - !(this._parent instanceof NgModelGroup) && - this._parent instanceof AbstractFormGroupDirective - ) { - throw formGroupNameException(); - } else if (!(this._parent instanceof NgModelGroup) && !(this._parent instanceof NgForm)) { - throw modelParentException(); - } - } - } - private _checkName(): void { if (this.options && this.options.name) this.name = this.options.name; @@ -387,3 +374,11 @@ export class NgModel extends NgControl implements OnChanges, OnDestroy { return this._parent ? controlPath(controlName, this._parent) : [controlName]; } } + +function checkParentType(parent: ControlContainer | null) { + if (!(parent instanceof NgModelGroup) && parent instanceof AbstractFormGroupDirective) { + throw formGroupNameException(); + } else if (!(parent instanceof NgModelGroup) && !(parent instanceof NgForm)) { + throw modelParentException(); + } +} diff --git a/packages/forms/src/directives/reactive_directives/form_control_name.ts b/packages/forms/src/directives/reactive_directives/form_control_name.ts index afd7af2d770..aa0601255ec 100644 --- a/packages/forms/src/directives/reactive_directives/form_control_name.ts +++ b/packages/forms/src/directives/reactive_directives/form_control_name.ts @@ -213,28 +213,23 @@ export class FormControlName extends NgControl implements OnChanges, OnDestroy { return this._parent ? this._parent.formDirective : null; } - private _checkParentType(): void { - if (typeof ngDevMode === 'undefined' || ngDevMode) { - if ( - !(this._parent instanceof FormGroupName) && - this._parent instanceof AbstractFormGroupDirective - ) { - throw ngModelGroupException(); - } else if ( - !(this._parent instanceof FormGroupName) && - !(this._parent instanceof FormGroupDirective) && - !(this._parent instanceof FormArrayName) - ) { - throw controlParentException(this.name); - } - } - } - private _setUpControl() { if (typeof ngDevMode === 'undefined' || ngDevMode) { - this._checkParentType(); + checkParentType(this._parent, this.name); } (this as Writable).control = this.formDirective.addControl(this); this._added = true; } } + +function checkParentType(parent: ControlContainer | null, name: string | number | null) { + if (!(parent instanceof FormGroupName) && parent instanceof AbstractFormGroupDirective) { + throw ngModelGroupException(); + } else if ( + !(parent instanceof FormGroupName) && + !(parent instanceof FormGroupDirective) && + !(parent instanceof FormArrayName) + ) { + throw controlParentException(name); + } +} diff --git a/packages/forms/src/directives/reactive_directives/form_group_name.ts b/packages/forms/src/directives/reactive_directives/form_group_name.ts index 0c0bbde27ea..304f308ba37 100644 --- a/packages/forms/src/directives/reactive_directives/form_group_name.ts +++ b/packages/forms/src/directives/reactive_directives/form_group_name.ts @@ -115,7 +115,7 @@ export class FormGroupName extends AbstractFormGroupDirective implements OnInit, /** @internal */ override _checkParentType(): void { - if (_hasInvalidParent(this._parent) && (typeof ngDevMode === 'undefined' || ngDevMode)) { + if (hasInvalidParent(this._parent) && (typeof ngDevMode === 'undefined' || ngDevMode)) { throw groupParentException(); } } @@ -190,8 +190,8 @@ export class FormArrayName extends ControlContainer implements OnInit, OnDestroy * @nodoc */ ngOnInit(): void { - if (typeof ngDevMode === 'undefined' || ngDevMode) { - this._checkParentType(); + if (hasInvalidParent(this._parent) && (typeof ngDevMode === 'undefined' || ngDevMode)) { + throw arrayParentException(); } this.formDirective!.addFormArray(this); } @@ -201,9 +201,7 @@ export class FormArrayName extends ControlContainer implements OnInit, OnDestroy * @nodoc */ ngOnDestroy(): void { - if (this.formDirective) { - this.formDirective.removeFormArray(this); - } + this.formDirective?.removeFormArray(this); } /** @@ -230,15 +228,9 @@ export class FormArrayName extends ControlContainer implements OnInit, OnDestroy override get path(): string[] { return controlPath(this.name == null ? this.name : this.name.toString(), this._parent); } - - private _checkParentType(): void { - if (_hasInvalidParent(this._parent) && (typeof ngDevMode === 'undefined' || ngDevMode)) { - throw arrayParentException(); - } - } } -function _hasInvalidParent(parent: ControlContainer): boolean { +function hasInvalidParent(parent: ControlContainer): boolean { return ( !(parent instanceof FormGroupName) && !(parent instanceof FormGroupDirective) &&