You are viewing a plain text version of this content. The canonical link for it is here.
Posted to commits@myfaces.apache.org by gp...@apache.org on 2013/12/17 12:20:48 UTC

svn commit: r1551515 - in /myfaces/extensions/cdi/trunk/jee-modules/jsf20-module/impl/src/main/java/org/apache/myfaces/extensions/cdi/jsf2/impl/navigation: CodiNavigationHandler.java NavigationCaseMapWrapper.java

Author: gpetracek
Date: Tue Dec 17 11:20:48 2013
New Revision: 1551515

URL: http://svn.apache.org/r1551515
Log:
EXTCDI-311 support external handling of navigation-cases

Modified:
    myfaces/extensions/cdi/trunk/jee-modules/jsf20-module/impl/src/main/java/org/apache/myfaces/extensions/cdi/jsf2/impl/navigation/CodiNavigationHandler.java
    myfaces/extensions/cdi/trunk/jee-modules/jsf20-module/impl/src/main/java/org/apache/myfaces/extensions/cdi/jsf2/impl/navigation/NavigationCaseMapWrapper.java

Modified: myfaces/extensions/cdi/trunk/jee-modules/jsf20-module/impl/src/main/java/org/apache/myfaces/extensions/cdi/jsf2/impl/navigation/CodiNavigationHandler.java
URL: http://svn.apache.org/viewvc/myfaces/extensions/cdi/trunk/jee-modules/jsf20-module/impl/src/main/java/org/apache/myfaces/extensions/cdi/jsf2/impl/navigation/CodiNavigationHandler.java?rev=1551515&r1=1551514&r2=1551515&view=diff
==============================================================================
--- myfaces/extensions/cdi/trunk/jee-modules/jsf20-module/impl/src/main/java/org/apache/myfaces/extensions/cdi/jsf2/impl/navigation/CodiNavigationHandler.java (original)
+++ myfaces/extensions/cdi/trunk/jee-modules/jsf20-module/impl/src/main/java/org/apache/myfaces/extensions/cdi/jsf2/impl/navigation/CodiNavigationHandler.java Tue Dec 17 11:20:48 2013
@@ -197,7 +197,7 @@ public class CodiNavigationHandler exten
             return result;
         }
 
