Repository: wicket
Updated Branches:
  refs/heads/WICKET-5677 70b7327d2 -> c3eb7e249


WICKET-5677 change onadd to onReAdd and only call when oninitialize wouldn't be 
called


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

Branch: refs/heads/WICKET-5677
Commit: 4703c1ae1af91fdcca44e34edbeeb8bbaeb63b6c
Parents: 70b7327
Author: Carl-Eric Menzel <cmen...@apache.org>
Authored: Mon Aug 18 13:35:44 2014 +0200
Committer: Carl-Eric Menzel <cmen...@apache.org>
Committed: Mon Aug 18 13:35:44 2014 +0200

----------------------------------------------------------------------
 .../main/java/org/apache/wicket/Component.java  | 430 ++++++++++---------
 .../java/org/apache/wicket/MarkupContainer.java |  48 +--
 .../test/java/org/apache/wicket/OnAddTest.java  | 160 -------
 .../java/org/apache/wicket/OnReAddTest.java     | 155 +++++++
 4 files changed, 375 insertions(+), 418 deletions(-)
----------------------------------------------------------------------


http://git-wip-us.apache.org/repos/asf/wicket/blob/4703c1ae/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 0eb62c3..e812caa 100644
--- a/wicket-core/src/main/java/org/apache/wicket/Component.java
+++ b/wicket-core/src/main/java/org/apache/wicket/Component.java
@@ -98,7 +98,7 @@ import org.slf4j.LoggerFactory;
 
 /**
  * Component serves as the highest level abstract base class for all 
components.
- * 
+ *
  * <ul>
  * <li><b>Identity </b>- All Components must have a non-null id which is 
retrieved by calling
  * getId(). The id must be unique within the {@link MarkupContainer} that 
holds the Component, but
@@ -207,7 +207,7 @@ import org.slf4j.LoggerFactory;
  * <li><b>Security </b>- All components are subject to an {@link 
IAuthorizationStrategy} which
  * controls instantiation, visibility and enabling. See {@link 
SimplePageAuthorizationStrategy} for
  * a simple implementation.</li>
- * 
+ *
  * @author Jonathan Locke
  * @author Chris Turner
  * @author Eelco Hillenius
@@ -241,14 +241,14 @@ public abstract class Component
         * When a component is not allowed to be enabled (in effect disabled 
through the implementation
         * of this interface), Wicket will try to prevent model updates too. 
This is not completely fail
         * safe, as constructs like:
-        * 
+        *
         * <pre>
-        * 
+        *
         * User u = (User)getModelObject();
         * u.setName(&quot;got you there!&quot;);
-        * 
+        *
         * </pre>
-        * 
+        *
         * can't be prevented. Indeed it can be argued that any model 
protection is best dealt with in
         * your model objects to be completely secured. Wicket will catch all 
normal framework-directed
         * use though.
@@ -447,7 +447,7 @@ public abstract class Component
        private static final short RFLAG_CONFIGURED = 0x10;
        private static final short RFLAG_BEFORE_RENDER_SUPER_CALL_VERIFIED = 
0x20;
        private static final short RFLAG_INITIALIZE_SUPER_CALL_VERIFIED = 0x40;
-       private static final short RFLAG_ONADD_SUPER_CALL_VERIFIED = 0x80;
+       private static final short RFLAG_ON_RE_ADD_SUPER_CALL_VERIFIED = 0x80;
 
        /**
         * Flags that only keep their value during the request. Useful for 
cache markers, etc. At the
@@ -655,7 +655,7 @@ public abstract class Component
        /**
         * Constructor. All components have names. A component's id cannot be 
null. This is the minimal
         * constructor of component. It does not register a model.
-        * 
+        *
         * @param id
         *            The non-null id of this component
         * @throws WicketRuntimeException
@@ -669,12 +669,12 @@ public abstract class Component
        /**
         * Constructor. All components have names. A component's id cannot be 
null. This constructor
         * includes a model.
-        * 
+        *
         * @param id
         *            The non-null id of this component
         * @param model
         *            The component's model
-        * 
+        *
         * @throws WicketRuntimeException
         *             Thrown if the component has been given a null id.
         */
@@ -718,9 +718,9 @@ public abstract class Component
         * Panel/Border/Enclosure.getMarkup(null) to return the associated 
markup file. And
         * Panel/Border/Enclosure.getMarkup(child) will search the child in the 
appropriate markup
         * fragment.
-        * 
+        *
         * @see MarkupContainer#getMarkup(Component)
-        * 
+        *
         * @return The markup fragment
         */
        public IMarkupFragment getMarkup()
@@ -779,7 +779,7 @@ public abstract class Component
         * Set the markup for the component. Note that the component's markup 
variable is transient and
         * thus must only be used for one render cycle. E.g. auto-component are 
using it. You may also
         * it if you subclassed getMarkup().
-        * 
+        *
         * @param markup
         */
        public final void setMarkup(final IMarkupFragment markup)
@@ -829,16 +829,16 @@ public abstract class Component
         * <p>
         * Parent containers are guaranteed to be initialized before their 
children
         * </p>
-        * 
+        *
         * <p>
         * It is safe to use {@link #getPage()} in this method
         * </p>
-        * 
+        *
         * <p>
         * NOTE:The timing of this call is not precise, the contract is that it 
is called sometime
         * before {@link Component#onBeforeRender()}.
         * </p>
-        * 
+        *
         */
        protected void onInitialize()
        {
@@ -847,7 +847,7 @@ public abstract class Component
 
        /**
         * Checks if the component has been initialized - {@link 
#onInitialize()} has been called
-        * 
+        *
         * @return {@code true} if component has been initialized
         */
        final boolean isInitialized()
@@ -857,7 +857,7 @@ public abstract class Component
 
        /**
         * THIS METHOD IS NOT PART OF THE PUBLIC API, DO NOT CALL IT
-        * 
+        *
         * Used to call {@link #onInitialize()}
         */
        public void internalInitialize()
@@ -886,6 +886,18 @@ public abstract class Component
 
                        
getApplication().getComponentInitializationListeners().onInitialize(this);
                }
+               else
+               {
+                       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");
+                       }
+               }
        }
 
        /**
@@ -920,7 +932,7 @@ public abstract class Component
        }
 
        /**
-        * 
+        *
         */
        private final void internalBeforeRender()
        {
@@ -1015,14 +1027,14 @@ public abstract class Component
         * visibility or enabled or other state of one component depends on the 
state of another this
         * method should be manually invoked on the other component by the 
user. EG to link visiliby of
         * two markup containers the following should be done:
-        * 
+        *
         * <pre>
         * final WebMarkupContainer source=new WebMarkupContainer("a") {
         *      protected void onConfigure() {
         *    setVisible(Math.rand()>0.5f);
         *  }
         * };
-        * 
+        *
         * WebMarkupContainer linked=new WebMarkupContainer("b") {
         *      protected void onConfigure() {
         *              source.configure(); // make sure source is configured
@@ -1030,7 +1042,7 @@ public abstract class Component
         *  }
         * }
         * </pre>
-        * 
+        *
         * </p>
         */
        public final void configure()
@@ -1060,9 +1072,9 @@ public abstract class Component
        }
 
        /**
-        * 
+        *
         * THIS METHOD IS NOT PART OF THE WICKET PUBLIC API. DO NOT USE IT!
-        * 
+        *
         * Called after the {@link #onConfigure()}, but before {@link 
#onBeforeRender()}
         */
        void internalOnAfterConfigure()
