Introduction To Pipes In Angular 2

In our previous post, we saw the following.

  1. How to create a component
  2. How to associate an html file with the component
  3. How to register the component with the application module
  4. How to use our component within another component
  5. How to format data using the built-in pipes

In this post, we’ll try to explore more on Angular 2 pipes & how we can create and use a custom pipe as per our business requirement.

As we saw in our last post, Pipes help us transform displayed values within a template. It takes in the data with provided optional parameters if any; and transforms the data into the desired output. We also saw that Angular 2 has certain built-in pipes which can be used wherever required in any template. In Angular 1.x, we used to have “filters” for performing the same task. In Angular 2, it’s renamed to “Pipes”. Both the versions share some common filters/pipes. The below table lists the same.

Filter/PipeAngular 1.xAngular2
dateüü
upperCaseüü
lowerCaseüü
jsonüü
currency ü
numberü
orderbyü
filterü 
limitToü
percentü
decimalü
asyncü

Angular 2 shares some common pipes along with some new additional pipes.

Chaining Pipes

In Angular 2, we can chain Pipes i.e. applying more than one pipe to a property or an object. The sequence of how the pipes will be executed/applied will depend on the order of pipes specified on to the property. For example, if a property has | date | uppercase pipe applied; then in that case, first date pipe will be executed/applied followed by the uppercase pipe. Syntax for applying multiple pipes is -

{{property | pipe1| pipe2}}

E.g.

{{ hiredate | date | uppercase}}

Custom Pipes

In Angular 2, we can create custom pipes too. It helps us to write our own custom specification as per our business requirement. To help us understand how to create a custom pipe, we’ll try to create a pipe which filters data (on employee name) from our employee’s[] model and displays the searched result on the UI. Since our employee search pipe is going to be used only inside the “emp” module, we’ll create this pipe inside our “emp” folder. The steps to create a pipe are almost similar to that of creating a component. Let’s have a look at it.


Our EmployeeSearchPipe implements PipeTransform interface and provides implementation for transform method. In transform, we are simply checking whether any parameter was passed or not in the args string[] along with the input value.

  1. var userInput = args ? args.toString().toLocaleLowerCase() : null;   

If there is any input, then we are filtering the value parameter which is of type IEmployee[] to return the filtered result, else to return the full result.

  1. return userInput ? value.filter((emp: IEmployee) => emp.name.toLocaleLowerCase().indexOf(userInput) != -1) : value;   

We’ve decorated the EmployeeSearchPipe class with @Pipe decorator which tells Angular that this is our custom pipe. Also, in the pipe decorator, we provided the name of our custom pipe, which, in our case, is “empByNameFilter”.

That’s it. We are done with creating our custom Angular 2 pipe. In order to put this pipe to work, we need to modify our app.module.ts file (so that we can register our custom pipe with that of the application module & use it throughout the application). We need to update emp-list.component.html file too (i.e. to provide users with an input text where the user can provide a value on which our custom pipe search would be applied).

Here is the updated code for the app.module.ts file.

  1. /** Importing the angular modules from namespace */  
  2. import { NgModule } from '@angular/core';  
  3. import { BrowserModule } from '@angular/platform-browser';  
  4. import { FormsModule } from '@angular/forms';  
  5. /** Importing the AppComponent from the application's app folder */  
  6. import { AppComponent } from './app.component';  
  7. import { EmployeeListComponent } from './emp/emp-list.component';  
  8. import { EmployeeSearchPipe } from './emp/emp-search.pipe';  
  9.   
  10. @NgModule({  
  11.  imports: [BrowserModule, FormsModule],//other modules whose exported classes are needed by component templates declared in this module.  
  12.   declarations: [AppComponent, EmployeeListComponent, EmployeeSearchPipe],// the view classes that belong to this module. Angular has three kinds of view classes: components, directives, and pipes.  
  13.   bootstrap: [AppComponent]//the main application view, called the root component, that hosts all other app views. Only the root module should set this bootstrap property.  
  14. })  
  15. export class AppModule { }   