-        return new NavigationCaseMapWrapper(result);
+        return new NavigationCaseMapWrapper(result, this.wrapped);
     }
 
     /**

Modified: myfaces/extensions/cdi/trunk/jee-modules/jsf20-module/impl/src/main/java/org/apache/myfaces/extensions/cdi/jsf2/impl/navigation/NavigationCaseMapWrapper.java
URL: http://svn.apache.org/viewvc/myfaces/extensions/cdi/trunk/jee-modules/jsf20-module/impl/src/main/java/org/apache/myfaces/extensions/cdi/jsf2/impl/navigation/NavigationCaseMapWrapper.java?rev=1551515&r1=1551514&r2=1551515&view=diff
==============================================================================
--- myfaces/extensions/cdi/trunk/jee-modules/jsf20-module/impl/src/main/java/org/apache/myfaces/extensions/cdi/jsf2/impl/navigation/NavigationCaseMapWrapper.java (original)
+++ myfaces/extensions/cdi/trunk/jee-modules/jsf20-module/impl/src/main/java/org/apache/myfaces/extensions/cdi/jsf2/impl/navigation/NavigationCaseMapWrapper.java Tue Dec 17 11:20:48 2013
@@ -25,7 +25,9 @@ import org.apache.myfaces.extensions.cdi
 import org.apache.myfaces.extensions.cdi.jsf.impl.util.JsfUtils;
 import org.apache.myfaces.extensions.cdi.jsf.impl.util.RequestParameter;
 
+import javax.faces.application.ConfigurableNavigationHandler;
 import javax.faces.application.NavigationCase;
+import javax.faces.application.NavigationHandler;
 import javax.faces.context.ExternalContext;
 import javax.faces.context.FacesContext;
 import java.util.List;
@@ -34,6 +36,7 @@ import java.util.Map;
 import java.util.HashSet;
 import java.util.HashMap;
 import java.util.Collection;
+import java.util.logging.Logger;
 
 /**
  * Destructive operations aren't supported (compared to the SubKeyMap used in MyFaces).
@@ -41,22 +44,39 @@ import java.util.Collection;
  */
 class NavigationCaseMapWrapper implements Map<String, Set<NavigationCase>>
 {
+    private static final Logger LOG = Logger.getLogger(NavigationCaseMapWrapper.class.getName());
+
     private Map<String, Set<NavigationCase>> wrappedNavigationCaseMap;
+    private NavigationHandler wrapped;
     private final Map<String, Set<NavigationCase>> viewConfigBasedNavigationCaseCache;
 
     /**
      * Constructor for wrapping the given navigation-cases
      * @param navigationCases current navigation-cases
+     * @param wrapped
      */
-    public NavigationCaseMapWrapper(Map<String, Set<NavigationCase>> navigationCases)
+    public NavigationCaseMapWrapper(Map<String, Set<NavigationCase>> navigationCases, NavigationHandler wrapped)
     {
         this.wrappedNavigationCaseMap = navigationCases;
+        this.wrapped = wrapped;
         this.viewConfigBasedNavigationCaseCache = createViewConfigBasedNavigationCases(false);
     }
 
     private Map<String, Set<NavigationCase>> createViewConfigBasedNavigationCases(boolean allowParameters)
     {
-        Map<String, Set<NavigationCase>> result = new HashMap<String, Set<NavigationCase>>();
+        Map<String, Set<NavigationCase>> result;
+
+        if (this.wrapped instanceof ConfigurableNavigationHandler)
+        {
+            result = new DelegatingMap((ConfigurableNavigationHandler)this.wrapped);
+        }
+        else
+        {
+            LOG.warning("the wrapped navigation-handler doesn't extend " +
+                ConfigurableNavigationHandler.class.getName() +
+                    ". therefore std. navigation-rules might not work correctly with mojarra");
+            result = new HashMap<String, Set<NavigationCase>>();
+        }
 
         Collection<ViewConfigDescriptor> viewConfigDescriptors = ViewConfigCache.getViewConfigDescriptors();
 
@@ -233,4 +253,70 @@ class NavigationCaseMapWrapper implement
         result.addAll(createViewConfigBasedNavigationCases(true).entrySet());
         return result;
     }
+
+    //currently not a complete handling, but enough to fix the issues with mojarra
+    private class DelegatingMap extends HashMap<String, Set<NavigationCase>>
+    {
+        private static final long serialVersionUID = -955468874397821639L;
+        private final ConfigurableNavigationHandler wrapped;
+
+        private DelegatingMap(ConfigurableNavigationHandler wrapped)
+        {
+            this.wrapped = wrapped;
+        }
+
+        @Override
+        public Set<NavigationCase> put(String key, Set<NavigationCase> value)
+        {
+            //delegate to the wrapped instance -> the innermost handler needs to receive it
+            //(because mojarra uses ConfigurableNavigationHandler#getNavigationCases
+            // to add cases for std. nav.rules from the outside)
+            return this.wrapped.getNavigationCases().put(key, value);
+        }
+
+        @Override
+        public Set<NavigationCase> get(Object key)
+        {
+            Set<NavigationCase> navigationCases = super.get(key);
+            if (navigationCases == null)
+            {
+                navigationCases = new HashSet<NavigationCase>();
+                put((String)key, navigationCases);
+            }
+
+            return new DelegatingSet(navigationCases, this.wrapped, (String)key);
+        }
+    }
+
+    //currently not a complete handling, but enough to fix the issues with mojarra
+    private class DelegatingSet extends HashSet<NavigationCase>
+    {
+        private static final long serialVersionUID = -7040572530963900394L;
+
+        private final ConfigurableNavigationHandler wrapped;
+        private String navigationCaseKey;
+
+        private DelegatingSet(Collection<? extends NavigationCase> c,
+                              ConfigurableNavigationHandler wrapped,
+                              String navigationCaseKey)
+        {
+            super(c);
+            this.wrapped = wrapped;
+            this.navigationCaseKey = navigationCaseKey;
+        }
+
+        @Override
+        public boolean add(NavigationCase navigationCase)
+        {
+            Set<NavigationCase> navigationCases = this.wrapped.getNavigationCases().get(this.navigationCaseKey);
+
+            if (navigationCases == null)
+            {
+                navigationCases = new HashSet<NavigationCase>();
+                this.wrapped.getNavigationCases().put(this.navigationCaseKey, navigationCases);
+            }
+
+            return navigationCases.add(navigationCase);
+        }
+    }
 }