You are viewing a plain text version of this content. The canonical link for it is here.
Posted to commits@struts.apache.org by jo...@apache.org on 2011/06/23 22:28:47 UTC

svn commit: r1139066 [1/3] - in /struts/struts2/trunk: ./ apps/portlet/ apps/portlet/src/main/webapp/WEB-INF/ plugins/portlet/ plugins/portlet/src/main/java/org/apache/struts2/components/ plugins/portlet/src/main/java/org/apache/struts2/portlet/ plugin...

Author: jogep
Date: Thu Jun 23 20:28:45 2011
New Revision: 1139066

URL: http://svn.apache.org/viewvc?rev=1139066&view=rev
Log:
WW-3620: Bring Portlet 2.0 (JSR286) plugin from sandbox to trunk

Added:
    struts/struts2/trunk/plugins/portlet/src/main/java/org/apache/struts2/portlet/PortletConstants.java
    struts/struts2/trunk/plugins/portlet/src/main/java/org/apache/struts2/portlet/dispatcher/Jsr286Dispatcher.java
    struts/struts2/trunk/plugins/portlet/src/main/java/org/apache/struts2/portlet/result/PortletResultHelper.java
    struts/struts2/trunk/plugins/portlet/src/main/java/org/apache/struts2/portlet/result/PortletResultHelperJSR168.java
    struts/struts2/trunk/plugins/portlet/src/main/java/org/apache/struts2/portlet/result/PortletResultHelperJSR286.java
    struts/struts2/trunk/plugins/portlet/src/main/java/org/apache/struts2/portlet/servlet/PortletServletResponseJSR286.java
    struts/struts2/trunk/plugins/portlet/src/main/java/org/apache/struts2/portlet/util/PortletUrlHelperJSR286.java
Modified:
    struts/struts2/trunk/apps/portlet/pom.xml
    struts/struts2/trunk/apps/portlet/src/main/webapp/WEB-INF/portlet.xml
    struts/struts2/trunk/apps/portlet/src/main/webapp/WEB-INF/web.xml
    struts/struts2/trunk/plugins/portlet/pom.xml
    struts/struts2/trunk/plugins/portlet/src/main/java/org/apache/struts2/components/PortletUrlRenderer.java
    struts/struts2/trunk/plugins/portlet/src/main/java/org/apache/struts2/portlet/PortletActionConstants.java
    struts/struts2/trunk/plugins/portlet/src/main/java/org/apache/struts2/portlet/PortletApplicationMap.java
    struts/struts2/trunk/plugins/portlet/src/main/java/org/apache/struts2/portlet/PortletRequestMap.java
    struts/struts2/trunk/plugins/portlet/src/main/java/org/apache/struts2/portlet/PortletSessionMap.java
    struts/struts2/trunk/plugins/portlet/src/main/java/org/apache/struts2/portlet/context/PortletActionContext.java
    struts/struts2/trunk/plugins/portlet/src/main/java/org/apache/struts2/portlet/dispatcher/DirectRenderFromEventAction.java
    struts/struts2/trunk/plugins/portlet/src/main/java/org/apache/struts2/portlet/dispatcher/DispatcherServlet.java
    struts/struts2/trunk/plugins/portlet/src/main/java/org/apache/struts2/portlet/dispatcher/Jsr168Dispatcher.java
    struts/struts2/trunk/plugins/portlet/src/main/java/org/apache/struts2/portlet/interceptor/PortletAwareInterceptor.java
    struts/struts2/trunk/plugins/portlet/src/main/java/org/apache/struts2/portlet/interceptor/PortletContextAware.java
    struts/struts2/trunk/plugins/portlet/src/main/java/org/apache/struts2/portlet/interceptor/PortletPreferencesAware.java
    struts/struts2/trunk/plugins/portlet/src/main/java/org/apache/struts2/portlet/interceptor/PortletPrincipalProxy.java
    struts/struts2/trunk/plugins/portlet/src/main/java/org/apache/struts2/portlet/interceptor/PortletRequestAware.java
    struts/struts2/trunk/plugins/portlet/src/main/java/org/apache/struts2/portlet/interceptor/PortletResponseAware.java
    struts/struts2/trunk/plugins/portlet/src/main/java/org/apache/struts2/portlet/interceptor/PortletStateInterceptor.java
    struts/struts2/trunk/plugins/portlet/src/main/java/org/apache/struts2/portlet/interceptor/ServletPortletPreferences.java
    struts/struts2/trunk/plugins/portlet/src/main/java/org/apache/struts2/portlet/result/PortletActionRedirectResult.java
    struts/struts2/trunk/plugins/portlet/src/main/java/org/apache/struts2/portlet/result/PortletResult.java
    struts/struts2/trunk/plugins/portlet/src/main/java/org/apache/struts2/portlet/result/PortletVelocityResult.java
    struts/struts2/trunk/plugins/portlet/src/main/java/org/apache/struts2/portlet/servlet/PortletHttpSession.java
    struts/struts2/trunk/plugins/portlet/src/main/java/org/apache/struts2/portlet/servlet/PortletServletConfig.java
    struts/struts2/trunk/plugins/portlet/src/main/java/org/apache/struts2/portlet/servlet/PortletServletContext.java
    struts/struts2/trunk/plugins/portlet/src/main/java/org/apache/struts2/portlet/servlet/PortletServletInputStream.java
    struts/struts2/trunk/plugins/portlet/src/main/java/org/apache/struts2/portlet/servlet/PortletServletOutputStream.java
    struts/struts2/trunk/plugins/portlet/src/main/java/org/apache/struts2/portlet/servlet/PortletServletRequest.java
    struts/struts2/trunk/plugins/portlet/src/main/java/org/apache/struts2/portlet/servlet/PortletServletRequestDispatcher.java
    struts/struts2/trunk/plugins/portlet/src/main/java/org/apache/struts2/portlet/servlet/PortletServletResponse.java
    struts/struts2/trunk/plugins/portlet/src/main/java/org/apache/struts2/portlet/util/PortletUrlHelper.java
    struts/struts2/trunk/plugins/portlet/src/main/java/org/apache/struts2/views/freemarker/PortletFreemarkerResult.java
    struts/struts2/trunk/plugins/portlet/src/main/resources/struts-plugin.xml
    struts/struts2/trunk/plugins/portlet/src/test/java/org/apache/struts2/portlet/PortletApplicationMapTest.java
    struts/struts2/trunk/plugins/portlet/src/test/java/org/apache/struts2/portlet/PortletRequestMapTest.java
    struts/struts2/trunk/plugins/portlet/src/test/java/org/apache/struts2/portlet/PortletSessionMapTest.java
    struts/struts2/trunk/plugins/portlet/src/test/java/org/apache/struts2/portlet/context/PortletActionContextTest.java
    struts/struts2/trunk/plugins/portlet/src/test/java/org/apache/struts2/portlet/dispatcher/Jsr168DispatcherTest.java
    struts/struts2/trunk/plugins/portlet/src/test/java/org/apache/struts2/portlet/interceptor/PortletAwareInterceptorTest.java
    struts/struts2/trunk/plugins/portlet/src/test/java/org/apache/struts2/portlet/interceptor/PortletStateInterceptorTest.java
    struts/struts2/trunk/plugins/portlet/src/test/java/org/apache/struts2/portlet/result/PortletResultTest.java
    struts/struts2/trunk/plugins/portlet/src/test/java/org/apache/struts2/portlet/util/PortletUrlHelperTest.java
    struts/struts2/trunk/plugins/portlet/src/test/java/org/apache/struts2/views/jsp/PortletUrlTagTest.java
    struts/struts2/trunk/pom.xml

Modified: struts/struts2/trunk/apps/portlet/pom.xml
URL: http://svn.apache.org/viewvc/struts/struts2/trunk/apps/portlet/pom.xml?rev=1139066&r1=1139065&r2=1139066&view=diff
==============================================================================
--- struts/struts2/trunk/apps/portlet/pom.xml (original)
+++ struts/struts2/trunk/apps/portlet/pom.xml Thu Jun 23 20:28:45 2011
@@ -93,8 +93,8 @@
 
     <dependencies>
         <dependency>
-            <groupId>portlet-api</groupId>
-            <artifactId>portlet-api</artifactId>
+            <groupId>javax.portlet</groupId>
+             <artifactId>portlet-api</artifactId>
             <scope>provided</scope>
         </dependency>
         <dependency>

Modified: struts/struts2/trunk/apps/portlet/src/main/webapp/WEB-INF/portlet.xml
URL: http://svn.apache.org/viewvc/struts/struts2/trunk/apps/portlet/src/main/webapp/WEB-INF/portlet.xml?rev=1139066&r1=1139065&r2=1139066&view=diff
==============================================================================
--- struts/struts2/trunk/apps/portlet/src/main/webapp/WEB-INF/portlet.xml (original)
+++ struts/struts2/trunk/apps/portlet/src/main/webapp/WEB-INF/portlet.xml Thu Jun 23 20:28:45 2011
@@ -73,7 +73,7 @@
         <portlet-name>StrutsPortlet2</portlet-name>
         <display-name xml:lang="EN">Struts Test Portlet2</display-name>
     
-        <portlet-class>org.apache.struts2.portlet.dispatcher.Jsr168Dispatcher</portlet-class>
+        <portlet-class>org.apache.struts2.portlet.dispatcher.Jsr286Dispatcher</portlet-class>
 
         <!-- The view mode namespace. Maps to a namespace in the Struts 2 config file. -->
         <init-param>

Modified: struts/struts2/trunk/apps/portlet/src/main/webapp/WEB-INF/web.xml
URL: http://svn.apache.org/viewvc/struts/struts2/trunk/apps/portlet/src/main/webapp/WEB-INF/web.xml?rev=1139066&r1=1139065&r2=1139066&view=diff
==============================================================================
--- struts/struts2/trunk/apps/portlet/src/main/webapp/WEB-INF/web.xml (original)
+++ struts/struts2/trunk/apps/portlet/src/main/webapp/WEB-INF/web.xml Thu Jun 23 20:28:45 2011
@@ -8,11 +8,8 @@
 			/WEB-INF/applicationContext*.xml
 		</param-value>
 	</context-param>
+    <listener>
+        <listener-class>org.springframework.web.context.ContextLoaderListener</listener-class>
+    </listener>
 
-	<!-- Uncomment to use the dispatcher servlet -->
-	<!--<servlet id="Struts2PortletDispatcherServlet">
-		<servlet-name>Struts2PortletDispatcherServlet</servlet-name>
-		<servlet-class>org.apache.struts2.portlet.dispatcher.DispatcherServlet</servlet-class>
-	</servlet>-->
-	
 </web-app>

Modified: struts/struts2/trunk/plugins/portlet/pom.xml
URL: http://svn.apache.org/viewvc/struts/struts2/trunk/plugins/portlet/pom.xml?rev=1139066&r1=1139065&r2=1139066&view=diff
==============================================================================
--- struts/struts2/trunk/plugins/portlet/pom.xml (original)
+++ struts/struts2/trunk/plugins/portlet/pom.xml Thu Jun 23 20:28:45 2011
@@ -78,7 +78,7 @@
 
         <!-- Portlet -->
         <dependency>
-            <groupId>portlet-api</groupId>
+            <groupId>javax.portlet</groupId>
             <artifactId>portlet-api</artifactId>
             <scope>provided</scope>
         </dependency>
@@ -121,20 +121,19 @@
         <!-- Mocks for unit testing (by Spring) -->
         <dependency>
             <groupId>org.springframework</groupId>
