How can I get all "dirty" (modified) fields using angular2 forms?

Well, this is how I'm going by at the moment:

private getChangedProperties(): string[] {
  let changedProperties = [];

  Object.keys(this.permissionForm.controls).forEach((name) => {
    const currentControl = this.permissionForm.controls[name];

    if (currentControl.dirty) {
      changedProperties.push(name);
    }
  });

  return changedProperties;
}

I was really hoping angular2 forms would have a simple property with that information. Please post another answer if there's a better way of doing this.


You can achieve this using Observables:

Observable.from(Object.values(this.permissionForm.controls))
  .filter(control => control.dirty)
  .subscribe(control => {
    // Here doing stuff with all your dirty control
  })

You can also subscribe to control changes :

this.permissionForm
  .valueChanges
  .subscribe(control => {
    // Here doing stuff with your control
    // like checking if control is dirty and append it to an array
  });

const keyValue = Object.entries(this.form.controls).filter(value => value[1].dirty);

For get control names array:

keyValue.map(value => value[0]);

For get controls array:

keyValue.map(value => value[1]);

For get controls object:

keyValue.reduce((a, v) => Object.assign(a, { [v[0]]: v[1] }), {});

Сompact function:

type GetDirtyControlsTypes = 'object' | 'array' | 'names';

export function getDirtyControls(form: FormGroup, type: GetDirtyControlsTypes = 'object') {
  // keyValue
  const kv = Object.entries(form.controls).filter(val => val[1].dirty);
  return {
    object: () => kv.reduce((accum, val) => Object.assign(accum, { [val[0]]: val[1] }), {}),
    array: () => kv.map(val => val[1]),
    names: () => kv.map(val => val[0]),
  }[type]();
}

Tags:

Angular