Special offer. See more information about Outbyte and uninstall instructions. Please review EULA and Privacy policy.

iTechGuides is reader-supported. When you buy through links on our site, we may earn an affiliate commission. As an Amazon Associate I earn from qualifying purchases. Learn more

In Angular, display a validation message by checking a control’s specific error and its interaction state. A practical default is to show a field error after the user has touched or changed that field, rather than showing errors on a newly opened, untouched form. The same principle works with both template-driven and reactive forms.

Choose when an error should appear

Angular controls expose validity, error details, and interaction state. Use the error key to identify what failed, then use touched or dirty to decide whether the message is timely. A control is touched after the user focuses and leaves it; it is dirty after its value changes.

  • Show a message when the control is invalid and touched: this waits until the user has left the field.
  • Alternatively, show it when invalid and dirty: this responds as soon as the value changes.
  • Check a specific error such as required or minlength so the explanation matches the failed rule.

Angular’s form-validation guide demonstrates conditional messages in both form styles. For a blank required field, hiding the message while the control is pristine prevents an error from appearing before the user interacts with the form.

Special offer. See more information about Outbyte and uninstall instructions. Please review EULA and Privacy policy.

Display errors in a template-driven form

Template-driven forms use validation attributes in the template. Angular maps supported attributes such as required to validators. Export the control’s NgModel instance with a template reference variable, then inspect its state and errors:

<label for="name">Name</label>
<input id="name" name="name" required minlength="4"
       [(ngModel)]="model.name" #name="ngModel">

<div *ngIf="name.invalid && (name.dirty || name.touched)">
  <p *ngIf="name.hasError('required')">Enter a name.</p>
  <p *ngIf="name.hasError('minlength')">Enter at least 4 characters.</p>
</div>

The name="name" attribute is important for registering the control with its parent template-driven form. The #name="ngModel" reference gives the template access to that control’s validity and error state. Angular’s template-driven forms guide also illustrates hiding an error while a control is valid or pristine with [hidden]="name.valid || name.pristine".

Write messages that tell the user what is wrong and how to fix it. A red border by itself does not explain whether a value is missing or too short.

Display errors in a reactive form

Reactive forms define controls and validators in the component model. The template then reads the corresponding control’s state. For example, a control can be configured with Angular’s required and minimum-length validators:

Free tools Windows power users keep installed

One-click scans. No signup required.

Special offer. See more information about Outbyte and uninstall instructions. Please review EULA and Privacy policy.
name = new FormControl('', [Validators.required, Validators.minLength(4)]);

Expose the control from the form group in the component, then check its error keys in the template:

<input id="name" formControlName="name">

<div *ngIf="nameControl.invalid && (nameControl.dirty || nameControl.touched)">
  <p *ngIf="nameControl.hasError('required')">Enter a name.</p>
  <p *ngIf="nameControl.hasError('minlength')">Enter at least 4 characters.</p>
</div>

Here, nameControl represents the form’s name control exposed by the component. Angular’s reactive forms guide covers controls, built-in validators, and form status; the validation guide documents using control state to conditionally show messages.

Handle asynchronous validation

An asynchronous validator returns a Promise or Observable. Angular runs async validators only after synchronous validators pass, so a field may be pending while the async check completes. Check the control’s pending state to show a suitable indication, and avoid presenting the field as definitively valid or invalid until that check finishes.

Show cross-field errors on the form group

A rule that compares sibling fields—such as requiring two values to be different—belongs to the parent group, because the failure comes from the combination rather than either field alone. Check the group’s error key and gate its message on group interaction:

Special offer. See more information about Outbyte and uninstall instructions. Please review EULA and Privacy policy.
<div *ngIf="actorForm.hasError('unambiguousRole') &&
            (actorForm.dirty || actorForm.touched)">
  Choose a role that does not conflict with the other value.
</div>

Angular’s validation example uses the group-level unambiguousRole error. This keeps the error attached to the rule that produced it instead of incorrectly marking one child as the sole cause.

Independent reader supportYour contribution helps us test, update, and keep practical guides available for everyone.Support on Ko-Fi

Choose a form style for the job

Both approaches support conditional error messages. The key difference is where the rules are defined and how custom validation is represented, as outlined in Angular’s forms overview.

Consideration Template-driven forms Reactive forms
Where rules live In template attributes and directives In the component model, attached to controls
Custom validator form A directive that wraps the validator and registers through NG_VALIDATORS A validator function attached to a control
Typical fit Small or simple forms More complex forms where explicit, scalable form modeling is useful

Product prices and availability are accurate as of the date/time indicated and are subject to change. Any price and availability information displayed on Amazon at the time of purchase will apply.