001 // Copyright 2004, 2005 The Apache Software Foundation
002 //
003 // Licensed under the Apache License, Version 2.0 (the "License");
004 // you may not use this file except in compliance with the License.
005 // You may obtain a copy of the License at
006 //
007 // http://www.apache.org/licenses/LICENSE-2.0
008 //
009 // Unless required by applicable law or agreed to in writing, software
010 // distributed under the License is distributed on an "AS IS" BASIS,
011 // WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
012 // See the License for the specific language governing permissions and
013 // limitations under the License.
014
015 package org.apache.tapestry;
016
017 import java.util.Locale;
018
019 import org.apache.tapestry.event.ChangeObserver;
020 import org.apache.tapestry.event.PageAttachListener;
021 import org.apache.tapestry.event.PageBeginRenderListener;
022 import org.apache.tapestry.event.PageDetachListener;
023 import org.apache.tapestry.event.PageEndRenderListener;
024 import org.apache.tapestry.event.PageValidateListener;
025 import org.apache.tapestry.services.ResponseBuilder;
026 import org.apache.tapestry.util.ContentType;
027
028 /**
029 * A root level component responsible for generating an entire a page within the application.
030 * <p>
031 * Pages are created dynamically from thier class names (part of the
032 * {@link org.apache.tapestry.spec.IComponentSpecification}).
033 *
034 * @see org.apache.tapestry.engine.IPageSource
035 * @see org.apache.tapestry.engine.IPageLoader
036 * @author Howard Lewis Ship
037 */
038
039 public interface IPage extends IComponent
040 {
041 /**
042 * Invoked on a page when it is no longer needed by the engine, just before is is returned to
043 * the pool. The page is expected to null the engine, visit and changeObserver properties.
044 * <p>
045 * Classes should also reset any properties to default values (as if the instance was freshly
046 * instantiated).
047 *
048 * @see org.apache.tapestry.engine.IPageSource#releasePage(IPage)
049 */
050
051 void detach();
052
053 /**
054 * Returns the {@link IEngine}that the page is currently attached to.
055 */
056
057 IEngine getEngine();
058
059 /**
060 * Returns the object (effectively, an {@link org.apache.tapestry.engine.IPageRecorder}) that
061 * is notified of any changes to persistant properties of the page.
062 */
063
064 ChangeObserver getChangeObserver();
065
066 /**
067 * Returns the <code>Locale</code> of the page. The locale may be used to determine what
068 * template is used by the page and the components contained by the page.
069 */
070
071 Locale getLocale();
072
073 /**
074 * Updates the page's locale. This is write-once, a subsequent attempt will throw an
075 * {@link ApplicationRuntimeException}.
076 */
077
078 void setLocale(Locale value);
079
080 /**
081 * Returns the fully qualified name of the page, including its namespace prefix, if any.
082 *
083 * @since 2.3
084 */
085
086 String getPageName();
087
088 /**
089 * Sets the name of the page.
090 *
091 * @param pageName
092 * fully qualified page name (including namespace prefix, if any)
093 * @since 3.0
094 */
095
096 void setPageName(String pageName);
097
098 /**
099 * Returns a particular component from within the page. The path is a dotted name sequence
100 * identifying the component. It may be null in which case the page returns itself.
101 *
102 * @exception ApplicationRuntimeException
103 * runtime exception thrown if the path does not identify a component.
104 */
105
106 IComponent getNestedComponent(String path);
107
108 /**
109 * Attaches the page to the {@link IEngine engine}. This method is used when a pooled page is
110 * claimed for use with a particular engine; it will stay attached to the engine until the end
111 * of the current request cycle, then be returned to the pool.
112 * <p>
113 * This method will notify any {@link PageAttachListener}s.
114 * <p>
115 * This method is rarely overriden; to initialize page properties before a render, implement the
116 * {@link PageBeginRenderListener}interface.
117 */
118
119 void attach(IEngine engine, IRequestCycle cycle);
120
121 /**
122 * Used to explicitly fire {@link PageAttachListener}s for this page. This is used when a page
123 * is first loaded; The page loader attaches the newly created page <em>instance</em> before
124 * the rest of the page and components is loaded. In order to have meaningful event
125 * notifications when a page is first loaded (rather than pulled from the pool), it is necessary
126 * to fire page attach listeners at the end of the load.
127 *
128 * @since 4.0
129 */
130
131 void firePageAttached();
132
133 /**
134 * Invoked to render the entire page. This should only be invoked by
135 * {@link IRequestCycle#renderPage(ResponseBuilder builder)}.
136 * <p>
137 * The page performs a render using the following steps:
138 * <ul>
139 * <li>Invokes
140 * {@link PageBeginRenderListener#pageBeginRender(org.apache.tapestry.event.PageEvent)}
141 * <li>Invokes {@link #beginResponse(IMarkupWriter, IRequestCycle)}
142 * <li>Invokes {@link IRequestCycle#commitPageChanges()}(if not rewinding)
143 * <li>Invokes {@link #render(IMarkupWriter, IRequestCycle)}
144 * <li>Invokes {@link PageEndRenderListener#pageEndRender(org.apache.tapestry.event.PageEvent)}
145 * (this occurs even if a previous step throws an exception).
146 * </ul>
147 */
148
149 void renderPage(ResponseBuilder builder, IRequestCycle cycle);
150
151 /**
152 * Invoked before a partial render of the page occurs (this happens when rewinding a
153 * {@link org.apache.tapestry.form.Form}within the page). The page is expected to fire
154 * appopriate events.
155 *
156 * @since 2.2
157 */
158
159 void beginPageRender();
160
161 /**
162 * Invoked after a partial render of the page occurs (this happens when rewinding a
163 * {@link org.apache.tapestry.form.Form}within the page). The page is expected to fire
164 * appropriate events.
165 *
166 * @since 2.2
167 */
168
169 void endPageRender();
170
171 void setChangeObserver(ChangeObserver value);
172
173 /**
174 * Method invoked by the page, action and direct services to validate that the user is allowed
175 * to visit the page.
176 * <p>
177 * Most web applications have a concept of 'logging in' and pages that an anonymous (not logged
178 * in) user should not be able to visit directly. This method acts as the first line of defense
179 * against a malicous user hacking URLs.
180 * <p>
181 * Pages that should be protected will typically throw a {@linkPageRedirectException}, to
182 * redirect the user to an appropriate part of the system (such as, a login page).
183 * <p>
184 * Since 3.0, it is easiest to not override this method, but to implement the
185 * {@link PageValidateListener}interface instead.
186 */
187
188 void validate(IRequestCycle cycle);
189
190 /**
191 * Invoked to obtain the content type to be used for the response. The implementation of this
192 * method is the primary difference between an HTML page and an XML/WML/etc. page.
193 */
194
195 ContentType getResponseContentType();
196
197 /**
198 * Invoked just before rendering of the page is initiated. This gives the page a chance to
199 * perform any additional setup. One possible behavior is to set HTTP headers and cookies before
200 * any output is generated.
201 * <p>
202 * The timing of this explicitly <em>before</em>
203 * {@link org.apache.tapestry.engine.IPageRecorder page recorder}changes are committed.
204 * Rendering occurs <em>after</em> the recorders are committed, when it is too late to make
205 * changes to dynamic page properties.
206 */
207
208 void beginResponse(IMarkupWriter writer, IRequestCycle cycle);
209
210 /**
211 * Returns the current {@link IRequestCycle}. This is set when the page is loaded (or obtained
212 * from the pool) and attached to the {@link IEngine engine}.
213 */
214
215 IRequestCycle getRequestCycle();
216
217 /** @since 4.0 */
218 void addPageBeginRenderListener(PageBeginRenderListener listener);
219
220 /** @since 4.0 */
221 void removePageBeginRenderListener(PageBeginRenderListener listener);
222
223 /** @since 4.0 */
224
225 void addPageEndRenderListener(PageEndRenderListener listener);
226
227 /** @since 4.0 */
228
229 void removePageEndRenderListener(PageEndRenderListener listener);
230
231 /**
232 * @since 1.0.5
233 */
234
235 void addPageDetachListener(PageDetachListener listener);
236
237 /**
238 * @since 2.1
239 */
240
241 void removePageDetachListener(PageDetachListener listener);
242
243 /**
244 * @since 3.0
245 */
246
247 void addPageValidateListener(PageValidateListener listener);
248
249 /**
250 * @since 3.0
251 */
252
253 void removePageValidateListener(PageValidateListener listener);
254
255 /** @since 4.0 */
256
257 void addPageAttachListener(PageAttachListener listener);
258
259 /** @since 4.0 */
260
261 void removePageAttachListener(PageAttachListener listener);
262 }