Revision: 1285
          http://stripes.svn.sourceforge.net/stripes/?rev=1285&view=rev
Author:   bengunter
Date:     2010-09-28 20:03:24 +0000 (Tue, 28 Sep 2010)

Log Message:
-----------
STS-391: Ensure that only one component renderer gets created for each 
component defined as a child of a render tag. The same renderer should be 
reused for the whole render process.

Modified Paths:
--------------
    
branches/1.5.x/stripes/src/net/sourceforge/stripes/tag/layout/LayoutComponentTag.java
    
branches/1.5.x/stripes/src/net/sourceforge/stripes/tag/layout/LayoutDefinitionTag.java
    
branches/1.5.x/stripes/src/net/sourceforge/stripes/tag/layout/LayoutRenderTag.java
    branches/1.5.x/stripes/src/net/sourceforge/stripes/tag/layout/LayoutTag.java

Modified: 
branches/1.5.x/stripes/src/net/sourceforge/stripes/tag/layout/LayoutComponentTag.java
===================================================================
--- 
branches/1.5.x/stripes/src/net/sourceforge/stripes/tag/layout/LayoutComponentTag.java
       2010-09-28 18:24:42 UTC (rev 1284)
+++ 
branches/1.5.x/stripes/src/net/sourceforge/stripes/tag/layout/LayoutComponentTag.java
       2010-09-28 20:03:24 UTC (rev 1285)
@@ -116,14 +116,22 @@
                     log.debug("No-op for ", getName(), " in ", 
context.getDefinitionPage());
                 }
                 else if (isChildOfComponent()) {
-                    if (isCurrentComponent()) {
-                        LayoutComponentTag parent = getLayoutAncestor();
-                        if (getName().equals(parent.getName())) {
-                            log.debug("Invoke layout component renderer for 
recursive render");
-                            LayoutComponentRenderer renderer = 
(LayoutComponentRenderer) pageContext
-                                    .getAttribute(getName());
-                            renderer.write();
-                        }
+                    // Use a layout component renderer to do the heavy lifting
+                    log.debug("Invoke layout component renderer for nested 
render");
+                    LayoutComponentRenderer renderer = 
(LayoutComponentRenderer) pageContext
+                            .getAttribute(getName());
+                    if (renderer == null)
+                        log.debug("No component renderer in page context for 
'" + getName() + "'");
+                    boolean rendered = renderer != null && renderer.write();
+
+                    // If the component did not render then we need to output 
the default contents
+                    // from the layout definition.
+                    if (!rendered) {
+                        log.debug("Component was not present in ", 
context.getRenderPage(),
+                                " so using default content from ", 
context.getDefinitionPage());
+
+                        context.getOut().setSilent(false, pageContext);
+                        return EVAL_BODY_INCLUDE;
                     }
                 }
             }
@@ -142,10 +150,12 @@
                 }
                 else if (isChildOfDefinition()) {
                     // Use a layout component renderer to do the heavy lifting
-                    log.debug("Invoke layout component renderer for recursive 
render");
-                    LayoutComponentRenderer renderer = new 
LayoutComponentRenderer(getName());
-                    renderer.pushPageContext(pageContext);
-                    boolean rendered = renderer.write();
+                    log.debug("Invoke layout component renderer for nested 
render");
+                    LayoutComponentRenderer renderer = 
(LayoutComponentRenderer) pageContext
+                            .getAttribute(getName());
+                    if (renderer == null)
+                        log.debug("No component renderer in page context for 
'" + getName() + "'");
+                    boolean rendered = renderer != null && renderer.write();
 
                     // If the component did not render then we need to output 
the default contents
                     // from the layout definition.

Modified: 
branches/1.5.x/stripes/src/net/sourceforge/stripes/tag/layout/LayoutDefinitionTag.java
===================================================================
--- 
branches/1.5.x/stripes/src/net/sourceforge/stripes/tag/layout/LayoutDefinitionTag.java
      2010-09-28 18:24:42 UTC (rev 1284)
+++ 
branches/1.5.x/stripes/src/net/sourceforge/stripes/tag/layout/LayoutDefinitionTag.java
      2010-09-28 20:03:24 UTC (rev 1285)
@@ -15,7 +15,6 @@
 package net.sourceforge.stripes.tag.layout;
 
 import java.util.Map;
-import java.util.Map.Entry;
 
 import javax.servlet.jsp.JspException;
 import javax.servlet.jsp.PageContext;
@@ -77,12 +76,7 @@
         }
 
         // Put component renderers into the page context, even those from 
previous contexts
-        for (LayoutContext c = LayoutContext.getOuterContext(context); c != 
null; c = c.getNext()) {
-            for (Entry<String, LayoutComponentRenderer> entry : 
c.getComponents().entrySet()) {
-                entry.getValue().pushPageContext(pageContext);
-                pageContext.setAttribute(entry.getKey(), entry.getValue());
-            }
-        }
+        exportComponentRenderers();
 
         // Enable output only if this is the definition execution, not a 
component render
         context.getOut().setSilent(renderPhase, pageContext);
@@ -97,19 +91,8 @@
     @Override
     public int doEndTag() throws JspException {
         try {
-            LayoutContext context = getContext();
-            if (!renderPhase) {
-                // Pop our page context off the renderers' page context stack
-                for (LayoutContext c = LayoutContext.getOuterContext(context); 
c != null; c = c.getNext()) {
-                    for (LayoutComponentRenderer renderer : 
c.getComponents().values()) {
-                        renderer.popPageContext();
-                    }
-                }
-            }
-
-            // Restore output's silent flag
-            context.getOut().setSilent(silent, pageContext);
-
+            cleanUpComponentRenderers();
+            getContext().getOut().setSilent(silent, pageContext);
             return SKIP_PAGE;
         }
         finally {

Modified: 
branches/1.5.x/stripes/src/net/sourceforge/stripes/tag/layout/LayoutRenderTag.java
===================================================================
--- 
branches/1.5.x/stripes/src/net/sourceforge/stripes/tag/layout/LayoutRenderTag.java
  2010-09-28 18:24:42 UTC (rev 1284)
+++ 
branches/1.5.x/stripes/src/net/sourceforge/stripes/tag/layout/LayoutRenderTag.java
  2010-09-28 20:03:24 UTC (rev 1285)
@@ -90,8 +90,9 @@
         }
 
         if (context.isComponentRenderPhase()) {
-            log.debug("Start component render phase for ", 
context.getComponent(), " in ", context
-                    .getRenderPage());
+            log.debug("Start component render phase for ", 
context.getComponent(), " in ",
+                    context.getRenderPage());
+            exportComponentRenderers();
         }
 
         // Render tags never output their contents directly
@@ -161,6 +162,7 @@
             if (context.isComponentRenderPhase()) {
                 log.debug("End component render phase for ", 
context.getComponent(), " in ",
                         context.getRenderPage());
+                cleanUpComponentRenderers();
             }
 
             // Restore output's silent flag

Modified: 
branches/1.5.x/stripes/src/net/sourceforge/stripes/tag/layout/LayoutTag.java
===================================================================
--- 
branches/1.5.x/stripes/src/net/sourceforge/stripes/tag/layout/LayoutTag.java    
    2010-09-28 18:24:42 UTC (rev 1284)
+++ 
branches/1.5.x/stripes/src/net/sourceforge/stripes/tag/layout/LayoutTag.java    
    2010-09-28 20:03:24 UTC (rev 1285)
@@ -14,6 +14,8 @@
  */
 package net.sourceforge.stripes.tag.layout;
 
+import java.util.Map.Entry;
+
 import javax.servlet.http.HttpServletRequest;
 import javax.servlet.jsp.tagext.Tag;
 
@@ -80,4 +82,29 @@
 
         return (T) layoutAncestor;
     }
+
+    /**
+     * Starting from the outer-most context and working up the stack, put a 
reference to each
+     * component renderer by name into the page context and push this tag's 
page context onto the
+     * renderer's page context stack. Working from the bottom of the stack up 
ensures that newly
+     * defined components override any that might have been defined previously 
by the same name.
+     */
+    public void exportComponentRenderers() {
+        LayoutContext outer = 
LayoutContext.getOuterContext(LayoutContext.lookup(pageContext));
+        for (LayoutContext c = outer; c != null; c = c.getNext()) {
+            for (Entry<String, LayoutComponentRenderer> entry : 
c.getComponents().entrySet()) {
+                entry.getValue().pushPageContext(pageContext);
+                pageContext.setAttribute(entry.getKey(), entry.getValue());
+            }
+        }
+    }
+
+    /** Pop this tag's page context off each of the component renderers' page 
context stacks. */
+    public void cleanUpComponentRenderers() {
+        for (LayoutContext c = LayoutContext.lookup(pageContext); c != null; c 
= c.getPrevious()) {
+            for (LayoutComponentRenderer renderer : 
c.getComponents().values()) {
+                renderer.popPageContext();
+            }
+        }
+    }
 }


This was sent by the SourceForge.net collaborative development platform, the 
world's largest Open Source development site.

------------------------------------------------------------------------------
Start uncovering the many advantages of virtual appliances
and start using them to simplify application deployment and
accelerate your shift to cloud computing.
http://p.sf.net/sfu/novell-sfdev2dev
_______________________________________________
Stripes-development mailing list
[email protected]
https://lists.sourceforge.net/lists/listinfo/stripes-development

Reply via email to