-            <artifactId>spring-test</artifactId>
-            <version>2.5.6</version>
+            <artifactId>spring-mock</artifactId>
+            <version>2.0.7</version>
             <scope>test</scope>
         </dependency>
         <dependency>
             <groupId>org.springframework</groupId>
-            <artifactId>spring-webmvc-portlet</artifactId>
-            <version>2.5.6</version>
+            <artifactId>spring-portlet</artifactId>
+            <version>2.0.8</version>
             <scope>test</scope>
         </dependency>
         <dependency>
             <groupId>org.springframework</groupId>
             <artifactId>spring-core</artifactId>
-            <version>2.5.6</version>
             <scope>test</scope>
         </dependency>
         <dependency>

Modified: struts/struts2/trunk/plugins/portlet/src/main/java/org/apache/struts2/components/PortletUrlRenderer.java
URL: http://svn.apache.org/viewvc/struts/struts2/trunk/plugins/portlet/src/main/java/org/apache/struts2/components/PortletUrlRenderer.java?rev=1139066&r1=1139065&r2=1139066&view=diff
==============================================================================
--- struts/struts2/trunk/plugins/portlet/src/main/java/org/apache/struts2/components/PortletUrlRenderer.java (original)
+++ struts/struts2/trunk/plugins/portlet/src/main/java/org/apache/struts2/components/PortletUrlRenderer.java Thu Jun 23 20:28:45 2011
@@ -18,92 +18,93 @@
  * specific language governing permissions and limitations
  * under the License.
  */
-
 package org.apache.struts2.components;
 
-import com.opensymphony.xwork2.ActionContext;
-import com.opensymphony.xwork2.ActionInvocation;
-import com.opensymphony.xwork2.inject.Inject;
+import java.io.IOException;
+import java.io.Writer;
+
 import org.apache.commons.lang.StringUtils;
 import org.apache.struts2.StrutsException;
 import org.apache.struts2.dispatcher.mapper.ActionMapper;
 import org.apache.struts2.portlet.context.PortletActionContext;
 import org.apache.struts2.portlet.util.PortletUrlHelper;
+import org.apache.struts2.portlet.util.PortletUrlHelperJSR286;
 
-import java.io.IOException;
-import java.io.Writer;
+import com.opensymphony.xwork2.ActionContext;
+import com.opensymphony.xwork2.ActionInvocation;
+import com.opensymphony.xwork2.inject.Inject;
+import com.opensymphony.xwork2.util.logging.Logger;
+import com.opensymphony.xwork2.util.logging.LoggerFactory;
 
 /**
  * Implementation of the {@link UrlRenderer} interface that renders URLs for portlet environments.
- * 
+ *
  * @see UrlRenderer
  *
  */
 public class PortletUrlRenderer implements UrlRenderer {
-	
-	/**
-	 * The servlet renderer used when not executing in a portlet context.
-	 */
-	private UrlRenderer servletRenderer = null;
-	
-	public PortletUrlRenderer() {
-		this.servletRenderer = new ServletUrlRenderer();
-	}
 
-	@Inject
-	public void setActionMapper(ActionMapper actionMapper) {
-		servletRenderer.setActionMapper(actionMapper);
-	}
-	
+    private static final Logger LOG = LoggerFactory.getLogger(PortletUrlRenderer.class);
+
+    /**
+     * The servlet renderer used when not executing in a portlet context.
+     */
+    private UrlRenderer servletRenderer = null;
+    private PortletUrlHelper portletUrlHelper = null;
+
+    public PortletUrlRenderer() {
+        this.servletRenderer = new ServletUrlRenderer();
+
+        if (PortletActionContext.isJSR268Supported()) {
+            this.portletUrlHelper = new PortletUrlHelperJSR286();
+        } else {
+            this.portletUrlHelper = new PortletUrlHelper();
+        }
+    }
+
+    @Inject
+    public void setActionMapper( ActionMapper actionMapper) {
+        servletRenderer.setActionMapper(actionMapper);
+    }
+
 	/**
 	 * {@inheritDoc}
 	 */
 	public void renderUrl(Writer writer, UrlProvider urlComponent) {
-		if(PortletActionContext.getPortletContext() == null || "none".equalsIgnoreCase(urlComponent.getPortletUrlType())) {
-			servletRenderer.renderUrl(writer, urlComponent);
-		}
-		else {
-			String action = null;
-			if(urlComponent.getAction() != null) {
-				action = urlComponent.findString(urlComponent.getAction());
-			}
-			String scheme = urlComponent.getHttpServletRequest().getScheme();
-
-			if (urlComponent.getScheme() != null) {
-				scheme = urlComponent.getScheme();
-			}
-
-			String result;
-			urlComponent.setNamespace(urlComponent.determineNamespace(urlComponent.getNamespace(), urlComponent.getStack(), urlComponent.getHttpServletRequest()));
-			if (onlyActionSpecified(urlComponent)) {
-				result = PortletUrlHelper.buildUrl(action, urlComponent.getNamespace(), urlComponent.getMethod(), urlComponent.getParameters(), urlComponent.getPortletUrlType(),
-                        urlComponent.getPortletMode(), urlComponent.getWindowState());
-			} else if(onlyValueSpecified(urlComponent)){
-				result = PortletUrlHelper.buildResourceUrl(urlComponent.getValue(), urlComponent.getParameters());
-			}
-			else {
-				result = createDefaultUrl(urlComponent);
-			}
-            String anchor = urlComponent.getAnchor();
-			if (StringUtils.isNotEmpty(anchor)) {
-				result += '#' + urlComponent.findString(anchor);
-			}
-
-			String var = urlComponent.getVar();
-
-			if (var != null) {
-				urlComponent.putInContext(result);
-
-				// add to the request and page scopes as well
-				urlComponent.getHttpServletRequest().setAttribute(var, result);
-			} else {
-				try {
-					writer.write(result);
-				} catch (IOException e) {
-					throw new StrutsException("IOError: " + e.getMessage(), e);
-				}
-			}
-		}
+        String scheme = urlComponent.getHttpServletRequest().getScheme();
+
+        if (urlComponent.getScheme() != null) {
+            scheme = urlComponent.getScheme();
+        }
+
+        String result;
+        if (onlyActionSpecified(urlComponent)) {
+                result = portletUrlHelper.buildUrl(urlComponent.getAction(), urlComponent.getNamespace(), urlComponent.getMethod(), urlComponent.getParameters(), urlComponent.getPortletUrlType(), urlComponent.getPortletMode(), urlComponent.getWindowState());
+        } else if(onlyValueSpecified(urlComponent)){
+                result = portletUrlHelper.buildResourceUrl(urlComponent.getValue(), urlComponent.getParameters());
+        }
+        else {
+        	result = createDefaultUrl(urlComponent);
+        }
+        final String anchor = urlComponent.getAnchor();
+        if ( anchor != null && anchor.length() > 0 ) {
+            result += '#' + anchor;
+        }
+
+        String var = urlComponent.getVar();
+
+        if (var != null) {
+            urlComponent.putInContext(result);
+
+            // add to the request and page scopes as well
+            urlComponent.getHttpServletRequest().setAttribute(var, result);
+        } else {
+            try {
+                writer.write(result);
+            } catch (IOException e) {
+                throw new StrutsException("IOError: " + e.getMessage(), e);
+            }
+        }
 	}
 
 	private String createDefaultUrl(UrlProvider urlComponent) {
@@ -111,65 +112,66 @@ public class PortletUrlRenderer implemen
 		ActionInvocation ai = (ActionInvocation)urlComponent.getStack().getContext().get(
 				ActionContext.ACTION_INVOCATION);
 		String action = ai.getProxy().getActionName();
-		result = PortletUrlHelper.buildUrl(action, urlComponent.getNamespace(), urlComponent.getMethod(), urlComponent.getParameters(),
+		result = portletUrlHelper.buildUrl(action, urlComponent.getNamespace(), urlComponent.getMethod(), urlComponent.getParameters(),
                 urlComponent.getPortletUrlType(), urlComponent.getPortletMode(), urlComponent.getWindowState());
 		return result;
 	}
 
-	private boolean onlyValueSpecified(UrlProvider urlComponent) {
-		return urlComponent.getValue() != null && urlComponent.getAction() == null;
-	}
-
-	private boolean onlyActionSpecified(UrlProvider urlComponent) {
-		return urlComponent.getValue() == null && urlComponent.getAction() != null;
-	}
+    private boolean onlyValueSpecified(UrlProvider urlComponent) {
+        return urlComponent.getValue() != null && urlComponent.getAction() == null;
+    }
+
+    private boolean onlyActionSpecified(UrlProvider urlComponent) {
+        return urlComponent.getValue() == null && urlComponent.getAction() != null;
+    }
 
 	/**
 	 * {@inheritDoc}
 	 */
 	public void renderFormUrl(Form formComponent) {
-		if(PortletActionContext.getPortletContext() == null) {
-			servletRenderer.renderFormUrl(formComponent);
-		}
-		else {
-			String namespace = formComponent.determineNamespace(formComponent.namespace, formComponent.getStack(),
-					formComponent.request);
-			String action = null;
-			if (formComponent.action != null) {
-				action = formComponent.findString(formComponent.action);
-			}
-			else {
-				ActionInvocation ai = (ActionInvocation) formComponent.getStack().getContext().get(ActionContext.ACTION_INVOCATION);
-				action = ai.getProxy().getActionName();
-			}
-			String type = "action";
-			if (StringUtils.isNotEmpty(formComponent.method)) {
-				if ("GET".equalsIgnoreCase(formComponent.method.trim())) {
-					type = "render";
-				}
-			}
-			if (action != null) {
-				String result = PortletUrlHelper.buildUrl(action, namespace, null,
-						formComponent.getParameters(), type, formComponent.portletMode, formComponent.windowState);
-				formComponent.addParameter("action", result);
-
-
-				// name/id: cut out anything between / and . should be the id and
-				// name
-				String id = formComponent.getId();
-				if (id == null) {
-					int slash = action.lastIndexOf('/');
-					int dot = action.indexOf('.', slash);
-					if (dot != -1) {
-						id = action.substring(slash + 1, dot);
-					} else {
-						id = action.substring(slash + 1);
-					}
-					formComponent.addParameter("id", formComponent.escape(id));
-				}
-			}
-		}
-		
+        if(PortletActionContext.getPortletContext() == null) {
+            servletRenderer.renderFormUrl(formComponent);
+        }
+        else {
+            String namespace = formComponent.determineNamespace(formComponent.namespace, formComponent.getStack(),
+                    formComponent.request);
+            String action = null;
+            if (formComponent.action != null) {
+                action = formComponent.findString(formComponent.action);
+            }
+            else {
+                ActionInvocation ai = (ActionInvocation) formComponent.getStack().getContext().get(ActionContext.ACTION_INVOCATION);
+                action = ai.getProxy().getActionName();
+            }
+
+            String type = "action";
+            if (StringUtils.isNotEmpty(formComponent.method)) {
+                if ("GET".equalsIgnoreCase(formComponent.method.trim())) {
+                    type = "render";
+                }
+            }
+            if (action != null) {
+                String result = portletUrlHelper.buildUrl(action, namespace, null,
+                        formComponent.getParameters(), type, formComponent.portletMode, formComponent.windowState);
+                formComponent.addParameter("action", result);
+
+
+                // name/id: cut out anything between / and . should be the id and
+                // name
+                String id = formComponent.getId();
+                if (id == null) {
+                    int slash = action.lastIndexOf('/');
+                    int dot = action.indexOf('.', slash);
+                    if (dot != -1) {
+                        id = action.substring(slash + 1, dot);
+                    } else {
+                        id = action.substring(slash + 1);
+                    }
+                    formComponent.addParameter("id", formComponent.escape(id));
+                }
+            }
+        }
+
 	}
 
 	public void beforeRenderUrl(UrlProvider urlComponent) {
@@ -178,9 +180,4 @@ public class PortletUrlRenderer implemen
 		}
 	}
 
-	public void setServletRenderer(UrlRenderer nonPortletRenderer) {
-		this.servletRenderer = nonPortletRenderer;
-		
-	}
-
 }

