You are viewing a plain text version of this content. The canonical link for it is here.
Posted to dev@commons.apache.org by ni...@apache.org on 2007/05/24 02:18:02 UTC

svn commit: r541122 - in /jakarta/commons/proper/beanutils/trunk/src: java/org/apache/commons/beanutils/converters/ test/org/apache/commons/beanutils/converters/

Author: niallp
Date: Wed May 23 17:18:01 2007
New Revision: 541122

URL: http://svn.apache.org/viewvc?view=rev&rev=541122
Log:
Improve exception error messages and add Calendar --> Long conversion

Modified:
    jakarta/commons/proper/beanutils/trunk/src/java/org/apache/commons/beanutils/converters/AbstractConverter.java
    jakarta/commons/proper/beanutils/trunk/src/java/org/apache/commons/beanutils/converters/DateTimeConverter.java
    jakarta/commons/proper/beanutils/trunk/src/java/org/apache/commons/beanutils/converters/NumberConverter.java
    jakarta/commons/proper/beanutils/trunk/src/test/org/apache/commons/beanutils/converters/NumberConverterTestBase.java

Modified: jakarta/commons/proper/beanutils/trunk/src/java/org/apache/commons/beanutils/converters/AbstractConverter.java
URL: http://svn.apache.org/viewvc/jakarta/commons/proper/beanutils/trunk/src/java/org/apache/commons/beanutils/converters/AbstractConverter.java?view=diff&rev=541122&r1=541121&r2=541122
==============================================================================
--- jakarta/commons/proper/beanutils/trunk/src/java/org/apache/commons/beanutils/converters/AbstractConverter.java (original)
+++ jakarta/commons/proper/beanutils/trunk/src/java/org/apache/commons/beanutils/converters/AbstractConverter.java Wed May 23 17:18:01 2007
@@ -404,7 +404,9 @@
         } else {
             typeName = type.getName();
         }
