Test for cookie expiration and extension behavior, add cookie_expires, disable condit...
[catagits/Catalyst-Plugin-Session-State-Cookie.git] / lib / Catalyst / Plugin / Session / State / Cookie.pm
index e865c3e..b0e18dd 100644 (file)
@@ -6,31 +6,66 @@ use warnings;
 
 use NEXT;
 
-sub finalize {
+our $VERSION = "0.01";
+
+sub setup_session {
     my $c = shift;
 
-    if ( my $sid = $c->sessionid ) {
-        my $cookie = $c->request->cookies->{session};
-        if ( !$cookie or $cookie->value ne $sid ) {
-            $c->response->cookies->{session} = { value => $sid };
-            $c->log->debug(qq/A cookie with the session id "$sid" was saved/)
-              if $c->debug;
-        }
-    }
+    $c->NEXT::setup_session(@_);
+
+    $c->config->{session}{cookie_name} ||= "session";
+}
+
+sub finalize_cookies {
+    my $c = shift;
+
+    if ( $c->sessionid) {
+               $c->update_session_cookie( $c->make_session_cookie );
+       }
+
+    return $c->NEXT::finalize_cookies(@_);
+}
+
+sub update_session_cookie {
+       my ( $c, $updated ) = @_;
+    my $cookie_name = $c->config->{session}{cookie_name};
+       $c->response->cookies->{$cookie_name} = $updated;
+}
+
+sub make_session_cookie {
+       my $c = shift;
 
-    return $c->NEXT::finalize(@_);
+       my $cfg = $c->config->{session};
+       my $cookie = {
+               value   => $c->sessionid,
+               ($cfg->{cookie_domain} ? (domain => $cfg->{cookie_domain}) : ()),
+       };
+
+       if ( exists $cfg->{cookie_expires} ) {
+               if ( my $ttl = $cfg->{cookie_expires} ) {
+                       $cookie->{expires} = time() + $ttl;
+               } # else { cookie is non-persistent }
+       } else {
+               $cookie->{expires} = $c->session->{__expires};
+       }
+
+       return $cookie;
 }
 
 sub prepare_cookies {
     my $c = shift;
 
-    if ( my $cookie = $c->request->cookies->{session} ) {
+    my $ret = $c->NEXT::prepare_cookies(@_);
+
+    my $cookie_name = $c->config->{session}{cookie_name};
+
+    if ( my $cookie = $c->request->cookies->{$cookie_name} ) {
         my $sid = $cookie->value;
         $c->sessionid($sid);
         $c->log->debug(qq/Found sessionid "$sid" in cookie/) if $c->debug;
     }
 
-    $c->NEXT::prepare_cookies(@_);
+    return $ret;
 }
 
 __PACKAGE__
@@ -45,7 +80,7 @@ Catalyst::Plugin::Session::State::Cookie - A session ID
 
 =head1 SYNOPSIS
 
-       use Catalyst qw/Session Session::State::Cookie Session::Store::Foo/;
+    use Catalyst qw/Session Session::State::Cookie Session::Store::Foo/;
 
 =head1 DESCRIPTION
 
@@ -62,12 +97,45 @@ This plugin stores the session ID on the client using the cookie mechanism.
 
 Will restore if an appropriate cookie is found.
 
-=item finalize
+=item finalize_cookies
 
-Will set a cookie called C<session> if it doesn't exist or if it's value is not the current session id.
+Will set a cookie called C<session> if it doesn't exist or if it's value is not
+the current session id.
+
+=item setup_session
+
+Will set the C<cookie_name> parameter to it's default value if it isn't set.
 
 =back
 
+=head1 CONFIGURATION
+
+=over 4
+
+=item cookie_name
+
+The name of the cookie to store (defaults to C<session>).
+
+=item cookie_domain
+
+The name of the domain to store in the cookie (defaults to current host)
+
+=back
+
+=item CAVEATS
+
+Sessions have to be created before the first write to be saved. For example:
+
+       sub action : Local {
+               my ( $self, $c ) = @_;
+               $c->res->write("foo");
+               $c->session( ... );
+               ...
+       }
+
+Will cause a session ID to not be set, because by the time a session is
+actually created the headers have already been sent to the client.
+
 =head1 SEE ALSO
 
 L<Catalyst>, L<Catalyst::Plugin::Session>.