diff --git a/core/src/main/java/com/opensymphony/xwork2/conversion/impl/DefaultTypeConverter.java b/core/src/main/java/com/opensymphony/xwork2/conversion/impl/DefaultTypeConverter.java index e8fdb2c00..731b8f503 100644 --- a/core/src/main/java/com/opensymphony/xwork2/conversion/impl/DefaultTypeConverter.java +++ b/core/src/main/java/com/opensymphony/xwork2/conversion/impl/DefaultTypeConverter.java @@ -44,16 +44,16 @@ import java.util.Map; */ public abstract class DefaultTypeConverter implements TypeConverter { - protected static String MILLISECOND_FORMAT = ".SSS"; + protected static final String MILLISECOND_FORMAT = ".SSS"; private static final String NULL_STRING = "null"; - private static final Map primitiveDefaults; + private static final Map, Object> baseTypeDefaults; private Container container; static { - Map map = new HashMap<>(); + Map, Object> map = new HashMap<>(); map.put(Boolean.TYPE, Boolean.FALSE); map.put(Byte.TYPE, Byte.valueOf((byte) 0)); map.put(Short.TYPE, Short.valueOf((short) 0)); @@ -62,9 +62,9 @@ public abstract class DefaultTypeConverter implements TypeConverter { map.put(Long.TYPE, Long.valueOf(0L)); map.put(Float.TYPE, new Float(0.0f)); map.put(Double.TYPE, new Double(0.0)); - map.put(BigInteger.class, new BigInteger("0")); - map.put(BigDecimal.class, new BigDecimal(0.0)); - primitiveDefaults = Collections.unmodifiableMap(map); + map.put(BigInteger.class, BigInteger.ZERO); + map.put(BigDecimal.class, BigDecimal.ZERO); + baseTypeDefaults = Collections.unmodifiableMap(map); } @Inject @@ -76,6 +76,7 @@ public abstract class DefaultTypeConverter implements TypeConverter { return convertValue(value, toType); } + @Override public Object convertValue(Map context, Object target, Member member, String propertyName, Object value, Class toType) { return convertValue(context, value, toType); @@ -118,7 +119,7 @@ public abstract class DefaultTypeConverter implements TypeConverter { if (value != null) { /* If array -> array then convert components of array individually */ if (value.getClass().isArray() && toType.isArray()) { - Class componentType = toType.getComponentType(); + final Class componentType = toType.getComponentType(); result = Array.newInstance(componentType, Array .getLength(value)); @@ -153,9 +154,7 @@ public abstract class DefaultTypeConverter implements TypeConverter { result = enumValue(toType, value); } } else { - if (toType.isPrimitive()) { - result = primitiveDefaults.get(toType); - } + result = baseTypeDefaults.get(toType); } return result; } @@ -172,7 +171,7 @@ public abstract class DefaultTypeConverter implements TypeConverter { public static boolean booleanValue(Object value) { if (value == null) return false; - Class c = value.getClass(); + final Class c = value.getClass(); if (c == Boolean.class) return (Boolean) value; // if ( c == String.class ) @@ -202,13 +201,11 @@ public abstract class DefaultTypeConverter implements TypeConverter { * @param value * an object to interpret as a long integer * @return the long integer value implied by the given object - * @throws NumberFormatException - * if the given object can't be understood as a long integer */ - public static long longValue(Object value) throws NumberFormatException { + public static long longValue(Object value) { if (value == null) return 0L; - Class c = value.getClass(); + final Class c = value.getClass(); if (c.getSuperclass() == Number.class) return ((Number) value).longValue(); if (c == Boolean.class) @@ -224,26 +221,19 @@ public abstract class DefaultTypeConverter implements TypeConverter { * @param value * an object to interpret as a double * @return the double value implied by the given object - * @throws NumberFormatException - * if the given object can't be understood as a double */ - public static double doubleValue(Object value) throws NumberFormatException { + public static double doubleValue(Object value) { if (value == null) return 0.0; - Class c = value.getClass(); + final Class c = value.getClass(); if (c.getSuperclass() == Number.class) return ((Number) value).doubleValue(); if (c == Boolean.class) return (Boolean) value ? 1 : 0; if (c == Character.class) return (Character) value; - String s = stringValue(value, true); - + final String s = stringValue(value, true); return (s.length() == 0) ? 0.0 : Double.parseDouble(s); - /* - * For 1.1 parseDouble() is not available - */ - // return Double.valueOf( value.toString() ).doubleValue(); } /** @@ -252,14 +242,11 @@ public abstract class DefaultTypeConverter implements TypeConverter { * @param value * an object to interpret as a BigInteger * @return the BigInteger value implied by the given object - * @throws NumberFormatException - * if the given object can't be understood as a BigInteger */ - public static BigInteger bigIntValue(Object value) - throws NumberFormatException { + public static BigInteger bigIntValue(Object value) { if (value == null) return BigInteger.valueOf(0L); - Class c = value.getClass(); + final Class c = value.getClass(); if (c == BigInteger.class) return (BigInteger) value; if (c == BigDecimal.class) @@ -279,20 +266,17 @@ public abstract class DefaultTypeConverter implements TypeConverter { * @param value * an object to interpret as a BigDecimal * @return the BigDecimal value implied by the given object - * @throws NumberFormatException - * if the given object can't be understood as a BigDecimal */ - public static BigDecimal bigDecValue(Object value) - throws NumberFormatException { + public static BigDecimal bigDecValue(Object value) { if (value == null) return BigDecimal.valueOf(0L); - Class c = value.getClass(); + final Class c = value.getClass(); if (c == BigDecimal.class) return (BigDecimal) value; if (c == BigInteger.class) return new BigDecimal((BigInteger) value); if (c.getSuperclass() == Number.class) - return new BigDecimal(((Number) value).doubleValue()); + return BigDecimal.valueOf(((Number) value).doubleValue()); if (c == Boolean.class) return BigDecimal.valueOf((Boolean) value ? 1 : 0); if (c == Character.class) diff --git a/core/src/test/java/com/opensymphony/xwork2/conversion/impl/XWorkBasicConverterTest.java b/core/src/test/java/com/opensymphony/xwork2/conversion/impl/XWorkBasicConverterTest.java index a0c66c69c..f8c3e7e41 100644 --- a/core/src/test/java/com/opensymphony/xwork2/conversion/impl/XWorkBasicConverterTest.java +++ b/core/src/test/java/com/opensymphony/xwork2/conversion/impl/XWorkBasicConverterTest.java @@ -23,6 +23,8 @@ import com.opensymphony.xwork2.XWorkException; import com.opensymphony.xwork2.XWorkTestCase; import com.opensymphony.xwork2.test.annotations.Person; +import java.math.BigDecimal; +import java.math.BigInteger; import java.text.DateFormat; import java.util.*; @@ -228,6 +230,57 @@ public class XWorkBasicConverterTest extends XWorkTestCase { assertEquals(94.1231233d, (Double) convertedObject, 0.0001); } + public void testBigInteger() { + Object convertedObject = basicConverter.convertValue(null, BigInteger.class); + assertEquals(BigInteger.ZERO, convertedObject); + assertEquals(0, BigInteger.ZERO.compareTo((BigInteger) convertedObject)); + + convertedObject = basicConverter.convertValue(BigInteger.ZERO, BigInteger.class); + assertEquals(BigInteger.ZERO, convertedObject); + assertEquals(0, BigInteger.ZERO.compareTo((BigInteger) convertedObject)); + + convertedObject = basicConverter.convertValue(new BigInteger("0"), BigInteger.class); + assertEquals(BigInteger.ZERO, convertedObject); + assertEquals(0, BigInteger.ZERO.compareTo((BigInteger) convertedObject)); + + convertedObject = basicConverter.convertValue(BigInteger.TEN, BigInteger.class); + assertEquals(BigInteger.TEN, convertedObject); + assertEquals(0, BigInteger.TEN.compareTo((BigInteger) convertedObject)); + } + + public void testBigDecimal() { + Object convertedObject = basicConverter.convertValue(null, BigDecimal.class); + assertEquals(BigDecimal.ZERO, convertedObject); + assertTrue(convertedObject instanceof BigDecimal); + assertEquals(0, BigDecimal.ZERO.compareTo((BigDecimal) convertedObject)); + + convertedObject = basicConverter.convertValue(new BigDecimal(0), BigDecimal.class); + assertEquals(BigDecimal.ZERO, convertedObject); + assertTrue(convertedObject instanceof BigDecimal); + assertEquals(0, BigDecimal.ZERO.compareTo((BigDecimal) convertedObject)); + + convertedObject = basicConverter.convertValue(BigDecimal.valueOf(0), BigDecimal.class); + assertEquals(BigDecimal.ZERO, convertedObject); + assertTrue(convertedObject instanceof BigDecimal); + assertEquals(0, BigDecimal.ZERO.compareTo((BigDecimal) convertedObject)); + + convertedObject = basicConverter.convertValue(BigDecimal.valueOf(0.0), BigDecimal.class); + assertEquals(BigDecimal.valueOf(0.0), convertedObject); + assertTrue(convertedObject instanceof BigDecimal); + assertEquals(0, BigDecimal.ZERO.compareTo((BigDecimal) convertedObject)); + + convertedObject = basicConverter.convertValue(BigDecimal.valueOf(0.000), BigDecimal.class); + assertEquals(BigDecimal.valueOf(0.000), convertedObject); + assertTrue(convertedObject instanceof BigDecimal); + assertEquals(0, BigDecimal.ZERO.compareTo((BigDecimal) convertedObject)); + + convertedObject = basicConverter.convertValue(BigDecimal.valueOf(10), BigDecimal.class); + assertEquals(BigDecimal.TEN, convertedObject); + + convertedObject = basicConverter.convertValue(BigDecimal.valueOf(12345.67890), BigDecimal.class); + assertEquals(BigDecimal.valueOf(12345.67890), convertedObject); + } + public void testNestedEnumValue() throws Exception { Object convertedObject = basicConverter.convertValue(ParentClass.NestedEnum.TEST.name(), ParentClass.NestedEnum.class); assertTrue(convertedObject instanceof ParentClass.NestedEnum);