-        if (typeName.startsWith("java.lang.")) {
+        if (typeName.startsWith("java.lang.") ||
+            typeName.startsWith("java.util.") ||
+            typeName.startsWith("java.math.")) {
             typeName = typeName.substring("java.lang.".length());
         } else if (typeName.startsWith(PACKAGE)) {
             typeName = typeName.substring(PACKAGE.length());

Modified: jakarta/commons/proper/beanutils/trunk/src/java/org/apache/commons/beanutils/converters/DateTimeConverter.java
URL: http://svn.apache.org/viewvc/jakarta/commons/proper/beanutils/trunk/src/java/org/apache/commons/beanutils/converters/DateTimeConverter.java?view=diff&rev=541122&r1=541121&r2=541122
==============================================================================
--- jakarta/commons/proper/beanutils/trunk/src/java/org/apache/commons/beanutils/converters/DateTimeConverter.java (original)
+++ jakarta/commons/proper/beanutils/trunk/src/java/org/apache/commons/beanutils/converters/DateTimeConverter.java Wed May 23 17:18:01 2007
@@ -281,12 +281,14 @@
      * Otherwise the default <code>DateFormat</code> for the default locale
      * (and <i>style</i> if configured) will be used.
      *
-     * @param type Data type to which this value should be converted.
+     * @param targetType Data type to which this value should be converted.
      * @param value The input value to be converted.
      * @return The converted value.
      * @throws Exception if conversion cannot be performed successfully
      */
-    protected Object convertToType(Class type, Object value) throws Exception {
+    protected Object convertToType(Class targetType, Object value) throws Exception {
+
+        Class sourceType = value.getClass();
 
         // Handle java.sql.Timestamp
         if (value instanceof java.sql.Timestamp) {
@@ -299,51 +301,51 @@
             long timeInMillis = ((timestamp.getTime() / 1000) * 1000);
             timeInMillis += timestamp.getNanos() / 1000000;
             // ---------------------- JDK 1.3 Fix ----------------------
-            return toDate(type, timeInMillis);
+            return toDate(targetType, timeInMillis);
         }
 
         // Handle Date (includes java.sql.Date & java.sql.Time)
         if (value instanceof Date) {
             Date date = (Date)value;
-            return toDate(type, date.getTime());
+            return toDate(targetType, date.getTime());
         }
 
         // Handle Calendar
         if (value instanceof Calendar) {
             Calendar calendar = (Calendar)value;
-            return toDate(type, calendar.getTime().getTime());
+            return toDate(targetType, calendar.getTime().getTime());
         }
 
         // Handle Long
         if (value instanceof Long) {
             Long longObj = (Long)value;
-            return toDate(type, longObj.longValue());
+            return toDate(targetType, longObj.longValue());
         }
 
         // Convert all other types to String & handle
         String stringValue = value.toString().trim();
         if (stringValue.length() == 0) {
-            return handleMissing(type);
+            return handleMissing(targetType);
         }
 
         // Parse the Date/Time
         if (useLocaleFormat) {
             Calendar calendar = null;
             if (patterns != null && patterns.length > 0) {
-                calendar = parse(type, stringValue);
+                calendar = parse(sourceType, targetType, stringValue);
             } else {
                 DateFormat format = getFormat(locale, timeZone);
-                calendar = parse(type, stringValue, format);
+                calendar = parse(sourceType, targetType, stringValue, format);
             }
-            if (Calendar.class.isAssignableFrom(type)) {
+            if (Calendar.class.isAssignableFrom(targetType)) {
                 return calendar;
             } else {
-                return toDate(type, calendar.getTime().getTime());
+                return toDate(targetType, calendar.getTime().getTime());
             }
         }
 
         // Default String conversion
-        return toDate(type, stringValue);
+        return toDate(targetType, stringValue);
 
     }
 
@@ -508,18 +510,19 @@
     /**
      * Parse a String date value using the set of patterns.
      *
-     * @param type The type to convert the value to
+     * @param sourceType The type of the value being converted
+     * @param targetType The type to convert the value to.
      * @param value The String date value.
-     * @param type The type to convert the value to.
+     *
      * @return The converted Date object.
      * @throws Exception if an error occurs parsing the date.
      */
-    private Calendar parse(Class type, String value) throws Exception {
+    private Calendar parse(Class sourceType, Class targetType, String value) throws Exception {
         Exception firstEx = null;
         for (int i = 0; i < patterns.length; i++) {
             try {
                 DateFormat format = getFormat(patterns[i]);
-                Calendar calendar = parse(type, value, format);
+                Calendar calendar = parse(sourceType, targetType, value, format);
                 return calendar;
             } catch (Exception ex) {
                 if (firstEx == null) {
@@ -528,7 +531,7 @@
             }
         }
         if (patterns.length > 1) {
-            throw new ConversionException("Error converting String to '" + toString(type)
+            throw new ConversionException("Error converting '" + toString(sourceType) + "' to '" + toString(targetType)
                     + "' using  patterns '" + displayPatterns + "'");
         } else {
             throw firstEx;
@@ -539,19 +542,21 @@
      * Parse a String into a <code>Calendar</code> object
      * using the specified <code>DateFormat</code>.
      *
-     * @param type The type to convert the value to
+     * @param sourceType The type of the value being converted
+     * @param targetType The type to convert the value to
      * @param value The String date value.
      * @param format The DateFormat to parse the String value.
+     *
      * @return The converted Calendar object.
      * @throws ConversionException if the String cannot be converted.
      */
-    private Calendar parse(Class type, String value, DateFormat format) {
+    private Calendar parse(Class sourceType, Class targetType, String value, DateFormat format) {
         logFormat("Parsing", format);
         format.setLenient(false);
         ParsePosition pos = new ParsePosition(0);
         Date parsedDate = format.parse(value, pos); // ignore the result (use the Calendar)
         if (pos.getErrorIndex() >= 0 || pos.getIndex() != value.length() || parsedDate == null) {
-            String msg = "Error converting String to '" + toString(type) + "'";
+            String msg = "Error converting '" + toString(sourceType) + "' to '" + toString(targetType) + "'";
             if (format instanceof SimpleDateFormat) {
                 msg += " using pattern '" + ((SimpleDateFormat)format).toPattern() + "'";
             }

Modified: jakarta/commons/proper/beanutils/trunk/src/java/org/apache/commons/beanutils/converters/NumberConverter.java
URL: http://svn.apache.org/viewvc/jakarta/commons/proper/beanutils/trunk/src/java/org/apache/commons/beanutils/converters/NumberConverter.java?view=diff&rev=541122&r1=541121&r2=541122
==============================================================================
--- jakarta/commons/proper/beanutils/trunk/src/java/org/apache/commons/beanutils/converters/NumberConverter.java (original)
+++ jakarta/commons/proper/beanutils/trunk/src/java/org/apache/commons/beanutils/converters/NumberConverter.java Wed May 23 17:18:01 2007
@@ -16,6 +16,7 @@
  */ 
 package org.apache.commons.beanutils.converters;
 
+import java.util.Calendar;
 import java.util.Date;
 import java.util.Locale;
 import java.math.BigDecimal;
@@ -226,48 +227,54 @@
      * Convert the input object into a Number object of the
      * specified type.
      *
-     * @param type Data type to which this value should be converted.
+     * @param targetType Data type to which this value should be converted.
      * @param value The input value to be converted.
      * @return The converted value.
      * @throws Throwable if an error occurs converting to the specified type
      */
-    protected Object convertToType(Class type, Object value) throws Throwable {
+    protected Object convertToType(Class targetType, Object value) throws Throwable {
 
+        Class sourceType = value.getClass();
         // Handle Number
         if (value instanceof Number) {
-            return toNumber(type, (Number)value);
+            return toNumber(sourceType, targetType, (Number)value);
         }
 
         // Handle Boolean
         if (value instanceof Boolean) {
-            return toNumber(type, ((Boolean)value).booleanValue() ? ONE : ZERO);
+            return toNumber(sourceType, targetType, ((Boolean)value).booleanValue() ? ONE : ZERO);
         }
 
         // Handle Date --> Long
-        if (value instanceof Date && Long.class.equals(type)) {
+        if (value instanceof Date && Long.class.equals(targetType)) {
             return new Long(((Date)value).getTime());
         }
 
+        // Handle Calendar --> Long
+        if (value instanceof Calendar  && Long.class.equals(targetType)) {
+            return new Long(((Calendar)value).getTime().getTime());
+        }
+
         // Convert all other types to String & handle
         String stringValue = value.toString().trim();
         if (stringValue.length() == 0) {
-            return handleMissing(type);
+            return handleMissing(targetType);
         }
 
         // Convert/Parse a String
         Number number = null;
         if (useLocaleFormat) {
             NumberFormat format = getFormat();
-            number = parse(type, stringValue, format);
+            number = parse(sourceType, targetType, stringValue, format);
         } else {
             if (log().isDebugEnabled()) {
                 log().debug("    No NumberFormat, using default conversion");
             }
-            number = toNumber(type, stringValue);
+            number = toNumber(sourceType, targetType, stringValue);
         }
 
         // Ensure the correct number type is returned
-        return toNumber(type, number);
+        return toNumber(sourceType, targetType, number);
 
     }
 
@@ -286,81 +293,82 @@
      *     <li><code>java.math.BigDecimal</code></li>
      *     <li><code>java.math.BigInteger</code></li>
      * </ul>
-     *
-     * @param type The Number type to convert to
+     * @param sourceType The type being converted from
+     * @param targetType The Number type to convert to
      * @param value The Number to convert.
+     *
      * @return The converted value.
      */
-    private Number toNumber(Class type, Number value) {
+    private Number toNumber(Class sourceType, Class targetType, Number value) {
 
         // Correct Number type already
-        if (type.equals(value.getClass())) {
+        if (targetType.equals(value.getClass())) {
             return value;
         }
 
         // Byte
-        if (type.equals(Byte.class)) {
+        if (targetType.equals(Byte.class)) {
             long longValue = value.longValue();
             if (longValue > Byte.MAX_VALUE) {
-                throw new ConversionException("Value '" + value + "' is too large for "
-                        + toString(type));
+                throw new ConversionException(toString(sourceType) + " value '" + value
+                        + "' is too large for " + toString(targetType));
             }
             if (longValue < Byte.MIN_VALUE) {
-                throw new ConversionException("Value '" + value + "' is too small "
-                        + toString(type));
+                throw new ConversionException(toString(sourceType) + " value '" + value
+                        + "' is too small " + toString(targetType));
             }
             return new Byte(value.byteValue());
         }
 
         // Short
-        if (type.equals(Short.class)) {
+        if (targetType.equals(Short.class)) {
             long longValue = value.longValue();
             if (longValue > Short.MAX_VALUE) {
-                throw new ConversionException("Value '" + value + "' is too large for "
-                        + toString(type));
+                throw new ConversionException(toString(sourceType) + " value '" + value
+                        + "' is too large for " + toString(targetType));
             }
             if (longValue < Short.MIN_VALUE) {
-                throw new ConversionException("Value '" + value + "' is too small "
-                        + toString(type));
+                throw new ConversionException(toString(sourceType) + " value '" + value
+                        + "' is too small " + toString(targetType));
             }
             return new Short(value.shortValue());
         }
 
         // Integer
-        if (type.equals(Integer.class)) {
+        if (targetType.equals(Integer.class)) {
             long longValue = value.longValue();
             if (longValue > Integer.MAX_VALUE) {
-                throw new ConversionException("Value '" + value + "' is too large for "
-                        + toString(type));
+                throw new ConversionException(toString(sourceType) + " value '" + value
+                        + "' is too large for " + toString(targetType));
             }
             if (longValue < Integer.MIN_VALUE) {
-                throw new ConversionException("Value '" + value + "' is too small "
-                        + toString(type));
+                throw new ConversionException(toString(sourceType) + " value '" + value
+                        + "' is too small " + toString(targetType));
             }
             return new Integer(value.intValue());
         }
 
         // Long
-        if (type.equals(Long.class)) {
+        if (targetType.equals(Long.class)) {
             return new Long(value.longValue());
         }
 
         // Float
-        if (type.equals(Float.class)) {
+        if (targetType.equals(Float.class)) {
             if (value.doubleValue() > Float.MAX_VALUE) {
-                throw new ConversionException("Value '" + value
-                        + "' is too large for " + toString(type));
+                throw new ConversionException(toString(sourceType) + " value '" + value
+                        + "' is too large for " + toString(targetType));
             }
             return new Float(value.floatValue());
         }
 
         // Double
-        if (type.equals(Double.class)) {
+        if (targetType.equals(Double.class)) {
             return new Double(value.doubleValue());
         }
 
         // BigDecimal
-        if (type.equals(BigDecimal.class)) {
+        if (targetType.equals(BigDecimal.class)) {
             if (value instanceof Float || value instanceof Double) {
                 return new BigDecimal(value.toString());
             } else if (value instanceof BigInteger) {
@@ -371,7 +379,7 @@
         }
 
         // BigInteger
-        if (type.equals(BigInteger.class)) {
+        if (targetType.equals(BigInteger.class)) {
             if (value instanceof BigDecimal) {
                 return ((BigDecimal)value).toBigInteger();
             } else {
@@ -380,7 +388,7 @@
         }
 
         String msg = toString(getClass()) + " cannot handle conversion to '"
-                   + toString(type) + "'";
+                   + toString(targetType) + "'";
         if (log().isWarnEnabled()) {
             log().warn("    " + msg);
         }
@@ -402,55 +410,56 @@
      *     <li><code>java.math.BigDecimal</code></li>
      *     <li><code>java.math.BigInteger</code></li>
      * </ul>
-     *
-     * @param type The Number type to convert to
+     * @param sourceType The type being converted from
+     * @param targetType The Number type to convert to
      * @param value The String value to convert.
+     *
      * @return The converted Number value.
      */
-    private Number toNumber(Class type, String value) {
+    private Number toNumber(Class sourceType, Class targetType, String value) {
 
         // Byte
-        if (type.equals(Byte.class)) {
+        if (targetType.equals(Byte.class)) {
             return new Byte(value);
         }
 
         // Short
-        if (type.equals(Short.class)) {
+        if (targetType.equals(Short.class)) {
             return new Short(value);
         }
 
         // Integer
-        if (type.equals(Integer.class)) {
+        if (targetType.equals(Integer.class)) {
             return new Integer(value);
         }
 
         // Long
-        if (type.equals(Long.class)) {
+        if (targetType.equals(Long.class)) {
             return new Long(value);
         }
 
         // Float
-        if (type.equals(Float.class)) {
+        if (targetType.equals(Float.class)) {
             return new Float(value);
         }
 
         // Double
-        if (type.equals(Double.class)) {
+        if (targetType.equals(Double.class)) {
             return new Double(value);
         }
 
         // BigDecimal
-        if (type.equals(BigDecimal.class)) {
+        if (targetType.equals(BigDecimal.class)) {
             return new BigDecimal(value);
         }
 
         // BigInteger
-        if (type.equals(BigInteger.class)) {
+        if (targetType.equals(BigInteger.class)) {
             return new BigInteger(value);
         }
 
-        String msg = toString(getClass())
-            + " cannot handle conversion from String to '" + toString(type) + "'";
+        String msg = toString(getClass()) + " cannot handle conversion from '" +
+                     toString(sourceType) + "' to '" + toString(targetType) + "'";
         if (log().isWarnEnabled()) {
             log().warn("    " + msg);
         }
@@ -499,18 +508,19 @@
 
     /**
      * Convert a String into a <code>Number</code> object.
-     *
-     * @param type The type to convert the value to
+     * @param sourceType TODO
+     * @param targetType The type to convert the value to
      * @param value The String date value.
      * @param format The NumberFormat to parse the String value.
+     *
      * @return The converted Number object.
      * @throws ConversionException if the String cannot be converted.
      */
-    private Number parse(Class type, String value, NumberFormat format) {
+    private Number parse(Class sourceType, Class targetType, String value, NumberFormat format) {
         ParsePosition pos = new ParsePosition(0);
         Number parsedNumber = (Number)format.parse(value, pos);
         if (pos.getErrorIndex() >= 0 || pos.getIndex() != value.length() || parsedNumber == null) {
-            String msg = "Error converting to '" + toString(type) + "'";
+            String msg = "Error converting from '" + toString(sourceType) + "' to '" + toString(targetType) + "'";
             if (format instanceof DecimalFormat) {
                 msg += " using pattern '" + ((DecimalFormat)format).toPattern() + "'";
             }

Modified: jakarta/commons/proper/beanutils/trunk/src/test/org/apache/commons/beanutils/converters/NumberConverterTestBase.java
URL: http://svn.apache.org/viewvc/jakarta/commons/proper/beanutils/trunk/src/test/org/apache/commons/beanutils/converters/NumberConverterTestBase.java?view=diff&rev=541122&r1=541121&r2=541122
==============================================================================
--- jakarta/commons/proper/beanutils/trunk/src/test/org/apache/commons/beanutils/converters/NumberConverterTestBase.java (original)
+++ jakarta/commons/proper/beanutils/trunk/src/test/org/apache/commons/beanutils/converters/NumberConverterTestBase.java Wed May 23 17:18:01 2007
@@ -19,6 +19,7 @@
 
 import java.math.BigDecimal;
 import java.math.BigInteger;
+import java.util.Calendar;
 import java.util.Date;
 import java.util.Locale;
 
@@ -192,6 +193,19 @@
             // expected result
         }
 
+        // Invalid Type (will try via String)
+        Object obj =  new Object() {
+            public String toString() {
+                return "dsdgsdsdg";
+            }
+        };
+        try {
+            converter.convert(getExpectedType(), obj);
+            fail("Expected invalid value to cause ConversionException");
+        } catch (Exception e) {
+            // expected result
+        }
+
         // Restore the default Locale
         Locale.setDefault(defaultLocale);
     }
@@ -271,16 +285,49 @@
     }
 
     /**
-     * Convert Date --> Long (default conversion)  
+     * Convert Date --> Long
      */
-    public void testDateToLongDefault() {
+    public void testDateToNumber() {
 
         NumberConverter converter = makeConverter();
 
-        // Other type --> String conversion
-        Date now = new Date();
-        assertEquals("Date to long", new Long(now.getTime()), converter.convert(Long.class, now));
-    
+        Date dateValue = new Date();
+        long longValue = dateValue.getTime();
+
+        // Date --> Long conversion
+        assertEquals("Date to Long", new Long(longValue), converter.convert(Long.class, dateValue));
+
+        // Date --> Integer
+        try {
+            converter.convert(Integer.class, dateValue);
+            fail("Date to Integer - expected a ConversionException");
+        } catch (ConversionException e) {
+            // expected result - too large for Integer
+        }
+
+    }
+
+    /**
+     * Convert Calendar --> Long
+     */
+    public void testCalendarToNumber() {
+
+        NumberConverter converter = makeConverter();
+
+        Calendar calendarValue = Calendar.getInstance();
+        long longValue = calendarValue.getTime().getTime();
+
+        // Calendar --> Long conversion
+        assertEquals("Calendar to Long", new Long(longValue), converter.convert(Long.class, calendarValue));
+
+        // Calendar --> Integer
+        try {
+            converter.convert(Integer.class, calendarValue);
+            fail("Calendar to Integer - expected a ConversionException");
+        } catch (ConversionException e) {
+            // expected result - too large for Integer
+        }
+
     }
 
     /**



---------------------------------------------------------------------
To unsubscribe, e-mail: commons-dev-unsubscribe@jakarta.apache.org
For additional commands, e-mail: commons-dev-help@jakarta.apache.org