Repository: struts Updated Branches: refs/heads/master a5f3bdd14 -> 07bb62ba8
WW-4686 Merges two implementations of I18N interceptor Project: http://git-wip-us.apache.org/repos/asf/struts/repo Commit: http://git-wip-us.apache.org/repos/asf/struts/commit/07bb62ba Tree: http://git-wip-us.apache.org/repos/asf/struts/tree/07bb62ba Diff: http://git-wip-us.apache.org/repos/asf/struts/diff/07bb62ba Branch: refs/heads/master Commit: 07bb62ba8f661aaf1f5d5f874408dcdf6c00a0a2 Parents: a5f3bdd Author: Lukasz Lenart <lukaszlen...@apache.org> Authored: Mon Sep 12 08:15:53 2016 +0200 Committer: Lukasz Lenart <lukaszlen...@apache.org> Committed: Mon Sep 12 08:15:53 2016 +0200 ---------------------------------------------------------------------- .../xwork2/interceptor/I18nInterceptor.java | 288 ------------------- .../struts2/interceptor/I18nInterceptor.java | 241 +++++++++++++--- .../xwork2/interceptor/I18nInterceptorTest.java | 218 -------------- .../interceptor/I18nInterceptorTest.java | 249 ++++++++-------- 4 files changed, 337 insertions(+), 659 deletions(-) ---------------------------------------------------------------------- http://git-wip-us.apache.org/repos/asf/struts/blob/07bb62ba/core/src/main/java/com/opensymphony/xwork2/interceptor/I18nInterceptor.java ---------------------------------------------------------------------- diff --git a/core/src/main/java/com/opensymphony/xwork2/interceptor/I18nInterceptor.java b/core/src/main/java/com/opensymphony/xwork2/interceptor/I18nInterceptor.java deleted file mode 100644 index acc0d7b..0000000 --- a/core/src/main/java/com/opensymphony/xwork2/interceptor/I18nInterceptor.java +++ /dev/null @@ -1,288 +0,0 @@ -/* - * Copyright 2002-2006,2009 The Apache Software Foundation. - * - * 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. - */ - -package com.opensymphony.xwork2.interceptor; - -import com.opensymphony.xwork2.ActionInvocation; -import com.opensymphony.xwork2.util.LocalizedTextUtil; -import org.apache.logging.log4j.LogManager; -import org.apache.logging.log4j.Logger; -import org.apache.struts2.dispatcher.Parameter; -import org.apache.struts2.dispatcher.HttpParameters; - -import java.util.Arrays; -import java.util.Locale; -import java.util.Map; - -/** - * <!-- START SNIPPET: description --> - * <p> - * An interceptor that handles setting the locale specified in a session as the locale for the current action request. - * In addition, this interceptor will look for a specific HTTP request parameter and set the locale to whatever value is - * provided. This means that this interceptor can be used to allow for your application to dynamically change the locale - * for the user's session or, alternatively, only for the current request (since XWork 2.1.3). - * This is very useful for applications that require multi-lingual support and want the user to - * be able to set his or her language preference at any point. The locale parameter is removed during the execution of - * this interceptor, ensuring that properties aren't set on an action (such as request_locale) that have no typical - * corresponding setter in your action. - * </p> - * - * <p> - * For example, using the default parameter name, a request to <b>foo.action?request_locale=en_US</b>, then the - * locale for US English is saved in the user's session and will be used for all future requests. - * If there is no locale set (for example with the first visit), the interceptor uses the browser locale. - * </p> - * - * <!-- END SNIPPET: description --> - * <p><u>Interceptor parameters:</u></p> - * <!-- START SNIPPET: parameters --> - * - * <ul> - * <li>parameterName (optional) - the name of the HTTP request parameter that dictates the locale to switch to and save - * in the session. By default this is <b>request_locale</b></li> - * <li>requestOnlyParameterName (optional) - the name of the HTTP request parameter that dictates the locale to switch to - * for the current request only, without saving it in the session. By default this is <b>request_only_locale</b></li> - * <li>attributeName (optional) - the name of the session key to store the selected locale. By default this is - * <b>WW_TRANS_I18N_LOCALE</b></li> - * </ul> - * <!-- END SNIPPET: parameters --> - * - * <p><u>Extending the interceptor:</u></p> - * - * <!-- START SNIPPET: extending --> - * <p> - * There are no known extensions points for this interceptor. - * </p> - * <!-- END SNIPPET: extending --> - * - * <p><u>Example code:</u></p> - * - * <pre> - * <!-- START SNIPPET: example --> - * <action name="someAction" class="com.examples.SomeAction"> - * <interceptor-ref name="i18n"/> - * <interceptor-ref name="basicStack"/> - * <result name="success">good_result.ftl</result> - * </action> - * <!-- END SNIPPET: example --> - * </pre> - * - * @author Aleksei Gopachenko - */ -public class I18nInterceptor extends AbstractInterceptor { - private static final long serialVersionUID = 2496830135246700300L; - - protected static final Logger LOG = LogManager.getLogger(I18nInterceptor.class); - - public static final String DEFAULT_SESSION_ATTRIBUTE = "WW_TRANS_I18N_LOCALE"; - public static final String DEFAULT_PARAMETER = "request_locale"; - public static final String DEFAULT_REQUESTONLY_PARAMETER = "request_only_locale"; - - protected String parameterName = DEFAULT_PARAMETER; - protected String requestOnlyParameterName = DEFAULT_REQUESTONLY_PARAMETER; - protected String attributeName = DEFAULT_SESSION_ATTRIBUTE; - - // Request-Only = None - protected enum Storage { SESSION, NONE } - - public I18nInterceptor() { - LOG.debug("new I18nInterceptor()"); - } - - public void setParameterName(String parameterName) { - this.parameterName = parameterName; - } - - public void setRequestOnlyParameterName(String requestOnlyParameterName) { - this.requestOnlyParameterName = requestOnlyParameterName; - } - - public void setAttributeName(String attributeName) { - this.attributeName = attributeName; - } - - @Override - public String intercept(ActionInvocation invocation) throws Exception { - if (LOG.isDebugEnabled()) { - LOG.debug("Intercept '{}/{}' {", invocation.getProxy().getNamespace(), invocation.getProxy().getActionName()); - } - - LocaleFinder localeFinder = new LocaleFinder(invocation); - Locale locale = getLocaleFromParam(localeFinder.getRequestedLocale()); - locale = storeLocale(invocation, locale, localeFinder.getStorage()); - saveLocale(invocation, locale); - - if (LOG.isDebugEnabled()) { - LOG.debug("before Locale: {}", invocation.getStack().findValue("locale")); - } - - final String result = invocation.invoke(); - - if (LOG.isDebugEnabled()) { - LOG.debug("after Locale {}", invocation.getStack().findValue("locale")); - LOG.debug("intercept } "); - } - - return result; - } - - /** - * Store the locale to the chosen storage, like f. e. the session - * - * @param invocation the action invocation - * @param locale the locale to store - * @param storage the place to store this locale (like Storage.SESSSION.toString()) - * - * @return the locale - */ - protected Locale storeLocale(ActionInvocation invocation, Locale locale, String storage) { - //save it in session - Map<String, Object> session = invocation.getInvocationContext().getSession(); - - if (session != null) { - synchronized (session) { - if (locale == null) { - storage = Storage.NONE.toString(); - locale = readStoredLocale(invocation, session); - } - - if (Storage.SESSION.toString().equals(storage)) { - session.put(attributeName, locale); - } - } - } - return locale; - } - - protected class LocaleFinder { - protected String storage = Storage.SESSION.toString(); - protected Parameter requestedLocale = null; - - protected ActionInvocation actionInvocation = null; - - protected LocaleFinder(ActionInvocation invocation) { - actionInvocation = invocation; - find(); - } - - protected void find() { - //get requested locale - HttpParameters params = actionInvocation.getInvocationContext().getParameters(); - - storage = Storage.SESSION.toString(); - - requestedLocale = findLocaleParameter(params, parameterName); - if (requestedLocale.isDefined()) { - return; - } - - requestedLocale = findLocaleParameter(params, requestOnlyParameterName); - if (requestedLocale.isDefined()) { - storage = Storage.NONE.toString(); - } - } - - public String getStorage() { - return storage; - } - - public String getRequestedLocale() { - return requestedLocale.getValue(); - } - } - - /** - * Creates a Locale object from the request param, which might - * be already a Local or a String - * - * @param requestedLocale the parameter from the request - * @return the Locale - */ - protected Locale getLocaleFromParam(Object requestedLocale) { - Locale locale = null; - if (requestedLocale != null) { - locale = (requestedLocale instanceof Locale) ? - (Locale) requestedLocale : - LocalizedTextUtil.localeFromString(requestedLocale.toString(), null); - if (locale != null) { - LOG.debug("Applied request locale: {}", locale); - } - } - - if (locale != null && !Arrays.asList(Locale.getAvailableLocales()).contains(locale)) { - locale = Locale.getDefault(); - } - return locale; - } - - /** - * Reads the locale from the session, and if not found from the - * current invocation (=browser) - * - * @param invocation the current invocation - * @param session the current session - * @return the read locale - */ - protected Locale readStoredLocale(ActionInvocation invocation, Map<String, Object> session) { - Locale locale = this.readStoredLocalFromSession(invocation, session); - - if (locale != null) { - return locale; - } - - return this.readStoredLocalFromCurrentInvocation(invocation); - } - - protected Locale readStoredLocalFromSession(ActionInvocation invocation, Map<String, Object> session) { - // check session for saved locale - Object sessionLocale = session.get(attributeName); - if (sessionLocale != null && sessionLocale instanceof Locale) { - Locale locale = (Locale) sessionLocale; - LOG.debug("Applied session locale: {}", locale); - return locale; - } - return null; - } - - protected Locale readStoredLocalFromCurrentInvocation(ActionInvocation invocation) { - // no overriding locale definition found, stay with current invocation (=browser) locale - Locale locale = invocation.getInvocationContext().getLocale(); - if (locale != null) { - LOG.debug("Applied invocation context locale: {}", locale); - } - return locale; - } - - protected Parameter findLocaleParameter(HttpParameters params, String parameterName) { - Parameter requestedLocale = params.get(parameterName); - params.remove(parameterName); - if (requestedLocale.isDefined()) { - LOG.debug("Requested locale: {}", requestedLocale.getValue()); - } - return requestedLocale; - } - - /** - * Save the given locale to the ActionInvocation. - * - * @param invocation The ActionInvocation. - * @param locale The locale to save. - */ - protected void saveLocale(ActionInvocation invocation, Locale locale) { - invocation.getInvocationContext().setLocale(locale); - } - -} http://git-wip-us.apache.org/repos/asf/struts/blob/07bb62ba/core/src/main/java/org/apache/struts2/interceptor/I18nInterceptor.java ---------------------------------------------------------------------- diff --git a/core/src/main/java/org/apache/struts2/interceptor/I18nInterceptor.java b/core/src/main/java/org/apache/struts2/interceptor/I18nInterceptor.java index a5c67f2..15c6e78 100644 --- a/core/src/main/java/org/apache/struts2/interceptor/I18nInterceptor.java +++ b/core/src/main/java/org/apache/struts2/interceptor/I18nInterceptor.java @@ -22,22 +22,40 @@ package org.apache.struts2.interceptor; import com.opensymphony.xwork2.ActionContext; import com.opensymphony.xwork2.ActionInvocation; +import com.opensymphony.xwork2.interceptor.AbstractInterceptor; +import com.opensymphony.xwork2.util.LocalizedTextUtil; +import org.apache.logging.log4j.LogManager; +import org.apache.logging.log4j.Logger; import org.apache.struts2.ServletActionContext; import org.apache.struts2.StrutsStatics; import org.apache.struts2.dispatcher.HttpParameters; +import org.apache.struts2.dispatcher.Parameter; import javax.servlet.http.Cookie; import javax.servlet.http.HttpServletResponse; +import java.util.Arrays; import java.util.Locale; import java.util.Map; /** * <!-- START SNIPPET: description --> * <p> - * This interceptor extends the original xwork i18n interceptor - * and adds functionality to support cookies. + * An interceptor that handles setting the locale specified in a session as the locale for the current action request. + * In addition, this interceptor will look for a specific HTTP request parameter and set the locale to whatever value is + * provided, it also looks for specific cookie to read locale from. This means that this interceptor can be used to allow + * for your application to dynamically change the locale for the user's session or, alternatively, only for the current + * request (since XWork 2.1.3). + * This is very useful for applications that require multi-lingual support and want the user to + * be able to set his or her language preference at any point. The locale parameter is removed during the execution of + * this interceptor, ensuring that properties aren't set on an action (such as request_locale) that have no typical + * corresponding setter in your action. * </p> * + * <p> + * For example, using the default parameter name, a request to <b>foo.action?request_locale=en_US</b>, then the + * locale for US English is saved in the user's session and will be used for all future requests. + * If there is no locale set (for example with the first visit), the interceptor uses the browser locale. + * </p> * <!-- END SNIPPET: description --> * * <!-- START SNIPPET: parameters --> @@ -70,45 +88,38 @@ import java.util.Map; * </action> * <!-- END SNIPPET: example --> */ -public class I18nInterceptor extends com.opensymphony.xwork2.interceptor.I18nInterceptor { - private static final long serialVersionUID = 4587460933182760358L; +public class I18nInterceptor extends AbstractInterceptor { - public static final String DEFAULT_COOKIE_ATTRIBUTE = DEFAULT_SESSION_ATTRIBUTE; + private static final Logger LOG = LogManager.getLogger(I18nInterceptor.class); - public static final String COOKIE_STORAGE = "cookie"; + public static final String DEFAULT_SESSION_ATTRIBUTE = "WW_TRANS_I18N_LOCALE"; + public static final String DEFAULT_PARAMETER = "request_locale"; + public static final String DEFAULT_REQUESTONLY_PARAMETER = "request_only_locale"; - public static final String DEFAULT_COOKIE_PARAMETER = "request_cookie_locale"; - protected String requestCookieParameterName = DEFAULT_COOKIE_PARAMETER; + protected String parameterName = DEFAULT_PARAMETER; + protected String requestOnlyParameterName = DEFAULT_REQUESTONLY_PARAMETER; + protected String attributeName = DEFAULT_SESSION_ATTRIBUTE; - protected class CookieLocaleFinder extends LocaleFinder { - protected CookieLocaleFinder(ActionInvocation invocation) { - super(invocation); - } + // Request-Only = None + protected enum Storage { SESSION, NONE } - @Override - protected void find() { - //get requested locale - HttpParameters params = actionInvocation.getInvocationContext().getParameters(); - storage = Storage.SESSION.toString(); + public static final String DEFAULT_COOKIE_ATTRIBUTE = DEFAULT_SESSION_ATTRIBUTE; - requestedLocale = findLocaleParameter(params, parameterName); + public static final String COOKIE_STORAGE = "cookie"; - if (requestedLocale != null) { - return; - } + public static final String DEFAULT_COOKIE_PARAMETER = "request_cookie_locale"; + protected String requestCookieParameterName = DEFAULT_COOKIE_PARAMETER; - requestedLocale = findLocaleParameter(params, requestCookieParameterName); - if (requestedLocale != null) { - storage = COOKIE_STORAGE; - return; - } + public void setParameterName(String parameterName) { + this.parameterName = parameterName; + } - requestedLocale = findLocaleParameter(params, requestOnlyParameterName); - if (requestedLocale != null) { - storage = Storage.NONE.toString(); - } + public void setRequestOnlyParameterName(String requestOnlyParameterName) { + this.requestOnlyParameterName = requestOnlyParameterName; + } - } + public void setAttributeName(String attributeName) { + this.attributeName = attributeName; } @Override @@ -137,7 +148,15 @@ public class I18nInterceptor extends com.opensymphony.xwork2.interceptor.I18nInt return result; } - @Override + /** + * Store the locale to the chosen storage, like f. e. the session + * + * @param invocation the action invocation + * @param locale the locale to store + * @param storage the place to store this locale (like Storage.SESSSION.toString()) + * + * @return the locale + */ protected Locale storeLocale(ActionInvocation invocation, Locale locale, String storage) { if (COOKIE_STORAGE.equals(storage)) { ActionContext ac = invocation.getInvocationContext(); @@ -150,10 +169,32 @@ public class I18nInterceptor extends com.opensymphony.xwork2.interceptor.I18nInt storage = Storage.SESSION.toString(); } - return super.storeLocale(invocation, locale, storage); + //save it in session + Map<String, Object> session = invocation.getInvocationContext().getSession(); + + if (session != null) { + synchronized (session) { + if (locale == null) { + storage = Storage.NONE.toString(); + locale = readStoredLocale(invocation, session); + } + + if (Storage.SESSION.toString().equals(storage)) { + session.put(attributeName, locale); + } + } + } + return locale; } - @Override + /** + * Reads the locale from the session, and if not found from the + * current invocation (=browser) + * + * @param invocation the current invocation + * @param session the current session + * @return the read locale + */ protected Locale readStoredLocale(ActionInvocation invocation, Map<String, Object> session) { Locale locale = this.readStoredLocalFromSession(invocation, session); @@ -173,7 +214,139 @@ public class I18nInterceptor extends com.opensymphony.xwork2.interceptor.I18nInt return this.readStoredLocalFromCurrentInvocation(invocation); } + /** + * Creates a Locale object from the request param, which might + * be already a Local or a String + * + * @param requestedLocale the parameter from the request + * @return the Locale + */ + protected Locale getLocaleFromParam(Object requestedLocale) { + Locale locale = null; + if (requestedLocale != null) { + locale = (requestedLocale instanceof Locale) ? + (Locale) requestedLocale : + LocalizedTextUtil.localeFromString(requestedLocale.toString(), null); + if (locale != null) { + LOG.debug("Applied request locale: {}", locale); + } + } + + if (locale != null && !Arrays.asList(Locale.getAvailableLocales()).contains(locale)) { + locale = Locale.getDefault(); + } + return locale; + } + + protected Locale readStoredLocalFromSession(ActionInvocation invocation, Map<String, Object> session) { + // check session for saved locale + Object sessionLocale = session.get(attributeName); + if (sessionLocale != null && sessionLocale instanceof Locale) { + Locale locale = (Locale) sessionLocale; + LOG.debug("Applied session locale: {}", locale); + return locale; + } + return null; + } + + protected Locale readStoredLocalFromCurrentInvocation(ActionInvocation invocation) { + // no overriding locale definition found, stay with current invocation (=browser) locale + Locale locale = invocation.getInvocationContext().getLocale(); + if (locale != null) { + LOG.debug("Applied invocation context locale: {}", locale); + } + return locale; + } + + protected Parameter findLocaleParameter(HttpParameters params, String parameterName) { + Parameter requestedLocale = params.get(parameterName); + params.remove(parameterName); + if (requestedLocale.isDefined()) { + LOG.debug("Requested locale: {}", requestedLocale.getValue()); + } + return requestedLocale; + } + + /** + * Save the given locale to the ActionInvocation. + * + * @param invocation The ActionInvocation. + * @param locale The locale to save. + */ + protected void saveLocale(ActionInvocation invocation, Locale locale) { + invocation.getInvocationContext().setLocale(locale); + } + public void setRequestCookieParameterName(String requestCookieParameterName) { this.requestCookieParameterName = requestCookieParameterName; } + + protected class LocaleFinder { + protected String storage = Storage.SESSION.toString(); + protected Parameter requestedLocale = null; + + protected ActionInvocation actionInvocation = null; + + protected LocaleFinder(ActionInvocation invocation) { + actionInvocation = invocation; + find(); + } + + protected void find() { + //get requested locale + HttpParameters params = actionInvocation.getInvocationContext().getParameters(); + + storage = Storage.SESSION.toString(); + + requestedLocale = findLocaleParameter(params, parameterName); + if (requestedLocale.isDefined()) { + return; + } + + requestedLocale = findLocaleParameter(params, requestOnlyParameterName); + if (requestedLocale.isDefined()) { + storage = Storage.NONE.toString(); + } + } + + public String getStorage() { + return storage; + } + + public String getRequestedLocale() { + return requestedLocale.getValue(); + } + } + + protected class CookieLocaleFinder extends LocaleFinder { + protected CookieLocaleFinder(ActionInvocation invocation) { + super(invocation); + } + + @Override + protected void find() { + //get requested locale + HttpParameters params = actionInvocation.getInvocationContext().getParameters(); + storage = Storage.SESSION.toString(); + + requestedLocale = findLocaleParameter(params, parameterName); + + if (requestedLocale.isDefined()) { + return; + } + + requestedLocale = findLocaleParameter(params, requestCookieParameterName); + if (requestedLocale.isDefined()) { + storage = COOKIE_STORAGE; + return; + } + + requestedLocale = findLocaleParameter(params, requestOnlyParameterName); + if (requestedLocale.isDefined()) { + storage = Storage.NONE.toString(); + } + + } + } + } http://git-wip-us.apache.org/repos/asf/struts/blob/07bb62ba/core/src/test/java/com/opensymphony/xwork2/interceptor/I18nInterceptorTest.java ---------------------------------------------------------------------- diff --git a/core/src/test/java/com/opensymphony/xwork2/interceptor/I18nInterceptorTest.java b/core/src/test/java/com/opensymphony/xwork2/interceptor/I18nInterceptorTest.java deleted file mode 100644 index f4dfa93..0000000 --- a/core/src/test/java/com/opensymphony/xwork2/interceptor/I18nInterceptorTest.java +++ /dev/null @@ -1,218 +0,0 @@ -/* - * Copyright 2002-2006,2009 The Apache Software Foundation. - * - * 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. - */ -package com.opensymphony.xwork2.interceptor; - -import com.opensymphony.xwork2.Action; -import com.opensymphony.xwork2.ActionContext; -import com.opensymphony.xwork2.ActionInvocation; -import com.opensymphony.xwork2.SimpleFooAction; -import com.opensymphony.xwork2.mock.MockActionInvocation; -import junit.framework.TestCase; -import org.apache.struts2.dispatcher.HttpParameters; -import org.apache.struts2.dispatcher.Parameter; - -import java.io.Serializable; -import java.util.HashMap; -import java.util.Locale; -import java.util.Map; - -/** - * Unit test for I18nInterceptor. - * - * @author Claus Ibsen - */ -public class I18nInterceptorTest extends TestCase { - - private I18nInterceptor interceptor; - private ActionContext ac; - private Map session; - private ActionInvocation mai; - - public void testEmptyParamAndSession() throws Exception { - interceptor.intercept(mai); - } - - public void testNoSession() throws Exception { - ac.setSession(null); - interceptor.intercept(mai); - } - - public void testDefaultLocale() throws Exception { - prepare(I18nInterceptor.DEFAULT_PARAMETER, "_"); // bad locale that would get us default locale instead - interceptor.intercept(mai); - - assertFalse(mai.getInvocationContext().getParameters().get(I18nInterceptor.DEFAULT_PARAMETER).isDefined()); // should have been removed - - assertNotNull(session.get(I18nInterceptor.DEFAULT_SESSION_ATTRIBUTE)); // should be stored here - assertEquals(Locale.getDefault(), session.get(I18nInterceptor.DEFAULT_SESSION_ATTRIBUTE)); // should create a locale object - } - - public void testDenmarkLocale() throws Exception { - prepare(I18nInterceptor.DEFAULT_PARAMETER, "da_DK"); - interceptor.intercept(mai); - - assertFalse(mai.getInvocationContext().getParameters().get(I18nInterceptor.DEFAULT_PARAMETER).isDefined()); // should have been removed - - Locale denmark = new Locale("da", "DK"); - assertNotNull(session.get(I18nInterceptor.DEFAULT_SESSION_ATTRIBUTE)); // should be stored here - assertEquals(denmark, session.get(I18nInterceptor.DEFAULT_SESSION_ATTRIBUTE)); // should create a locale object - } - - public void testDenmarkLocaleRequestOnly() throws Exception { - prepare(I18nInterceptor.DEFAULT_REQUESTONLY_PARAMETER, "da_DK"); - interceptor.intercept(mai); - - assertFalse(mai.getInvocationContext().getParameters().get(I18nInterceptor.DEFAULT_PARAMETER).isDefined()); // should have been removed - - Locale denmark = new Locale("da", "DK"); - assertNull(session.get(I18nInterceptor.DEFAULT_SESSION_ATTRIBUTE)); // should be stored here - assertEquals(denmark, mai.getInvocationContext().getLocale()); // should create a locale object - } - - public void testCountryOnlyLocale() throws Exception { - prepare(I18nInterceptor.DEFAULT_PARAMETER, "NL"); - interceptor.intercept(mai); - - assertFalse(mai.getInvocationContext().getParameters().get(I18nInterceptor.DEFAULT_PARAMETER).isDefined()); // should have been removed - - Locale denmark = new Locale("NL"); - assertNotNull(session.get(I18nInterceptor.DEFAULT_SESSION_ATTRIBUTE)); // should be stored here - assertEquals(denmark, session.get(I18nInterceptor.DEFAULT_SESSION_ATTRIBUTE)); // should create a locale object - } - - public void testLanguageOnlyLocale() throws Exception { - prepare(I18nInterceptor.DEFAULT_PARAMETER, "da_"); - interceptor.intercept(mai); - - assertFalse(mai.getInvocationContext().getParameters().get(I18nInterceptor.DEFAULT_PARAMETER).isDefined()); // should have been removed - - Locale denmark = new Locale("da"); - assertNotNull(session.get(I18nInterceptor.DEFAULT_SESSION_ATTRIBUTE)); // should be stored here - assertEquals(denmark, session.get(I18nInterceptor.DEFAULT_SESSION_ATTRIBUTE)); // should create a locale object - } - - public void testWithVariant() throws Exception { - prepare(I18nInterceptor.DEFAULT_PARAMETER, "ja_JP_JP"); - interceptor.intercept(mai); - - assertFalse(mai.getInvocationContext().getParameters().get(I18nInterceptor.DEFAULT_PARAMETER).isDefined()); // should have been removed - - Locale variant = new Locale("ja", "JP", "JP"); - Locale locale = (Locale) session.get(I18nInterceptor.DEFAULT_SESSION_ATTRIBUTE); - assertNotNull(locale); // should be stored here - assertEquals(variant, locale); - assertEquals("JP", locale.getVariant()); - } - - public void testWithVariantRequestOnly() throws Exception { - prepare(I18nInterceptor.DEFAULT_REQUESTONLY_PARAMETER, "ja_JP_JP"); - interceptor.intercept(mai); - - assertFalse(mai.getInvocationContext().getParameters().get(I18nInterceptor.DEFAULT_PARAMETER).isDefined()); // should have been removed - assertNull(session.get(I18nInterceptor.DEFAULT_SESSION_ATTRIBUTE)); - - Locale variant = new Locale("ja", "JP", "JP"); - Locale locale = mai.getInvocationContext().getLocale(); - assertNotNull(locale); // should be stored here - assertEquals(variant, locale); - assertEquals("JP", locale.getVariant()); - } - - public void testRealLocaleObjectInParams() throws Exception { - prepare(I18nInterceptor.DEFAULT_PARAMETER, Locale.CANADA_FRENCH); - interceptor.intercept(mai); - - assertFalse(mai.getInvocationContext().getParameters().get(I18nInterceptor.DEFAULT_PARAMETER).isDefined()); // should have been removed - - assertNotNull(session.get(I18nInterceptor.DEFAULT_SESSION_ATTRIBUTE)); // should be stored here - assertEquals(Locale.CANADA_FRENCH, session.get(I18nInterceptor.DEFAULT_SESSION_ATTRIBUTE)); // should create a locale object - } - - public void testRealLocalesInParams() throws Exception { - Locale[] locales = new Locale[] { Locale.CANADA_FRENCH }; - assertTrue(locales.getClass().isArray()); - prepare(I18nInterceptor.DEFAULT_PARAMETER, locales); - interceptor.intercept(mai); - - assertFalse(mai.getInvocationContext().getParameters().get(I18nInterceptor.DEFAULT_PARAMETER).isDefined()); // should have been removed - - assertNotNull(session.get(I18nInterceptor.DEFAULT_SESSION_ATTRIBUTE)); // should be stored here - assertEquals(Locale.CANADA_FRENCH, session.get(I18nInterceptor.DEFAULT_SESSION_ATTRIBUTE)); - } - - public void testSetParameterAndAttributeNames() throws Exception { - // given - prepare("world", Locale.CHINA); - - interceptor.setAttributeName("hello"); - interceptor.setParameterName("world"); - - // when - interceptor.intercept(mai); - - // then - assertFalse(mai.getInvocationContext().getParameters().contains("world")); // should have been removed - - assertNotNull(session.get("hello")); // should be stored here - assertEquals(Locale.CHINA, session.get("hello")); - } - - public void testActionContextLocaleIsPreservedWhenNotOverridden() throws Exception { - final Locale locale1 = Locale.TRADITIONAL_CHINESE; - mai.getInvocationContext().setLocale(locale1); - interceptor.intercept(mai); - - Locale locale = (Locale) session.get(I18nInterceptor.DEFAULT_SESSION_ATTRIBUTE); - assertNull(locale); // should not be stored here - locale = mai.getInvocationContext().getLocale(); - assertEquals(locale1, locale); - } - - private void prepare(String key, Serializable value) { - Map<String, Serializable> params = new HashMap<>(); - params.put(key, value); - - mai.getInvocationContext().setParameters(HttpParameters.create(params).build()); - } - - @Override - protected void setUp() throws Exception { - interceptor = new I18nInterceptor(); - interceptor.init(); - - session = new HashMap(); - - Map<String, Object> ctx = new HashMap<>(); - ctx.put(ActionContext.PARAMETERS, HttpParameters.createEmpty().build()); - ctx.put(ActionContext.SESSION, session); - ac = new ActionContext(ctx); - - Action action = new SimpleFooAction(); - mai = new MockActionInvocation(); - ((MockActionInvocation) mai).setAction(action); - ((MockActionInvocation) mai).setInvocationContext(ac); - } - - @Override - protected void tearDown() throws Exception { - interceptor.destroy(); - interceptor = null; - ac = null; - session = null; - mai = null; - } - -} http://git-wip-us.apache.org/repos/asf/struts/blob/07bb62ba/core/src/test/java/org/apache/struts2/interceptor/I18nInterceptorTest.java ---------------------------------------------------------------------- diff --git a/core/src/test/java/org/apache/struts2/interceptor/I18nInterceptorTest.java b/core/src/test/java/org/apache/struts2/interceptor/I18nInterceptorTest.java index 07abec2..5089be9 100644 --- a/core/src/test/java/org/apache/struts2/interceptor/I18nInterceptorTest.java +++ b/core/src/test/java/org/apache/struts2/interceptor/I18nInterceptorTest.java @@ -24,183 +24,96 @@ import com.opensymphony.xwork2.Action; import com.opensymphony.xwork2.ActionContext; import com.opensymphony.xwork2.ActionInvocation; import com.opensymphony.xwork2.mock.MockActionInvocation; +import junit.framework.TestCase; +import org.apache.struts2.ServletActionContext; import org.apache.struts2.StrutsStatics; +import org.apache.struts2.dispatcher.HttpParameters; import org.easymock.EasyMock; import org.easymock.IArgumentMatcher; -import org.junit.After; -import org.junit.Before; -import org.junit.Test; +import org.springframework.mock.web.MockHttpServletRequest; import javax.servlet.http.Cookie; import javax.servlet.http.HttpServletResponse; +import java.io.Serializable; import java.util.HashMap; import java.util.Locale; import java.util.Map; -import static org.jmock.expectation.AssertMo.assertEquals; -import static org.junit.Assert.assertNotNull; -import static org.junit.Assert.assertNull; -import static org.junit.Assert.assertTrue; +public class I18nInterceptorTest extends TestCase { -public class I18nInterceptorTest { private I18nInterceptor interceptor; private ActionInvocation mai; private ActionContext ac; - private Map<String, Object> params; private Map session; - @Before - public void setUp() throws Exception { - interceptor = new I18nInterceptor(); - interceptor.init(); - params = new HashMap<String, Object>(); - session = new HashMap(); - - Map<String, Object> ctx = new HashMap<String, Object>(); - ctx.put(ActionContext.PARAMETERS, params); - ctx.put(ActionContext.SESSION, session); - ac = new ActionContext(ctx); - - Action action = new Action() { - public String execute() throws Exception { - return SUCCESS; - } - }; - mai = new MockActionInvocation(); - ((MockActionInvocation) mai).setAction(action); - ((MockActionInvocation) mai).setInvocationContext(ac); - } - - @After - public void tearDown() throws Exception { - interceptor.destroy(); - interceptor = null; - ac = null; - params = null; - session = null; - mai = null; - } - - static class CookieMatcher implements IArgumentMatcher { - private Cookie expected; - - CookieMatcher(Cookie cookie) { - expected = cookie; - } - - public boolean matches(Object argument) { - Cookie cookie = ((Cookie) argument); - return - (cookie.getName().equals(expected.getName()) && - cookie.getValue().equals(expected.getValue())); - } - - public static Cookie eqCookie(Cookie ck) { - EasyMock.reportMatcher(new CookieMatcher(ck)); - return null; - } - - public void appendTo(StringBuffer buffer) { - buffer - .append("Received") - .append(expected.getName()) - .append("/") - .append(expected.getValue()); - } - } - - @Test - public void testCookieCreation() throws Exception { - - params.put(I18nInterceptor.DEFAULT_COOKIE_PARAMETER, "da_DK"); - - final Cookie cookie = new Cookie(I18nInterceptor.DEFAULT_COOKIE_ATTRIBUTE, "da_DK"); - - HttpServletResponse response = EasyMock.createMock(HttpServletResponse.class); - response.addCookie(CookieMatcher.eqCookie(cookie)); - EasyMock.replay(response); - - ac.put(StrutsStatics.HTTP_RESPONSE, response); + public void testEmptyParamAndSession() throws Exception { interceptor.intercept(mai); - - EasyMock.verify(response); - - Locale denmark = new Locale("da", "DK"); - assertNotNull(session.get(I18nInterceptor.DEFAULT_SESSION_ATTRIBUTE)); // should be stored here - assertEquals(denmark, session.get(I18nInterceptor.DEFAULT_SESSION_ATTRIBUTE)); // should create a locale object } - @Test public void testNoSession() throws Exception { ac.setSession(null); interceptor.intercept(mai); } - @Test public void testDefaultLocale() throws Exception { - params.put(I18nInterceptor.DEFAULT_PARAMETER, "_"); // bad locale that would get us default locale instead + prepare(I18nInterceptor.DEFAULT_PARAMETER, "_"); // bad locale that would get us default locale instead interceptor.intercept(mai); - assertNull(params.get(I18nInterceptor.DEFAULT_PARAMETER)); // should have been removed + assertFalse(mai.getInvocationContext().getParameters().get(I18nInterceptor.DEFAULT_PARAMETER).isDefined()); // should have been removed assertNotNull(session.get(I18nInterceptor.DEFAULT_SESSION_ATTRIBUTE)); // should be stored here assertEquals(Locale.getDefault(), session.get(I18nInterceptor.DEFAULT_SESSION_ATTRIBUTE)); // should create a locale object } - @Test public void testDenmarkLocale() throws Exception { - params.put(I18nInterceptor.DEFAULT_PARAMETER, "da_DK"); + prepare(I18nInterceptor.DEFAULT_PARAMETER, "da_DK"); interceptor.intercept(mai); - assertNull(params.get(I18nInterceptor.DEFAULT_PARAMETER)); // should have been removed + assertFalse(mai.getInvocationContext().getParameters().get(I18nInterceptor.DEFAULT_PARAMETER).isDefined()); // should have been removed Locale denmark = new Locale("da", "DK"); assertNotNull(session.get(I18nInterceptor.DEFAULT_SESSION_ATTRIBUTE)); // should be stored here assertEquals(denmark, session.get(I18nInterceptor.DEFAULT_SESSION_ATTRIBUTE)); // should create a locale object } - @Test public void testDenmarkLocaleRequestOnly() throws Exception { - params.put(I18nInterceptor.DEFAULT_REQUESTONLY_PARAMETER, "da_DK"); + prepare(I18nInterceptor.DEFAULT_REQUESTONLY_PARAMETER, "da_DK"); interceptor.intercept(mai); - assertNull(params.get(I18nInterceptor.DEFAULT_PARAMETER)); // should have been removed + assertFalse(mai.getInvocationContext().getParameters().get(I18nInterceptor.DEFAULT_PARAMETER).isDefined()); // should have been removed Locale denmark = new Locale("da", "DK"); assertNull(session.get(I18nInterceptor.DEFAULT_SESSION_ATTRIBUTE)); // should be stored here assertEquals(denmark, mai.getInvocationContext().getLocale()); // should create a locale object } - @Test public void testCountryOnlyLocale() throws Exception { - params.put(I18nInterceptor.DEFAULT_PARAMETER, "NL"); + prepare(I18nInterceptor.DEFAULT_PARAMETER, "NL"); interceptor.intercept(mai); - assertNull(params.get(I18nInterceptor.DEFAULT_PARAMETER)); // should have been removed + assertFalse(mai.getInvocationContext().getParameters().get(I18nInterceptor.DEFAULT_PARAMETER).isDefined()); // should have been removed Locale denmark = new Locale("NL"); assertNotNull(session.get(I18nInterceptor.DEFAULT_SESSION_ATTRIBUTE)); // should be stored here assertEquals(denmark, session.get(I18nInterceptor.DEFAULT_SESSION_ATTRIBUTE)); // should create a locale object } - @Test public void testLanguageOnlyLocale() throws Exception { - params.put(I18nInterceptor.DEFAULT_PARAMETER, "da_"); + prepare(I18nInterceptor.DEFAULT_PARAMETER, "da_"); interceptor.intercept(mai); - assertNull(params.get(I18nInterceptor.DEFAULT_PARAMETER)); // should have been removed + assertFalse(mai.getInvocationContext().getParameters().get(I18nInterceptor.DEFAULT_PARAMETER).isDefined()); // should have been removed Locale denmark = new Locale("da"); assertNotNull(session.get(I18nInterceptor.DEFAULT_SESSION_ATTRIBUTE)); // should be stored here assertEquals(denmark, session.get(I18nInterceptor.DEFAULT_SESSION_ATTRIBUTE)); // should create a locale object } - @Test public void testWithVariant() throws Exception { - params.put(I18nInterceptor.DEFAULT_PARAMETER, "ja_JP_JP"); + prepare(I18nInterceptor.DEFAULT_PARAMETER, "ja_JP_JP"); interceptor.intercept(mai); - assertNull(params.get(I18nInterceptor.DEFAULT_PARAMETER)); // should have been removed + assertFalse(mai.getInvocationContext().getParameters().get(I18nInterceptor.DEFAULT_PARAMETER).isDefined()); // should have been removed Locale variant = new Locale("ja", "JP", "JP"); Locale locale = (Locale) session.get(I18nInterceptor.DEFAULT_SESSION_ATTRIBUTE); @@ -209,12 +122,11 @@ public class I18nInterceptorTest { assertEquals("JP", locale.getVariant()); } - @Test public void testWithVariantRequestOnly() throws Exception { - params.put(I18nInterceptor.DEFAULT_REQUESTONLY_PARAMETER, "ja_JP_JP"); + prepare(I18nInterceptor.DEFAULT_REQUESTONLY_PARAMETER, "ja_JP_JP"); interceptor.intercept(mai); - assertNull(params.get(I18nInterceptor.DEFAULT_PARAMETER)); // should have been removed + assertFalse(mai.getInvocationContext().getParameters().get(I18nInterceptor.DEFAULT_PARAMETER).isDefined()); // should have been removed assertNull(session.get(I18nInterceptor.DEFAULT_SESSION_ATTRIBUTE)); Locale variant = new Locale("ja", "JP", "JP"); @@ -224,41 +136,140 @@ public class I18nInterceptorTest { assertEquals("JP", locale.getVariant()); } - @Test public void testRealLocaleObjectInParams() throws Exception { - params.put(I18nInterceptor.DEFAULT_PARAMETER, Locale.CANADA_FRENCH); + prepare(I18nInterceptor.DEFAULT_PARAMETER, Locale.CANADA_FRENCH); interceptor.intercept(mai); - assertNull(params.get(I18nInterceptor.DEFAULT_PARAMETER)); // should have been removed + assertFalse(mai.getInvocationContext().getParameters().get(I18nInterceptor.DEFAULT_PARAMETER).isDefined()); // should have been removed assertNotNull(session.get(I18nInterceptor.DEFAULT_SESSION_ATTRIBUTE)); // should be stored here assertEquals(Locale.CANADA_FRENCH, session.get(I18nInterceptor.DEFAULT_SESSION_ATTRIBUTE)); // should create a locale object } - @Test public void testRealLocalesInParams() throws Exception { - Locale[] locales = new Locale[]{Locale.CANADA_FRENCH}; + Locale[] locales = new Locale[] { Locale.CANADA_FRENCH }; assertTrue(locales.getClass().isArray()); - params.put(I18nInterceptor.DEFAULT_PARAMETER, locales); + prepare(I18nInterceptor.DEFAULT_PARAMETER, locales); interceptor.intercept(mai); - assertNull(params.get(I18nInterceptor.DEFAULT_PARAMETER)); // should have been removed + assertFalse(mai.getInvocationContext().getParameters().get(I18nInterceptor.DEFAULT_PARAMETER).isDefined()); // should have been removed assertNotNull(session.get(I18nInterceptor.DEFAULT_SESSION_ATTRIBUTE)); // should be stored here assertEquals(Locale.CANADA_FRENCH, session.get(I18nInterceptor.DEFAULT_SESSION_ATTRIBUTE)); } - @Test public void testSetParameterAndAttributeNames() throws Exception { + // given + prepare("world", Locale.CHINA); + interceptor.setAttributeName("hello"); interceptor.setParameterName("world"); - params.put("world", Locale.CHINA); + // when interceptor.intercept(mai); - assertNull(params.get("world")); // should have been removed + // then + assertFalse(mai.getInvocationContext().getParameters().contains("world")); // should have been removed assertNotNull(session.get("hello")); // should be stored here assertEquals(Locale.CHINA, session.get("hello")); } + + public void testActionContextLocaleIsPreservedWhenNotOverridden() throws Exception { + final Locale locale1 = Locale.TRADITIONAL_CHINESE; + mai.getInvocationContext().setLocale(locale1); + interceptor.intercept(mai); + + Locale locale = (Locale) session.get(I18nInterceptor.DEFAULT_SESSION_ATTRIBUTE); + assertNull(locale); // should not be stored here + locale = mai.getInvocationContext().getLocale(); + assertEquals(locale1, locale); + } + + private void prepare(String key, Serializable value) { + Map<String, Serializable> params = new HashMap<>(); + params.put(key, value); + + mai.getInvocationContext().setParameters(HttpParameters.create(params).build()); + } + + public void setUp() throws Exception { + interceptor = new I18nInterceptor(); + interceptor.init(); + session = new HashMap(); + + Map<String, Object> ctx = new HashMap<String, Object>(); + ctx.put(ActionContext.PARAMETERS, HttpParameters.createEmpty().build()); + ctx.put(ActionContext.SESSION, session); + + ac = new ActionContext(ctx); + + ServletActionContext.setContext(ac); + ServletActionContext.setRequest(new MockHttpServletRequest()); + + Action action = new Action() { + public String execute() throws Exception { + return SUCCESS; + } + }; + mai = new MockActionInvocation(); + ((MockActionInvocation) mai).setAction(action); + ((MockActionInvocation) mai).setInvocationContext(ac); + } + + public void tearDown() throws Exception { + interceptor.destroy(); + interceptor = null; + ac = null; + session = null; + mai = null; + } + + static class CookieMatcher implements IArgumentMatcher { + private Cookie expected; + + CookieMatcher(Cookie cookie) { + expected = cookie; + } + + public boolean matches(Object argument) { + Cookie cookie = ((Cookie) argument); + return + (cookie.getName().equals(expected.getName()) && + cookie.getValue().equals(expected.getValue())); + } + + public static Cookie eqCookie(Cookie ck) { + EasyMock.reportMatcher(new CookieMatcher(ck)); + return null; + } + + public void appendTo(StringBuffer buffer) { + buffer + .append("Received") + .append(expected.getName()) + .append("/") + .append(expected.getValue()); + } + } + + public void testCookieCreation() throws Exception { + + prepare(I18nInterceptor.DEFAULT_COOKIE_PARAMETER, "da_DK"); + + final Cookie cookie = new Cookie(I18nInterceptor.DEFAULT_COOKIE_ATTRIBUTE, "da_DK"); + + HttpServletResponse response = EasyMock.createMock(HttpServletResponse.class); + response.addCookie(CookieMatcher.eqCookie(cookie)); + EasyMock.replay(response); + + ac.put(StrutsStatics.HTTP_RESPONSE, response); + interceptor.intercept(mai); + + EasyMock.verify(response); + + Locale denmark = new Locale("da", "DK"); + assertNotNull(session.get(I18nInterceptor.DEFAULT_SESSION_ATTRIBUTE)); // should be stored here + assertEquals(denmark, session.get(I18nInterceptor.DEFAULT_SESSION_ATTRIBUTE)); // should create a locale object + } }