- Introduction
- The Apache Request Object
- The HTTP Request Message
- The Client Request
- Accessing Client Request Headers
- Accessing HTML Form Fields
- Reading POSTed Data Manually
- Manipulating Cookies
- Handling File Uploads
- Setting Server Response Headers
- Controlling Caching Behavior
- Sending Server Response Headers
- Setting the Response Status
- Setting Error Headers
- Manipulating Headers with Multiple Like Fields
- Using Subrequests
- Setting Headers for Subrequests
- Short-Circuiting Subrequests
- Getting or Setting the Request Method
- Accessing the Request Object from XS
Manipulating Cookies
You need to store persistent data on the client browser by accessing and creating cookies.
Technique
Use the Apache::Cookie module, which provides a simple, object-oriented interface to cookies.
This example reads cookies from the client request, and prints the name and value:
use Apache::Constants qw(OK); use Apache::Cookie; use Apache::Request; use strict; sub handler { my $r = Apache::Request->new(shift); my %cookiejar = Apache::Cookie->new($r)->parse; $r->send_http_header('text/plain'); foreach my $cookie (keys %cookiejar) { $r->print($cookiejar{$cookie}->name, " => ", $cookiejar{$cookie}->value, "\n"); } return OK; }
This code creates two cookies and sends them with the next response.
use Apache::Cookie; use Digest::MD5; use strict; sub handler { my $r = shift; my $md5 = Digest::MD5->new; $md5->add($$, time(), $r->dir_config('SECRET')); my $session_cookie = Apache::Cookie->new($r, -name => "sessionid", -value => $md5->hexdigest, -path => "/", -expires => "+10d" ); # Set the cookie. $session_cookie->bake(); my $identity_cookie = Apache::Cookie->new($r, -name => "identity", -value => 'Arthur McCurry', -path => "/hall_of_justice/", -expires => "+365d", -domain => ".superfriends.com", -secure => 1 ); # Change the value... $identity_cookie->value('aquaman'); # ... then set it. $identity_cookie->bake(); # Continue along... }
Comments
Apache::Cookie, like Apache::Request, is part of the libapreq package available on CPAN. Like Apache::Request, it has a C back-end that makes fast and direct calls to the Apache API, making it preferable to the CGI::Cookie interface on which it is based.
The Apache::Cookie class is used both to get and parse cookies from incoming requests and to create and send cookies on outgoing requests. Programmatically, you can pass in either an Apache::Request object as in the first example or, if you do not need to take advantage of any of Apache::Request's added features, you can just use the standard Apache request object, as shown in the second example. In both cases you will need to use Apache::Cookie's bake() method to actually send your cookies to the client.
Reading cookies is quite easy. Create an empty cookie object with new() method and then call parse(). This method returns either a hash or a hash reference that maps cookie names to cookie objects.
Creating cookies is easy, too. Just specify named parameters to the new() method for your cookie, like -name and -value, after which you can call methods to get and set the cookie's data elements. These methods all return the value of the data requested. Passing in an argument to any of these methods will change the value and return the new value. Table 3.4 summarizes the available methods and the corresponding named parameters used in the new() method.
Table 3.4 Apache::Cookie Methods
Method Name |
Named Parameter for new() |
Notes |
name() |
name |
The name of the cookie. |
value() |
value |
The value of this cookie; it can be a scalar or an array. |
domain() |
domain |
Specifies that this cookie should be sent to all hosts that end with the specified domain. The domain must begin with a dot. |
path() |
path |
Ensures that this cookie is only sent to URLs that start with the specified path. |
expires() |
expires |
Determines when the cookie becomes stale. Use any absolute or relative date format allowed by CGI.pm. |
secure() |
secure |
If set, informs the client that the cookie should only be used on an encrypted (SSL) connection. |
The interesting thing to note is that bake() places the cookies into the err_headers_out table in the Apache request record, which makes them persist across redirects and other errors. See Recipe 3.13 for more details on the different outgoing headers.