Below is the updated code for emp-list.component.html

  1. <div class="col-md-10 text-center">  
  2.     <div class="row">  
  3.         <div class="col-md-2">  
  4.             <label class="control-label">Filter By:</label>  
  5.         </div>  
  6.         <div class="col-md-4">  
  7.             <input type="text" class="form-control" [(ngModel)]='filterByName' />  
  8.         </div>  
  9.     </div>  
  10.     <div class="row">  
  11.         <div class="col-md-2">  
  12.             <label class="control-label">Filtered By:</label>  
  13.         </div>  
  14.         <div class="col-md-4">  
  15.            <strong> {{filterByName}}</strong>  
  16.         </div>  
  17.     </div>  
  18.     <div class="row">  
  19.         <div class="col-md-10">  
  20.             <div class="table-responsive">  
  21.                 <table class="table table-striped table-bordered">  
  22.                     <thead>  
  23.                         <tr>  
  24.                             <th>Emp Id</th>  
  25.                             <th>Name</th>  
  26.                             <th>Email</th>  
  27.                             <th>Phone</th>  
  28.                             <th>Salary</th>  
  29.                             <th>Photo</th>  
  30.                             <th>Appraisal Rating</th>  
  31.                         </tr>  
  32.                     </thead>  
  33.                     <tbody>  
  34.                         <tr *ngIf="employees.length==0">  
  35.                             <td colspan="7">  
  36.                                 No Records Found...  
  37.                             </td>  
  38.                         </tr>  
  39.                         <tr *ngFor="let emp of employees | empByNameFilter:filterByName">  
  40.                             <td class="leftAlign">{{emp.empId}}</td>  
  41.                             <td class="leftAlign">{{emp.name|uppercase}}</td>  
  42.                             <td class="leftAlign">{{emp.email|lowercase}}</td>  
  43.                             <td class="leftAlign">{{emp.phone}}</td>  
  44.                             <td class="rightAlign">{{emp.salary|currency:'INR':true:'1.2-2'}}</td>  
  45.                             <td class="centerAlign">  
  46.                                 <img [src]="emp.photo" [style.width.px]='imageWidth' [style.height.px]='imageHeight' />  
  47.                             </td>  
  48.                             <td class="centerAlign">{{emp.appraisalRating|number}}</td>  
  49.                         </tr>  
  50.                     </tbody>  
  51.                 </table>  
  52.             </div>  
  53.         </div>  
  54.     </div>  
  55. </div>   

Note

  1. I’ve added a new variable/property in emp-list.component.ts file named as “filterByName” of string type. Default value of this property is empty.


  1. For two way binding in Angular 2, we need to enclose ngModel inside the [( )] brackets.

    [(ngModel)]='filterByName'. As we’ve seen earlier that [] brackets in Angular 2 are used for performing property binding which we did on our img HTML element [SRC] attribute. ( ) brackets in Angular 2 are used for binding an event with that of a TypeScript class method. We will discuss more on this, a bit later.
  1. We’ve applied our custom pipe “empByName” on the *ngFor row. There we are iterating over the number of records in the employees[]. Also, we’ve passed the value there in the filterByName variable/property.
    1. <tr *ngFor="let emp of employees | empByNameFilter: filterByName">  
  1. I’ve imported FormsModule (for including ngModel) in the app.module.ts and registered it in imports of @NgModule in app.module.ts. If FormsModule is not included, it will give ngModel undefined error.

Now, run the application and you’ll see the below output.

output

Try to provide a filter value in the input text box and check whether your data is been filtered like the below snapshot or not.

output

In our next post, we’ll continue further. Until then, you can download the solution and test it locally at your end. I am uploading the solution with this post; but I won’t be able to upload the node_modules folder because of heavy size. So, I request you to do npm install before you run the application, after downloading the solution.