diff --git a/src/data/formatters/converterNumberToCurrency/__tests__/convertNumberToCurrency.test.ts b/src/data/formatters/converterNumberToCurrency/__tests__/convertNumberToCurrency.test.ts new file mode 100644 index 0000000..e5cf321 --- /dev/null +++ b/src/data/formatters/converterNumberToCurrency/__tests__/convertNumberToCurrency.test.ts @@ -0,0 +1,39 @@ +import { converterNumberToCurrency } from '..' + +describe('[Data] convertNumberToCurrency', () => { + it('should return a currency formatted string when passed a valid number', () => { + expect(converterNumberToCurrency({ value: 12345.67 })).toBe('12.345,67') + expect( + converterNumberToCurrency({ value: 12345.67, setsCurrencySymbol: true }) + ).toBe('R$\xa012.345,67') + expect( + converterNumberToCurrency({ value: 12345.678, setsDecimalPlaces: 3 }) + ).toBe('12.345,678') + }) + + it('should return a currency formatted string when passed a valid string number', () => { + expect(converterNumberToCurrency({ value: '12345.67' })).toBe('12.345,67') + expect( + converterNumberToCurrency({ value: '12345.67', setsCurrencySymbol: true }) + ).toBe('R$\xa012.345,67') + expect( + converterNumberToCurrency({ value: '12345.678', setsDecimalPlaces: 3 }) + ).toBe('12.345,678') + }) + + it('should return an empty string when passed an invalid value', () => { + expect(converterNumberToCurrency({ value: 'not a number' })).toBe('') + expect(converterNumberToCurrency({ value: NaN })).toBe('') + expect(converterNumberToCurrency({ value: Infinity })).toBe('') + }) + + it('should throw an error when passed a negative number', () => { + expect(() => converterNumberToCurrency({ value: -12345.67 })).toThrow() + }) + + it('should throw an error when passed a number that is too large', () => { + expect(() => + converterNumberToCurrency({ value: Number.MAX_SAFE_INTEGER + 1 }) + ).toThrow() + }) +}) diff --git a/src/data/formatters/converterNumberToCurrency/index.ts b/src/data/formatters/converterNumberToCurrency/index.ts new file mode 100644 index 0000000..180b099 --- /dev/null +++ b/src/data/formatters/converterNumberToCurrency/index.ts @@ -0,0 +1,33 @@ +import { type converterNumberToCurrencyProps } from './types' + +export const converterNumberToCurrency = ({ + value, + setsDecimalPlaces, + setsCurrencySymbol +}: converterNumberToCurrencyProps) => { + const isNumber = typeof value === 'number' + const convertToNumber = isNumber ? value : Number(value) + + if (isNaN(convertToNumber) || !isFinite(convertToNumber)) return '' + + if (convertToNumber < 0) { + throw new Error('O valor não pode ser negativo!') + } + + if (convertToNumber > Number.MAX_SAFE_INTEGER) { + throw new Error('O valor fornecido é muito grande!') + } + + const language = 'pt-BR' + const currency = 'BRL' + const includesCurrency = setsCurrencySymbol + ? { style: 'currency', currency } + : {} + const options = { + ...includesCurrency, + minimumFractionDigits: setsDecimalPlaces ?? 2, + maximumFractionDigits: setsDecimalPlaces ?? 2 + } + const currentCurrency = new Intl.NumberFormat(language, options) + return currentCurrency.format(convertToNumber) +} diff --git a/src/data/formatters/converterNumberToCurrency/types.ts b/src/data/formatters/converterNumberToCurrency/types.ts new file mode 100644 index 0000000..b0d2b45 --- /dev/null +++ b/src/data/formatters/converterNumberToCurrency/types.ts @@ -0,0 +1,5 @@ +export interface converterNumberToCurrencyProps { + value: number | string + setsCurrencySymbol?: boolean + setsDecimalPlaces?: number +}