/* * Copyright (c) 2005-2011 Grameen Foundation USA * All rights reserved. * * Licensed under the Apache License, Version 2.0 (the "License"); * you may not use this file except in compliance with the License. * You may obtain a copy of the License at * * http://www.apache.org/licenses/LICENSE-2.0 * * Unless required by applicable law or agreed to in writing, software * distributed under the License is distributed on an "AS IS" BASIS, * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or * implied. See the License for the specific language governing * permissions and limitations under the License. * * See also http://www.apache.org/licenses/LICENSE-2.0.html for an * explanation of the license and how it is applied. */ package org.mifos.framework.util; import static org.hamcrest.Matchers.is; import static org.junit.Assert.assertThat; import java.math.BigDecimal; import java.text.DateFormat; import java.util.Calendar; import java.util.Locale; import junit.framework.Assert; import org.junit.Before; import org.junit.Ignore; import org.junit.Test; import org.mifos.application.master.business.MifosCurrency; import org.mifos.config.AccountingRules; import org.mifos.config.Localization; import org.mifos.framework.util.helpers.ConversionError; import org.mifos.framework.util.helpers.DateUtils; import org.mifos.framework.util.helpers.DoubleConversionResult; public class LocalizationConverterTest { private LocalizationConverter converter; @Before public void setup() { short digitsAfterDecimalForMoney = Short.valueOf("1"); short digitsBeforeDecimalForMoney= Short.valueOf("1"); short digitsAfterDecimalForInterest = Short.valueOf("5"); short digitsBeforeDecimalForInterest = Short.valueOf("1"); short digitsBeforeDecimalForCashFlowValidations = Short.valueOf("1"); short digitsAfterDecimalForCashFlowValidations = Short.valueOf("5"); converter = new LocalizationConverter(digitsAfterDecimalForMoney, digitsBeforeDecimalForMoney, digitsAfterDecimalForInterest, digitsBeforeDecimalForInterest, digitsBeforeDecimalForCashFlowValidations, digitsAfterDecimalForCashFlowValidations); } @Test public void testDateFormattingWithFourDigitsInYear() throws Exception { DateFormat dateFormat = converter.getDateFormatWithFullYear(); Assert.assertEquals("13/12/2008", dateFormat.format(DateUtils.getDate(2008, Calendar.DECEMBER, 13))); } @Test public void testGetDecimalFormatSymbol() { Locale locale = Localization.getInstance().getConfiguredLocale(); char sep = '.'; if (locale.getCountry().equalsIgnoreCase("GB") && locale.getLanguage().equalsIgnoreCase("EN")) { Assert.assertEquals(sep, converter.getDecimalFormatSymbol()); } converter.setCurrentLocale(new Locale("IS", "is")); sep = ','; Assert.assertEquals(sep, converter.getDecimalFormatSymbol()); converter.setCurrentLocale(locale); } @Test public void testGetDoubleStringForMoney() { String doubleValueString = "2.5"; Double dValue = 2.5000000000; Locale locale = Localization.getInstance().getConfiguredLocale(); String dString = converter.getDoubleStringForMoney(dValue); if (locale.getCountry().equalsIgnoreCase("GB") && locale.getLanguage().equalsIgnoreCase("EN")) { Assert.assertEquals(doubleValueString, dString); } converter.setCurrentLocale(new Locale("IS", "is")); doubleValueString = "2,5"; dString = converter.getDoubleStringForMoney(dValue); Assert.assertEquals(doubleValueString, dString); converter.setCurrentLocale(locale); } @Test public void testGetDoubleStringForInterest() { String doubleValueString = "2123.12345"; Double dValue = 2123.12345000000; Locale locale = Localization.getInstance().getConfiguredLocale(); String dString = converter.getDoubleStringForInterest(dValue); if (locale.getCountry().equalsIgnoreCase("GB") && locale.getLanguage().equalsIgnoreCase("EN")) { Assert.assertEquals(doubleValueString, dString); } converter.setCurrentLocale(new Locale("IS", "is")); doubleValueString = "2123,12345"; dString = converter.getDoubleStringForInterest(dValue); Assert.assertEquals(doubleValueString, dString); converter.setCurrentLocale(locale); } @Test public void testGetDoubleValueString() { String doubleValueString = "2.59"; Double dValue = 2.59; Locale locale = Localization.getInstance().getConfiguredLocale(); String dString = converter.getDoubleValueString(dValue); if (locale.getCountry().equalsIgnoreCase("GB") && locale.getLanguage().equalsIgnoreCase("EN")) { Assert.assertEquals(doubleValueString, dString); } converter.setCurrentLocale(new Locale("IS", "is")); doubleValueString = "2,59"; dString = converter.getDoubleValueString(dValue); Assert.assertEquals(doubleValueString, dString); converter.setCurrentLocale(locale); } /** * Currently broken -- incomplete support for multiple locales for numeric * input. */ @Ignore @Test public void testGetDateSeparator() { String separator = "/"; Locale locale = Localization.getInstance().getConfiguredLocale(); String dateSeparator = converter.getDateSeparatorForCurrentLocale(); if (locale.getCountry().equalsIgnoreCase("GB") && locale.getLanguage().equalsIgnoreCase("EN")) { Assert.assertEquals(separator, dateSeparator); } converter.setCurrentLocale(new Locale("IS", "is")); dateSeparator = converter.getDateSeparatorForCurrentLocale(); Assert.assertEquals(".", dateSeparator); converter.setCurrentLocale(locale); } @Test public void testParseDoubleForMoney() { String doubleValueString = "2.5"; Double dValue = 2.5; Short digitsAfterForMoneySaved = AccountingRules.getDigitsAfterDecimal(); Short digitsAfterForMoney = 1; AccountingRules.setDigitsAfterDecimal(digitsAfterForMoney); Locale locale = Localization.getInstance().getConfiguredLocale(); DoubleConversionResult result = converter.parseDoubleForMoney(doubleValueString); if (locale.getCountry().equalsIgnoreCase("GB") && locale.getLanguage().equalsIgnoreCase("EN")) { Assert.assertEquals(result.getDoubleValue(), dValue); // if the wrong decimal separator is entered, error will be returned doubleValueString = "2,59"; result = converter.parseDoubleForMoney(doubleValueString); Assert.assertEquals(result.getErrors().get(0), ConversionError.NOT_ALL_NUMBER); doubleValueString = "2a59"; result = converter.parseDoubleForMoney(doubleValueString); Assert.assertEquals(result.getErrors().get(0), ConversionError.NOT_ALL_NUMBER); doubleValueString = "123456789111111.59"; result = converter.parseDoubleForMoney(doubleValueString); Assert.assertEquals(result.getErrors().get(0), ConversionError.EXCEEDING_NUMBER_OF_DIGITS_AFTER_DECIMAL_SEPARATOR_FOR_MONEY); Assert.assertEquals(result.getErrors().get(1), ConversionError.EXCEEDING_NUMBER_OF_DIGITS_BEFORE_DECIMAL_SEPARATOR_FOR_MONEY); doubleValueString = "222222222111111.5"; result = converter.parseDoubleForMoney(doubleValueString); Assert.assertEquals(result.getErrors().get(0), ConversionError.EXCEEDING_NUMBER_OF_DIGITS_BEFORE_DECIMAL_SEPARATOR_FOR_MONEY); } AccountingRules.setDigitsAfterDecimal(digitsAfterForMoneySaved); converter.setCurrentLocale(locale); } @Test public void testParseDoubleForInstallmentTotalAmount() { MifosCurrency mifosCurrency = new MifosCurrency(Short.valueOf("1"), "Rupee", BigDecimal.valueOf(1), "INR"); LocalizationConverter localizationConverter = new LocalizationConverter(mifosCurrency); DoubleConversionResult result = localizationConverter.parseDoubleForInstallmentTotalAmount("-478.2"); assertThat(result.getDoubleValue(), is(-478.2)); result = localizationConverter.parseDoubleForInstallmentTotalAmount("478.2"); assertThat(result.getDoubleValue(), is(478.2)); result = localizationConverter.parseDoubleForInstallmentTotalAmount("2,59"); assertThat(result.getErrors().get(0), is(ConversionError.NOT_ALL_NUMBER)); result = localizationConverter.parseDoubleForInstallmentTotalAmount("222222222111111.5"); assertThat(result.getErrors().get(0), is(ConversionError.EXCEEDING_NUMBER_OF_DIGITS_BEFORE_DECIMAL_SEPARATOR_FOR_MONEY)); } @Test public void testParseDoubleForInterest() { String doubleValueString = "222.59562"; Double dValue = 222.59562; Short digitsAfterForInterestSaved = AccountingRules.getDigitsAfterDecimalForInterest(); Short digitsAfterForInterest = 5; AccountingRules.setDigitsAfterDecimalForInterest(digitsAfterForInterest); Locale locale = Localization.getInstance().getConfiguredLocale(); short digitsAfterDecimalForMoney = Short.valueOf("1"); short digitsBeforeDecimalForMoney= Short.valueOf("1"); short digitsAfterDecimalForInterest = Short.valueOf("5"); short digitsBeforeDecimalForInterest = Short.valueOf("6"); short digitsBeforeDecimalForCashFlowValidations = Short.valueOf("1"); short digitsAfterDecimalForCashFlowValidations = Short.valueOf("5"); converter = new LocalizationConverter(digitsAfterDecimalForMoney, digitsBeforeDecimalForMoney, digitsAfterDecimalForInterest, digitsBeforeDecimalForInterest, digitsBeforeDecimalForCashFlowValidations, digitsAfterDecimalForCashFlowValidations); DoubleConversionResult result = converter.parseDoubleForInterest(doubleValueString); if (locale.getCountry().equalsIgnoreCase("GB") && locale.getLanguage().equalsIgnoreCase("EN")) { Assert.assertEquals(result.getDoubleValue(), dValue); // if the wrong decimal separator is entered, error will be returned doubleValueString = "222,59562"; result = converter.parseDoubleForInterest(doubleValueString); Assert.assertEquals(result.getErrors().get(0), ConversionError.NOT_ALL_NUMBER); doubleValueString = "2a5922"; result = converter.parseDoubleForInterest(doubleValueString); Assert.assertEquals(result.getErrors().get(0), ConversionError.NOT_ALL_NUMBER); doubleValueString = "222.595690"; result = converter.parseDoubleForInterest(doubleValueString); Assert.assertEquals(result.getErrors().get(0), ConversionError.EXCEEDING_NUMBER_OF_DIGITS_AFTER_DECIMAL_SEPARATOR_FOR_INTEREST); doubleValueString = "22222222222.5"; result = converter.parseDoubleForInterest(doubleValueString); Assert.assertEquals(result.getErrors().get(0), ConversionError.EXCEEDING_NUMBER_OF_DIGITS_BEFORE_DECIMAL_SEPARATOR_FOR_INTEREST); } AccountingRules.setDigitsAfterDecimalForInterest(digitsAfterForInterestSaved); converter.setCurrentLocale(locale); } @Test public void testParseDoubleForCashFlowValidations() { MifosCurrency mifosCurrency = new MifosCurrency(Short.valueOf("1"), "Rupee", BigDecimal.valueOf(1), "INR"); LocalizationConverter localizationConverter = new LocalizationConverter(mifosCurrency); DoubleConversionResult result = parseForCashFlow(localizationConverter, "22.59"); assertThat(result.getDoubleValue(), is(22.59)); result = parseForCashFlow(localizationConverter, "222,59562"); assertThat(result.getErrors().get(0), is(ConversionError.NOT_ALL_NUMBER)); result = parseForCashFlow(localizationConverter, "2a5922"); assertThat(result.getErrors().get(0), is(ConversionError.NOT_ALL_NUMBER)); result = parseForCashFlow(localizationConverter, "22222222222.5"); assertThat(result.getErrors().get(0), is(ConversionError.EXCEEDING_NUMBER_OF_DIGITS_BEFORE_DECIMAL_SEPARATOR_FOR_CASHFLOW_VALIDATION)); result = parseForCashFlow(localizationConverter, "222.595690"); assertThat(result.getErrors().get(0), is(ConversionError.EXCEEDING_NUMBER_OF_DIGITS_AFTER_DECIMAL_SEPARATOR_FOR_CASHFLOW_VALIDATION)); result = parseForCashFlow(localizationConverter, "222.59"); assertThat(result.getErrors().get(0), is(ConversionError.CASH_FLOW_THRESHOLD_OUT_OF_RANGE)); } private DoubleConversionResult parseForCashFlow(LocalizationConverter localizationConverter, String doubleValueStr) { return localizationConverter.parseDoubleForCashFlowValidations(doubleValueStr, ConversionError.CASH_FLOW_THRESHOLD_OUT_OF_RANGE, AccountingRules.getMinCashFlowThreshold(), AccountingRules.getMaxCashFlowThreshold()); } /* * get convert a string to a double to the config locale and the format is * the money format 7.1 */ @Test public void testGetDoubleValueForCurrentLocale() { String doubleValueString = "223.59"; Double dValue = 223.59; Locale locale = Localization.getInstance().getConfiguredLocale(); Double dNumber = converter.getDoubleValueForCurrentLocale(doubleValueString); if (locale.getCountry().equalsIgnoreCase("GB") && locale.getLanguage().equalsIgnoreCase("EN")) { Assert.assertEquals(dNumber, dValue); // if the wrong decimal separator is entered, it will throw // exception doubleValueString = "223,59"; try { dNumber = converter.getDoubleValueForCurrentLocale(doubleValueString); } catch (Exception ex) { Assert.assertTrue(ex.getMessage().startsWith("The format of the number is invalid.")); } } converter.setCurrentLocale(new Locale("IS", "is")); doubleValueString = "223,59"; dNumber = converter.getDoubleValueForCurrentLocale(doubleValueString); Assert.assertEquals(dNumber, dValue); // if the wrong decimal separator is entered, it will throw exception doubleValueString = "223.59"; try { dNumber = converter.getDoubleValueForCurrentLocale(doubleValueString); } catch (Exception ex) { Assert.assertTrue(ex.getMessage().startsWith("The format of the number is invalid.")); } converter.setCurrentLocale(locale); } }