Modified: struts/struts2/trunk/plugins/portlet/src/main/java/org/apache/struts2/portlet/PortletActionConstants.java
URL: http://svn.apache.org/viewvc/struts/struts2/trunk/plugins/portlet/src/main/java/org/apache/struts2/portlet/PortletActionConstants.java?rev=1139066&r1=1139065&r2=1139066&view=diff
==============================================================================
--- struts/struts2/trunk/plugins/portlet/src/main/java/org/apache/struts2/portlet/PortletActionConstants.java (original)
+++ struts/struts2/trunk/plugins/portlet/src/main/java/org/apache/struts2/portlet/PortletActionConstants.java Thu Jun 23 20:28:45 2011
@@ -57,10 +57,10 @@ public interface PortletActionConstants 
     Integer RENDER_PHASE = new Integer(1);
 
     /**
-     * Constant used for the event phase (
+     * Constant used for the action phase (
      * {@link javax.portlet.Portlet#processAction(javax.portlet.ActionRequest, javax.portlet.ActionResponse)})
      */
-    Integer EVENT_PHASE = new Integer(2);
+    Integer ACTION_PHASE = new Integer(2);
 
     /**
      * Key used for looking up and storing the
@@ -107,22 +107,22 @@ public interface PortletActionConstants 
      * {@link org.apache.struts2.portlet.context.PortletActionContext}.
      */
     String DEFAULT_ACTION_FOR_MODE = "struts.portlet.defaultActionForMode";
-    
+
     /**
-     * Key for request attribute indicating if the action has been reset. 
+     * Key for request attribute indicating if the action has been reset.
      */
     String ACTION_RESET = "struts.portlet.actionReset";
-    
+
     /**
      * Key for session attribute indicating the location of the render direct action.
      */
     String RENDER_DIRECT_LOCATION = "struts.portlet.renderDirectLocation";
-    
+
     /**
      * Key for the dispatch instruction for the {@link DispatcherServlet}
      */
 	String DISPATCH_TO = "struts.portlet.dispatchTo";
-	
+
 	/**
 	 * Session key where the value stack from the event phase is stored.
 	 */
@@ -132,7 +132,7 @@ public interface PortletActionConstants 
 	 * Default name of dispatcher servlet in web.xml
 	 */
 	String DEFAULT_DISPATCHER_SERVLET_NAME = "Struts2PortletDispatcherServlet";
-	
+
 	/**
 	 * Key for the action mapping in the context
     */

Modified: struts/struts2/trunk/plugins/portlet/src/main/java/org/apache/struts2/portlet/PortletApplicationMap.java
URL: http://svn.apache.org/viewvc/struts/struts2/trunk/plugins/portlet/src/main/java/org/apache/struts2/portlet/PortletApplicationMap.java?rev=1139066&r1=1139065&r2=1139066&view=diff
==============================================================================
--- struts/struts2/trunk/plugins/portlet/src/main/java/org/apache/struts2/portlet/PortletApplicationMap.java (original)
+++ struts/struts2/trunk/plugins/portlet/src/main/java/org/apache/struts2/portlet/PortletApplicationMap.java Thu Jun 23 20:28:45 2011
@@ -18,7 +18,6 @@
  * specific language governing permissions and limitations
  * under the License.
  */
-
 package org.apache.struts2.portlet;
 
 import java.io.Serializable;

Added: struts/struts2/trunk/plugins/portlet/src/main/java/org/apache/struts2/portlet/PortletConstants.java
URL: http://svn.apache.org/viewvc/struts/struts2/trunk/plugins/portlet/src/main/java/org/apache/struts2/portlet/PortletConstants.java?rev=1139066&view=auto
==============================================================================
--- struts/struts2/trunk/plugins/portlet/src/main/java/org/apache/struts2/portlet/PortletConstants.java (added)
+++ struts/struts2/trunk/plugins/portlet/src/main/java/org/apache/struts2/portlet/PortletConstants.java Thu Jun 23 20:28:45 2011
@@ -0,0 +1,119 @@
+package org.apache.struts2.portlet;
+
+import org.apache.struts2.portlet.dispatcher.DispatcherServlet;
+
+public class PortletConstants {
+	/**
+     * Default action name to use when no default action has been configured in the portlet
+     * init parameters.
+     */
+    public static String DEFAULT_ACTION_NAME = "default";
+
+    /**
+     * Action name parameter name
+     */
+    public static String ACTION_PARAM = "struts.portlet.action";
+
+    /**
+     * Key for parameter holding the last executed portlet mode.
+     */
+    public static String MODE_PARAM = "struts.portlet.mode";
+
+    /**
+     * Key used for looking up and storing the portlet phase
+     */
+    public static String PHASE = "struts.portlet.phase";
+
+    /**
+     * Constant used for the render phase (
+     * {@link javax.portlet.Portlet#render(javax.portlet.RenderRequest, javax.portlet.RenderResponse)})
+     */
+    public static Integer RENDER_PHASE = new Integer(1);
+
+    /**
+     * Constant used for the action phase (
+     * {@link javax.portlet.Portlet#processAction(javax.portlet.ActionRequest, javax.portlet.ActionResponse)})
+     */
+    public static Integer ACTION_PHASE = new Integer(2);
+    
+    /**
+     * Constant used for the event phase
+     */
+    public static Integer EVENT_PHASE = new Integer(3);
+    
+    /**
+     * 
+     */
+    public static Integer SERVE_RESOURCE_PHASE = new Integer(4);
+
+    /**
+     * Key used for looking up and storing the
+     * {@link javax.portlet.PortletRequest}
+     */
+    public static String REQUEST = "struts.portlet.request";
+
+    /**
+     * Key used for looking up and storing the
+     * {@link javax.portlet.PortletResponse}
+     */
+    public static String RESPONSE = "struts.portlet.response";
+
+    /**
+     * Key used for looking up and storing the action that was invoked in the action or event phase.
+     */
+    public static String EVENT_ACTION = "struts.portlet.eventAction";
+
+    /**
+     * Key used for looking up and storing the
+     * {@link javax.portlet.PortletConfig}
+     */
+    public static String PORTLET_CONFIG = "struts.portlet.config";
+
+    /**
+     * Name of the action used as error handler
+     */
+    public static String ERROR_ACTION = "errorHandler";
+
+    /**
+     * Key for the portlet namespace stored in the
+     * {@link org.apache.struts2.portlet.context.PortletActionContext}.
+     */
+    public static String PORTLET_NAMESPACE = "struts.portlet.portletNamespace";
+
+    /**
+     * Key for the mode-to-namespace map stored in the
+     * {@link org.apache.struts2.portlet.context.PortletActionContext}.
+     */
+    public static String MODE_NAMESPACE_MAP = "struts.portlet.modeNamespaceMap";
+
+    /**
+     * Key for the default action name for the portlet, stored in the
+     * {@link org.apache.struts2.portlet.context.PortletActionContext}.
+     */
+    public static String DEFAULT_ACTION_FOR_MODE = "struts.portlet.defaultActionForMode";
+    
+    /**
+     * Key for request attribute indicating if the action has been reset. 
+     */
+    public static String ACTION_RESET = "struts.portlet.actionReset";
+    
+    /**
+     * Key for session attribute indicating the location of the render direct action.
+     */
+    public static String RENDER_DIRECT_LOCATION = "struts.portlet.renderDirectLocation";
+    
+    /**
+     * Key for the dispatch instruction for the {@link DispatcherServlet}
+     */
+	public static String DISPATCH_TO = "struts.portlet.dispatchTo";
+	
+	/**
+	 * Session key where the value stack from the event phase is stored.
+	 */
+	public static String STACK_FROM_EVENT_PHASE = "struts.portlet.valueStackFromEventPhase";
+
+	/**
+	 * Default name of dispatcher servlet in web.xml
+	 */
+	public static String DEFAULT_DISPATCHER_SERVLET_NAME = "Struts2PortletDispatcherServlet";
+}

Modified: struts/struts2/trunk/plugins/portlet/src/main/java/org/apache/struts2/portlet/PortletRequestMap.java
URL: http://svn.apache.org/viewvc/struts/struts2/trunk/plugins/portlet/src/main/java/org/apache/struts2/portlet/PortletRequestMap.java?rev=1139066&r1=1139065&r2=1139066&view=diff
==============================================================================
--- struts/struts2/trunk/plugins/portlet/src/main/java/org/apache/struts2/portlet/PortletRequestMap.java (original)
+++ struts/struts2/trunk/plugins/portlet/src/main/java/org/apache/struts2/portlet/PortletRequestMap.java Thu Jun 23 20:28:45 2011
@@ -18,7 +18,6 @@
  * specific language governing permissions and limitations
  * under the License.
  */
-
 package org.apache.struts2.portlet;
 
 import java.util.AbstractMap;

Modified: struts/struts2/trunk/plugins/portlet/src/main/java/org/apache/struts2/portlet/PortletSessionMap.java
URL: http://svn.apache.org/viewvc/struts/struts2/trunk/plugins/portlet/src/main/java/org/apache/struts2/portlet/PortletSessionMap.java?rev=1139066&r1=1139065&r2=1139066&view=diff
==============================================================================
--- struts/struts2/trunk/plugins/portlet/src/main/java/org/apache/struts2/portlet/PortletSessionMap.java (original)
+++ struts/struts2/trunk/plugins/portlet/src/main/java/org/apache/struts2/portlet/PortletSessionMap.java Thu Jun 23 20:28:45 2011
@@ -18,7 +18,6 @@
  * specific language governing permissions and limitations
  * under the License.
  */
-
 package org.apache.struts2.portlet;
 
 import java.util.AbstractMap;

Modified: struts/struts2/trunk/plugins/portlet/src/main/java/org/apache/struts2/portlet/context/PortletActionContext.java
URL: http://svn.apache.org/viewvc/struts/struts2/trunk/plugins/portlet/src/main/java/org/apache/struts2/portlet/context/PortletActionContext.java?rev=1139066&r1=1139065&r2=1139066&view=diff
==============================================================================
--- struts/struts2/trunk/plugins/portlet/src/main/java/org/apache/struts2/portlet/context/PortletActionContext.java (original)
+++ struts/struts2/trunk/plugins/portlet/src/main/java/org/apache/struts2/portlet/context/PortletActionContext.java Thu Jun 23 20:28:45 2011
@@ -18,7 +18,6 @@
  * specific language governing permissions and limitations
  * under the License.
  */
-
 package org.apache.struts2.portlet.context;
 
 import java.util.Map;
@@ -34,17 +33,18 @@ import javax.portlet.RenderResponse;
 
 import org.apache.struts2.StrutsStatics;
 import org.apache.struts2.dispatcher.mapper.ActionMapping;
-import org.apache.struts2.portlet.PortletActionConstants;
 
 import com.opensymphony.xwork2.ActionContext;
 
+import static org.apache.struts2.portlet.PortletConstants.*;
+
 
 /**
  * PortletActionContext. ActionContext thread local for the portlet environment.
  *
  * @version $Revision$ $Date$
  */
