How To Share Data Between Components Using Subscription And Subject In Angular 6

While working on a problem, I needed to search a data using the auto search functionality in Angular and had to pull the records from API and populate the data into the search box so that the user can select the records. Based on the selected data, all the records had to display on the screen. As it was a huge data, so I had used loading spinner functionality to avoid the confusion. In this case, all the data was fetched through API and bind into the data table.

As we know that there were following ways to share the data between components.

  1. Parent to Child: Sharing Data via Input
  2. Child to Parent: Sharing Data via ViewChild
  3. Child to Parent: Sharing Data via Output() and EventEmitter

Apart from the above approach, we can use the sharing service to pass the data between components.

There was a scenario where we can show the number of records based on the search data. There were two separate components named header and product was created to achieve the problem.

Solution

I had used an ngx-spinner and message service to achieve this functionality. If you look closely at the application you can see that there is a search bar in the top header which is used to search the data and the record is displayed based on the search record. You can set auto-search functionality in this case. Because when we start the search, it will automatically populate the data which you want to search and based on the data you need to apply to the spinner functionality as it might take few seconds to load the data if it is a huge number of record.

I have created a sample POC to illustrate the use of shared service using subject and subscription to pass the data between components.

Following things are used to develop this POC.

  1. Angular 6,
  2. Bootstrap 4
  3. Add the required packages like ngx-spinner, primeng.

I would suggest you download the sample code and explore for more information.

Create a Header component and design accordingly.

header.component.ts

  1. import { Component, OnInit } from '@angular/core';  
  2. import { Subscription } from 'rxjs';  
  3. import { MessageServiceService } from '../services/message-service.service';  
  4.   
  5. @Component({  
  6.   selector: 'app-header',  
  7.   templateUrl: './header.component.html',  
  8.   styleUrls: ['./header.component.css']  
  9. })  
  10. export class HeaderComponent implements OnInit {  
  11.   searchText:any;  
  12.   constructor(private message_service: MessageServiceService) {  
  13.      
  14.   }  
  15.   
  16.   ngOnInit() {  
  17.   
  18.   }  
  19.   onSearch() {      
  20.     this.message_service.sendProductId(this.searchText);  
  21.   }  
  22.   
  23. }  

Create product component and design accordingly

product.component.ts

  1. import { Component, OnInit } from '@angular/core';  
  2. import { Subscription } from 'rxjs';  
  3. import { MessageServiceService } from '../../services/message-service.service';  
  4. import { UserService } from '../../services/user.service';  
  5. import { NgxSpinnerService } from 'ngx-spinner';  
  6.   
  7. @Component({  
  8.   selector: 'app-product',  
  9.   templateUrl: './product.component.html',  
  10.   styleUrls: ['./product.component.css']  
  11. })  
  12. export class ProductComponent implements OnInit {  
  13.   subscription: Subscription;  
  14.   productName: string;  
  15.   productList: any;  
  16.   constructor(private message_service: MessageServiceService, private productService: UserService,private spinner: NgxSpinnerService) {  
  17.     this.subscription = this.message_service.getProductID().subscribe(message => {  
  18.        
  19.       this.productName = message.text;  
  20.       if (this.productName) {         
  21.         this.getProduct(this.productName);         
  22.       }  
  23.     });  
  24.   }  
  25.   
  26.   ngOnInit() {   
  27.     this.productList = this.productService.getProductData();  
  28.   }  
  29.   getProduct(name) {  
  30.     this.spinner.show();  
  31.     setTimeout(() => {  
  32.       /** spinner ends after 5 seconds */  
  33.       this.spinner.hide();  
  34.       this.productList=this.productService.getProductDataByName(name);  
  35.   }, 5000);  
  36.     //this.productList=this.productService.getProductDataByName(name);  
  37.     // this.spinner.hide();  
  38.   }  
  39.   
  40. }  

Create shared service

message-service.service.ts

  1. import { Injectable } from '@angular/core';  
  2. import { Subject } from 'rxjs';  
  3. import { Observable } from 'rxjs';  
  4.   
  5. @Injectable()  
  6. export class MessageServiceService {  
  7.   private subject = new Subject<any>();  
  8.   constructor() { }  
  9.   
  10.   sendProductID(message: string) {  
  11.     this.subject.next({ text: message });  
  12.   }  
  13.   
  14.   getProductID(): Observable<any> {  
  15.     return this.subject.asObservable();  
  16.   }}  

The output of the application will look like below,

Screen 1

When you run the application you will get all the data showing on the screen.
 
Share Data Between Components Using Subscription And Subject In Angular 

Screen 2

Enter the product what you want to search and click on search button.
 
Share Data Between Components Using Subscription And Subject In Angular 

Screen 3

Share Data Between Components Using Subscription And Subject In Angular