Formatting dates and numbers in React


Formatting numbers and dates is a common requirement for lots of apps but how do we do this in react apps?

Let’s say we have a component in our app that shows a list of customers, looking like this:

… and here’s the current code for this component:`// CustomerSearchResults.tsx

CustomerSearchResults.tsx
import * as React from "react";
import Customer from "./Customer";
interface CustomerSearchResultsProps {
customers: Customer[];
}
const CustomerSearchResults = (props: CustomerSearchResultsProps) => {
const rows = props.customers.map(customer => (
<tr key={customer.id}>
<th>{customer.id}</th>
<td>{customer.name}</td>
<td>{customer.revenue}</td>
<td>{customer.firstSale.toString()}</td>
</tr>
));
return (
<table className="table table-hover">
<thead>
<tr>
<th>Id</th>
<th>Name</th>
<th>Revenue</th>
<th>First Sale</th>
</tr>
</thead>
<tbody>{rows}</tbody>
</table>
);
};
export default CustomerSearchResults;

… with the following data:`// customers.json

// customers.json
[
{
id: 1,
name: "Alfreds Futterkiste",
revenue: 12000,
firstSale: "2012-04-23T00:00:00.000Z"
},
{
id: 2,
name: "Chop-suey Chinese",
revenue: 34000,
firstSale: "2000-10-21T00:00:00.000Z"
},
{
id: 3,
name: "Ernst Handel",
revenue: 82400,
firstSale: "2000-01-03T00:00:00.000Z"
},
{
id: 4,
name: "Maison Dewey",
revenue: 10000,
firstSale: "2012-06-02T00:00:00.000Z"
},
{
id: 5,
name: "Rancho grande",
revenue: 40000,
firstSale: "1976-01-04T00:00:00.000Z"
}
];

You can see that we need to clean up the revenue and first sale data by formatting them.

Formatting numbers

We can use Intl.NumberFormat to format the revenue:

<td>
{new Intl.NumberFormat("en-GB", {
style: "currency",
currency: "GBP"
}).format(customer.revenue)}
</td>

In the above example we are formatting to revenue using Great British locale, using the Great British currency style.

So, we now have this:

But what if we don’t want the decimals in the revenue? We just add the min and max fraction digits in the options:

<td>
{new Intl.NumberFormat("en-GB", {
style: "currency",
currency: "GBP",
minimumFractionDigits: 0,
maximumFractionDigits: 0
}).format(customer.revenue)}
</td>

Formatting dates

We could just use toLocaleDateString instead of toString:

<td>{customer.firstSale.toLocaleDateString()}</td>

… which gives us a nice short date:

However, we can use Intl.DateTimeFormat to gain more control on the formatting:

<td>
{new Intl.DateTimeFormat("en-GB", {
year: "numeric",
month: "long",
day: "2-digit"
}).format(customer.firstSale)}
</td>

Here we are specifying a 2 digit day, a long month and a 4 digit year.

So, here’s our final CustomerSearchResults component code:

CustomerSearchResults.tsx
import * as React from "react";
import Customer from "./Customer";
interface CustomerSearchResultsProps {
customers: Customer[];
}
const CustomerSearchResults = (props: CustomerSearchResultsProps) => {
const rows = props.customers.map(customer => (
<tr key={customer.id}>
<th>{customer.id}</th>
<td>{customer.name}</td>
<td>
{new Intl.NumberFormat("en-GB", {
style: "currency",
currency: "GBP",
minimumFractionDigits: 0,
maximumFractionDigits: 0
}).format(customer.revenue)}
</td>
<td>
{new Intl.DateTimeFormat("en-GB", {
year: "numeric",
month: "long",
day: "2-digit"
}).format(customer.firstSale)}
</td>
</tr>
));
return (
<table className="table table-hover">
<thead>
<tr>
<th>Id</th>
<th>Name</th>
<th>Revenue</th>
<th>First Sale</th>
</tr>
</thead>
<tbody>{rows}</tbody>
</table>
);
};
export default CustomerSearchResults;

… and here’s what it looks like:

Much better!

Learn React with TypeScript - 3rd Edition

New

A comprehensive guide to building modern React applications with TypeScript. Learn best practices, advanced patterns, and real-world development techniques.

View on Amazon
Learn React with TypeScript - Third Edition