You are viewing a plain text version of this content. The canonical link for it is here.
Posted to commits@struts.apache.org by lu...@apache.org on 2021/01/10 11:19:11 UTC

[struts] branch WW-4799-conversion-format created (now d876a2a)

This is an automated email from the ASF dual-hosted git repository.

lukaszlenart pushed a change to branch WW-4799-conversion-format
in repository https://gitbox.apache.org/repos/asf/struts.git.


      at d876a2a  WW-4799 Adding struts.date.format as a conversion format for DateConverter

This branch includes the following new commits:

     new d876a2a  WW-4799 Adding struts.date.format as a conversion format for DateConverter

The 1 revisions listed above as "new" are entirely new to this
repository and will be described in separate emails.  The revisions
listed as "add" were already present in the repository and have only
been added to this reference.



[struts] 01/01: WW-4799 Adding struts.date.format as a conversion format for DateConverter

Posted by lu...@apache.org.
This is an automated email from the ASF dual-hosted git repository.

lukaszlenart pushed a commit to branch WW-4799-conversion-format
in repository https://gitbox.apache.org/repos/asf/struts.git

commit d876a2ad930e41dca3a05f8ba252cb16e92aa3d7
Author: Cabasson, Denis - CoSD/DSCo <de...@statcan.gc.ca>
AuthorDate: Mon Jun 12 16:26:02 2017 -0400

    WW-4799 Adding struts.date.format as a conversion format for DateConverter
---
 .../xwork2/conversion/impl/DateConverter.java      | 67 ++++++++++++++++--
 .../com/opensymphony/xwork2/StubTextProvider.java  | 80 ++++++++++++++++++++++
 .../xwork2/conversion/impl/XWorkConverterTest.java | 27 ++++++++
 3 files changed, 169 insertions(+), 5 deletions(-)

diff --git a/core/src/main/java/com/opensymphony/xwork2/conversion/impl/DateConverter.java b/core/src/main/java/com/opensymphony/xwork2/conversion/impl/DateConverter.java
index 749b08b..8337529 100644
--- a/core/src/main/java/com/opensymphony/xwork2/conversion/impl/DateConverter.java
+++ b/core/src/main/java/com/opensymphony/xwork2/conversion/impl/DateConverter.java
@@ -19,6 +19,9 @@
 package com.opensymphony.xwork2.conversion.impl;
 
 import org.apache.struts2.conversion.TypeConversionException;
+import com.opensymphony.xwork2.ActionContext;
+import com.opensymphony.xwork2.TextProvider;
+import com.opensymphony.xwork2.util.ValueStack;
 
 import java.lang.reflect.Constructor;
 import java.lang.reflect.Member;
@@ -35,7 +38,7 @@ public class DateConverter extends DefaultTypeConverter {
     public Object convertValue(Map<String, Object> context, Object target, Member member, String propertyName, Object value, Class toType) {
         Date result = null;
 
-        if (value instanceof String && value != null && ((String) value).length() > 0) {
+        if (value instanceof String && ((String) value).length() > 0) {
             String sa = (String) value;
             Locale locale = getLocale(context);
 
@@ -66,7 +69,8 @@ public class DateConverter extends DefaultTypeConverter {
                 }
             } else if (java.util.Date.class == toType) {
                 Date check;
-                DateFormat[] dfs = getDateFormats(locale);
+                DateFormat[] dfs = getDateFormats(ActionContext.of(context), locale);
+
                 for (DateFormat df1 : dfs) {
                     try {
                         check = df1.parse(sa);
@@ -87,7 +91,7 @@ public class DateConverter extends DefaultTypeConverter {
                 result = df.parse(sa);
                 if (!(Date.class == toType)) {
                     try {
-                        Constructor constructor = toType.getConstructor(new Class[]{long.class});
+                        Constructor<?> constructor = toType.getConstructor(new Class[]{long.class});
                         return constructor.newInstance(new Object[]{Long.valueOf(result.getTime())});
                     } catch (Exception e) {
                         throw new TypeConversionException("Couldn't create class " + toType + " using default (long) constructor", e);
@@ -102,7 +106,43 @@ public class DateConverter extends DefaultTypeConverter {
         return result;
     }
 
-    private DateFormat[] getDateFormats(Locale locale) {
+    /**
+     * The user defined global date format,
+     * see {@link org.apache.struts2.components.Date#DATETAG_PROPERTY}
+     *
+     * @param context current ActionContext
+     * @param locale current Locale to convert to
+     * @return defined global format
+     */
+    protected DateFormat getGlobalDateFormat(ActionContext context, Locale locale) {
+        // Add the user provided date format if any
+        SimpleDateFormat globalDateFormat = null;
+
+        final TextProvider tp = findProviderInStack(context.getValueStack());
+
+        if (tp != null) {
+            String globalFormat = tp.getText(org.apache.struts2.components.Date.DATETAG_PROPERTY);
+
+            // if tp.getText can not find the property then the
+            // returned string is the same as input =
+            // DATETAG_PROPERTY
+            if (globalFormat != null
+                && !org.apache.struts2.components.Date.DATETAG_PROPERTY.equals(globalFormat)) {
+                globalDateFormat = new SimpleDateFormat(globalFormat, locale);
+            }
+        }
+        return globalDateFormat;
+    }
+
+    /**
+     * Retrieves the list of date formats to be used when converting dates
+     * @param context the current ActionContext
+     * @param locale the current locale of the action
+     * @return a list of DateFormat to be used for date conversion
+     */
+    private DateFormat[] getDateFormats(ActionContext context, Locale locale) {
+        DateFormat globalDateFormat = getGlobalDateFormat(context, locale);
+
         DateFormat dt1 = DateFormat.getDateTimeInstance(DateFormat.SHORT, DateFormat.LONG, locale);
         DateFormat dt2 = DateFormat.getDateTimeInstance(DateFormat.SHORT, DateFormat.MEDIUM, locale);
         DateFormat dt3 = DateFormat.getDateTimeInstance(DateFormat.SHORT, DateFormat.SHORT, locale);
@@ -114,7 +154,24 @@ public class DateConverter extends DefaultTypeConverter {
         DateFormat rfc3339         = new SimpleDateFormat("yyyy-MM-dd'T'HH:mm:ss");
         DateFormat rfc3339dateOnly = new SimpleDateFormat("yyyy-MM-dd");
 
-        return new DateFormat[]{dt1, dt2, dt3, rfc3339, d1, d2, d3, rfc3339dateOnly};
+        final DateFormat[] dateFormats;
+
+        if (globalDateFormat == null) {
+            dateFormats = new DateFormat[]{dt1, dt2, dt3, rfc3339, d1, d2, d3, rfc3339dateOnly};
+        } else {
+            dateFormats = new DateFormat[]{globalDateFormat, dt1, dt2, dt3, rfc3339, d1, d2, d3, rfc3339dateOnly};
+        }
+
+        return dateFormats;
+    }
+
+    private TextProvider findProviderInStack(ValueStack stack) {
+        for (Object o : stack.getRoot()) {
+            if (o instanceof TextProvider) {
+                return (TextProvider) o;
+            }
+        }
+        return null;
     }
 
 }
diff --git a/core/src/test/java/com/opensymphony/xwork2/StubTextProvider.java b/core/src/test/java/com/opensymphony/xwork2/StubTextProvider.java
new file mode 100644
index 0000000..4908cb5
--- /dev/null
+++ b/core/src/test/java/com/opensymphony/xwork2/StubTextProvider.java
@@ -0,0 +1,80 @@
+package com.opensymphony.xwork2;
+
+import com.opensymphony.xwork2.util.ValueStack;
+
+import java.util.List;
+import java.util.Map;
+import java.util.ResourceBundle;
+
+/**
+ * Created by cabaden on 12/06/2017.
+ */
+public class StubTextProvider implements TextProvider {
+
+    private final Map<String, String> map;
+
+    public StubTextProvider(final Map<String, String> map) {
+        this.map = map;
+    }
+
+    @Override
+    public boolean hasKey(final String key) {
+        return map.containsKey(key);
+    }
+
+    @Override
+    public String getText(final String key) {
+        return map.get(key);
+    }
+
+    @Override
+    public String getText(final String key, final String defaultValue) {
+        final String text = this.getText(key);
+        return text == null? defaultValue : text;
+    }
+
+    @Override
+    public String getText(final String key, final String defaultValue, final String obj) {
+        return this.getText(key, defaultValue);
+    }
+
+    @Override
+    public String getText(final String key, final List<?> args) {
+        return this.getText(key);
+    }
+
+    @Override
+    public String getText(final String key, final String[] args) {
+        return this.getText(key);
+    }
+
+    @Override
+    public String getText(final String key, final String defaultValue, final List<?> args) {
+        return this.getText(key);
+    }
+
+    @Override
+    public String getText(final String key, final String defaultValue, final String[] args) {
+        return this.getText(key);
+    }
+
+    @Override
+    public String getText(final String key, final String defaultValue, final List<?> args, final ValueStack stack) {
+        return this.getText(key, defaultValue);
+    }
+
+    @Override
+    public String getText(final String key, final String defaultValue, final String[] args, final ValueStack stack) {
+        return this.getText(key, defaultValue);
+    }
+
+    @Override
+    public ResourceBundle getTexts(final String bundleName) {
+        throw new UnsupportedOperationException();
+    }
+
+    @Override
+    public ResourceBundle getTexts() {
+        throw new UnsupportedOperationException();
+    }
+}
diff --git a/core/src/test/java/com/opensymphony/xwork2/conversion/impl/XWorkConverterTest.java b/core/src/test/java/com/opensymphony/xwork2/conversion/impl/XWorkConverterTest.java
index 3465737..9ca0e0e 100644
--- a/core/src/test/java/com/opensymphony/xwork2/conversion/impl/XWorkConverterTest.java
+++ b/core/src/test/java/com/opensymphony/xwork2/conversion/impl/XWorkConverterTest.java
@@ -28,6 +28,8 @@ import com.opensymphony.xwork2.util.Foo;
 import com.opensymphony.xwork2.util.FurColor;
 import com.opensymphony.xwork2.util.reflection.ReflectionContextState;
 import ognl.OgnlRuntime;
+import ognl.TypeConverter;
+import org.apache.struts2.components.*;
 
 import java.io.IOException;
 import java.math.BigDecimal;
@@ -41,6 +43,8 @@ import java.util.*;
 
 import static org.junit.Assert.assertArrayEquals;
 
+import java.util.Date;
+import java.util.Set;
 
 /**
  * @author $Author$
@@ -122,6 +126,29 @@ public class XWorkConverterTest extends XWorkTestCase {
         assertEquals(date, dateRfc3339DateOnly);
     }
 
+    public void testDateConversionWithDefault() throws ParseException {
+        Map<String, String> lookupMap = new HashMap<>();
+        TextProvider tp = new StubTextProvider(lookupMap);
+        StubValueStack valueStack = new StubValueStack();
+        valueStack.push(tp);
+        context.put(ActionContext.VALUE_STACK, valueStack);
+
+        String dateToFormat = "2017---06--15";
+        Object unparseableDate = converter.convertValue(context, null, null, null, dateToFormat, Date.class);
+        assertEquals(unparseableDate, com.opensymphony.xwork2.conversion.TypeConverter.NO_CONVERSION_POSSIBLE);
+
+        lookupMap.put(org.apache.struts2.components.Date.DATETAG_PROPERTY, "yyyy---MM--dd");
+
+        SimpleDateFormat format = new SimpleDateFormat("yyyy---MM--dd");
+        Date expectedDate = format.parse(dateToFormat);
+        Object parseableDate = converter.convertValue(context, null, null, null, dateToFormat, Date.class);
+        assertEquals(expectedDate, parseableDate);
+
+        Object standardDate = converter.convertValue(context, null, null, null, "2017-06-15", Date.class);
+        assertEquals(expectedDate, standardDate);
+
+    }
+
     public void testFieldErrorMessageAddedForComplexProperty() {
         SimpleAction action = new SimpleAction();
         action.setBean(new TestBean());