@@ -1073,9 +1085,9 @@ public abstract class Component
         * Redirects to any intercept page previously specified by a call to 
redirectToInterceptPage.
         * The redirect is done by throwing an exception. If there is no 
intercept page no exception
         * will be thrown and the program flow will continue uninterrupted.
-        * 
+        *
         * Example:
-        * 
+        *
         * <pre>
         * add(new Link(&quot;login&quot;)
         * {
@@ -1089,7 +1101,7 @@ public abstract class Component
         *              }
         *      }
         * });
-        * 
+        *
         * @see Component#redirectToInterceptPage(Page)
         */
        public final void continueToOriginalDestination()
@@ -1107,7 +1119,7 @@ public abstract class Component
 
        /**
         * Registers a debug feedback message for this component
-        * 
+        *
         * @param message
         *            The feedback message
         */
@@ -1230,7 +1242,7 @@ public abstract class Component
 
        /**
         * Registers an error feedback message for this component
-        * 
+        *
         * @param message
         *            The feedback message
         */
@@ -1242,7 +1254,7 @@ public abstract class Component
 
        /**
         * Registers a fatal feedback message for this component
-        * 
+        *
         * @param message
         *            The feedback message
         */
@@ -1254,11 +1266,11 @@ public abstract class Component
 
        /**
         * Finds the first container parent of this component of the given 
class.
-        * 
+        *
         * @param <Z>
         *            type of parent
-        * 
-        * 
+        *
+        *
         * @param c
         *            MarkupContainer class to search for
         * @return First container parent that is an instance of the given 
class, or null if none can be
@@ -1307,7 +1319,7 @@ public abstract class Component
 
        /**
         * Gets interface to application that this component is a part of.
-        * 
+        *
         * @return The application associated with the session that this 
component is in.
         * @see Application
         */
@@ -1327,10 +1339,10 @@ public abstract class Component
 
        /**
         * Gets the converter that should be used by this component.
-        * 
+        *
         * @param type
         *            The type to convert to
-        * 
+        *
         * @return The converter that should be used by this component
         */
        @Override
@@ -1341,7 +1353,7 @@ public abstract class Component
 
        /**
         * Gets whether model strings should be escaped.
-        * 
+        *
         * @return Returns whether model strings should be escaped
         */
        public final boolean getEscapeModelStrings()
@@ -1351,7 +1363,7 @@ public abstract class Component
 
        /**
         * Gets the id of this component.
-        * 
+        *
         * @return The id of this component
         */
        @Override
@@ -1371,7 +1383,7 @@ public abstract class Component
        /**
         * Gets the locale for this component. By default, it searches its 
parents for a locale. If no
         * parents (it's a recursive search) returns a locale, it gets one from 
the session.
-        * 
+        *
         * @return The locale to be used for this component
         * @see Session#getLocale()
         */
@@ -1386,7 +1398,7 @@ public abstract class Component
 
        /**
         * Convenience method to provide easy access to the localizer object 
within any component.
-        * 
+        *
         * @return The localizer object
         */
        public final Localizer getLocalizer()
@@ -1396,7 +1408,7 @@ public abstract class Component
 
        /**
         * Get the first component tag in the associated markup
-        * 
+        *
         * @return first component tag
         */
        private final ComponentTag getMarkupTag()
@@ -1418,14 +1430,14 @@ public abstract class Component
 
        /**
         * THIS IS WICKET INTERNAL ONLY. DO NOT USE IT.
-        * 
+        *
         * Get a copy of the markup's attributes which are associated with the 
component.
         * <p>
         * Modifications to the map returned don't change the tags attributes. 
It is just a copy.
         * <p>
         * Note: The component must have been added (directly or indirectly) to 
a container with an
         * associated markup file (Page, Panel or Border).
-        * 
+        *
         * @return markup attributes
         */
        public final ValueMap getMarkupAttributes()
@@ -1442,7 +1454,7 @@ public abstract class Component
 
        /**
         * Get the markupId
-        * 
+        *
         * @return MarkupId
         */
        public final Object getMarkupIdImpl()
@@ -1473,15 +1485,15 @@ public abstract class Component
         * the preferred way as there is no chance of id collision. This will 
