Today I would like to discuss two methods of sharing state between components. Say, we have record detail page, which is page for viewing record data. It has summary component inside. 1) Container – component design pattern.
@Component({
selector: 'app-summary',
template: '<div>{{redordName}}</div>',
changeDetection: ChangeDetectionStrategy.OnPush
})
export class SummaryComponent implements OnDestroy {
@Input() public recordName;
}
@Component({
selector: 'app-record-detail',
template: '<app-summary recordName="recordName"></app-summary>',
})
export class RecordDetailComponent implements OnInit,
public recordName;
private sub: Subscription;
constructor(private graphQlService: GraphQlService){}
ngOnInit() {
this.nameService.fetch((data) => this.recordName = data.recordName);
}
ngOnDestroy() { this.sub.unsubscribe();}
Here Container deals with data fetching and passes the data to subcomponent. After closing page fetched data gets cleared because we don’t need this. Name service is only for fetching data, it does not store anything. Also such way has one big advantage: we can use OnPush strategy in subcomponent which only works with Inputs.
2) Service which shares data
@Injectable({
providedIn: 'root',
})
export class nameService implements OnDestroy {
public recordName;
public sub;
constructor(private http: HttpClient){}
init() {
if (!recordName)
this.sub = this.http.get(url).subscribe((data) => {this.recordName = data.name})
}
ngOnDestroy() { this.sub.unsubscribe();}
@Component({
providers: [NameService],
selector: 'app-summary',
template: '<div>{{redordName}}</div>',
})
export class SummaryComponent implements OnDestroy {
public get recordName() { return this.nameService.recordName };
constructor(private nameService: NameService){}
ngOnInit() {
this.nameService.init();
}
}
@Component({
providers: [NameService],
selector: 'app-record-detail',
template: '<div>{{redordName}}</div>',
})
export class RecordDetailComponent implements OnInit
public get recordName() { return this.nameService.recordName };
private sub: Subscription;
constructor(private nameService: NameService){}
ngOnInit() {
this.nameService.init();
}
This way is more complex as you may notice. And is mostly used when components have no direct parent – child connection.
Leave a Reply