[MANUAL] English:
[zend.git] / documentation / manual / en / module_specs / Zend_Controller-Request.xml
blob9d3b51a655c8e1c5a2f0aa54856e0e36d6ebd51e
1 <?xml version="1.0" encoding="UTF-8"?>
2 <!-- Reviewed: no -->
3 <sect1 id="zend.controller.request">
4     <title>The Request Object</title>
6     <sect2 id="zend.controller.request.introduction">
7         <title>Introduction</title>
9         <para>
10             The request object is a simple value object that is passed between
11             <classname>Zend_Controller_Front</classname> and the router, dispatcher, and
12             controller classes. It packages the names of the requested module,
13             controller, action, and optional parameters, as well as the rest of
14             the request environment, be it <acronym>HTTP</acronym>, the <acronym>CLI</acronym>, or
15             <acronym>PHP</acronym>-GTK.
16         </para>
18         <itemizedlist>
19             <listitem>
20                 <para>
21                     The module name is accessed by <methodname>getModuleName()</methodname> and
22                     <methodname>setModuleName()</methodname>.
23                 </para>
24             </listitem>
26             <listitem>
27                 <para>
28                     The controller name is accessed by <methodname>getControllerName()</methodname>
29                     and <methodname>setControllerName()</methodname>.
30                 </para>
31             </listitem>
33             <listitem>
34                 <para>
35                     The name of the action to call within that controller is
36                     accessed by <methodname>getActionName()</methodname> and
37                     <methodname>setActionName()</methodname>.
38                 </para>
39             </listitem>
41             <listitem>
42                 <para>
43                     Parameters to be accessible by the action are an associative array
44                     of key and value pairs that are retrieved by
45                     <methodname>getParams()</methodname> and set with
46                     <methodname>setParams()</methodname>, or individually by
47                     <methodname>getParam()</methodname> and <methodname>setParam()</methodname>.
48                 </para>
49             </listitem>
50         </itemizedlist>
52         <para>
53             Based on the type of request, there may be more methods available.
54             The default request used, <classname>Zend_Controller_Request_Http</classname>,
55             for instance, has methods for retrieving the request <acronym>URI</acronym>, path
56             information, <varname>$_GET</varname> and <varname>$_POST</varname> parameters,
57             etc.
58         </para>
60         <para>
61             The request object is passed to the front controller, or if none is
62             provided, it is instantiated at the beginning of the dispatch
63             process, before routing occurs. It is passed through to every object
64             in the dispatch chain.
65         </para>
67         <para>
68             Additionally, the request object is particularly useful in testing.
69             The developer may craft the request environment, including module,
70             controller, action, parameters, <acronym>URI</acronym>, etc, and pass the request
71             object to the front controller to test application flow. When paired
72             with the <link linkend="zend.controller.response">response
73                 object</link>, elaborate and precise unit testing of <acronym>MVC</acronym>
74             applications becomes possible.
75         </para>
76     </sect2>
78     <sect2 id="zend.controller.request.http">
79         <title>HTTP Requests</title>
81         <sect3 id="zend.controller.request.http.dataacess">
82             <title>Accessing Request Data</title>
84             <para>
85                 <classname>Zend_Controller_Request_Http</classname> encapsulates access to
86                 relevant values such as the key name and value for the
87                 controller and action router variables, and all additional
88                 parameters parsed from the <acronym>URI</acronym>. It additionally allows access to
89                 values contained in the superglobals as public members, and
90                 manages the current Base <acronym>URL</acronym> and Request <acronym>URI</acronym>.
91                 Superglobal values cannot be set on a request object, instead use the
92                 <methodname>setParam()</methodname> and <methodname>getParam()</methodname> methods
93                 to set or retrieve user parameters.
94             </para>
96             <note>
97                 <title>Superglobal Data</title>
99                 <para>
100                     When accessing superglobal data through
101                     <classname>Zend_Controller_Request_Http</classname> as public member
102                     properties, it is necessary to keep in mind that the
103                     property name (superglobal array key) is matched to a
104                     superglobal in a specific order of precedence: 1. <constant>GET</constant>, 2.
105                     <constant>POST</constant>, 3. <constant>COOKIE</constant>, 4.
106                     <constant>SERVER</constant>, 5. <constant>ENV</constant>.
107                 </para>
108             </note>
110             <para>
111                 Specific superglobals can be accessed using a public method as
112                 an alternative. For example, the raw value of
113                 <varname>$_POST['user']</varname> can be accessed by calling
114                 <methodname>getPost('user')</methodname> on the request object. These
115                 include <methodname>getQuery()</methodname> for retrieving
116                 <varname>$_GET</varname> elements, and <methodname>getHeader()</methodname> for
117                 retrieving request headers.
118             </para>
120             <note>
121                 <title>GET and POST Data</title>
123                 <para>
124                     Be cautious when accessing data from the request object as
125                     it is not filtered in any way. The router and dispatcher
126                     validate and filter data for use with their tasks, but leave
127                     the data untouched in the request object.
128                 </para>
129             </note>
131             <note>
132                 <title>Retrieving the Raw POST Data</title>
134                 <para>
135                     As of 1.5.0, you can also retrieve the raw post data via the
136                     <methodname>getRawBody()</methodname> method. This method returns
137                     <constant>FALSE</constant> if no data was submitted in that fashion, but the
138                     full body of the post otherwise.
139                 </para>
141                 <para>
142                     This is primarily useful for accepting content when
143                     developing a RESTful <acronym>MVC</acronym> application.
144                 </para>
145             </note>
147             <para>
148                 You may also set user parameters in the request object using
149                 <methodname>setParam()</methodname> and retrieve these later using
150                 <methodname>getParam()</methodname>. The router makes use of this
151                 functionality to set parameters matched in the request <acronym>URI</acronym> into
152                 the request object.
153             </para>
155             <note>
156                 <title>getParam() Retrieves More than User Parameters</title>
158                 <para>
159                     In order to do some of its work, <methodname>getParam()</methodname> actually
160                     retrieves from several sources. In order of priority, these
161                     include: user parameters set via <methodname>setParam()</methodname>,
162                     <constant>GET</constant> parameters, and finally <constant>POST</constant>
163                     parameters. Be aware of this when pulling data via this
164                     method.
165                 </para>
167                 <para>
168                     If you wish to pull only from parameters you set via
169                     <methodname>setParam()</methodname>, use the
170                     <methodname>getUserParam()</methodname>.
171                 </para>
173                 <para>
174                     Additionally, as of 1.5.0, you can lock down which parameter
175                     sources will be searched. <methodname>setParamSources()</methodname>
176                     allows you to specify an empty array or an array with one or
177                     more of the values '_GET' or '_POST' indicating which
178                     parameter sources are allowed (by default, both are
179                     allowed); if you wish to restrict access to only '_GET'
180                     specify <methodname>setParamSources(array('_GET'))</methodname>.
181                 </para>
182             </note>
184             <note>
185                 <title>Apache Quirks</title>
187                 <para>
188                     If you are using Apache's 404 handler to pass incoming
189                     requests to the front controller, or using a PT flag with
190                     rewrite rules, <varname>$_SERVER['REDIRECT_URL']</varname>
191                     contains the <acronym>URI</acronym> you need, not
192                     <varname>$_SERVER['REQUEST_URI']</varname>. If you are using such
193                     a setup and getting invalid routing, you should use the
194                     <classname>Zend_Controller_Request_Apache404</classname> class instead
195                     of the default <acronym>HTTP</acronym> class for your request object:
196                 </para>
198                 <programlisting language="php"><![CDATA[
199 $request = new Zend_Controller_Request_Apache404();
200 $front->setRequest($request);
201 ]]></programlisting>
203                 <para>
204                     This class extends the
205                     <classname>Zend_Controller_Request_Http</classname> class and simply
206                     modifies the autodiscovery of the request <acronym>URI</acronym>. It can be
207                     used as a drop-in replacement.
208                 </para>
209             </note>
210         </sect3>
212         <sect3 id="zend.controller.request.http.baseurl">
213             <title>Base Url and Subdirectories</title>
215             <para>
216                 <classname>Zend_Controller_Request_Http</classname> allows
217                 <classname>Zend_Controller_Router_Rewrite</classname> to be used in subdirectories.
218                 <classname>Zend_Controller_Request_Http</classname> will attempt to automatically
219                 detect your base <acronym>URL</acronym> and set it accordingly.
220             </para>
222             <para>
223                 For example, if you keep your <filename>index.php</filename> in a
224                 webserver subdirectory named
225                 <filename>/projects/myapp/index.php</filename>, base <acronym>URL</acronym> (rewrite
226                 base) should be set to <filename>/projects/myapp</filename>. This string will
227                 then be stripped from the beginning of the path before
228                 calculating any route matches. This frees one from the necessity
229                 of prepending it to any of your routes. A route of
230                 <command>'user/:username'</command> will match <acronym>URI</acronym>s like
231                 <filename>http://localhost/projects/myapp/user/martel</filename> and
232                 <filename>http://example.com/user/martel</filename>.
233             </para>
235             <note>
236                 <title>URL Detection is Case Sensitive</title>
238                 <para>
239                     Automatic base <acronym>URL</acronym> detection is case sensitive, so make sure
240                     your <acronym>URL</acronym> will match a subdirectory name in a filesystem (even
241                     on Windows machines). If it doesn't, an exception will be raised.
242                 </para>
243             </note>
245             <para>
246                 Should base <acronym>URL</acronym> be detected incorrectly you can override it
247                 with your own base path with the help of the
248                 <methodname>setBaseUrl()</methodname> method of either the
249                 <classname>Zend_Controller_Request_Http</classname> class, or the
250                 <classname>Zend_Controller_Front</classname> class. The easiest
251                 method is to set it in <classname>Zend_Controller_Front</classname>,
252                 which will proxy it into the request object. Example usage to
253                 set a custom base <acronym>URL</acronym>:
254             </para>
256             <programlisting language="php"><![CDATA[
258  * Dispatch Request with custom base URL with Zend_Controller_Front.
259  */
260 $router     = new Zend_Controller_Router_Rewrite();
261 $controller = Zend_Controller_Front::getInstance();
262 $controller->setControllerDirectory('./application/controllers')
263            ->setRouter($router)
264            ->setBaseUrl('/projects/myapp'); // set the base url!
265 $response   = $controller->dispatch();
266 ]]></programlisting>
267         </sect3>
269         <sect3 id="zend.controller.request.http.method">
270             <title>Determining the Request Method</title>
272             <para>
273                 <methodname>getMethod()</methodname> allows you to determine the
274                 <acronym>HTTP</acronym> request method used to request the current resource.
275                 Additionally, a variety of methods exist that allow you to get
276                 boolean responses when asking if a specific type of request has
277                 been made:
278             </para>
280             <itemizedlist>
281                 <listitem><para><methodname>isGet()</methodname></para></listitem>
282                 <listitem><para><methodname>isPost()</methodname></para></listitem>
283                 <listitem><para><methodname>isPut()</methodname></para></listitem>
284                 <listitem><para><methodname>isDelete()</methodname></para></listitem>
285                 <listitem><para><methodname>isHead()</methodname></para></listitem>
286                 <listitem><para><methodname>isOptions()</methodname></para></listitem>
287             </itemizedlist>
289             <para>
290                 The primary use case for these is for creating RESTful <acronym>MVC</acronym>
291                 architectures.
292             </para>
293         </sect3>
295         <sect3 id="zend.controller.request.http.ajax">
296             <title>Detecting AJAX Requests</title>
298             <para>
299                 <classname>Zend_Controller_Request_Http</classname> has a rudimentary
300                 method for detecting <acronym>AJAX</acronym> requests:
301                 <methodname>isXmlHttpRequest()</methodname>. This method looks for an
302                 <acronym>HTTP</acronym> request header <emphasis>X-Requested-With</emphasis> with
303                 the value 'XMLHttpRequest'; if found, it returns <constant>TRUE</constant>.
304             </para>
306             <para>
307                 Currently, this header is known to be passed by default with the
308                 following JS libraries:
309             </para>
311             <itemizedlist>
312                 <listitem>
313                     <para>Prototype and Scriptaculous (and libraries derived from Prototype)</para>
314                 </listitem>
316                 <listitem><para>Yahoo! UI Library</para></listitem>
317                 <listitem><para>jQuery</para></listitem>
318                 <listitem><para>MochiKit</para></listitem>
319             </itemizedlist>
321             <para>
322                 Most <acronym>AJAX</acronym> libraries allow you to send custom
323                 <acronym>HTTP</acronym> request headers; if your library does not send this header,
324                 simply add it as a request header to ensure the
325                 <methodname>isXmlHttpRequest()</methodname> method works for you.
326             </para>
327         </sect3>
328     </sect2>
330     <sect2 id="zend.controller.request.subclassing">
331         <title>Subclassing the Request Object</title>
333         <para>
334             The base request class used for all request objects is the abstract
335             class <classname>Zend_Controller_Request_Abstract</classname>. At its most
336             basic, it defines the following methods:
337         </para>
339         <programlisting language="php"><![CDATA[
340 abstract class Zend_Controller_Request_Abstract
342     /**
343      * @return string
344      */
345     public function getControllerName();
347     /**
348      * @param string $value
349      * @return self
350      */
351     public function setControllerName($value);
353     /**
354      * @return string
355      */
356     public function getActionName();
358     /**
359      * @param string $value
360      * @return self
361      */
362     public function setActionName($value);
364     /**
365      * @return string
366      */
367     public function getControllerKey();
369     /**
370      * @param string $key
371      * @return self
372      */
373     public function setControllerKey($key);
375     /**
376      * @return string
377      */
378     public function getActionKey();
380     /**
381      * @param string $key
382      * @return self
383      */
384     public function setActionKey($key);
386     /**
387      * @param string $key
388      * @return mixed
389      */
390     public function getParam($key);
392     /**
393      * @param string $key
394      * @param mixed $value
395      * @return self
396      */
397     public function setParam($key, $value);
399     /**
400      * @return array
401      */
402      public function getParams();
404     /**
405      * @param array $array
406      * @return self
407      */
408     public function setParams(array $array);
410     /**
411      * @param boolean $flag
412      * @return self
413      */
414     public function setDispatched($flag = true);
416     /**
417      * @return boolean
418      */
419     public function isDispatched();
421 ]]></programlisting>
423         <para>
424             The request object is a container for the request environment. The
425             controller chain really only needs to know how to set and retrieve the
426             controller, action, optional parameters, and dispatched status. By
427             default, the request will search its own parameters using the
428             controller or action keys in order to determine the controller and
429             action.
430         </para>
432         <para>
433             Extend this class, or one of its derivatives, when you need the
434             request class to interact with a specific environment in order to
435             retrieve data for use in the above tasks. Examples include <link
436                 linkend="zend.controller.request.http">the <acronym>HTTP</acronym>
437                 environment</link>, a <acronym>CLI</acronym> environment, or a
438             <acronym>PHP</acronym>-GTK environment.
439         </para>
440     </sect2>
441 </sect1>
442 <!--
443 vim:se ts=4 sw=4 et: