WICKET-6503 reintroduced markRendering

- so rendered page or part checks hierarchy changes while rendering
- stateless pages can be unmarked after beforeRender() in 
PageAndComponentProvider
- prevent multiple onBeforeRender() calls for auto components that are already 
added


Project: http://git-wip-us.apache.org/repos/asf/wicket/repo
Commit: http://git-wip-us.apache.org/repos/asf/wicket/commit/d21bfe32
Tree: http://git-wip-us.apache.org/repos/asf/wicket/tree/d21bfe32
Diff: http://git-wip-us.apache.org/repos/asf/wicket/diff/d21bfe32

Branch: refs/heads/WICKET-6498_deferred_javascript_2
Commit: d21bfe32525151a235afb3a6288ea11bcfa15329
Parents: 2e4496e
Author: Sven Meier <[email protected]>
Authored: Sat Jan 27 22:02:46 2018 +0100
Committer: Sven Meier <[email protected]>
Committed: Sat Jan 27 22:47:43 2018 +0100

----------------------------------------------------------------------
 .../main/java/org/apache/wicket/Component.java  | 32 +++++++++
 .../java/org/apache/wicket/MarkupContainer.java | 15 +++++
 .../src/main/java/org/apache/wicket/Page.java   |  2 +
 .../handler/PageAndComponentProvider.java       |  1 +
 .../org/apache/wicket/MarkupContainerTest.java  | 71 +++++++++++++-------
 5 files changed, 97 insertions(+), 24 deletions(-)
----------------------------------------------------------------------


http://git-wip-us.apache.org/repos/asf/wicket/blob/d21bfe32/wicket-core/src/main/java/org/apache/wicket/Component.java
----------------------------------------------------------------------
diff --git a/wicket-core/src/main/java/org/apache/wicket/Component.java 
b/wicket-core/src/main/java/org/apache/wicket/Component.java
index fc32b09..c1ae823 100644
--- a/wicket-core/src/main/java/org/apache/wicket/Component.java
+++ b/wicket-core/src/main/java/org/apache/wicket/Component.java
@@ -2117,6 +2117,23 @@ public abstract class Component
        }
 
        /**
+        * THIS METHOD IS NOT PART OF THE WICKET PUBLIC API. DO NOT USE IT!
+        * 
+        * Sets the RENDERING flag and removes the PREPARED_FOR_RENDER flag on 
component and it's
+        * children.
+        * 
+        * @param setRenderingFlag
+        *            if this is false only the PREPARED_FOR_RENDER flag is 
removed from component, the
+        *            RENDERING flag is not set.
+        * 
+        * @see #internalPrepareForRender(boolean)
+        */
+       public final void markRendering(boolean setRenderingFlag)
+       {
+               internalMarkRendering(setRenderingFlag);
+       }
+
+       /**
         * Called to indicate that the model content for this component has 
been changed
         */
        public final void modelChanged()
@@ -2190,6 +2207,8 @@ public abstract class Component
 
                page.startComponentRender(this);
 
+               markRendering(true);
+
                render();
                
                page.endComponentRender(this);
@@ -3790,6 +3809,7 @@ public abstract class Component
         */
        protected void onBeforeRender()
        {
+               setRequestFlag(RFLAG_PREPARED_FOR_RENDER, true);
                onBeforeRenderChildren();
                setRequestFlag(RFLAG_BEFORE_RENDER_SUPER_CALL_VERIFIED, true);
        }
@@ -4132,6 +4152,18 @@ public abstract class Component
        }
 
        /**
+        * @param setRenderingFlag
+        *            rendering flag
+        */
+       void internalMarkRendering(boolean setRenderingFlag)
+       {
+               // WICKET-5460 no longer prepared for render
+               setRequestFlag(RFLAG_PREPARED_FOR_RENDER, false);
+
+               setRequestFlag(RFLAG_RENDERING, setRenderingFlag);
+       }
+
+       /**
         * @return True if this component or any of its parents is in auto-add 
mode
         */
        public final boolean isAuto()

