diff --git a/packages/forms/src/model.ts b/packages/forms/src/model.ts index ae6550a82b578..96c8f320fd89c 100644 --- a/packages/forms/src/model.ts +++ b/packages/forms/src/model.ts @@ -1167,7 +1167,7 @@ export class FormControl extends AbstractControl { // `VALID` or `INVALID`. // The status should be broadcasted via the `statusChanges` observable, so we set `emitEvent` // to `true` to allow that during the control creation process. - emitEvent: !!asyncValidator + emitEvent: !!this.asyncValidator }); } @@ -1433,7 +1433,7 @@ export class FormGroup extends AbstractControl { // If `asyncValidator` is present, it will trigger control status change from `PENDING` to // `VALID` or `INVALID`. The status should be broadcasted via the `statusChanges` observable, // so we set `emitEvent` to `true` to allow that during the control creation process. - emitEvent: !!asyncValidator + emitEvent: !!this.asyncValidator }); } @@ -1887,7 +1887,7 @@ export class FormArray extends AbstractControl { // `VALID` or `INVALID`. // The status should be broadcasted via the `statusChanges` observable, so we set `emitEvent` // to `true` to allow that during the control creation process. - emitEvent: !!asyncValidator + emitEvent: !!this.asyncValidator }); } diff --git a/packages/forms/test/form_array_spec.ts b/packages/forms/test/form_array_spec.ts index 5097be6621569..0ddc42a564273 100644 --- a/packages/forms/test/form_array_spec.ts +++ b/packages/forms/test/form_array_spec.ts @@ -1055,6 +1055,23 @@ describe('FormArray', () => { expect(g.errors).toEqual({'async': true, 'other': true}); expect(g.pending).toEqual(false); })); + + it('should fire statusChanges events when async validators are added via options object', + fakeAsync(() => { + // The behavior is tested (in other spec files) for each of the model types (`FormControl`, + // `FormGroup` and `FormArray`). + let statuses: string[] = []; + + // Create a form control with an async validator added via options object. + const asc = new FormArray([], {asyncValidators: [() => Promise.resolve(null)]}); + + // Subscribe to status changes. + asc.statusChanges.subscribe((status: any) => statuses.push(status)); + + // After a tick, the async validator should change status PENDING -> VALID. + tick(); + expect(statuses).toEqual(['VALID']); + })); }); describe('disable() & enable()', () => { diff --git a/packages/forms/test/form_control_spec.ts b/packages/forms/test/form_control_spec.ts index d4344e8ce5f1c..3584e963f17db 100644 --- a/packages/forms/test/form_control_spec.ts +++ b/packages/forms/test/form_control_spec.ts @@ -879,6 +879,22 @@ describe('FormControl', () => { tick(); })); + it('should fire statusChanges events for async validators added via options object', + fakeAsync(() => { + // The behavior can be tested for each of the model types. + let statuses: string[] = []; + + // Create a form control with an async validator added via options object. + const asc = new FormControl('', {asyncValidators: [() => Promise.resolve(null)]}); + + // Subscribe to status changes. + asc.statusChanges.subscribe((status: any) => statuses.push(status)); + + // After a tick, the async validator should change status PENDING -> VALID. + tick(); + expect(statuses).toEqual(['VALID']); + })); + it('should fire an event after the status has been updated to pending', fakeAsync(() => { const c = new FormControl('old', Validators.required, asyncValidator('expected')); diff --git a/packages/forms/test/form_group_spec.ts b/packages/forms/test/form_group_spec.ts index 830a3ae587e3b..37de0698503bd 100644 --- a/packages/forms/test/form_group_spec.ts +++ b/packages/forms/test/form_group_spec.ts @@ -819,6 +819,21 @@ describe('FormGroup', () => { group = new FormGroup({'one': control}); })); + it('should fire statusChanges events for async validators added via options object', + fakeAsync(() => { + // The behavior can be tested for each of the model types. + let statuses: string[] = []; + + // Create a form control with an async validator added via options object. + const asc = new FormGroup({}, {asyncValidators: [() => Promise.resolve(null)]}); + + // Subscribe to status changes. + asc.statusChanges.subscribe((status: any) => statuses.push(status)); + + // After a tick, the async validator should change status PENDING -> VALID. + tick(); + expect(statuses).toEqual(['VALID']); + })); // TODO(kara): update these tests to use fake Async it('should fire a statusChange if child has async validation change', done => {