Click here for v1.x documentation.
Dinero.js
Dinero.js version

Formatting in a multilingual site

Different languages and locations can have radically different formatting styles when it comes to money. For example, ten U.S. dollars in American English should be written down "$10.00". However, in Canadian French, the same amount would be "10,00 $ US".

Dinero.js provides a toFormat function that gives you full control over how to format a Dinero object. Yet, if you're working on a multilingual site or app, such as a booking site for a hotel, you might want to rely on established formatting conventions.

Copy linkBuilding a custom Internationalization formatter

ECMAScript provides an Internationalization API (Intl) that lets you natively format monetary values into a given language by passing a locale. You can create your own Intl formatter by wrapping toFormat.

import { dinero, toFormat } from 'dinero.js';
import { USD } from '@dinero.js/currencies';

function intlFormat(dineroObject, locale, options = {}) {
  function transformer({ amount, currency }) {
    return amount.toLocaleString(locale, {
      ...options,
      style: 'currency',
      currency: currency.code,
    });
  };

  return toFormat(dineroObject, transformer);
};

const d = dinero({ amount: 1000, currency: USD });

intlFormat(d, 'en-US'); // "$10.00"
intlFormat(d, 'fr-CA'); // "10,00 $ US"

Copy linkUsing the custom formatter

You can use the formatter to display monetary values differently according to the current language of your site or app. For example, a React implementation could look like the following.

import React from 'react';
import { dinero } from 'dinero.js';
import { USD } from '@dinero.js/currencies';

import { intlFormat } from './intlFormat';

const languages = [
  {
    label: 'English (U.S.)',
    locale: 'en-US',
  },
  {
    label: 'Français (Canada)',
    locale: 'fr-CA',
  },
];

function App() {
  const [defaultLanguage] = locales;
  const [language, setLanguage] = React.useState(defaultLanguage);

  const price = dinero({ amount: 1000, currency: USD });

  return (
    <>
      <select
        value={language.locale}
        onChange={(event) => setLanguage(event.target.value)}
      >
        {languages.map(({ label, locale }) => (
          <option key={locale} value={locale}>
            {label}
          </option>
        ))}
      </select>
      <p>Price: {intlFormat(price, language.locale)}</p>
    </>
  );
}