Pipes
By Syncfusion®, Inc. · Last updated
What pipes are and why to use them, the built-in date, currency, number, percent, case and json pipes, chaining pipes, pipe parameters, and writing a custom pipe.
What Are Pipes?
A pipe is a function that formats a value inside a template, without changing the value stored in the class. You apply a pipe with the | character: {{ value | pipeName }}.
The value on the left goes into the pipe. The pipe returns the formatted text, and Angular displays that text.
Real-World Example
An orders API returns createdAt: "2026-03-15T09:30:00Z" and total: 54999. The orders table must show 15 Mar 2026 and ₹54,999.00.
Pipes do this formatting in the template, so the component keeps the raw API values for sorting, filtering and calculations.
54999value in the class| currency: 'INR'the pipe₹54,999.00text on screenThe class still stores 54999, so calculations stay correct.
A pipe formats the value on its way to the screen.
Why Pipes?
Without pipes, every component would need its own formatting methods, such as formatDate() and formatPrice(). That code is repeated across the app and easy to get wrong.
Pipes solve this:
- Reusable. One pipe formats values in every template of the app.
- Raw data stays raw. The class keeps numbers and dates, so calculations stay correct.
- Locale-aware. Built-in pipes follow the app's locale for dates, currencies and number separators.
- Fast. By default, Angular runs a pipe again only when its input value changes.
- Readable.
{{ total | currency:'INR' }}states its purpose clearly in the template.
Built-in Pipes
Angular ships common pipes in @angular/common. Import each pipe you use into the component's imports list.
| Pipe | Template name | Example input | Example output |
|---|---|---|---|
DatePipe | date | '2026-03-15' | Mar 15, 2026 |
CurrencyPipe | currency | 54999 | $54,999.00 |
DecimalPipe | number | 1234.5 | 1,234.5 |
PercentPipe | percent | 0.256 | 26% |
UpperCasePipe | uppercase | 'angular' | ANGULAR |
LowerCasePipe | lowercase | 'ANGULAR' | angular |
TitleCasePipe | titlecase | 'order shipped' | Order Shipped |
JsonPipe | json | { id: 7 } | { "id": 7 } |
The examples on this page use the default en-US locale, so numbers use western grouping: 1,284,503. To use Indian grouping (12,84,503) and Indian date formats, register the en-IN locale data with registerLocaleData and provide LOCALE_ID in app.config.ts.
DatePipe
DatePipe formats a date, a timestamp or an ISO date string. Pass a format name or a pattern as a parameter.
DatePipe formats one date in several ways
import { Component } from '@angular/core';
import { DatePipe } from '@angular/common';
@Component({
selector: 'app-root',
imports: [DatePipe],
template: `
<p>Default: {{ orderDate | date }}</p>
<p>Short: {{ orderDate | date: 'shortDate' }}</p>
<p>Custom: {{ orderDate | date: 'dd MMM yyyy' }}</p>
<p>Full: {{ orderDate | date: 'fullDate' }}</p>
`,
})
export class App {
orderDate = new Date(2026, 2, 15);
}
Common pattern letters are dd (day), MMM (short month name), MM (month number), yyyy (year), HH:mm (24-hour time) and h:mm a (12-hour time).
CurrencyPipe
CurrencyPipe formats a number as money. The first parameter is the ISO currency code, such as 'INR', 'USD' or 'EUR'.
CurrencyPipe formats prices in different currencies
import { Component } from '@angular/core';
import { CurrencyPipe } from '@angular/common';
@Component({
selector: 'app-root',
imports: [CurrencyPipe],
template: `
<p>Default: {{ price | currency }}</p>
<p>Rupees: {{ price | currency: 'INR' }}</p>
<p>Euros: {{ price | currency: 'EUR' }}</p>
<p>No decimals: {{ price | currency: 'INR' : 'symbol' : '1.0-0' }}</p>
`,
})
export class App {
price = 54999;
}
DecimalPipe
DecimalPipe, used as number, adds thousands separators and controls decimal places. Its parameter has the form 'minInteger.minFraction-maxFraction'.
DecimalPipe controls separators and decimal places
import { Component } from '@angular/core';
import { DecimalPipe } from '@angular/common';
@Component({
selector: 'app-root',
imports: [DecimalPipe],
template: `
<p>Page views: {{ views | number }}</p>
<p>Rating: {{ rating | number: '1.1-1' }}</p>
<p>Distance: {{ distance | number: '1.2-2' }} km</p>
`,
})
export class App {
views = 1284503;
rating = 4.4666;
distance = 7.5;
}
'1.2-2' means: at least 1 digit before the decimal point, and exactly 2 digits after it.
PercentPipe
PercentPipe multiplies a number by 100 and adds a percent sign. It accepts the same digit format as DecimalPipe.
PercentPipe turns ratios into percentages
import { Component } from '@angular/core';
import { PercentPipe } from '@angular/common';
@Component({
selector: 'app-root',
imports: [PercentPipe],
template: `
<p>Conversion rate: {{ conversion | percent }}</p>
<p>Test coverage: {{ coverage | percent: '1.1-1' }}</p>
`,
})
export class App {
conversion = 0.256;
coverage = 0.8734;
}
UpperCasePipe, LowerCasePipe and TitleCasePipe
These three pipes change the letter case of text.
uppercasechanges every letter to a capital letter.lowercasechanges every letter to a small letter.titlecasecapitalises the first letter of each word.
Case pipes normalise text from an API
import { Component } from '@angular/core';
import { LowerCasePipe, TitleCasePipe, UpperCasePipe } from '@angular/common';
@Component({
selector: 'app-root',
imports: [UpperCasePipe, LowerCasePipe, TitleCasePipe],
template: `
<p>Coupon code: {{ coupon | uppercase }}</p>
<p>Email: {{ email | lowercase }}</p>
<p>Status: {{ status | titlecase }}</p>
`,
})
export class App {
coupon = 'save20now';
email = 'Asha.Kumar@Example.COM';
status = 'out for delivery';
}
JsonPipe
JsonPipe converts an object to formatted JSON text. Developers use it to inspect data while debugging a template.
JsonPipe prints an object for debugging
import { Component } from '@angular/core';
import { JsonPipe } from '@angular/common';
@Component({
selector: 'app-root',
imports: [JsonPipe],
template: `<pre>{{ user | json }}</pre>`,
})
export class App {
user = { id: 42, name: 'Ravi', roles: ['editor', 'reviewer'] };
}
Wrap json output in a <pre> element. <pre> keeps the line breaks and indentation, so nested objects stay readable.
Chaining Pipes
You can apply several pipes to one value by writing them one after another. This is called chaining. Angular runs the pipes from left to right, and each pipe receives the output of the previous one.
Chained pipes run from left to right
import { Component } from '@angular/core';
import { DatePipe, UpperCasePipe } from '@angular/common';
@Component({
selector: 'app-root',
imports: [DatePipe, UpperCasePipe],
template: `
<p>Delivery: {{ deliveryDate | date: 'EEEE, d MMMM' | uppercase }}</p>
`,
})
export class App {
deliveryDate = new Date(2026, 2, 18);
}
First date produces Wednesday, 18 March. Then uppercase produces WEDNESDAY, 18 MARCH.
The order matters. {{ name | uppercase | slice: 0 : 3 }} is valid, but putting a date pipe after uppercase fails, because uppercase returns text that is no longer a date.
Pipe Parameters
A pipe parameter changes how a pipe formats its value. You write a colon after the pipe name, then the parameter value. Separate several parameters with more colons.
{{ value | pipeName : parameter1 : parameter2 }}
| Example | Pipe | Parameters |
|---|---|---|
{{ d | date: 'shortTime' }} | date | format |
{{ p | currency: 'INR' : 'code' }} | currency | currency code, display style |
{{ n | number: '1.0-2' }} | number | digit format |
{{ text | slice: 0 : 20 }} | slice | start index, end index |
Parameters can also be expressions from the class, such as {{ price | currency: selectedCurrency }}. When selectedCurrency changes, the pipe runs again.
Custom Pipes
A custom pipe is your own formatting function, packaged so every template can use it.
You create one with the @Pipe decorator and a class that has a transform method. Angular calls transform with the value from the left side of |, followed by any parameters. In a project, the CLI creates the file for you:
ng generate pipe file-size
A custom pipe formats file sizes
import { Component, Pipe, PipeTransform } from '@angular/core';
@Pipe({ name: 'fileSize' })
export class FileSizePipe implements PipeTransform {
transform(bytes: number, decimals: number = 1): string {
if (bytes < 1024) return bytes + ' B';
const units = ['KB', 'MB', 'GB'];
let size = bytes / 1024;
let unit = 0;
while (size >= 1024 && unit < units.length - 1) {
size = size / 1024;
unit++;
}
return size.toFixed(decimals) + ' ' + units[unit];
}
}
@Component({
selector: 'app-root',
imports: [FileSizePipe],
template: `
@for (file of files; track file.name) {
<p>{{ file.name }}: {{ file.bytes | fileSize }}</p>
}
<p>Precise: {{ 5368709120 | fileSize: 2 }}</p>
`,
})
export class App {
files = [
{ name: 'notes.txt', bytes: 820 },
{ name: 'photo.jpg', bytes: 2457600 },
{ name: 'backup.zip', bytes: 1610612736 },
];
}
A custom pipe has three parts:
@Pipe({ name: 'fileSize' })sets the name used in templates.implements PipeTransformdeclares that the class has atransformmethod.transform(value, ...params)returns the formatted result.
Custom pipes are pure by default. Angular runs a pure pipe again only when its input value or a parameter changes. This keeps templates fast. Keep transform free of side effects, so the same input always gives the same output.
Common Mistakes
| Mistake | What you see | Fix |
|---|---|---|
| Pipe not imported | NG0302: The pipe 'date' could not be found | Add DatePipe (or the pipe you use) to imports |
| Using the class name in the template | {{ d | DatePipe }} is not found | Use the template name: {{ d | date }} |
| Spaces in the digit format | '1.2 - 2' causes a format error | Write it without spaces: '1.2-2' |
percent on a whole number | 25 shows as 2,500% | Pass a ratio: 0.25 |
| Chaining in the wrong order | A pipe receives text it cannot read | Put pipes that need raw values first |
| Formatting in the class instead | Duplicated formatting code in many components | Move the formatting into a pipe |
Check Yourself
Exercises
What to Remember
- A pipe formats a value for display with
{{ value | pipe }}and leaves the class data unchanged. - Built-in pipes cover dates, currency, numbers, percentages, letter case and JSON. Pass settings with
:and chain pipes from left to right. - A custom pipe is a class with
@Pipeand atransformmethod.
Next: Event Handling, how to respond to clicks, key presses and form changes.