http://git-wip-us.apache.org/repos/asf/wicket/blob/d21bfe32/wicket-core/src/main/java/org/apache/wicket/MarkupContainer.java
----------------------------------------------------------------------
diff --git a/wicket-core/src/main/java/org/apache/wicket/MarkupContainer.java 
b/wicket-core/src/main/java/org/apache/wicket/MarkupContainer.java
index aad0aac..038585d 100644
--- a/wicket-core/src/main/java/org/apache/wicket/MarkupContainer.java
+++ b/wicket-core/src/main/java/org/apache/wicket/MarkupContainer.java
@@ -1695,6 +1695,21 @@ public abstract class MarkupContainer extends Component 
implements Iterable<Comp
        }
 
        /**
+        * 
+        * @see org.apache.wicket.Component#internalMarkRendering(boolean)
+        */
+       @Override
+       void internalMarkRendering(boolean setRenderingFlag)
+       {
+               super.internalMarkRendering(setRenderingFlag);
+
+               for (Component child : this)
+               {
+                       child.internalMarkRendering(setRenderingFlag);
+               }
+       }
+
+       /**
         * @return a copy of the children array.
         */
        @SuppressWarnings("unchecked")

http://git-wip-us.apache.org/repos/asf/wicket/blob/d21bfe32/wicket-core/src/main/java/org/apache/wicket/Page.java
----------------------------------------------------------------------
diff --git a/wicket-core/src/main/java/org/apache/wicket/Page.java 
b/wicket-core/src/main/java/org/apache/wicket/Page.java
index 9b8dc7f..ca8a874 100644
--- a/wicket-core/src/main/java/org/apache/wicket/Page.java
+++ b/wicket-core/src/main/java/org/apache/wicket/Page.java
@@ -995,6 +995,8 @@ public abstract class Page extends MarkupContainer
                                delay.release();
                        }
 
+                       markRendering(true);
+                       
                        render();
                }
                finally

http://git-wip-us.apache.org/repos/asf/wicket/blob/d21bfe32/wicket-core/src/main/java/org/apache/wicket/core/request/handler/PageAndComponentProvider.java
----------------------------------------------------------------------
diff --git 
a/wicket-core/src/main/java/org/apache/wicket/core/request/handler/PageAndComponentProvider.java
 
b/wicket-core/src/main/java/org/apache/wicket/core/request/handler/PageAndComponentProvider.java
index de59ecc..79b8d0d 100644
--- 
a/wicket-core/src/main/java/org/apache/wicket/core/request/handler/PageAndComponentProvider.java
+++ 
b/wicket-core/src/main/java/org/apache/wicket/core/request/handler/PageAndComponentProvider.java
@@ -170,6 +170,7 @@ public class PageAndComponentProvider extends PageProvider 
implements IPageAndCo
                                        Page p = (Page)page;
                                        p.internalInitialize();
                                        p.beforeRender();
+                                       p.markRendering(false);
                                        component = page.get(componentPath);
                                }
                        }

http://git-wip-us.apache.org/repos/asf/wicket/blob/d21bfe32/wicket-core/src/test/java/org/apache/wicket/MarkupContainerTest.java
----------------------------------------------------------------------
diff --git 
a/wicket-core/src/test/java/org/apache/wicket/MarkupContainerTest.java 
b/wicket-core/src/test/java/org/apache/wicket/MarkupContainerTest.java
index 4ab69da..8be4fe8 100644
--- a/wicket-core/src/test/java/org/apache/wicket/MarkupContainerTest.java
+++ b/wicket-core/src/test/java/org/apache/wicket/MarkupContainerTest.java
@@ -25,7 +25,6 @@ import static org.hamcrest.CoreMatchers.sameInstance;
 import static org.hamcrest.Matchers.greaterThanOrEqualTo;
 
 import java.lang.reflect.Field;
-import java.util.ConcurrentModificationException;
 import java.util.Iterator;
 import java.util.List;
 import java.util.Optional;
@@ -153,6 +152,43 @@ public class MarkupContainerTest extends WicketTestCase
                assertEquals(2, page.beforeRenderCalls);
        }
 
