Here is my component:
@Component({ selector: 'bc-goods-detail', template: ` <span>good id: {{good?.id}}</span> <input [value]="good?.name" (input)="onInput($event)" /> <button (click)="onClick()">Save</button> `, styles: [] }) export class GoodsDetailComponent { @Input() good: Good; @Output() save = new EventEmitter<Good>(); onClick() { this.save.emit(this.good); } onInput ($event) { this.good.name = $event.target.value; } }
When I change the name in input and then I am pressing save button and this.good
is NOT CHANGED good. It is old good
, like it was passed to the component.
I started to debug the problem. I added onInput
handler. I found that when I do this instruction: this.good.name = $event.target.value;
I get this error in console:
ERROR TypeError: Cannot assign to read only property 'name' of object '#<Object>' at GoodsDetailComponent.webpackJsonp.435.GoodsDetailComponent.onInput (goods-detail.ts:24)
Here is usage of the component:
<bc-goods-detail [good]="selectedGood$ | async" (save)="onSave($event)" ></bc-goods-detail>
Here is how I receive data for this component:
/*…*/ selectedGood$: Observable<Good>; constructor(private store: Store<fromRoot.State>) { /*…*/ this.selectedGood$ = store.select(fromRoot.getGoodSelectedEntity); }
Here is the full code of container component: here.
Thoughts: I think the problem is because Observable returns immutable structure. I don’t think it is totally bad idea, but how to handle it?
I am trying to get same behaviour there: http://plnkr.co/edit/gdxEcSvC0v6JwoLEZDkJ?p=preview. It does not reproduce. I think this is because
How to solve my problem? I don’t want to get such error. When I press save I want this.good
to contain mutated object. How to achieve this?