You are viewing a plain text version of this content. The canonical link for it is here.
Posted to commits@wicket.apache.org by cm...@apache.org on 2014/09/27 21:25:00 UTC
git commit: WICKET-5677 add onReAdd to Component
Repository: wicket
Updated Branches:
refs/heads/master 572df1583 -> 623da3924
WICKET-5677 add onReAdd to Component
Squashed commit of the following:
commit fab66e85410c14b7a0ede5c953e315a7e5143e3d
Merge: 10d83d2 c728d89
Author: Carl-Eric Menzel <cm...@wicketbuch.de>
Date: Sat Sep 27 19:35:52 2014 +0200
Merge branch 'wicket-6.x' into WICKET-5677
commit 10d83d2932c53dd165dbcc4c3f226f4597c142de
Author: Carl-Eric Menzel <cm...@wicketbuch.de>
Date: Tue Aug 26 23:38:17 2014 +0200
WICKET-5677 readd should only be called after a remove, never before
commit 0a8e964f1a3c3226f52ab22137455acf55f45c74
Merge: 055958a 3a5648b
Author: Carl-Eric Menzel <cm...@apache.org>
Date: Mon Aug 25 07:41:06 2014 +0200
Merge branch 'wicket-6.x' into WICKET-5677
commit 055958a9c60db45d96c1828803dbee37e5926678
Author: Carl-Eric Menzel <cm...@wicketbuch.de>
Date: Mon Aug 25 07:23:57 2014 +0200
add re_added flag
commit 348e9dbc899c3a62eccf7c50739162b0c0be63c2
Merge: 40c4210 c3eb7e2
Author: Carl-Eric Menzel <cm...@wicketbuch.de>
Date: Fri Aug 22 00:29:16 2014 +0200
Merge remote-tracking branch 'github/WICKET-5677' into WICKET-5677
Conflicts:
wicket-core/src/main/java/org/apache/wicket/Component.java
wicket-core/src/main/java/org/apache/wicket/MarkupContainer.java
commit c3eb7e24954d3909c74201682dba5e4de8fcadd4
Author: Carl-Eric Menzel <cm...@apache.org>
Date: Mon Aug 18 14:08:16 2014 +0200
WICKET-5677 clean up tests
commit 4703c1ae1af91fdcca44e34edbeeb8bbaeb63b6c
Author: Carl-Eric Menzel <cm...@apache.org>
Date: Mon Aug 18 13:35:44 2014 +0200
WICKET-5677 change onadd to onReAdd and only call when oninitialize wouldn't be called
commit 70b7327d2ce142707171cd31a1b612cffaa7a066
Author: Carl-Eric Menzel <cm...@apache.org>
Date: Mon Aug 18 11:27:24 2014 +0200
added javadoc
commit 9a6ba692a48b76c30ead6915d4bc43275a255b3c
Author: Carl-Eric Menzel <cm...@wicketbuch.de>
Date: Mon Aug 18 10:42:33 2014 +0200
WICKET-5677: add onAddToPage lifecycle event
commit 40c42104f9882b938dd84e8469f2922efebd2ce3
Author: Carl-Eric Menzel <cm...@wicketbuch.de>
Date: Mon Aug 18 10:42:33 2014 +0200
WICKET-5677: add onAddToPage lifecycle event
(cherry picked from commit 0adb864ff18951a9630bd2339fb9e92963867d4a)
Conflicts:
wicket-core/src/main/java/org/apache/wicket/Component.java
wicket-core/src/main/java/org/apache/wicket/MarkupContainer.java
Project: http://git-wip-us.apache.org/repos/asf/wicket/repo
Commit: http://git-wip-us.apache.org/repos/asf/wicket/commit/623da392
Tree: http://git-wip-us.apache.org/repos/asf/wicket/tree/623da392
Diff: http://git-wip-us.apache.org/repos/asf/wicket/diff/623da392
Branch: refs/heads/master
Commit: 623da39243372d2e5a93d7e2ead8c47921929d59
Parents: 572df15
Author: Carl-Eric Menzel <cm...@wicketbuch.de>
Authored: Sat Sep 27 21:24:00 2014 +0200
Committer: Carl-Eric Menzel <cm...@wicketbuch.de>
Committed: Sat Sep 27 21:24:00 2014 +0200
----------------------------------------------------------------------
.../main/java/org/apache/wicket/Component.java | 49 ++++-
.../java/org/apache/wicket/MarkupContainer.java | 4 +-
.../java/org/apache/wicket/OnReAddTest.java | 215 +++++++++++++++++++
3 files changed, 264 insertions(+), 4 deletions(-)
----------------------------------------------------------------------
http://git-wip-us.apache.org/repos/asf/wicket/blob/623da392/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 a47d728..2b248de 100644
--- a/wicket-core/src/main/java/org/apache/wicket/Component.java
+++ b/wicket-core/src/main/java/org/apache/wicket/Component.java
@@ -377,8 +377,8 @@ public abstract class Component
protected static final int FLAG_RESERVED5 = 0x10000;
/** onInitialize called */
protected static final int FLAG_INITIALIZED = 0x20000;
- /** Reserved subclass-definable flag bit */
- private static final int FLAG_NOTUSED7 = 0x40000;
+ /** Set when a component is removed from the hierarchy */
+ private static final int FLAG_REMOVED = 0x40000;
/** Reserved subclass-definable flag bit */
protected static final int FLAG_RESERVED8 = 0x80000;
@@ -410,7 +410,7 @@ public abstract class Component
private static final int FLAG_VISIBILITY_ALLOWED = 0x40000000;
private static final int FLAG_DETACHING = 0x80000000;
-
+
/**
* The name of attribute that will hold markup id
*/
@@ -447,6 +447,7 @@ public abstract class Component
private static final short RFLAG_BEFORE_RENDER_SUPER_CALL_VERIFIED = 0x20;
private static final short RFLAG_INITIALIZE_SUPER_CALL_VERIFIED = 0x40;
protected static final short RFLAG_CONTAINER_DEQUEING = 0x80;
+ private static final short RFLAG_ON_RE_ADD_SUPER_CALL_VERIFIED = 0x100;
/**
* Flags that only keep their value during the request. Useful for cache markers, etc. At the
@@ -885,6 +886,22 @@ public abstract class Component
getApplication().getComponentInitializationListeners().onInitialize(this);
}
+ else
+ {
+ if (getFlag(FLAG_REMOVED))
+ {
+ setFlag(FLAG_REMOVED, false);
+ setRequestFlag(RFLAG_ON_RE_ADD_SUPER_CALL_VERIFIED, false);
+ onReAdd();
+ if (!getRequestFlag(RFLAG_ON_RE_ADD_SUPER_CALL_VERIFIED))
+ {
+ throw new IllegalStateException(Component.class.getName() +
+ " has not been properly added. Something in the hierarchy of " +
+ getClass().getName() +
+ " has not called super.onReAdd() in the override of onReAdd() method");
+ }
+ }
+ }
}
/**
@@ -1123,6 +1140,7 @@ public abstract class Component
{
setFlag(FLAG_REMOVING_FROM_HIERARCHY, true);
onRemove();
+ setFlag(FLAG_REMOVED, true);
if (getFlag(FLAG_REMOVING_FROM_HIERARCHY))
{
throw new IllegalStateException(Component.class.getName() +
@@ -4544,4 +4562,29 @@ public abstract class Component
return getApplication().getPageSettings()
.getCallListenerInterfaceAfterExpiry() || isStateless();
}
+ /**
+ * This method is called whenever a component is re-added to the page's component tree, if it
+ * had been removed at some earlier time, i.e., if it is already initialized
+ * (see {@link org.apache.wicket.Component#isInitialized()}).
+ *
+ * This is similar to onInitialize, but only comes after the component has been removed and
+ * then
+ * added again:
+ *
+ * <ul>
+ * <li>onInitialize is only called the very first time a component is added</li>
+ * <li>onReAdd is not called the first time, but every time it is re-added after having been
+ * removed</li>
+ * </ul>
+ *
+ * You can think of it as the opposite of onRemove. A component that was once removed will
+ * not be
+ * re-initialized but only re-added.
+ *
+ * Subclasses that override this must call super.onReAdd().
+ */
+ protected void onReAdd()
+ {
+ setRequestFlag(RFLAG_ON_RE_ADD_SUPER_CALL_VERIFIED, true);
+ }
}
http://git-wip-us.apache.org/repos/asf/wicket/blob/623da392/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 029fcfb..09f169c 100644
--- a/wicket-core/src/main/java/org/apache/wicket/MarkupContainer.java
+++ b/wicket-core/src/main/java/org/apache/wicket/MarkupContainer.java
@@ -970,8 +970,8 @@ public abstract class MarkupContainer extends Component implements Iterable<Comp
{
child.internalInitialize();
}
- }
+ }
// if the PREPARED_FOR_RENDER flag is set, we have already called
// beforeRender on this component's children. So we need to initialize the newly added one
if (isPreparedForRender())
@@ -980,6 +980,8 @@ public abstract class MarkupContainer extends Component implements Iterable<Comp
}
}
+
+
/**
* THIS METHOD IS NOT PART OF THE PUBLIC API, DO NOT CALL IT
*
http://git-wip-us.apache.org/repos/asf/wicket/blob/623da392/wicket-core/src/test/java/org/apache/wicket/OnReAddTest.java
----------------------------------------------------------------------
diff --git a/wicket-core/src/test/java/org/apache/wicket/OnReAddTest.java b/wicket-core/src/test/java/org/apache/wicket/OnReAddTest.java
new file mode 100644
index 0000000..be664cc
--- /dev/null
+++ b/wicket-core/src/test/java/org/apache/wicket/OnReAddTest.java
@@ -0,0 +1,215 @@
+/*
+ * Licensed to the Apache Software Foundation (ASF) under one or more
+ * contributor license agreements. See the NOTICE file distributed with
+ * this work for additional information regarding copyright ownership.
+ * The ASF licenses this file to You under the Apache License, Version 2.0
+ * (the "License"); you may not use this file except in compliance with
+ * the License. You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+package org.apache.wicket;
+
+import static org.junit.Assert.assertFalse;
+import static org.junit.Assert.assertTrue;
+import static org.junit.Assert.fail;
+
+import org.apache.wicket.markup.html.WebMarkupContainer;
+import org.apache.wicket.markup.html.WebPage;
+import org.apache.wicket.markup.html.basic.Label;
+import org.apache.wicket.util.tester.WicketTesterScope;
+import org.junit.Rule;
+import org.junit.Test;
+
+public class OnReAddTest
+{
+ @Rule
+ public WicketTesterScope scope = new WicketTesterScope();
+
+ private boolean onReAddCalled = false;
+ private boolean onInitializeCalled = false;
+
+ @Test
+ public void onFirstAddInitializeIsCalled()
+ {
+ Page page = createPage();
+ page.internalInitialize();
+ page.add(createUninitializedProbe());
+ assertFalse(onReAddCalled);
+ assertTrue(onInitializeCalled);
+ }
+
+ @Test
+ public void nothingIsCalledWithoutConnectionToPage()
+ {
+ MarkupContainer container = createContainer();
+ container.internalInitialize();
+ container.add(createUninitializedProbe());
+ assertFalse(onReAddCalled);
+ assertFalse(onInitializeCalled);
+ }
+
+ @Test
+ public void uninitializedComponentIsInitializedOnConnectionToPage()
+ {
+ // "old", initialized container + "new" uninitialized component:
+ // oninitialize should be called on the component when the container
+ // is added to the page, not before.
+ MarkupContainer container = createContainer();
+ container.internalInitialize();
+ container.add(createUninitializedProbe());
+ assertFalse(onReAddCalled);
+ assertFalse(onInitializeCalled);
+ WebPage page = createPage();
+ page.internalInitialize();
+ page.add(container);
+ assertFalse(onReAddCalled);
+ assertTrue(onInitializeCalled);
+ }
+
+ @Test
+ public void onReAddIsOnlyCalledAfterRemove()
+ {
+ Page page = createPage();
+ page.internalInitialize();
+ Component probe = createUninitializedProbe();
+ page.add(probe);
+ assertFalse(onReAddCalled);
+ assertTrue(onInitializeCalled);
+ onInitializeCalled = false;
+ page.internalInitialize();
+ assertFalse(onReAddCalled);
+ assertFalse(onInitializeCalled);
+ page.remove(probe);
+ assertFalse(onReAddCalled);
+ assertFalse(onInitializeCalled);
+ page.add(probe);
+ assertTrue(onReAddCalled);
+ assertFalse(onInitializeCalled);
+ }
+
+ @Test
+ public void initializeIsCalledOnFirstAdd_OnReAddIsCalledAfterEachRemoveAndAdd()
+ {
+ Page page = createPage();
+ page.internalInitialize();
+ Component probe = createUninitializedProbe();
+ page.add(probe);
+ assertFalse(onReAddCalled);
+ assertTrue(onInitializeCalled);
+ onInitializeCalled = false;
+ page.internalInitialize();
+ assertFalse(onReAddCalled);
+ assertFalse(onInitializeCalled);
+ page.remove(probe);
+ assertFalse(onReAddCalled);
+ assertFalse(onInitializeCalled);
+ page.add(probe);
+ assertTrue(onReAddCalled);
+ assertFalse(onInitializeCalled);
+ onReAddCalled = false;
+ page.internalInitialize();
+ // just another initialize run shouldn't call onReAdd nor onInitialize. onReAdd should only be called
+ // after remove and add
+ assertFalse(onReAddCalled);
+ assertFalse(onInitializeCalled);
+ page.remove(probe);
+ page.add(probe);
+ assertTrue(onReAddCalled);
+ assertFalse(onInitializeCalled);
+ }
+
+ @Test
+ public void onReAddRecursesToChildrenLikeOnInitialize()
+ {
+ Page page = createPage();
+ page.internalInitialize();
+ Component probe = createNestedProbe();
+ page.add(probe);
+ assertFalse(onReAddCalled);
+ assertTrue(onInitializeCalled);
+ onInitializeCalled = false;
+ probe.remove();
+ assertFalse(onInitializeCalled);
+ assertFalse(onReAddCalled);
+ page.add(probe);
+ assertFalse(onInitializeCalled);
+ assertTrue(onReAddCalled);
+ }
+
+ @Test
+ public void onReAddEnforcesSuperCall()
+ {
+ Page page = createPage();
+ page.internalInitialize();
+ Label brokenProbe = new Label("foo")
+ {
+ @Override
+ protected void onReAdd()
+ {
+ ; // I should call super, but since I don't, this should throw an exception
+ }
+ };
+ brokenProbe.internalInitialize();
+ page.add(brokenProbe);
+ page.remove(brokenProbe);
+ try
+ {
+ page.add(brokenProbe);
+ fail("should have thrown exception");
+ } catch (IllegalStateException e)
+ {
+ assertTrue(e.getMessage().contains("super.onReAdd"));
+ }
+ }
+
+ private Component createUninitializedProbe()
+ {
+ return new Label("foo")
+ {
+ @Override
+ protected void onReAdd()
+ {
+ super.onReAdd();
+ onReAddCalled = true;
+ }
+
+ @Override
+ protected void onInitialize()
+ {
+ super.onInitialize();
+ onInitializeCalled = true;
+ }
+ };
+ }
+
+ private Component createInitializedProbe()
+ {
+ Component probe = createUninitializedProbe();
+ probe.internalInitialize();
+ return probe;
+ }
+
+ private WebPage createPage()
+ {
+ return new WebPage()
+ {
+ };
+ }
+
+ private Component createNestedProbe()
+ {
+ return createContainer().add(createUninitializedProbe());
+ }
+
+ private MarkupContainer createContainer()
+ {
+ return new WebMarkupContainer("bar");
+ }
+}