-public class PortletActionContext implements PortletActionConstants {
+public class PortletActionContext {
 
     /**
      * Get the PortletConfig of the portlet that is executing.
@@ -90,7 +90,7 @@ public class PortletActionContext implem
      * @throws IllegalStateException If the method is invoked in the wrong phase.
      */
     public static ActionRequest getActionRequest() {
-        if (!isEvent()) {
+        if (!isAction()) {
             throw new IllegalStateException(
                     "ActionRequest cannot be obtained in render phase");
         }
@@ -104,7 +104,7 @@ public class PortletActionContext implem
      * @throws IllegalStateException If the method is invoked in the wrong phase.
      */
     public static ActionResponse getActionResponse() {
-        if (!isEvent()) {
+        if (!isAction()) {
             throw new IllegalStateException(
                     "ActionResponse cannot be obtained in render phase");
         }
@@ -129,14 +129,6 @@ public class PortletActionContext implem
     public static PortletRequest getRequest() {
         return (PortletRequest) getContext().get(REQUEST);
     }
-    
-    /**
-     * Convenience setter for the portlet request.
-     * @param request
-     */
-    public static void setRequest(PortletRequest request) {
-    	getContext().put(REQUEST, request);
-    }
 
     /**
      * Get the current PortletResponse
@@ -146,20 +138,12 @@ public class PortletActionContext implem
     public static PortletResponse getResponse() {
         return (PortletResponse) getContext().get(RESPONSE);
     }
-    
-    /**
-     * Convenience setter for the portlet response.
-     * @param response
-     */
-    public static void setResponse(PortletResponse response) {
-    	getContext().put(RESPONSE, response);
-    }
 
     /**
      * Get the phase that the portlet is executing in.
      *
      * @return {@link PortletActionConstants#RENDER_PHASE} in render phase, and
-     * {@link PortletActionConstants#EVENT_PHASE} in the event phase.
+     * {@link PortletActionConstants#ACTION_PHASE} in the event phase.
      */
     public static Integer getPhase() {
         return (Integer) getContext().get(PHASE);
@@ -169,14 +153,21 @@ public class PortletActionContext implem
      * @return <code>true</code> if the Portlet is executing in render phase.
      */
     public static boolean isRender() {
-        return PortletActionConstants.RENDER_PHASE.equals(getPhase());
+        return RENDER_PHASE.equals(getPhase());
     }
 
     /**
      * @return <code>true</code> if the Portlet is executing in the event phase.
      */
-    public static boolean isEvent() {
-        return PortletActionConstants.EVENT_PHASE.equals(getPhase());
+    public static boolean isAction() {
+        return ACTION_PHASE.equals(getPhase());
+    }
+
+    /**
+     * @return <code>true</code> if the Portlet is executing in the resource phase.
+     */
+    public static boolean isResource() {
+        return SERVE_RESOURCE_PHASE.equals(getPhase());
     }
 
     /**
@@ -220,22 +211,18 @@ public class PortletActionContext implem
     public static PortletContext getPortletContext() {
     	return (PortletContext)getContext().get(StrutsStatics.STRUTS_PORTLET_CONTEXT);
     }
-    
-    /**
-     * Convenience setter for the portlet context.
-     * @param context
-     */
-    public static void setPortletContext(PortletContext context) {
-    	getContext().put(StrutsStatics.STRUTS_PORTLET_CONTEXT, context);
-    }
-    
+
+	public static boolean isEvent() {
+		return EVENT_PHASE.equals(getPhase());
+	}
+
     /**
-     * Gets the action mapping for this context
+     * Whether JSR286 features are supported.
      *
-     * @return The action mapping
+     * @return <code>true</code> if {@link javax.portlet.PortletContext#getMajorVersion()} returns a value greater than 1
      */
-    public static ActionMapping getActionMapping() {
-        return (ActionMapping) getContext().get(ACTION_MAPPING);
+    public static boolean isJSR268Supported() {
+        return getPortletContext().getMajorVersion() > 1;
     }
 
 }

Modified: struts/struts2/trunk/plugins/portlet/src/main/java/org/apache/struts2/portlet/dispatcher/DirectRenderFromEventAction.java
URL: http://svn.apache.org/viewvc/struts/struts2/trunk/plugins/portlet/src/main/java/org/apache/struts2/portlet/dispatcher/DirectRenderFromEventAction.java?rev=1139066&r1=1139065&r2=1139066&view=diff
==============================================================================
--- struts/struts2/trunk/plugins/portlet/src/main/java/org/apache/struts2/portlet/dispatcher/DirectRenderFromEventAction.java (original)
+++ struts/struts2/trunk/plugins/portlet/src/main/java/org/apache/struts2/portlet/dispatcher/DirectRenderFromEventAction.java Thu Jun 23 20:28:45 2011
@@ -18,7 +18,6 @@
  * specific language governing permissions and limitations
  * under the License.
  */
-
 package org.apache.struts2.portlet.dispatcher;
 
 import com.opensymphony.xwork2.Action;

Modified: struts/struts2/trunk/plugins/portlet/src/main/java/org/apache/struts2/portlet/dispatcher/DispatcherServlet.java
URL: http://svn.apache.org/viewvc/struts/struts2/trunk/plugins/portlet/src/main/java/org/apache/struts2/portlet/dispatcher/DispatcherServlet.java?rev=1139066&r1=1139065&r2=1139066&view=diff
==============================================================================
--- struts/struts2/trunk/plugins/portlet/src/main/java/org/apache/struts2/portlet/dispatcher/DispatcherServlet.java (original)
+++ struts/struts2/trunk/plugins/portlet/src/main/java/org/apache/struts2/portlet/dispatcher/DispatcherServlet.java Thu Jun 23 20:28:45 2011
@@ -18,18 +18,18 @@
  * specific language governing permissions and limitations
  * under the License.
  */
-
 package org.apache.struts2.portlet.dispatcher;
 
-import org.apache.commons.lang.StringUtils;
-import org.apache.struts2.dispatcher.StrutsRequestWrapper;
-import org.apache.struts2.portlet.PortletActionConstants;
+import java.io.IOException;
 
 import javax.servlet.ServletException;
 import javax.servlet.http.HttpServlet;
 import javax.servlet.http.HttpServletRequest;
 import javax.servlet.http.HttpServletResponse;
-import java.io.IOException;
+
+import org.apache.commons.lang.StringUtils;
+import org.apache.struts2.dispatcher.StrutsRequestWrapper;
+import org.apache.struts2.portlet.PortletActionConstants;
 
 public class DispatcherServlet extends HttpServlet implements PortletActionConstants {
 

Modified: struts/struts2/trunk/plugins/portlet/src/main/java/org/apache/struts2/portlet/dispatcher/Jsr168Dispatcher.java
URL: http://svn.apache.org/viewvc/struts/struts2/trunk/plugins/portlet/src/main/java/org/apache/struts2/portlet/dispatcher/Jsr168Dispatcher.java?rev=1139066&r1=1139065&r2=1139066&view=diff
==============================================================================
--- struts/struts2/trunk/plugins/portlet/src/main/java/org/apache/struts2/portlet/dispatcher/Jsr168Dispatcher.java (original)
+++ struts/struts2/trunk/plugins/portlet/src/main/java/org/apache/struts2/portlet/dispatcher/Jsr168Dispatcher.java Thu Jun 23 20:28:45 2011
@@ -21,8 +21,21 @@
 
 package org.apache.struts2.portlet.dispatcher;
 
+import static org.apache.struts2.portlet.PortletConstants.ACTION_PARAM;
+import static org.apache.struts2.portlet.PortletConstants.ACTION_PHASE;
+import static org.apache.struts2.portlet.PortletConstants.ACTION_RESET;
+import static org.apache.struts2.portlet.PortletConstants.DEFAULT_ACTION_FOR_MODE;
+import static org.apache.struts2.portlet.PortletConstants.DEFAULT_ACTION_NAME;
+import static org.apache.struts2.portlet.PortletConstants.MODE_NAMESPACE_MAP;
+import static org.apache.struts2.portlet.PortletConstants.MODE_PARAM;
+import static org.apache.struts2.portlet.PortletConstants.PHASE;
+import static org.apache.struts2.portlet.PortletConstants.PORTLET_CONFIG;
+import static org.apache.struts2.portlet.PortletConstants.PORTLET_NAMESPACE;
+import static org.apache.struts2.portlet.PortletConstants.RENDER_PHASE;
+import static org.apache.struts2.portlet.PortletConstants.REQUEST;
+import static org.apache.struts2.portlet.PortletConstants.RESPONSE;
+
 import java.io.IOException;
-import java.io.InputStream;
 import java.util.Enumeration;
 import java.util.HashMap;
 import java.util.Locale;
@@ -43,6 +56,7 @@ import javax.servlet.ServletContext;
 import javax.servlet.http.HttpServletRequest;
 import javax.servlet.http.HttpServletResponse;
 
+import org.apache.commons.lang.StringUtils;
 import org.apache.struts2.StrutsConstants;
 import org.apache.struts2.StrutsException;
 import org.apache.struts2.StrutsStatics;
@@ -62,7 +76,6 @@ import org.apache.struts2.portlet.servle
 import org.apache.struts2.portlet.servlet.PortletServletRequest;
 import org.apache.struts2.portlet.servlet.PortletServletResponse;
 import org.apache.struts2.util.AttributeMap;
-import org.apache.commons.lang.StringUtils;
 
 import com.opensymphony.xwork2.ActionContext;
 import com.opensymphony.xwork2.ActionProxy;
@@ -164,8 +177,7 @@ import com.opensymphony.xwork2.util.logg
  * <!-- END SNIPPET: example -->
  * </pre>
  */
-public class Jsr168Dispatcher extends GenericPortlet implements StrutsStatics,
-        PortletActionConstants {
+public class Jsr168Dispatcher extends GenericPortlet implements StrutsStatics {
 
     private static final Logger LOG = LoggerFactory.getLogger(Jsr168Dispatcher.class);
 
@@ -175,12 +187,12 @@ public class Jsr168Dispatcher extends Ge
 
     private Map<PortletMode,ActionMapping> actionMap = new HashMap<PortletMode,ActionMapping>(3);
 
-    private String portletNamespace = null;
+    String portletNamespace = null;
 
     private Dispatcher dispatcherUtils;
-    
+
     private ActionMapper actionMapper;
-    
+
     private Container container;
 
     /**
@@ -189,17 +201,17 @@ public class Jsr168Dispatcher extends Ge
     public void init(PortletConfig cfg) throws PortletException {
         super.init(cfg);
         if (LOG.isDebugEnabled()) LOG.debug("Initializing portlet " + getPortletName());
-        
+
         Map<String,String> params = new HashMap<String,String>();
         for (Enumeration e = cfg.getInitParameterNames(); e.hasMoreElements(); ) {
             String name = (String) e.nextElement();
             String value = cfg.getInitParameter(name);
             params.put(name, value);
         }
-        
+
         dispatcherUtils = new Dispatcher(new PortletServletContext(cfg.getPortletContext()), params);
         dispatcherUtils.init();
-        
+
         // For testability
         if (factory == null) {
             factory = dispatcherUtils.getConfigurationManager().getConfiguration().getContainer().getInstance(ActionProxyFactory.class);
@@ -233,7 +245,7 @@ public class Jsr168Dispatcher extends Ge
         if ("true".equalsIgnoreCase(container.getInstance(String.class, StrutsConstants.STRUTS_CONFIGURATION_XML_RELOAD))) {
             FileManager.setReloadingConfigs(true);
         }
-        
+
         actionMapper = container.getInstance(ActionMapper.class);
     }
 
@@ -297,7 +309,7 @@ public class Jsr168Dispatcher extends Ge
         try {
             serviceAction(request, response, getRequestMap(request), getParameterMap(request),
                     getSessionMap(request), getApplicationMap(),
-                    portletNamespace, EVENT_PHASE);
+                    portletNamespace, ACTION_PHASE);
             if (LOG.isDebugEnabled()) LOG.debug("Leaving processAction");
         } finally {
             ActionContext.setContext(null);
@@ -332,10 +344,10 @@ public class Jsr168Dispatcher extends Ge
     /**
      *  Reset the action context.
      */
-    private void resetActionContext() {
+    void resetActionContext() {
         ActionContext.setContext(null);
     }
-    
+
     /**
      * Merges all application and portlet attributes into a single
      * <tt>HashMap</tt> to represent the entire <tt>Action</tt> context.
@@ -357,7 +369,7 @@ public class Jsr168Dispatcher extends Ge
 
         // TODO Must put http request/response objects into map for use with
     	container.inject(servletRequest);
-    	
+
         // ServletActionContext
         HashMap<String, Object> extraContext = new HashMap<String, Object>();
         // The dummy servlet objects. Eases reuse of existing interceptors that uses the servlet objects.
@@ -425,8 +437,8 @@ public class Jsr168Dispatcher extends Ge
         try {
             ServletContext servletContext = new PortletServletContext(getPortletContext());
             HttpServletRequest servletRequest = new PortletServletRequest(request, getPortletContext());
-            HttpServletResponse servletResponse = new PortletServletResponse(response);
-            if(EVENT_PHASE.equals(phase)) {
+            HttpServletResponse servletResponse = createPortletServletResponse(response);
+            if(ACTION_PHASE.equals(phase)) {
             	servletRequest = dispatcherUtils.wrapRequest(servletRequest, servletContext);
         		if(servletRequest instanceof MultiPartRequestWrapper) {
         			// Multipart request. Request parameters are encoded in the multipart data,
@@ -442,9 +454,8 @@ public class Jsr168Dispatcher extends Ge
                     sessionMap, applicationMap, request, response, servletRequest, servletResponse,
                     servletContext, getPortletConfig(), phase);
             extraContext.put(PortletActionConstants.ACTION_MAPPING, mapping);
-            if (LOG.isDebugEnabled()) {
-        	LOG.debug("Creating action proxy for name = " + actionName + ", namespace = " + namespace);
-            }
+            LOG.debug("Creating action proxy for name = " + actionName
+                    + ", namespace = " + namespace);
             ActionProxy proxy = factory.createActionProxy(namespace,
                     actionName, mapping.getMethod(), extraContext);
             request.setAttribute("struts.valueStack", proxy.getInvocation()
@@ -462,7 +473,7 @@ public class Jsr168Dispatcher extends Ge
         }
     }
 
-	/**
+    /**
      * Returns a Map of all application attributes. Copies all attributes from
      * the {@link PortletActionContext}into an {@link ApplicationMap}.
      *
@@ -478,12 +489,14 @@ public class Jsr168Dispatcher extends Ge
      * <code>view</code>, and edit mode is mapped to the namespace
      * <code>edit</code>
      *
-     * @param request the PortletRequest object.
+     * @param portletRequest the PortletRequest object.
+     * @param servletRequest the ServletRequest to use
+     *
      * @return the namespace of the action.
      */
     protected ActionMapping getActionMapping(final PortletRequest portletRequest, final HttpServletRequest servletRequest) {
         ActionMapping mapping = null;
-        String actionPath = null;
+        String actionPath = getDefaultActionPath(portletRequest);
         if (resetAction(portletRequest)) {
             mapping = (ActionMapping) actionMap.get(portletRequest.getPortletMode());
         } else {
@@ -492,14 +505,14 @@ public class Jsr168Dispatcher extends Ge
                 mapping = (ActionMapping) actionMap.get(portletRequest
                         .getPortletMode());
             } else {
-                
+
                 // Use the usual action mapper, but it is expecting an action extension
                 // on the uri, so we add the default one, which should be ok as the
                 // portlet is a portlet first, a servlet second
                 mapping = actionMapper.getMapping(servletRequest, dispatcherUtils.getConfigurationManager());
             }
         }
-        
+
         if (mapping == null) {
             throw new StrutsException("Unable to locate action mapping for request, probably due to " +
                     "an invalid action path: "+actionPath);
@@ -507,6 +520,10 @@ public class Jsr168Dispatcher extends Ge
         return mapping;
     }
 
+    protected String getDefaultActionPath( PortletRequest portletRequest ) {
+        return null;
+    }
+
     /**
      * Get the namespace part of the action path.
      * @param actionPath Full path to action
@@ -610,9 +627,7 @@ public class Jsr168Dispatcher extends Ge
 
     public void destroy() {
         if (dispatcherUtils == null) {
-            if (LOG.isWarnEnabled()) {
-        	LOG.warn("something is seriously wrong, DispatcherUtil is not initialized (null) ");
-            }
+            LOG.warn("something is seriously wrong, DispatcherUtil is not initialized (null) ");
         } else {
             dispatcherUtils.cleanup();
         }
@@ -624,5 +639,16 @@ public class Jsr168Dispatcher extends Ge
     public void setActionMapper(ActionMapper actionMapper) {
         this.actionMapper = actionMapper;
     }
-    
+
+    /**
+     * Method to create a PortletServletResponse matching the used Portlet API, to be overridden for JSR286 Dispatcher.
+     *
+     * @param response The Response used for building the wrapper.
+     *
+     * @return The wrapper response for Servlet bound usage.
+     */
+    protected PortletServletResponse createPortletServletResponse( PortletResponse response ) {
+        return new PortletServletResponse(response);
+    }
+
 }

Added: struts/struts2/trunk/plugins/portlet/src/main/java/org/apache/struts2/portlet/dispatcher/Jsr286Dispatcher.java
URL: http://svn.apache.org/viewvc/struts/struts2/trunk/plugins/portlet/src/main/java/org/apache/struts2/portlet/dispatcher/Jsr286Dispatcher.java?rev=1139066&view=auto
==============================================================================
--- struts/struts2/trunk/plugins/portlet/src/main/java/org/apache/struts2/portlet/dispatcher/Jsr286Dispatcher.java (added)
+++ struts/struts2/trunk/plugins/portlet/src/main/java/org/apache/struts2/portlet/dispatcher/Jsr286Dispatcher.java Thu Jun 23 20:28:45 2011
@@ -0,0 +1,65 @@
+package org.apache.struts2.portlet.dispatcher;
+
+import com.opensymphony.xwork2.ActionContext;
+import com.opensymphony.xwork2.util.logging.Logger;
+import com.opensymphony.xwork2.util.logging.LoggerFactory;
+import org.apache.struts2.portlet.servlet.PortletServletResponse;
+import org.apache.struts2.portlet.servlet.PortletServletResponseJSR286;
+
+import javax.portlet.*;
+import java.io.IOException;
+
+import static org.apache.struts2.portlet.PortletConstants.EVENT_PHASE;
+import static org.apache.struts2.portlet.PortletConstants.SERVE_RESOURCE_PHASE;
+
+public class Jsr286Dispatcher extends Jsr168Dispatcher {
+
+	private final static Logger LOG = LoggerFactory.getLogger(Jsr286Dispatcher.class);
+
+
+	@Override
+	public void processEvent( EventRequest request, EventResponse response)
+			throws PortletException, IOException {
+		if (LOG.isDebugEnabled()) LOG.debug("Entering processEvent");
+		resetActionContext();
+		try {
+			// We'll use the event name as the "action"
+			serviceAction(request, response,
+					getRequestMap(request), getParameterMap(request),
+					getSessionMap(request), getApplicationMap(),
+					portletNamespace, EVENT_PHASE);
+			if (LOG.isDebugEnabled()) LOG.debug("Leaving processEvent");
+		} finally {
+			ActionContext.setContext(null);
+		}
+	}
+
+	@Override
+	public void serveResource( ResourceRequest request, ResourceResponse response)
+			throws PortletException, IOException {
+		if (LOG.isDebugEnabled()) LOG.debug("Entering serveResource");
+		resetActionContext();
+		try {
+			serviceAction(request, response,
+					getRequestMap(request), getParameterMap(request),
+					getSessionMap(request), getApplicationMap(),
+					portletNamespace, SERVE_RESOURCE_PHASE);
+		}
+		finally {
+			ActionContext.setContext(null);
+		}
+	}
+
+    @Override
+    protected String getDefaultActionPath( PortletRequest portletRequest ) {
+        if (portletRequest instanceof EventRequest) {
+            return ((EventRequest) portletRequest).getEvent().getName();
+        }
+        return super.getDefaultActionPath(portletRequest);
+    }
+
+    @Override
+    protected PortletServletResponse createPortletServletResponse( PortletResponse response ) {
+        return new PortletServletResponseJSR286(response);
+    }
+}

Modified: struts/struts2/trunk/plugins/portlet/src/main/java/org/apache/struts2/portlet/interceptor/PortletAwareInterceptor.java
URL: http://svn.apache.org/viewvc/struts/struts2/trunk/plugins/portlet/src/main/java/org/apache/struts2/portlet/interceptor/PortletAwareInterceptor.java?rev=1139066&r1=1139065&r2=1139066&view=diff
==============================================================================
--- struts/struts2/trunk/plugins/portlet/src/main/java/org/apache/struts2/portlet/interceptor/PortletAwareInterceptor.java (original)
+++ struts/struts2/trunk/plugins/portlet/src/main/java/org/apache/struts2/portlet/interceptor/PortletAwareInterceptor.java Thu Jun 23 20:28:45 2011
@@ -18,10 +18,8 @@
  * specific language governing permissions and limitations
  * under the License.
  */
-
 package org.apache.struts2.portlet.interceptor;
 
-import javax.portlet.PortletConfig;
 import javax.portlet.PortletContext;
 import javax.portlet.PortletRequest;
 import javax.portlet.PortletResponse;
@@ -70,18 +68,12 @@ public class PortletAwareInterceptor ext
             PortletContext portletContext = (PortletContext) context.get(STRUTS_PORTLET_CONTEXT);
             ((PortletContextAware) action).setPortletContext(portletContext);
         }
-        if (action instanceof PortletConfigAware) {
-        	PortletConfig portletConfig = (PortletConfig)context.get(PORTLET_CONFIG);
-        	((PortletConfigAware) action).setPortletConfig(portletConfig);
-        }
         if (action instanceof PortletPreferencesAware) {
         	PortletRequest request = (PortletRequest) context.get(REQUEST);
             
             // Check if running in a servlet environment
             if (request == null) {
-                if (LOG.isWarnEnabled()) {
-                    LOG.warn("This portlet preferences implementation should only be used during development");
-                }
+                LOG.warn("This portlet preferences implementation should only be used during development");
                 ((PortletPreferencesAware)action).setPortletPreferences(new ServletPortletPreferences(ActionContext.getContext().getSession()));
             } else {
             	((PortletPreferencesAware)action).setPortletPreferences(request.getPreferences());

Modified: struts/struts2/trunk/plugins/portlet/src/main/java/org/apache/struts2/portlet/interceptor/PortletContextAware.java
URL: http://svn.apache.org/viewvc/struts/struts2/trunk/plugins/portlet/src/main/java/org/apache/struts2/portlet/interceptor/PortletContextAware.java?rev=1139066&r1=1139065&r2=1139066&view=diff
==============================================================================
--- struts/struts2/trunk/plugins/portlet/src/main/java/org/apache/struts2/portlet/interceptor/PortletContextAware.java (original)
+++ struts/struts2/trunk/plugins/portlet/src/main/java/org/apache/struts2/portlet/interceptor/PortletContextAware.java Thu Jun 23 20:28:45 2011
@@ -18,7 +18,6 @@
  * specific language governing permissions and limitations
  * under the License.
  */
-
 package org.apache.struts2.portlet.interceptor;
 
 import javax.portlet.PortletContext;

Modified: struts/struts2/trunk/plugins/portlet/src/main/java/org/apache/struts2/portlet/interceptor/PortletPreferencesAware.java
URL: http://svn.apache.org/viewvc/struts/struts2/trunk/plugins/portlet/src/main/java/org/apache/struts2/portlet/interceptor/PortletPreferencesAware.java?rev=1139066&r1=1139065&r2=1139066&view=diff
==============================================================================
--- struts/struts2/trunk/plugins/portlet/src/main/java/org/apache/struts2/portlet/interceptor/PortletPreferencesAware.java (original)
+++ struts/struts2/trunk/plugins/portlet/src/main/java/org/apache/struts2/portlet/interceptor/PortletPreferencesAware.java Thu Jun 23 20:28:45 2011
@@ -18,7 +18,6 @@
  * specific language governing permissions and limitations
  * under the License.
  */
-
 package org.apache.struts2.portlet.interceptor;
 
 import javax.portlet.PortletPreferences;

Modified: struts/struts2/trunk/plugins/portlet/src/main/java/org/apache/struts2/portlet/interceptor/PortletPrincipalProxy.java
URL: http://svn.apache.org/viewvc/struts/struts2/trunk/plugins/portlet/src/main/java/org/apache/struts2/portlet/interceptor/PortletPrincipalProxy.java?rev=1139066&r1=1139065&r2=1139066&view=diff
==============================================================================
--- struts/struts2/trunk/plugins/portlet/src/main/java/org/apache/struts2/portlet/interceptor/PortletPrincipalProxy.java (original)
+++ struts/struts2/trunk/plugins/portlet/src/main/java/org/apache/struts2/portlet/interceptor/PortletPrincipalProxy.java Thu Jun 23 20:28:45 2011
@@ -18,7 +18,6 @@
  * specific language governing permissions and limitations
  * under the License.
  */
-
 package org.apache.struts2.portlet.interceptor;
 
 import org.apache.struts2.interceptor.PrincipalProxy;

Modified: struts/struts2/trunk/plugins/portlet/src/main/java/org/apache/struts2/portlet/interceptor/PortletRequestAware.java
URL: http://svn.apache.org/viewvc/struts/struts2/trunk/plugins/portlet/src/main/java/org/apache/struts2/portlet/interceptor/PortletRequestAware.java?rev=1139066&r1=1139065&r2=1139066&view=diff
==============================================================================
--- struts/struts2/trunk/plugins/portlet/src/main/java/org/apache/struts2/portlet/interceptor/PortletRequestAware.java (original)
+++ struts/struts2/trunk/plugins/portlet/src/main/java/org/apache/struts2/portlet/interceptor/PortletRequestAware.java Thu Jun 23 20:28:45 2011
@@ -18,7 +18,6 @@
  * specific language governing permissions and limitations
  * under the License.
  */
-
 package org.apache.struts2.portlet.interceptor;
 
 import javax.portlet.PortletRequest;

Modified: struts/struts2/trunk/plugins/portlet/src/main/java/org/apache/struts2/portlet/interceptor/PortletResponseAware.java
URL: http://svn.apache.org/viewvc/struts/struts2/trunk/plugins/portlet/src/main/java/org/apache/struts2/portlet/interceptor/PortletResponseAware.java?rev=1139066&r1=1139065&r2=1139066&view=diff
==============================================================================
--- struts/struts2/trunk/plugins/portlet/src/main/java/org/apache/struts2/portlet/interceptor/PortletResponseAware.java (original)
+++ struts/struts2/trunk/plugins/portlet/src/main/java/org/apache/struts2/portlet/interceptor/PortletResponseAware.java Thu Jun 23 20:28:45 2011
@@ -18,7 +18,6 @@
  * specific language governing permissions and limitations
  * under the License.
  */
-
 package org.apache.struts2.portlet.interceptor;
 
 import javax.portlet.PortletResponse;

Modified: struts/struts2/trunk/plugins/portlet/src/main/java/org/apache/struts2/portlet/interceptor/PortletStateInterceptor.java
URL: http://svn.apache.org/viewvc/struts/struts2/trunk/plugins/portlet/src/main/java/org/apache/struts2/portlet/interceptor/PortletStateInterceptor.java?rev=1139066&r1=1139065&r2=1139066&view=diff
==============================================================================
--- struts/struts2/trunk/plugins/portlet/src/main/java/org/apache/struts2/portlet/interceptor/PortletStateInterceptor.java (original)
+++ struts/struts2/trunk/plugins/portlet/src/main/java/org/apache/struts2/portlet/interceptor/PortletStateInterceptor.java Thu Jun 23 20:28:45 2011
@@ -18,24 +18,32 @@
  * specific language governing permissions and limitations
  * under the License.
  */
-
 package org.apache.struts2.portlet.interceptor;
 
+import static org.apache.struts2.portlet.PortletConstants.ACTION_PHASE;
+import static org.apache.struts2.portlet.PortletConstants.EVENT_ACTION;
+import static org.apache.struts2.portlet.PortletConstants.PHASE;
+import static org.apache.struts2.portlet.PortletConstants.RENDER_PHASE;
+import static org.apache.struts2.portlet.PortletConstants.REQUEST;
+import static org.apache.struts2.portlet.PortletConstants.RESPONSE;
+import static org.apache.struts2.portlet.PortletConstants.STACK_FROM_EVENT_PHASE;
+
+import java.util.Map;
+
+import javax.portlet.ActionResponse;
+import javax.portlet.RenderRequest;
+
+import org.apache.commons.lang.StringUtils;
+import org.apache.struts2.portlet.dispatcher.DirectRenderFromEventAction;
+
 import com.opensymphony.xwork2.ActionInvocation;
 import com.opensymphony.xwork2.interceptor.AbstractInterceptor;
 import com.opensymphony.xwork2.util.CompoundRoot;
 import com.opensymphony.xwork2.util.ValueStack;
 import com.opensymphony.xwork2.util.logging.Logger;
 import com.opensymphony.xwork2.util.logging.LoggerFactory;
-import org.apache.commons.lang.StringUtils;
-import org.apache.struts2.portlet.PortletActionConstants;
-import org.apache.struts2.portlet.dispatcher.DirectRenderFromEventAction;
-
-import javax.portlet.ActionResponse;
-import javax.portlet.RenderRequest;
-import java.util.Map;
 
-public class PortletStateInterceptor extends AbstractInterceptor implements PortletActionConstants {
+public class PortletStateInterceptor extends AbstractInterceptor {
 
 	private final static Logger LOG = LoggerFactory.getLogger(PortletStateInterceptor.class);
 
@@ -47,7 +55,7 @@ public class PortletStateInterceptor ext
 		if (RENDER_PHASE.equals(phase)) {
 			restoreStack(invocation);
 			return invocation.invoke();
-		} else if (EVENT_PHASE.equals(phase)) {
+		} else if (ACTION_PHASE.equals(phase)) {
 			try {
 				return invocation.invoke();
 			} finally {
@@ -78,7 +86,7 @@ public class PortletStateInterceptor ext
 					CompoundRoot oldRoot = oldStack.getRoot();
 					ValueStack currentStack = invocation.getStack();
 					CompoundRoot root = currentStack.getRoot();
-					root.addAll(0, oldRoot);
+					root.addAll(oldRoot);
 					if (LOG.isDebugEnabled()) LOG.debug("Restored stack");
 				}
 			}

Modified: struts/struts2/trunk/plugins/portlet/src/main/java/org/apache/struts2/portlet/interceptor/ServletPortletPreferences.java
URL: http://svn.apache.org/viewvc/struts/struts2/trunk/plugins/portlet/src/main/java/org/apache/struts2/portlet/interceptor/ServletPortletPreferences.java?rev=1139066&r1=1139065&r2=1139066&view=diff
==============================================================================
--- struts/struts2/trunk/plugins/portlet/src/main/java/org/apache/struts2/portlet/interceptor/ServletPortletPreferences.java (original)
+++ struts/struts2/trunk/plugins/portlet/src/main/java/org/apache/struts2/portlet/interceptor/ServletPortletPreferences.java Thu Jun 23 20:28:45 2011
@@ -18,7 +18,6 @@
  * specific language governing permissions and limitations
  * under the License.
  */
-
 package org.apache.struts2.portlet.interceptor;
 
 import java.io.IOException;

Modified: struts/struts2/trunk/plugins/portlet/src/main/java/org/apache/struts2/portlet/result/PortletActionRedirectResult.java
URL: http://svn.apache.org/viewvc/struts/struts2/trunk/plugins/portlet/src/main/java/org/apache/struts2/portlet/result/PortletActionRedirectResult.java?rev=1139066&r1=1139065&r2=1139066&view=diff
==============================================================================
--- struts/struts2/trunk/plugins/portlet/src/main/java/org/apache/struts2/portlet/result/PortletActionRedirectResult.java (original)
+++ struts/struts2/trunk/plugins/portlet/src/main/java/org/apache/struts2/portlet/result/PortletActionRedirectResult.java Thu Jun 23 20:28:45 2011
@@ -18,7 +18,6 @@
  * specific language governing permissions and limitations
  * under the License.
  */
-
 package org.apache.struts2.portlet.result;
 
 import java.util.Arrays;
@@ -36,19 +35,15 @@ import org.apache.struts2.portlet.Portle
 import org.apache.struts2.views.util.UrlHelper;
 
 import com.opensymphony.xwork2.ActionInvocation;
-import com.opensymphony.xwork2.util.reflection.ReflectionExceptionHandler;
-import com.opensymphony.xwork2.util.reflection.ReflectionException;
-import com.opensymphony.xwork2.util.logging.Logger;
-import com.opensymphony.xwork2.util.logging.LoggerFactory;
 import com.opensymphony.xwork2.config.entities.ResultConfig;
 import com.opensymphony.xwork2.inject.Inject;
 
 /**
- *
+ * 
  * Portlet modification of the {@link ServletActionRedirectResult}.
- *
+ * 
  * <!-- START SNIPPET: description -->
- *
+ * 
  * This result uses the {@link ActionMapper} provided by the
  * {@link ActionMapperFactory} to instruct the render phase to invoke the
  * specified action and (optional) namespace. This is better than the
@@ -58,63 +53,63 @@ import com.opensymphony.xwork2.inject.In
  * and your application will still work. It is strongly recommended that if you
  * are redirecting to another action, you use this result rather than the
  * standard redirect result.
- *
+ * 
  * See examples below for an example of how request parameters could be passed
  * in.
- *
+ * 
  * <!-- END SNIPPET: description -->
- *
+ * 
  * <b>This result type takes the following parameters:</b>
- *
+ * 
  * <!-- START SNIPPET: params -->
- *
+ * 
  * <ul>
- *
+ * 
  * <li><b>actionName (default)</b> - the name of the action that will be
  * redirect to</li>
- *
+ * 
  * <li><b>namespace</b> - used to determine which namespace the action is in
  * that we're redirecting to . If namespace is null, this defaults to the
  * current namespace</li>
- *
+ * 
  * </ul>
- *
+ * 
  * <!-- END SNIPPET: params -->
- *
+ * 
  * <b>Example:</b>
- *
+ * 
  * <pre>
  * &lt;!-- START SNIPPET: example --&gt;
  *  &lt;package name=&quot;public&quot; extends=&quot;struts-default&quot;&gt;
  *      &lt;action name=&quot;login&quot; class=&quot;...&quot;&gt;
  *          &lt;!-- Redirect to another namespace --&gt;
- *          &lt;result type=&quot;redirectAction&quot;&gt;
+ *          &lt;result type=&quot;redirect-action&quot;&gt;
  *              &lt;param name=&quot;actionName&quot;&gt;dashboard&lt;/param&gt;
  *              &lt;param name=&quot;namespace&quot;&gt;/secure&lt;/param&gt;
  *          &lt;/result&gt;
  *      &lt;/action&gt;
  *  &lt;/package&gt;
- *
+ * 
  *  &lt;package name=&quot;secure&quot; extends=&quot;struts-default&quot; namespace=&quot;/secure&quot;&gt;
  *      &lt;-- Redirect to an action in the same namespace --&gt;
  *      &lt;action name=&quot;dashboard&quot; class=&quot;...&quot;&gt;
  *          &lt;result&gt;dashboard.jsp&lt;/result&gt;
- *          &lt;result name=&quot;error&quot; type=&quot;redirectAction&quot;&gt;error&lt;/result&gt;
+ *          &lt;result name=&quot;error&quot; type=&quot;redirect-action&quot;&gt;error&lt;/result&gt;
  *      &lt;/action&gt;
- *
+ * 
  *      &lt;action name=&quot;error&quot; class=&quot;...&quot;&gt;
  *          &lt;result&gt;error.jsp&lt;/result&gt;
  *      &lt;/action&gt;
  *  &lt;/package&gt;
- *
+ * 
  *  &lt;package name=&quot;passingRequestParameters&quot; extends=&quot;struts-default&quot; namespace=&quot;/passingRequestParameters&quot;&gt;
  *     &lt;-- Pass parameters (reportType, width and height) --&gt;
  *     &lt;!--
- *     The redirectAction url generated will be :
+ *     The redirect-action url generated will be :
  *     /genReport/generateReport.action?reportType=pie&amp;width=100&amp;height=100
  *     --&gt;
  *     &lt;action name=&quot;gatherReportInfo&quot; class=&quot;...&quot;&gt;
- *        &lt;result name=&quot;showReportResult&quot; type=&quot;redirectAction&quot;&gt;
+ *        &lt;result name=&quot;showReportResult&quot; type=&quot;redirect-action&quot;&gt;
  *           &lt;param name=&quot;actionName&quot;&gt;generateReport&lt;/param&gt;
  *           &lt;param name=&quot;namespace&quot;&gt;/genReport&lt;/param&gt;
  *           &lt;param name=&quot;reportType&quot;&gt;pie&lt;/param&gt;
@@ -123,20 +118,18 @@ import com.opensymphony.xwork2.inject.In
  *        &lt;/result&gt;
  *     &lt;/action&gt;
  *  &lt;/package&gt;
- *
- *
+ * 
+ * 
  *  &lt;!-- END SNIPPET: example --&gt;
  * </pre>
- *
+ * 
  * @see ActionMapper
  */
-public class PortletActionRedirectResult extends PortletResult implements ReflectionExceptionHandler {
+public class PortletActionRedirectResult extends PortletResult {
 
 	private static final long serialVersionUID = -7627388936683562557L;
 
-    private static final Logger LOG = LoggerFactory.getLogger(PortletActionRedirectResult.class);
-
-    /** The default parameter */
+	/** The default parameter */
 	public static final String DEFAULT_PARAM = "actionName";
 
 	protected String actionName;
@@ -181,6 +174,7 @@ public class PortletActionRedirectResult
 	 */
 	public void execute(ActionInvocation invocation) throws Exception {
 		actionName = conditionalParse(actionName, invocation);
+		String portletNamespace = (String)invocation.getInvocationContext().get(PortletActionConstants.PORTLET_NAMESPACE);
 		if (portletMode != null) {
 			Map<PortletMode, String> namespaceMap = (Map<PortletMode, String>) invocation.getInvocationContext().get(
 					PortletActionConstants.MODE_NAMESPACE_MAP);
@@ -211,7 +205,7 @@ public class PortletActionRedirectResult
 		}
 
 		StringBuilder tmpLocation = new StringBuilder(actionMapper.getUriFromActionMapping(new ActionMapping(actionName,
-                namespace, method, null)));
+				(portletNamespace == null ? namespace : portletNamespace + namespace), method, null)));
 		UrlHelper.buildParametersString(requestParameters, tmpLocation, "&");
 
 		setLocation(tmpLocation.toString());
@@ -221,7 +215,7 @@ public class PortletActionRedirectResult
 
 	/**
 	 * Sets the action name
-	 *
+	 * 
 	 * @param actionName
 	 *            The name
 	 */
@@ -231,7 +225,7 @@ public class PortletActionRedirectResult
 
 	/**
 	 * Sets the namespace
-	 *
+	 * 
 	 * @param namespace
 	 *            The namespace
 	 */
@@ -241,7 +235,7 @@ public class PortletActionRedirectResult
 
 	/**
 	 * Sets the method
-	 *
+	 * 
 	 * @param method
 	 *            The method
 	 */
@@ -251,7 +245,7 @@ public class PortletActionRedirectResult
 
 	/**
 	 * Adds a request parameter to be added to the redirect url
-	 *
+	 * 
 	 * @param key
 	 *            The parameter name
 	 * @param value
@@ -262,8 +256,4 @@ public class PortletActionRedirectResult
 		return this;
 	}
 
-    public void handle(ReflectionException ex) {
-        // Only log as debug as they are probably parameters to be appended to the url
-        if (LOG.isDebugEnabled()) LOG.debug(ex.getMessage(), ex);
-    }
 }

Modified: struts/struts2/trunk/plugins/portlet/src/main/java/org/apache/struts2/portlet/result/PortletResult.java
URL: http://svn.apache.org/viewvc/struts/struts2/trunk/plugins/portlet/src/main/java/org/apache/struts2/portlet/result/PortletResult.java?rev=1139066&r1=1139065&r2=1139066&view=diff
==============================================================================
--- struts/struts2/trunk/plugins/portlet/src/main/java/org/apache/struts2/portlet/result/PortletResult.java (original)
+++ struts/struts2/trunk/plugins/portlet/src/main/java/org/apache/struts2/portlet/result/PortletResult.java Thu Jun 23 20:28:45 2011
@@ -18,44 +18,45 @@
  * specific language governing permissions and limitations
  * under the License.
  */
-
 package org.apache.struts2.portlet.result;
 
-import com.opensymphony.xwork2.ActionInvocation;
-import com.opensymphony.xwork2.inject.Inject;
-import com.opensymphony.xwork2.util.logging.Logger;
-import com.opensymphony.xwork2.util.logging.LoggerFactory;
-import org.apache.commons.lang.StringUtils;
-import org.apache.struts2.ServletActionContext;
-import org.apache.struts2.dispatcher.StrutsResultSupport;
-import org.apache.struts2.portlet.PortletActionConstants;
-import org.apache.struts2.portlet.context.PortletActionContext;
+import java.io.IOException;
+import java.util.Map;
+import java.util.StringTokenizer;
 
-import javax.portlet.ActionResponse;
 import javax.portlet.PortletContext;
 import javax.portlet.PortletException;
 import javax.portlet.PortletMode;
+import javax.portlet.PortletRequest;
 import javax.portlet.PortletRequestDispatcher;
-import javax.portlet.RenderRequest;
+import javax.portlet.PortletResponse;
 import javax.portlet.RenderResponse;
 import javax.servlet.ServletContext;
 import javax.servlet.ServletException;
 import javax.servlet.http.HttpServletRequest;
 import javax.servlet.http.HttpServletResponse;
-import java.io.IOException;
-import java.util.Map;
-import java.util.StringTokenizer;
+
+import org.apache.commons.lang.StringUtils;
+import org.apache.struts2.ServletActionContext;
+import org.apache.struts2.dispatcher.StrutsResultSupport;
+import org.apache.struts2.portlet.PortletActionConstants;
+import org.apache.struts2.portlet.context.PortletActionContext;
+
+import com.opensymphony.xwork2.ActionInvocation;
+import com.opensymphony.xwork2.inject.Inject;
+import com.opensymphony.xwork2.util.logging.Logger;
+import com.opensymphony.xwork2.util.logging.LoggerFactory;
 
 /**
  * Result type that includes a JSP to render.
- * 
+ *
  */
 public class PortletResult extends StrutsResultSupport implements PortletActionConstants {
 
 	private static final long serialVersionUID = 434251393926178567L;
 
 	private boolean useDispatcherServlet;
-	
+
 	private String dispatcherServletName = DEFAULT_DISPATCHER_SERVLET_NAME;
 
 	/**
@@ -66,29 +67,41 @@ public class PortletResult extends Strut
 	private String contentType = "text/html";
 
 	private String title;
-	
+
 	protected PortletMode portletMode;
 
+    PortletResultHelper resultHelper;
+
 	public PortletResult() {
 		super();
+        determineResultHelper();
 	}
 
 	public PortletResult(String location) {
 		super(location);
+        determineResultHelper();
 	}
 
+    private void determineResultHelper() {
+        if (PortletActionContext.isJSR268Supported()) {
+            this.resultHelper = new PortletResultHelperJSR286();
+        } else {
+            this.resultHelper = new PortletResultHelperJSR168();
+        }
+    }
+
 	/**
 	 * Execute the result. Obtains the
 	 * {@link javax.portlet.PortletRequestDispatcher}from the
 	 * {@link PortletActionContext}and includes the JSP.
-	 * 
+	 *
 	 * @see com.opensymphony.xwork2.Result#execute(com.opensymphony.xwork2.ActionInvocation)
 	 */
 	public void doExecute(String finalLocation, ActionInvocation actionInvocation) throws Exception {
 
-		if (PortletActionContext.isRender()) {
-			executeRenderResult(finalLocation);
-		} else if (PortletActionContext.isEvent()) {
+		if (PortletActionContext.isRender() || PortletActionContext.isResource()) {
+			executeMimeResult(finalLocation);
+		} else if (PortletActionContext.isAction() || PortletActionContext.isEvent()) {
 			executeActionResult(finalLocation, actionInvocation);
 		} else {
 			executeRegularServletResult(finalLocation, actionInvocation);
@@ -97,7 +110,7 @@ public class PortletResult extends Strut
 
 	/**
 	 * Executes the regular servlet result.
-	 * 
+	 *
 	 * @param finalLocation
 	 * @param actionInvocation
 	 */
@@ -119,95 +132,91 @@ public class PortletResult extends Strut
 
 	/**
 	 * Executes the action result.
-	 * 
+	 *
 	 * @param finalLocation
 	 * @param invocation
 	 */
 	protected void executeActionResult(String finalLocation, ActionInvocation invocation) throws Exception {
-		if (LOG.isDebugEnabled()) LOG.debug("Executing result in Event phase");
-		ActionResponse res = PortletActionContext.getActionResponse();
+        String phase = (PortletActionContext.isEvent()) ? "Event" : "Action";
+		if (LOG.isDebugEnabled()) LOG.debug("Executing result in "+phase+" phase");
 		Map sessionMap = invocation.getInvocationContext().getSession();
 		if (LOG.isDebugEnabled()) LOG.debug("Setting event render parameter: " + finalLocation);
 		if (finalLocation.indexOf('?') != -1) {
-			convertQueryParamsToRenderParams(res, finalLocation.substring(finalLocation.indexOf('?') + 1));
+			convertQueryParamsToRenderParams(finalLocation.substring(finalLocation.indexOf('?') + 1));
 			finalLocation = finalLocation.substring(0, finalLocation.indexOf('?'));
 		}
+        PortletResponse response = PortletActionContext.getResponse();
 		if (finalLocation.endsWith(".action")) {
 			// View is rendered with a view action...luckily...
 			finalLocation = finalLocation.substring(0, finalLocation.lastIndexOf("."));
-			res.setRenderParameter(ACTION_PARAM, finalLocation);
+			resultHelper.setRenderParameter(response, ACTION_PARAM, finalLocation);
 		} else {
 			// View is rendered outside an action...uh oh...
-            String namespace = invocation.getProxy().getNamespace();
-            if ( namespace != null && namespace.length() > 0 && !namespace.endsWith("/")) {
-                namespace += "/";
-                
-            }
-            res.setRenderParameter(ACTION_PARAM, namespace + "renderDirect");
+			resultHelper.setRenderParameter(response, ACTION_PARAM, "renderDirect");
 			sessionMap.put(RENDER_DIRECT_LOCATION, finalLocation);
 		}
 		if(portletMode != null) {
-			res.setPortletMode(portletMode);
-			res.setRenderParameter(PortletActionConstants.MODE_PARAM, portletMode.toString());
+			resultHelper.setPortletMode(response, portletMode);
+			resultHelper.setRenderParameter(response, PortletActionConstants.MODE_PARAM, portletMode.toString());
 		}
 		else {
-			res.setRenderParameter(PortletActionConstants.MODE_PARAM, PortletActionContext.getRequest().getPortletMode()
+			resultHelper.setRenderParameter(response, PortletActionConstants.MODE_PARAM, PortletActionContext.getRequest().getPortletMode()
 					.toString());
 		}
 	}
 
 	/**
 	 * Converts the query params to render params.
-	 * 
+	 *
 	 * @param response
 	 * @param queryParams
 	 */
-	protected static void convertQueryParamsToRenderParams(ActionResponse response, String queryParams) {
+	protected void convertQueryParamsToRenderParams(String queryParams) {
 		StringTokenizer tok = new StringTokenizer(queryParams, "&");
 		while (tok.hasMoreTokens()) {
 			String token = tok.nextToken();
 			String key = token.substring(0, token.indexOf('='));
 			String value = token.substring(token.indexOf('=') + 1);
-			response.setRenderParameter(key, value);
+			resultHelper.setRenderParameter(PortletActionContext.getResponse(), key, value);
 		}
 	}
 
-	/**
-	 * Executes the render result.
-	 * 
-	 * @param finalLocation
-	 * @throws PortletException
-	 * @throws IOException
-	 */
-	protected void executeRenderResult(final String finalLocation) throws PortletException, IOException {
-		if (LOG.isDebugEnabled()) LOG.debug("Executing result in Render phase");
-		PortletContext ctx = PortletActionContext.getPortletContext();
-		RenderRequest req = PortletActionContext.getRenderRequest();
-		RenderResponse res = PortletActionContext.getRenderResponse();
-		res.setContentType(contentType);
-		if (StringUtils.isNotEmpty(title)) {
-			res.setTitle(title);
-		}
-		if (LOG.isDebugEnabled()) LOG.debug("Location: " + finalLocation);
-		if (useDispatcherServlet) {
-			req.setAttribute(DISPATCH_TO, finalLocation);
-			PortletRequestDispatcher dispatcher = ctx.getNamedDispatcher(dispatcherServletName);
-			if(dispatcher == null) {
-				throw new PortletException("Could not locate dispatcher servlet \"" + dispatcherServletName + "\". Please configure it in your web.xml file");
-			}
-			dispatcher.include(req, res);
-		} else {
-			PortletRequestDispatcher dispatcher = ctx.getRequestDispatcher(finalLocation);
-			if (dispatcher == null) {
-				throw new PortletException("Could not locate dispatcher for '" + finalLocation + "'");
-			}
-			dispatcher.include(req, res);
-		}
-	}
+    /**
+     * Executes the render result.
+     *
+     * @param finalLocation
+     * @throws PortletException
+     * @throws IOException
+     */
+    protected void executeMimeResult(final String finalLocation) throws PortletException, IOException {
+        if (LOG.isDebugEnabled()) LOG.debug("Executing mime result");
+        PortletContext ctx = PortletActionContext.getPortletContext();
+        PortletRequest req = PortletActionContext.getRequest();
+        PortletResponse res = PortletActionContext.getResponse();
+
+		if (StringUtils.isNotEmpty(title) && res instanceof RenderResponse) {
+		    ((RenderResponse)res).setTitle(title);
+		}
+        if (LOG.isDebugEnabled()) LOG.debug("Location: " + finalLocation);
+        PortletRequestDispatcher dispatcher;
+        if (useDispatcherServlet) {
+            req.setAttribute(DISPATCH_TO, finalLocation);
+            dispatcher = ctx.getNamedDispatcher(dispatcherServletName);
+            if(dispatcher == null) {
+                throw new PortletException("Could not locate dispatcher servlet \"" + dispatcherServletName + "\". Please configure it in your web.xml file");
+            }
+        } else {
+            dispatcher = ctx.getRequestDispatcher(finalLocation);
+            if (dispatcher == null) {
+                throw new PortletException("Could not locate dispatcher for '" + finalLocation + "'");
+            }
+        }
+        resultHelper.include( dispatcher, contentType, req, res );
+    }
 
 	/**
 	 * Sets the content type.
-	 * 
+	 *
 	 * @param contentType
 	 *            The content type to set.
 	 */
@@ -217,25 +226,25 @@ public class PortletResult extends Strut
 
 	/**
 	 * Sets the title.
-	 * 
+	 *
 	 * @param title
 	 *            The title to set.
 	 */
 	public void setTitle(String title) {
 		this.title = title;
 	}
-	
+
 	public void setPortletMode(String portletMode) {
 		if(portletMode != null) {
 			this.portletMode = new PortletMode(portletMode);
 		}
 	}
 
-	@Inject("struts.portlet.useDispatcherServlet") 
+	@Inject("struts.portlet.useDispatcherServlet")
 	public void setUseDispatcherServlet(String useDispatcherServlet) {
 		this.useDispatcherServlet = "true".equalsIgnoreCase(useDispatcherServlet);
 	}
-	
+
 	@Inject("struts.portlet.dispatcherServletName")
 	public void setDispatcherServletName(String dispatcherServletName) {
 		this.dispatcherServletName = dispatcherServletName;

Added: struts/struts2/trunk/plugins/portlet/src/main/java/org/apache/struts2/portlet/result/PortletResultHelper.java
URL: http://svn.apache.org/viewvc/struts/struts2/trunk/plugins/portlet/src/main/java/org/apache/struts2/portlet/result/PortletResultHelper.java?rev=1139066&view=auto
==============================================================================
--- struts/struts2/trunk/plugins/portlet/src/main/java/org/apache/struts2/portlet/result/PortletResultHelper.java (added)
+++ struts/struts2/trunk/plugins/portlet/src/main/java/org/apache/struts2/portlet/result/PortletResultHelper.java Thu Jun 23 20:28:45 2011
@@ -0,0 +1,41 @@
+package org.apache.struts2.portlet.result;
+
+import javax.portlet.*;
+import java.io.IOException;
+
+/**
+ * PortletResultHelper abstracts Portlet API result functions specific to the used API spec version.
+ *
+ * @author Rene Gielen
+ */
+
+public interface PortletResultHelper {
+
+    /**
+     * Set a render parameter, abstracted from the used Portlet API version
+     *
+     * @param response The response to set the parameter on.
+     * @param key      The parameter key to set.
+     * @param value    The parameter value to set.
+     */
+    void setRenderParameter( PortletResponse response, String key, String value );
+
+    /**
+     * Set a portlet mode, abstracted from the used Portlet API version
+     *
+     * @param response    The response to set the portlet mode on.
+     * @param portletMode The portlet mode to set.
+     */
+    void setPortletMode( PortletResponse response, PortletMode portletMode ) throws PortletModeException;
+
+    /**
+     * Call a dispatcher's include method, abstracted from the used Portlet API version.
+     *
+     * @param dispatcher  The dispatcher to call the include method on.
+     * @param contentType The content type to set for the response.
+     * @param request     The request to use for including
+     * @param response    The response to use for including
+     */
+    void include( PortletRequestDispatcher dispatcher, String contentType, PortletRequest request,
+                  PortletResponse response ) throws IOException, PortletException;
+}

Added: struts/struts2/trunk/plugins/portlet/src/main/java/org/apache/struts2/portlet/result/PortletResultHelperJSR168.java
URL: http://svn.apache.org/viewvc/struts/struts2/trunk/plugins/portlet/src/main/java/org/apache/struts2/portlet/result/PortletResultHelperJSR168.java?rev=1139066&view=auto
==============================================================================
--- struts/struts2/trunk/plugins/portlet/src/main/java/org/apache/struts2/portlet/result/PortletResultHelperJSR168.java (added)
+++ struts/struts2/trunk/plugins/portlet/src/main/java/org/apache/struts2/portlet/result/PortletResultHelperJSR168.java Thu Jun 23 20:28:45 2011
@@ -0,0 +1,54 @@
+package org.apache.struts2.portlet.result;
+
+import javax.portlet.*;
+import java.io.IOException;
+
+/**
+ * PortletResultHelperJSR168 implements PortletResultHelper for Portlet 1.0 API (JSR168).
+ *
+ * @author Rene Gielen
+ */
+public class PortletResultHelperJSR168 implements PortletResultHelper {
+
+    /**
+     * Set a render parameter, abstracted from the used Portlet API version. This implementation assumes that the given
+     * response must be a {@link javax.portlet.ActionResponse}, as JSR168 implies.
+     *
+     * @param response The response to set the parameter on.
+     * @param key      The parameter key to set.
+     * @param value    The parameter value to set.
+     */
+    public void setRenderParameter( PortletResponse response, String key, String value ) {
+        ((ActionResponse) response).setRenderParameter(key, value);
+    }
+
+    /**
+     * Set a portlet mode, abstracted from the used Portlet API version. This implementation assumes that the given
+     * response must be a {@link javax.portlet.ActionResponse}, as JSR168 implies.
+     *
+     * @param response    The response to set the portlet mode on.
+     * @param portletMode The portlet mode to set.
+     */
+    public void setPortletMode( PortletResponse response, PortletMode portletMode ) throws PortletModeException {
+        ((ActionResponse) response).setPortletMode(portletMode);
+    }
+
+    /**
+     * Call a dispatcher's include method, abstracted from the used Portlet API version. This implementation assumes
+     * that the given the request must be a {@link javax.portlet.RenderRequest} and the response must be a {@link
+     * javax.portlet.RenderResponse}, as JSR168 implies.
+     *
+     * @param dispatcher  The dispatcher to call the include method on.
+     * @param contentType The content type to set for the response.
+     * @param request     The request to use for including
+     * @param response    The response to use for including
+     */
+    public void include( PortletRequestDispatcher dispatcher, String contentType, PortletRequest request,
+                         PortletResponse response ) throws IOException, PortletException {
+        RenderRequest req = (RenderRequest) request;
+        RenderResponse res = (RenderResponse) response;
+        res.setContentType(contentType);
+        dispatcher.include(req, res);
+    }
+
+}
\ No newline at end of file