also enable
         * {@link #setOutputMarkupId(boolean)}.
         * <p>
-        * 
+        *
         * <p>
         * Note: This method should only be called after the component or its 
parent have been added to
         * the page.
-        * 
+        *
         * @param createIfDoesNotExist
         *            When there is no existing markup id, determines whether 
it should be generated or
         *            whether <code>null</code> should be returned.
-        * 
+        *
         * @return markup id of the component
         */
        public String getMarkupId(boolean createIfDoesNotExist)
@@ -1502,7 +1514,7 @@ public abstract class Component
         * <p>
         * Note: This method should only be called after the component or its 
parent have been added to
         * the page.
-        * 
+        *
         * @return markup id of the component
         */
        public String getMarkupId()
@@ -1512,10 +1524,10 @@ public abstract class Component
 
        /**
         * Gets metadata for this component using the given key.
-        * 
+        *
         * @param <M>
         *            The type of the metadata.
-        * 
+        *
         * @param key
         *            The key for the data
         * @return The metadata or null of no metadata was found for the given 
key
@@ -1527,7 +1539,7 @@ public abstract class Component
        }
 
        /**
-        * 
+        *
         * @return meta data entry
         */
        private MetaDataEntry<?>[] getMetaData()
@@ -1557,7 +1569,7 @@ public abstract class Component
 
        /**
         * Gets the model. It returns the object that wraps the backing model.
-        * 
+        *
         * @return The model
         */
        public final IModel<?> getDefaultModel()
@@ -1577,7 +1589,7 @@ public abstract class Component
        /**
         * Gets the backing model object. Unlike getDefaultModel().getObject(), 
this method returns null
         * for a null model.
-        * 
+        *
         * @return The backing model object
         */
        public final Object getDefaultModelObject()
@@ -1608,10 +1620,10 @@ public abstract class Component
         * sensitive chars are escaped but not all none-ascii chars. Proper 
HTML encoding should be used
         * instead. In case you really need a fully escaped model string you 
may call
         * {@link Strings#escapeMarkup(CharSequence, boolean, boolean)} on the 
model string returned.
-        * 
+        *
         * @see Strings#escapeMarkup(CharSequence, boolean, boolean)
         * @see #getEscapeModelStrings()
-        * 
+        *
         * @return Model object for this component as a string
         */
        public final String getDefaultModelObjectAsString()
@@ -1625,10 +1637,10 @@ public abstract class Component
         * sensitive chars are escaped but not all none-ascii chars. Proper 
HTML encoding should be used
         * instead. In case you really need a fully escaped model string you 
may call
         * {@link Strings#escapeMarkup(CharSequence, boolean, boolean)} on the 
model string returned.
-        * 
+        *
         * @see Strings#escapeMarkup(CharSequence, boolean, boolean)
         * @see #getEscapeModelStrings()
-        * 
+        *
         * @param modelObject
         *            Model object to convert to string
         * @return The string
@@ -1663,7 +1675,7 @@ public abstract class Component
        /**
         * Gets whether or not component will output id attribute into the 
markup. id attribute will be
         * set to the value returned from {@link Component#getMarkupId()}.
-        * 
+        *
         * @return whether or not component will output id attribute into the 
markup
         */
        public final boolean getOutputMarkupId()
@@ -1673,7 +1685,7 @@ public abstract class Component
 
        /**
         * Gets whether or not an invisible component will render a placeholder 
tag.
-        * 
+        *
         * @return true if a placeholder tag should be rendered
         */
        public final boolean getOutputMarkupPlaceholderTag()
@@ -1683,7 +1695,7 @@ public abstract class Component
 
        /**
         * Gets the page holding this component.
-        * 
+        *
         * @return The page holding this component
         * @throws IllegalStateException
         *             Thrown if component is not yet attached to a Page.
@@ -1707,7 +1719,7 @@ public abstract class Component
        /**
         * Gets the path to this component relative to its containing page, 
i.e. without leading page
         * id.
-        * 
+        *
         * @return The path to this component relative to the page it is in
         */
        @Override
@@ -1718,7 +1730,7 @@ public abstract class Component
 
        /**
         * Gets any parent container, or null if there is none.
-        * 
+        *
         * @return Any parent container, or null if there is none
         */
        @Override
@@ -1729,7 +1741,7 @@ public abstract class Component
 
        /**
         * Gets this component's path.
-        * 
+        *
         * @return Colon separated path to this component in the component 
hierarchy
         */
        public final String getPath()
@@ -1749,7 +1761,7 @@ public abstract class Component
        /**
         * If false the component's tag will be printed as well as its body 
(which is default). If true
         * only the body will be printed, but not the component's tag.
-        * 
+        *
         * @return If true, the component tag will not be printed
         */
        public final boolean getRenderBodyOnly()
@@ -1774,7 +1786,7 @@ public abstract class Component
 
        /**
         * Gets the active request cycle for this component
-        * 
+        *
         * @return The request cycle
         */
        public final RequestCycle getRequestCycle()
@@ -1792,7 +1804,7 @@ public abstract class Component
 
        /**
         * Gets the current Session object.
-        * 
+        *
         * @return The Session that this component is in
         */
        public Session getSession()
@@ -1861,9 +1873,9 @@ public abstract class Component
 
        /**
         * A convenience method to access the Sessions's style.
-        * 
+        *
         * @return The style of this component respectively the style of the 
Session.
-        * 
+        *
         * @see org.apache.wicket.Session#getStyle()
         */
        public final String getStyle()
@@ -1880,7 +1892,7 @@ public abstract class Component
         * Gets the variation string of this component that will be used to 
look up markup for this
         * component. Subclasses can override this method to define by an 
instance what markup variation
         * should be picked up. By default it will return null or the value of 
a parent.
-        * 
+        *
         * @return The variation of this component.
         */
        public String getVariation()
@@ -1894,7 +1906,7 @@ public abstract class Component
 
        /**
         * Gets whether this component was rendered at least once.
-        * 
+        *
         * @return true if the component has been rendered before, false if it 
is merely constructed
         */
        public final boolean hasBeenRendered()
@@ -1907,7 +1919,7 @@ public abstract class Component
         * {@link FeedbackMessages} instance and add it to the component 
metadata, even when called on a
         * component that has no feedback messages, to avoid the overhead use
         * {@link #hasFeedbackMessage()}
-        * 
+        *
         * @return feedback messages instance
         */
        public FeedbackMessages getFeedbackMessages()
@@ -1936,7 +1948,7 @@ public abstract class Component
 
        /**
         * @return True if this component has some kind of feedback message
-        * 
+        *
         */
        public final boolean hasFeedbackMessage()
        {
@@ -1950,7 +1962,7 @@ public abstract class Component
 
        /**
         * Registers an informational feedback message for this component
-        * 
+        *
         * @param message
         *            The feedback message
         */
@@ -1962,7 +1974,7 @@ public abstract class Component
 
        /**
         * Registers an success feedback message for this component
-        * 
+        *
         * @param message
         *            The feedback message
         */
@@ -1974,7 +1986,7 @@ public abstract class Component
 
        /**
         * Authorizes an action for a component.
-        * 
+        *
         * @param action
         *            The action to authorize
         * @return True if the action is allowed
@@ -2003,7 +2015,7 @@ public abstract class Component
         * Gets whether this component is enabled. Specific components may 
decide to implement special
         * behavior that uses this property, like web form components that add 
a disabled='disabled'
         * attribute when enabled is false.
-        * 
+        *
         * @return Whether this component is enabled.
         */
        public boolean isEnabled()
@@ -2014,7 +2026,7 @@ public abstract class Component
        /**
         * Checks the security strategy if the {@link Component#RENDER} action 
is allowed on this
         * component
-        * 
+        *
         * @return ture if {@link Component#RENDER} action is allowed, false 
otherwise
         */
        public final boolean isRenderAllowed()
@@ -2026,7 +2038,7 @@ public abstract class Component
         * Returns if the component is stateless or not. It checks the 
stateless hint if that is false
         * it returns directly false. If that is still true it checks all its 
behaviors if they can be
         * stateless.
-        * 
+        *
         * @return whether the component is stateless.
         */
        public final boolean isStateless()
@@ -2092,7 +2104,7 @@ public abstract class Component
         * method, it is a good idea to keep it cheap in terms of processing. 
Alternatively, you can
         * call {@link #setVisible(boolean)}.
         * <p>
-        * 
+        *
         * @return True if component and any children are visible
         */
        public boolean isVisible()
@@ -2102,7 +2114,7 @@ public abstract class Component
 
        /**
         * Checks if the component itself and all its parents are visible.
-        * 
+        *
         * @return true if the component and all its parents are visible.
         */
        public final boolean isVisibleInHierarchy()
@@ -2120,14 +2132,14 @@ 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)
@@ -2168,7 +2180,7 @@ public abstract class Component
         * <p>
         * Prepares the component and it's children for rendering. On whole 
page render this method must
         * be called on the page. On AJAX request, this method must be called 
on the updated component.
-        * 
+        *
         * @param setRenderingFlag
         *            Whether to set the rendering flag. This must be true if 
the page is about to be
         *            rendered. However, there are usecases to call this method 
without an immediate
@@ -2210,7 +2222,7 @@ public abstract class Component
 
        /**
         * THIS METHOD IS NOT PART OF THE WICKET PUBLIC API. DO NOT USE IT!
-        * 
+        *
         * Prepares the component and it's children for rendering. On whole 
page render this method must
         * be called on the page. On AJAX request, this method must be called 
on updated component.
         */
@@ -2224,10 +2236,10 @@ public abstract class Component
         * is saved for future use by method continueToOriginalDestination(); 
Only use this method when
         * you plan to continue to the current url at some later time; 
otherwise just use
         * setResponsePage or - when you are in a constructor or 
checkAccessMethod, call redirectTo.
-        * 
+        *
         * @param page
         *            The sign in page
-        * 
+        *
         * @see Component#continueToOriginalDestination()
         */
        public final void redirectToInterceptPage(final Page page)
@@ -2370,7 +2382,7 @@ public abstract class Component
 
        /**
         * Called when a runtime exception is caught during the render process
-        * 
+        *
         * @param ex
         *            The exception caught.
         */
@@ -2400,7 +2412,7 @@ public abstract class Component
        /**
         * Renders a placeholder tag for the component when it is invisible and
         * {@link #setOutputMarkupPlaceholderTag(boolean)} has been called with 
<code>true</code>.
-        * 
+        *
         * @param tag
         *            component tag
         * @param response
@@ -2432,7 +2444,7 @@ public abstract class Component
         * Returns the id of the markup region that will be updated via ajax. 
This can be different to
         * the markup id of the component if a {@link 
IAjaxRegionMarkupIdProvider} behavior has been
         * added.
-        * 
+        *
         * @return the markup id of the region to be updated via ajax.
         */
        public final String getAjaxRegionMarkupId()
@@ -2541,7 +2553,7 @@ public abstract class Component
        }
 
        /**
-        * 
+        *
         * @param openTag
         * @return true, if the tag shall be rendered
         */
@@ -2582,7 +2594,7 @@ public abstract class Component
        /**
         * Get the markup sourcing strategy for the component. If null,
         * {@link #newMarkupSourcingStrategy()} will be called.
-        * 
+        *
         * @return Markup sourcing strategy
         */
        protected final IMarkupSourcingStrategy getMarkupSourcingStrategy()
@@ -2608,7 +2620,7 @@ public abstract class Component
         * Please note that markup source strategies are not persisted. Instead 
they get re-created by
         * calling this method again. That's ok since markup sourcing 
strategies usually do not maintain
         * a state.
-        * 
+        *
         * @return Markup sourcing strategy
         */
        protected IMarkupSourcingStrategy newMarkupSourcingStrategy()
@@ -2618,14 +2630,14 @@ public abstract class Component
 
        /**
         * THIS METHOD IS NOT PART OF THE WICKET PUBLIC API. DO NOT USE IT.
-        * 
+        *
         * Print to the web response what ever the component wants to 
contribute to the head section.
         * Make sure that all attached behaviors are asked as well.
         * <p>
         * NOT intended for overriding by framework clients. Rather, use
         * {@link 
Component#renderHead(org.apache.wicket.markup.head.IHeaderResponse)}
         * </p>
-        * 
+        *
         * @param container
         *            The HtmlHeaderContainer
         */
@@ -2686,16 +2698,16 @@ public abstract class Component
        /**
         * Replaces this component with another. The replacing component must 
have the same component id
         * as this component. This method serves as a shortcut to
-        * 
+        *
         * <code>this.getParent().replace(replacement)</code>
-        * 
+        *
         * and provides a better context for errors.
         * <p>
         * Usage: <code>component = component.replaceWith(replacement);</code>
         * </p>
-        * 
+        *
         * @since 1.2.1
-        * 
+        *
         * @param replacement
         *            component to replace this one
         * @return the component which replaced this one
@@ -2754,7 +2766,7 @@ public abstract class Component
         * attribute when enabled is false. If it is not enabled, it will not 
be allowed to call any
         * listener method on it (e.g. Link.onClick) and the model object will 
be protected (for the
         * common use cases, not for programmer's misuse)
-        * 
+        *
         * @param enabled
         *            whether this component is enabled
         * @return This
@@ -2793,7 +2805,7 @@ public abstract class Component
 
        /**
         * Sets whether model strings should be escaped.
-        * 
+        *
         * @param escapeMarkup
         *            True is model strings should be escaped
         * @return This
@@ -2806,7 +2818,7 @@ public abstract class Component
 
        /**
         * Set markup ID, which must be String or Integer
-        * 
+        *
         * @param markupId
         */
        public final void setMarkupIdImpl(Object markupId)
@@ -2831,7 +2843,7 @@ public abstract class Component
 
        /**
         * Copy markupId
-        * 
+        *
         * @param comp
         */
        final void setMarkupId(Component comp)
@@ -2855,9 +2867,9 @@ public abstract class Component
         * <p>
         * If null is passed in the user defined value is cleared and markup id 
value will fall back on
         * automatically generated value
-        * 
+        *
         * @see #getMarkupId()
-        * 
+        *
         * @param markupId
         *            markup id value or null to clear any previous user 
defined value
         * @return this for chaining
@@ -2878,10 +2890,10 @@ public abstract class Component
         * Sets the metadata for this component using the given key. If the 
metadata object is not of
         * the correct type for the metadata key, an IllegalArgumentException 
will be thrown. For
         * information on creating MetaDataKeys, see {@link MetaDataKey}.
-        * 
+        *
         * @param <M>
         *            The type of the metadata
-        * 
+        *
         * @param key
         *            The singleton key for the metadata
         * @param object
@@ -2922,7 +2934,7 @@ public abstract class Component
         * WARNING: DO NOT OVERRIDE THIS METHOD UNLESS YOU HAVE A VERY GOOD 
REASON FOR IT. OVERRIDING
         * THIS MIGHT OPEN UP SECURITY LEAKS AND BREAK BACK-BUTTON SUPPORT.
         * </p>
-        * 
+        *
         * @param model
         *            The model
         * @return This
@@ -2970,7 +2982,7 @@ public abstract class Component
        }
 
        /**
-        * 
+        *
         * @param model
         */
        void setModelImpl(IModel<?> model)
@@ -3001,7 +3013,7 @@ public abstract class Component
         * Sets the backing model object. Unlike 
<code>getDefaultModel().setObject(object)</code>, this
         * method checks authorisation and model comparator, and invokes 
<code>modelChanging</code> and
         * <code>modelChanged</code> if the value really changes.
-        * 
+        *
         * @param object
         *            The object to set
         * @return This
@@ -3038,13 +3050,13 @@ public abstract class Component
        /**
         * Sets whether or not component will output id attribute into the 
markup. id attribute will be
         * set to the value returned from {@link Component#getMarkupId()}.
-        * 
+        *
         * @param output
         *            True if the component will output the id attribute into 
markup. Please note that
         *            the default behavior is to use the same id as the 
component. This means that your
         *            component must begin with [a-zA-Z] in order to generate a 
valid markup id
         *            according to: 
http://www.w3.org/TR/html401/types.html#type-name
-        * 
+        *
         * @return this for chaining
         */
        public final Component setOutputMarkupId(final boolean output)
@@ -3057,15 +3069,15 @@ public abstract class Component
         * Render a placeholder tag when the component is not visible. The tag 
is of form:
         * &lt;componenttag style="display:none;" id="markupid"/&gt;. This 
method will also call
         * <code>setOutputMarkupId(true)</code>.
-        * 
+        *
         * This is useful, for example, in ajax situations where the component 
starts out invisible and
         * then becomes visible through an ajax update. With a placeholder tag 
already in the markup you
         * do not need to repaint this component's parent, instead you can 
repaint the component
         * directly.
-        * 
+        *
         * When this method is called with parameter <code>false</code> the 
outputmarkupid flag is not
         * reverted to false.
-        * 
+        *
         * @param outputTag
         * @return this for chaining
         */
@@ -3091,7 +3103,7 @@ public abstract class Component
        /**
         * If false the component's tag will be printed as well as its body 
(which is default). If true
         * only the body will be printed, but not the component's tag.
-        * 
+        *
         * @param renderTag
         *            If true, the component tag will not be printed
         * @return This
@@ -3104,9 +3116,9 @@ public abstract class Component
 
        /**
         * Sets the page that will respond to this request
-        * 
+        *
         * @param <C>
-        * 
+        *
         * @param cls
         *            The response page class
         * @see RequestCycle#setResponsePage(Class)
@@ -3118,9 +3130,9 @@ public abstract class Component
 
        /**
         * Sets the page class and its parameters that will respond to this 
request
-        * 
+        *
         * @param <C>
-        * 
+        *
         * @param cls
         *            The response page class
         * @param parameters
@@ -3135,10 +3147,10 @@ public abstract class Component
 
        /**
         * Sets the page that will respond to this request
-        * 
+        *
         * @param page
         *            The response page
-        * 
+        *
         * @see 
RequestCycle#setResponsePage(org.apache.wicket.request.component.IRequestablePage)
         */
        public final void setResponsePage(final Page page)
@@ -3160,7 +3172,7 @@ public abstract class Component
 
        /**
         * Sets whether this component and any children are visible.
-        * 
+        *
         * @param visible
         *            True if this component and any children should be visible
         * @return This
@@ -3193,7 +3205,7 @@ public abstract class Component
 
        /**
         * Gets the string representation of this component.
-        * 
+        *
         * @return The path to this component
         */
        @Override
@@ -3261,11 +3273,11 @@ public abstract class Component
         * Returns a bookmarkable URL that references a given page class using 
a given set of page
         * parameters. Since the URL which is returned contains all information 
necessary to instantiate
         * and render the page, it can be stored in a user's browser as a 
stable bookmark.
-        * 
+        *
         * @param <C>
-        * 
+        *
         * @see RequestCycle#urlFor(Class, 
org.apache.wicket.request.mapper.parameter.PageParameters)
-        * 
+        *
         * @param pageClass
         *            Class of page
         * @param parameters
@@ -3281,7 +3293,7 @@ public abstract class Component
        /**
         * Gets a URL for the listener interface on a behavior (e.g. 
IBehaviorListener on
         * AjaxPagingNavigationBehavior).
-        * 
+        *
         * @param behaviour
         *            The behavior that the URL should point to
         * @param listener
@@ -3322,12 +3334,12 @@ public abstract class Component
 
        /**
         * Returns a URL that references the given request target.
-        * 
+        *
         * @see RequestCycle#urlFor(IRequestHandler)
-        * 
+        *
         * @param requestHandler
         *            the request target to reference
-        * 
+        *
         * @return a URL that references the given request target
         */
        public final CharSequence urlFor(final IRequestHandler requestHandler)
@@ -3337,9 +3349,9 @@ public abstract class Component
 
        /**
         * Gets a URL for the listener interface (e.g. ILinkListener).
-        * 
+        *
         * @see RequestCycle#urlFor(IRequestHandler)
-        * 
+        *
         * @param listener
         *            The listener interface that the URL should call
         * @param parameters
@@ -3355,9 +3367,9 @@ public abstract class Component
 
        /**
         * Returns a URL that references a shared resource through the provided 
resource reference.
-        * 
+        *
         * @see RequestCycle#urlFor(IRequestHandler)
-        * 
+        *
         * @param resourceReference
         *            The resource reference
         * @param parameters
@@ -3373,7 +3385,7 @@ public abstract class Component
        /**
         * Traverses all parent components of the given class in this 
parentClass, calling the visitor's
         * visit method at each one.
-        * 
+        *
         * @param <R>
         *            the type of the result object
         * @param parentClass
@@ -3391,7 +3403,7 @@ public abstract class Component
        /**
         * Traverses all parent components of the given class in this 
parentClass, calling the visitor's
         * visit method at each one.
-        * 
+        *
         * @param <R>
         *            the type of the result object
         * @param parentClass
@@ -3435,7 +3447,7 @@ public abstract class Component
 
        /**
         * Registers a warning feedback message for this component.
-        * 
+        *
         * @param message
         *            The feedback message
         */
@@ -3479,7 +3491,7 @@ public abstract class Component
        /**
         * TODO WICKET-NG rename to something more useful - like 
componentChanged(), this method used to
         * be called with a Change object
-        * 
+        *
         * Adds state change to page.
         */
        protected final void addStateChange()
@@ -3494,7 +3506,7 @@ public abstract class Component
 
        /**
         * Checks whether the given type has the expected name.
-        * 
+        *
         * @param tag
         *            The tag to check
         * @param name
@@ -3516,7 +3528,7 @@ public abstract class Component
 
        /**
         * Checks that a given tag has a required attribute value.
-        * 
+        *
         * @param tag
         *            The tag
         * @param key
@@ -3546,7 +3558,7 @@ public abstract class Component
        /**
         * Checks whether the hierarchy may be changed at all, and throws an 
exception if this is not
         * the case.
-        * 
+        *
         * @param component
         *            the component which is about to be added or removed
         */
@@ -3580,7 +3592,7 @@ public abstract class Component
 
        /**
         * Suffixes an exception message with useful information about this. 
component.
-        * 
+        *
         * @param message
         *            The message
         * @return The modified message
@@ -3592,7 +3604,7 @@ public abstract class Component
 
        /**
         * Finds the markup stream for this component.
-        * 
+        *
         * @return The markup stream for this component. Since a Component 
cannot have a markup stream,
         *         we ask this component's parent to search for it.
         */
@@ -3604,7 +3616,7 @@ public abstract class Component
        /**
         * If this Component is a Page, returns self. Otherwise, searches for 
the nearest Page parent in
         * the component hierarchy. If no Page parent can be found, null is 
returned.
-        * 
+        *
         * @return The Page or null if none can be found
         */
        protected final Page findPage()
@@ -3617,7 +3629,7 @@ public abstract class Component
         * Gets the subset of the currently coupled {@link Behavior}s that are 
of the provided type as
         * an unmodifiable list. Returns an empty list if there are no 
behaviors coupled to this
         * component.
-        * 
+        *
         * @param type
         *            The type or null for all
         * @return The subset of the currently coupled behaviors that are of 
the provided type as an
@@ -3632,7 +3644,7 @@ public abstract class Component
 
        /**
         * THIS METHOD IS NOT PART OF THE WICKET PUBLIC API. DO NOT USE IT!
-        * 
+        *
         * @param flag
         *            The flag to test
         * @return True if the flag is set
@@ -3644,7 +3656,7 @@ public abstract class Component
 
        /**
         * THIS METHOD IS NOT PART OF THE WICKET PUBLIC API. DO NOT USE IT!
-        * 
+        *
         * @param flag
         *            The flag to test
         * @return True if the flag is set
@@ -3656,7 +3668,7 @@ public abstract class Component
 
        /**
         * Finds the innermost IModel object for an IModel that might contain 
nested IModel(s).
-        * 
+        *
         * @param model
         *            The model
         * @return The innermost (most nested) model
@@ -3679,7 +3691,7 @@ public abstract class Component
        /**
         * Gets the component's current model comparator. Implementations can 
be used for testing the
         * current value of the components model data with the new value that 
is given.
-        * 
+        *
         * @return the value defaultModelComparator
         */
        public IModelComparator getModelComparator()
@@ -3692,7 +3704,7 @@ public abstract class Component
         * stateless, otherwise the component will be treat as stateful. In 
order for page to be
         * stateless (and not to be stored in session), all components (and 
component behaviors) must be
         * stateless.
-        * 
+        *
         * @return whether the component can be stateless
         */
        protected boolean getStatelessHint()
@@ -3711,7 +3723,7 @@ public abstract class Component
         * For example a {@link FormComponent} has the opportunity to 
instantiate a model on the fly
         * using its {@code id} and the containing {@link Form}'s model, if the 
form holds a
         * {@link CompoundPropertyModel}.
-        * 
+        *
         * @return The model
         */
        protected IModel<?> initModel()
@@ -3746,7 +3758,7 @@ public abstract class Component
 
        /**
         * THIS METHOD IS NOT PART OF THE WICKET PUBLIC API. DO NOT CALL OR 
OVERRIDE.
-        * 
+        *
         * <p>
         * Called anytime a model is changed via setModel or setModelObject.
         * </p>
@@ -3757,7 +3769,7 @@ public abstract class Component
 
        /**
         * Components are allowed to reject behavior modifiers.
-        * 
+        *
         * @param behavior
         * @return False, if the component should not apply this behavior
         */
@@ -3775,7 +3787,7 @@ public abstract class Component
 
        /**
         * If true, all attribute modifiers will be ignored
-        * 
+        *
         * @return True, if attribute modifiers are to be ignored
         */
        protected final boolean isIgnoreAttributeModifier()
@@ -3796,7 +3808,7 @@ public abstract class Component
         * <p>
         * <strong>NOTE</strong>: If you override this, you *must* call 
super.onBeforeRender() within
         * your implementation.
-        * 
+        *
         * Because this method is responsible for cascading {@link 
#onBeforeRender()} call to its
         * children it is strongly recommended that super call is made at the 
end of the override.
         * </p>
@@ -3804,7 +3816,7 @@ public abstract class Component
         * Changes to the component tree can be made only 
<strong>before</strong> calling
         * super.onBeforeRender().
         *
-        * @see org.apache.wicket.MarkupContainer#addOrReplace(Component...) 
+        * @see org.apache.wicket.MarkupContainer#addOrReplace(Component...)
         */
        protected void onBeforeRender()
        {
@@ -3815,9 +3827,9 @@ public abstract class Component
 
        /**
         * Processes the component tag.
-        * 
+        *
         * Overrides of this method most likely should call the super 
implementation.
-        * 
+        *
         * @param tag
         *            Tag to modify
         */
@@ -3846,7 +3858,7 @@ public abstract class Component
 
        /**
         * Processes the body.
-        * 
+        *
         * @param markupStream
         *            The markup stream
         * @param openTag
@@ -3858,7 +3870,7 @@ public abstract class Component
 
        /**
         * Called to allow a component to detach resources after use.
-        * 
+        *
         * Overrides of this method MUST call the super implementation, the 
most logical place to do
         * this is the last line of the override method.
         */
@@ -3869,7 +3881,7 @@ public abstract class Component
 
        /**
         * Called to notify the component it is being removed from the 
component hierarchy
-        * 
+        *
         * Overrides of this method MUST call the super implementation, the 
most logical place to do
         * this is the last line of the override method.
         */
@@ -3901,7 +3913,7 @@ public abstract class Component
         * Writes a simple tag out to the response stream. Any components that 
might be referenced by
         * the tag are ignored. Also undertakes any tag attribute modifications 
if they have been added
         * to the component.
-        * 
+        *
         * @param tag
         *            The tag to write
         */
@@ -3966,7 +3978,7 @@ public abstract class Component
 
        /**
         * Replaces the body with the given one.
-        * 
+        *
         * @param markupStream
         *            The markup stream to replace the tag body in
         * @param tag
@@ -4029,7 +4041,7 @@ public abstract class Component
 
        /**
         * THIS METHOD IS NOT PART OF THE WICKET PUBLIC API. DO NOT USE IT!
-        * 
+        *
         * @param flag
         *            The flag to set
         * @param set
@@ -4049,7 +4061,7 @@ public abstract class Component
 
        /**
         * THIS METHOD IS NOT PART OF THE WICKET PUBLIC API. DO NOT USE IT!
-        * 
+        *
         * @param flag
         *            The flag to set
         * @param set
@@ -4069,7 +4081,7 @@ public abstract class Component
 
        /**
         * If true, all attribute modifiers will be ignored
-        * 
+        *
         * @param ignore
         *            If true, all attribute modifiers will be ignored
         * @return This
@@ -4112,7 +4124,7 @@ public abstract class Component
 
        /**
         * Gets the component at the given path.
-        * 
+        *
         * @param path
         *            Path to component
         * @return The component at the path
@@ -4159,7 +4171,7 @@ public abstract class Component
        }
 
        /**
-        * 
+        *
         * @return <code>true</code> if component has been prepared for render
         */
        boolean isPreparedForRender()
@@ -4168,7 +4180,7 @@ public abstract class Component
        }
 
        /**
-        * 
+        *
         */
        protected void onAfterRenderChildren()
        {
@@ -4186,7 +4198,7 @@ public abstract class Component
 
        /**
         * Renders the close tag at the current position in the markup stream.
-        * 
+        *
         * @param markupStream
         *            the markup stream
         * @param openTag
@@ -4220,9 +4232,9 @@ public abstract class Component
 
        /**
         * THIS METHOD IS NOT PART OF THE WICKET PUBLIC API. DO NOT USE IT!
-        * 
+        *
         * Sets the id of this component.
-        * 
+        *
         * @param id
         *            The non-null id of this component
         */
@@ -4246,13 +4258,13 @@ public abstract class Component
 
        /**
         * THIS IS A WICKET INTERNAL API. DO NOT USE IT.
-        * 
+        *
         * Sets the parent of a component. Typically what you really want is 
parent.add(child).
         * <p/>
         * Note that calling setParent() and not parent.add() will connect the 
child to the parent, but
         * the parent will not know the child. This might not be a problem in 
some cases, but e.g.
         * child.onDetach() will not be invoked (since the parent doesn't know 
it is his child).
-        * 
+        *
         * @param parent
         *            The parent container
         */
@@ -4267,7 +4279,7 @@ public abstract class Component
 
        /**
         * Sets the render allowed flag.
-        * 
+        *
         * @param renderAllowed
         */
        final void setRenderAllowed(boolean renderAllowed)
@@ -4277,7 +4289,7 @@ public abstract class Component
 
        /**
         * Sets the render allowed flag.
-        * 
+        *
         * Visit all this page's children (overridden in MarkupContainer) to 
check rendering
         * authorization, as appropriate. We set any result; positive or 
negative as a temporary boolean
         * in the components, and when a authorization exception is thrown it 
will block the rendering
@@ -4294,7 +4306,7 @@ public abstract class Component
         * {@link #setVisible(boolean)} will not always have a desired effect 
because that component may
         * have {@link #isVisible()} overridden. Both {@link 
#setVisibilityAllowed(boolean)} and
         * {@link #isVisibilityAllowed()} are <code>final</code> so their 
contract is enforced always.
-        * 
+        *
         * @param allowed
         * @return <code>this</code> for chaining
         */
@@ -4307,7 +4319,7 @@ public abstract class Component
        /**
         * Gets whether or not visibility is allowed on this component. See
         * {@link #setVisibilityAllowed(boolean)} for details.
-        * 
+        *
         * @return true if this component is allowed to be visible, false 
otherwise.
         */
        public final boolean isVisibilityAllowed()
@@ -4318,7 +4330,7 @@ public abstract class Component
        /**
         * Determines whether or not a component should be visible, taking into 
account all the factors:
         * {@link #isVisible()}, {@link #isVisibilityAllowed()}, {@link 
#isRenderAllowed()}
-        * 
+        *
         * @return <code>true</code> if the component should be visible, 
<code>false</code> otherwise
         */
        public final boolean determineVisibility()
@@ -4331,7 +4343,7 @@ public abstract class Component
         * Calculates enabled state of the component taking its hierarchy into 
account. A component is
         * enabled iff it is itself enabled ({@link #isEnabled()} and {@link 
#isEnableAllowed()} both
         * return <code>true</code>), and all of its parents are enabled.
-        * 
+        *
         * @return <code>true</code> if this component is enabled</code>
         */
        public final boolean isEnabledInHierarchy()
@@ -4374,11 +4386,11 @@ public abstract class Component
         * method so that image data can be streamed. Such a component would 
override this method and
         * return {@literal true} if the listener method belongs to {@link 
IRequestListener}.
         * </p>
-        * 
+        *
         * @param method
         *            listener method about to be invoked on this component. 
Could be {@code null} - in
         *            this case it means <em>any</em> method.
-        * 
+        *
         * @return {@literal true} iff the listener method can be invoked on 
this component
         */
        public boolean canCallListenerInterface(Method method)
@@ -4391,7 +4403,7 @@ public abstract class Component
         * implementing {@link IHeaderContributor}. overload
         * {@link 
Component#renderHead(org.apache.wicket.markup.head.IHeaderResponse)} instead to
         * contribute to the response header.
-        * 
+        *
         * @param component
         * @param response
         */
@@ -4407,7 +4419,7 @@ public abstract class Component
 
        /**
         * Render to the web response whatever the component wants to 
contribute to the head section.
-        * 
+        *
         * @param response
         *            Response object
         */
@@ -4433,10 +4445,10 @@ public abstract class Component
 
        /**
         * Removes behavior from component
-        * 
+        *
         * @param behaviors
         *            behaviors to remove
-        * 
+        *
         * @return this (to allow method call chaining)
         */
        public Component remove(final Behavior... behaviors)
@@ -4465,7 +4477,7 @@ public abstract class Component
 
        /**
         * Adds a behavior modifier to the component.
-        * 
+        *
         * @param behaviors
         *            The behavior modifier(s) to be added
         * @return this (to allow method call chaining)
@@ -4479,7 +4491,7 @@ public abstract class Component
        /**
         * Gets the currently coupled {@link Behavior}s as a unmodifiable list. 
Returns an empty list
         * rather than null if there are no behaviors coupled to this component.
-        * 
+        *
         * @return The currently coupled behaviors as a unmodifiable list
         */
        public final List<? extends Behavior> getBehaviors()
@@ -4487,32 +4499,28 @@ public abstract class Component
                return getBehaviors(null);
        }
 
-       final void internalOnAdd()
-       {
-               setRequestFlag(RFLAG_ONADD_SUPER_CALL_VERIFIED, false);
-               onAddToPage();
-               if (!getRequestFlag(RFLAG_ONADD_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.onAddToPage() in 
the override of onAddToPage() method");
-               }
-       }
-
        /**
-        * This method is called whenever a component is added to the component 
tree connected to the page,
-        * to allow it to initialize things that depend on other components in 
the page. This is similar
-        * to {@link #onInitialize()}. However, onInitialize is only ever 
called once, the first time the
-        * component is added. It is not called when a component is removed and 
then added again.
+        * 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>
         *
-        * This method, however, is called every time the component is added to 
the page's tree. It is
-        * never called before onInitialize(). It is thus the opposite of 
onRemove().
+        * 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.onAddToPage().
+        * Subclasses that override this must call super.onReAdd().
         */
-       protected void onAddToPage()
+       protected void onReAdd()
        {
-               setRequestFlag(RFLAG_ONADD_SUPER_CALL_VERIFIED, true);
+               setRequestFlag(RFLAG_ON_RE_ADD_SUPER_CALL_VERIFIED, true);
        }
 }

http://git-wip-us.apache.org/repos/asf/wicket/blob/4703c1ae/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 cbb1d05..66ebf17 100644
--- a/wicket-core/src/main/java/org/apache/wicket/MarkupContainer.java
+++ b/wicket-core/src/main/java/org/apache/wicket/MarkupContainer.java
@@ -939,17 +939,6 @@ public abstract class MarkupContainer extends Component 
implements Iterable<Comp
                        }
 
                }
-               // onAdd should only be triggered
-               // - after onInitialize
-               //   - if we are not initialized ourselves yet, then we delay 
calling onAdd until onInitialize
-               //   - if we are initialized already, we can just call onAdd now
-               // - AND if we already have a page. See #onAdd
-               //   - if we don't have a page yet, our own onAdd will be 
called when we get added to the page component tree.
-               if (page != null && this.isInitialized())
-               {
-                       child.internalOnAdd();
-               }
-
                // 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())
@@ -958,36 +947,7 @@ public abstract class MarkupContainer extends Component 
implements Iterable<Comp
                }
        }
 
-       @Override protected void onAddToPage()
-       {
-               super.onAddToPage();
-               Component[] children = copyChildren();
-               try
-               {
-                       for (final Component child : children)
-                       {
-                               // We need to check whether the child's wasn't 
removed from the
-                               // component in the meanwhile (e.g. from 
another's child
-                               // onAddToPage)
-                               if (child.getParent() == this)
-                               {
-                                       child.internalOnAdd();
-                               }
-                       }
-               }
-               catch (RuntimeException ex)
-               {
-                       if (ex instanceof WicketRuntimeException)
-                       {
-                               throw ex;
-                       }
-                       else
-                       {
-                               throw new WicketRuntimeException("Error adding 
this container: " +
-                                               this, ex);
-                       }
-               }
-       }
+
 
        /**
         * THIS METHOD IS NOT PART OF THE PUBLIC API, DO NOT CALL IT
@@ -1988,10 +1948,4 @@ public abstract class MarkupContainer extends Component 
implements Iterable<Comp
                        }
                }
        }
-
-       @Override protected void onInitialize()
-       {
-               super.onInitialize();
-               internalOnAdd();
-       }
 }

http://git-wip-us.apache.org/repos/asf/wicket/blob/4703c1ae/wicket-core/src/test/java/org/apache/wicket/OnAddTest.java
----------------------------------------------------------------------
diff --git a/wicket-core/src/test/java/org/apache/wicket/OnAddTest.java 
b/wicket-core/src/test/java/org/apache/wicket/OnAddTest.java
deleted file mode 100644
index 117b22d..0000000
--- a/wicket-core/src/test/java/org/apache/wicket/OnAddTest.java
+++ /dev/null
@@ -1,160 +0,0 @@
-/*
- * 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 OnAddTest
-{
-       @Rule
-       public WicketTesterScope scope = new WicketTesterScope();
-
-       private boolean onAddCalled = false;
-
-       private Component createProbe()
-       {
-               return new Label("foo")
-               {
-                       @Override
-                       protected void onAddToPage()
-                       {
-                               super.onAddToPage();
-                               onAddCalled = true;
-                       }
-               };
-       }
-
-       @Test
-       public void onAddIsCalledIfParentIsInitialized()
-       {
-               Page page = createPage();
-               page.internalInitialize();
-               page.add(createProbe());
-               assertTrue(onAddCalled);
-       }
-
-       private WebPage createPage()
-       {
-               return new WebPage()
-               {
-               };
-       }
-
-       @Test
-       public void onAddIsNotCalledIfParentIsNotInitialized()
-       {
-               Page page = createPage();
-               page.add(createProbe());
-               assertFalse(onAddCalled);
-       }
-
-       @Test
-       public void onAddIsCalledWhenParentIsInitialized()
-       {
-               Page page = createPage();
-               page.add(createProbe());
-               page.internalInitialize();
-               assertTrue(onAddCalled);
-       }
-
-       @Test
-       public void onAddIsNotCalledWhenParentIsNotConnectedToPage()
-       {
-               MarkupContainer container = createContainer();
-               container.internalInitialize();
-               container.add(createProbe());
-               assertFalse(onAddCalled);
-       }
-
-       @Test
-       public void onAddIsCalledWhenParentIsAddedToPage()
-       {
-               MarkupContainer container = createContainer();
-               container.internalInitialize();
-               container.add(createProbe());
-               assertFalse(onAddCalled);
-               WebPage page = createPage();
-               page.internalInitialize();
-               page.add(container);
-               assertTrue(onAddCalled);
-       }
-
-       @Test
-       public void onAddIsCalledAfterRemoveAndAdd()
-       {
-               Page page = createPage();
-               page.internalInitialize();
-               Component probe = createProbe();
-               page.add(probe);
-               assertTrue(onAddCalled);
-               onAddCalled = false;
-               page.remove(probe);
-               assertFalse(onAddCalled);
-               page.add(probe);
-               assertTrue(onAddCalled);
-       }
-
-       @Test
-       public void onAddRecursesToChildren()
-       {
-               Page page = createPage();
-               page.internalInitialize();
-               page.add(createNestedProbe());
-               assertTrue(onAddCalled);
-       }
-
-       @Test
-       public void onAddEnforcesSuperCall()
-       {
-               Page page = createPage();
-               page.internalInitialize();
-               try
-               {
-                       page.add(new Label("foo")
-                       {
-                               @Override
-                               protected void onAddToPage()
-                               {
-                                       ; // I should call super, but since I 
don't, this should throw an exception
-                               }
-                       });
-                       fail("should have thrown exception");
-               } catch (IllegalStateException e)
-               {
-                       
assertTrue(e.getMessage().contains("super.onAddToPage"));
-               }
-       }
-
-       private Component createNestedProbe()
-       {
-               return createContainer().add(createProbe());
-       }
-
-       private MarkupContainer createContainer()
-       {
-               return new WebMarkupContainer("bar");
-       }
-}

http://git-wip-us.apache.org/repos/asf/wicket/blob/4703c1ae/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..989b163
--- /dev/null
+++ b/wicket-core/src/test/java/org/apache/wicket/OnReAddTest.java
@@ -0,0 +1,155 @@
+/*
+ * 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 Component createUninitializedProbe()
+       {
+               return new Label("foo")
+               {
+                       @Override
+                       protected void onReAdd()
+                       {
+                               super.onReAdd();
+                               onReAddCalled = true;
+                       }
+               };
+       }
+
+       private Component createInitializedProbe() {
+               Component probe = createUninitializedProbe();
+               probe.internalInitialize();
+               return probe;
+       }
+
+       @Test
+       public void onAddIsNotCalledOnFirstAdd()
+       {
+               Page page = createPage();
+               page.internalInitialize();
+               page.add(createUninitializedProbe());
+               assertFalse(onReAddCalled);
+       }
+
+       private WebPage createPage()
+       {
+               return new WebPage()
+               {
+               };
+       }
+
+       @Test
+       public void onAddIsNotCalledWhenParentIsNotConnectedToPage()
+       {
+               MarkupContainer container = createContainer();
+               container.internalInitialize();
+               container.add(createUninitializedProbe());
+               assertFalse(onReAddCalled);
+       }
+
+       @Test
+       public void 
onAddIsNotCalledOnUninitializedProbeWhenParentIsAddedToPage()
+       {
+               MarkupContainer container = createContainer();
+               container.internalInitialize();
+               container.add(createUninitializedProbe());
+               assertFalse(onReAddCalled);
+               WebPage page = createPage();
+               page.internalInitialize();
+               page.add(container);
+               assertFalse(onReAddCalled);
+       }
+
+       @Test
+       public void onAddIsCalledAfterRemoveAndAdd()
+       {
+               Page page = createPage();
+               page.internalInitialize();
+               Component probe = createUninitializedProbe();
+               page.add(probe);
+               assertFalse(onReAddCalled);
+               page.remove(probe);
+               assertFalse(onReAddCalled);
+               page.add(probe);
+               assertTrue(onReAddCalled);
+       }
+
+       @Test
+       public void onAddRecursesToChildren()
+       {
+               Page page = createPage();
+               page.internalInitialize();
+               Component probe = createNestedProbe();
+               page.add(probe);
+               assertFalse(onReAddCalled);
+               probe.remove();
+               assertFalse(onReAddCalled);
+               page.add(probe);
+               assertTrue(onReAddCalled);
+       }
+
+       @Test
+       public void onAddEnforcesSuperCall()
+       {
+               Page page = createPage();
+               page.internalInitialize();
+               try
+               {
+                       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);
+                       fail("should have thrown exception");
+               } catch (IllegalStateException e)
+               {
+                       assertTrue(e.getMessage().contains("super.onReAdd"));
+               }
+       }
+
+       private Component createNestedProbe()
+       {
+               return createContainer().add(createUninitializedProbe());
+       }
+
+       private MarkupContainer createContainer()
+       {
+               return new WebMarkupContainer("bar");
+       }
+}

Reply via email to