My form is binding to ngrx correctly and I've added the FormGroupState into my reducer state but when deleting required values I'm not getting any mat-error messages appearing despite the fact that my form model does contain the correct error child value.
import { createEntityAdapter, EntityAdapter, EntityState } from '@ngrx/entity';
import { createFeatureSelector, createSelector } from '@ngrx/store';
import { createFormGroupReducerWithUpdate, createFormGroupState, FormGroupState, validate } from 'ngrx-forms';
import { required } from 'ngrx-forms/validation';
import { System } from '../../../model/fusion.dtos';
import { FusionCoreAppState } from '../../index';
import { SystemsActions, SystemsActionTypes } from '../actions/systems.actions';
const SystemEditFormId = 'SystemEditFormId';
const InitialSystemEditFormValue: System = {
id: 0,
name: '',
initials: '',
colour: ''
};
export const InitialSystemEditFormState = createFormGroupState<System>(SystemEditFormId, InitialSystemEditFormValue);
const validationFormGroupReducer = createFormGroupReducerWithUpdate<System>({
name: validate(required),
initials: validate(required),
});
export interface State extends EntityState<System> {
selectedSystemId: number;
systemEditForm: FormGroupState<System>;
loaded: boolean;
loading: boolean;
error: string | null;
}
export const initialState: State = adapter.getInitialState({
selectedSystemId: null,
systemEditForm: InitialSystemEditFormState,
loaded: false,
loading: false,
error: null,
});
export function reducer(state = initialState,
action: SystemsActions): State {
const systemEditForm = validationFormGroupReducer(state.systemEditForm, action);
if (systemEditForm !== state.systemEditForm) {
state = { ...state, systemEditForm };
return state;
}
switch (action.type) {
case SystemsActionTypes.LoadSingle:
case SystemsActionTypes.Load: {
return {
...state,
loading: true,
error: null,
};
}
case SystemsActionTypes.LoadSuccess: {
return adapter.addMany(action.payload, {
...state,
loaded: true,
loading: false,
error: null,
});
}
case SystemsActionTypes.LoadSingleSuccess: {
return adapter.addOne(action.payload, {
...state,
loaded: true,
loading: false,
error: null,
});
}
case SystemsActionTypes.Select: {
return {
...state,
selectedSystemId: action.payload,
};
}
default: {
return state;
}
}
}
import { ChangeDetectionStrategy, Component, Input } from '@angular/core';
import { ActionsSubject } from '@ngrx/store';
import { FormGroupState, ResetAction, SetValueAction } from 'ngrx-forms';
import { System } from '../../../../model/fusion.dtos';
import { InitialSystemEditFormState } from '../../../../store/systems/reducers/systems.reducer';
@Component({
selector: 'fusion-system-edit-form',
template: `
<div class="content p-24">
<div fxLayout="column" fxLayoutAlign="start start" fxLayout.gt-md="row">
<form class="mat-white-bg mat-elevation-z4 p-24 mr-24 mb-24" fxLayout="column" fxLayoutAlign="start"
fxFlex="1 0 auto" name="form" novalidate [ngrxFormState]="systemEditState"
(submit)="submit()">
<div fxLayout="row" fxLayoutAlign="start center" fxFlex="1 0 auto">
<mat-form-field fxFlex="50">
<input matInput
placeholder="Name"
[ngrxFormControlState]="systemEditState.controls.name" required>
<mat-error *ngIf="systemEditState.errors._name?.required">
A name is required
</mat-error>
</mat-form-field>
<mat-form-field fxFlex="50">
<input matInput placeholder="Initials"
[ngrxFormControlState]="systemEditState.controls.initials" required>
<mat-error *ngIf="systemEditState.errors._initials?.required">
Initials are required
</mat-error>
</mat-form-field>
</div>
<ul *ngIf="systemEditState.isInvalid"
class="error-messages">
<li *ngIf="systemEditState.errors._name?.required">
A name is required
</li>
<li *ngIf="systemEditState.errors._initials?.required">
Initials are required
</li>
</ul>
<div class="buttons">
<div>
<button mat-raised-button
color="primary"
type="submit"
[disabled]="systemEditState.isInvalid && systemEditState.isSubmitted">
Register
</button>
<button mat-raised-button
type="button"
[disabled]="systemEditState.isPristine
&& systemEditState.isUntouched
&& systemEditState.isUnsubmitted"
(click)="reset()">
Reset
</button>
</div>
</div>
</form>
<div class="form-errors-model mat-white-bg p-24 mat-elevation-z4">
<div class="h2 mb-24">Reactive Form Errors Model</div>
<pre><code>{{systemEditState.errors | json}}</code></pre>
</div>
</div>
</div>
`,
changeDetection: ChangeDetectionStrategy.OnPush,
})
export class SystemEditFormComponent {
@Input() systemEditState: FormGroupState<System>;
@Input() originalValue: System;
submittedValue: System;
constructor(private actionsSubject: ActionsSubject) {
}
reset() {
this.actionsSubject.next(new SetValueAction(InitialSystemEditFormState.id, this.originalValue));
this.actionsSubject.next(new ResetAction(InitialSystemEditFormState.id));
}
submit() {
if (this.systemEditState.isInvalid) {
return;
}
this.submittedValue = this.systemEditState.value;
}
}
Is there something I'm doing wrong? I suspect that I'm not adding the ngrx-forms reducer into my existing reducer correctly?