+       @Test
+       public void hierarchyChangeDuringRender()
+       {
+               HierarchyChangePage page = new HierarchyChangePage();
+               try
+               {
+                       tester.startPage(page);
+                       fail();
+               }
+               catch (WicketRuntimeException expected)
+               {
+                       assertEquals(
+                               "Cannot modify component hierarchy after render 
phase has started (page version cant change then anymore)",
+                               expected.getMessage());
+               }
+       }
+
+       private static class HierarchyChangePage extends WebPage
+               implements
+                       IMarkupResourceStreamProvider
+       {
+
+               @Override
+               protected void onRender()
+               {
+                       // change hierarchy during render
+                       add(new Label("child"));
+               }
+
+               @Override
+               public IResourceStream getMarkupResourceStream(MarkupContainer 
container,
+                       Class<?> containerClass)
+               {
+                       return new 
StringResourceStream("<html><body></body></html>");
+               }
+       }
+
        /**
         * https://issues.apache.org/jira/browse/WICKET-4012
         */
@@ -1274,28 +1310,23 @@ public class MarkupContainerTest extends WicketTestCase
        public void stream()
        {
                LoginPage loginPage = new LoginPage();
-               Optional<Component> first = loginPage.stream()
-                       .filter(c -> c.getId().equals("form"))
+               Optional<Component> first = loginPage.stream().filter(c -> 
c.getId().equals("form"))
                        .findFirst();
                assertThat(first.isPresent(), is(false));
 
                loginPage.add(new Form<>("form"));
-               Optional<Component> second = loginPage.stream()
-                       .filter(c -> c.getId().equals("form"))
+               Optional<Component> second = loginPage.stream().filter(c -> 
c.getId().equals("form"))
                        .findFirst();
                assertThat(second.isPresent(), is(true));
 
                loginPage.add(new WebMarkupContainer("wmc"));
 
-               Optional<Form> form = loginPage.stream()
-                       .filter(Form.class::isInstance)
-                       .map(Form.class::cast)
-                       .findFirst();
+               Optional<Form> form = 
loginPage.stream().filter(Form.class::isInstance)
+                       .map(Form.class::cast).findFirst();
                assertThat(form.isPresent(), is(true));
 
                Optional<WebMarkupContainer> wmc = loginPage.stream()
-                       .filter(WebMarkupContainer.class::isInstance)
-                       .map(WebMarkupContainer.class::cast)
+                       
.filter(WebMarkupContainer.class::isInstance).map(WebMarkupContainer.class::cast)
                        .findFirst();
                assertThat(wmc.isPresent(), is(true));
        }
@@ -1304,8 +1335,7 @@ public class MarkupContainerTest extends WicketTestCase
        public void streamChildren()
        {
                LoginPage loginPage = new LoginPage();
-               Optional<Component> first = loginPage.stream()
-                       .filter(c -> c.getId().equals("form"))
+               Optional<Component> first = loginPage.stream().filter(c -> 
c.getId().equals("form"))
                        .findFirst();
                assertThat(first.isPresent(), is(false));
 
@@ -1314,20 +1344,13 @@ public class MarkupContainerTest extends WicketTestCase
 
                form.add(new TextField<>("field"));
 
-               assertThat(loginPage.streamChildren()
-                       .filter(c -> c.getId().equals("form"))
-                       .findFirst()
+               assertThat(loginPage.streamChildren().filter(c -> 
c.getId().equals("form")).findFirst()
                        .isPresent(), is(true));
 
-               assertThat(loginPage.streamChildren()
-                       .filter(c -> c.getId().equals("field"))
-                       .findFirst()
+               assertThat(loginPage.streamChildren().filter(c -> 
c.getId().equals("field")).findFirst()
                        .isPresent(), is(true));
 
-               assertThat(loginPage.streamChildren()
-                       .filter(TextField.class::isInstance)
-                       .filter(c -> c.getId().equals("field"))
-                       .findFirst()
-                       .isPresent(), is(true));
+               
assertThat(loginPage.streamChildren().filter(TextField.class::isInstance)
+                       .filter(c -> 
c.getId().equals("field")).findFirst().isPresent(), is(true));
        }
 }

Reply via email to