[Catalyst] Still weird behavior in sessions and cookies (Hey
Nothingmuch:!)
Bill Moseley
moseley at hank.org
Sun Dec 2 20:03:22 GMT 2007
I'm hoping I've got something configured wrong, but session and cookie
handling still seem to have a problems.
This has been an ongoing problem. I'm all up-to-date with Catalyst
and Plugins. What I see, once in a while is a state where the browser
returns a cookie. The returned session id is invalid, so a new
session id is created. But, when the new Set-Cookie headers is added
it's yet a 2nd session id.
In that case I think the session is getting cleared before the cookie
is created, so when it is created a new session id is generated.
Anyway, that's not much help without some examples.
My code was overriding calculate_session_cookie_expires() to implement
"Remember Me". So I removed that and now trying to use the
Session::DynamicExpiry plugin.
So I have some overrides to print out the stages. So I see:
--- in dispatch --
--- in default -- with sid = 35028fd915cc76898ca6ab47b82d8d990193818c
--- in finailze_headers --
--- in calculate_session_cookie_expires
--- in update_session_cookie
Which seems like a good order. But sometimes, and I'm not sure, but I
think this happens when a session expires, I see:
--- in dispatch --
--- in calculate_session_cookie_expires
--- in update_session_cookie
--- in default -- with sid = 35028fd915cc76898ca6ab47b82d8d990193818c
--- in finailze_headers --
Which makes it kind of hard to effect the cookies in an action
(default) *after* the cookie has been created. If you wait for a
while and then reload then this
Now, specifically, with the Session::DynamicExpiry plugin I'm not
having much luck. I want a session cookie unless they click "remember
me".
I'll attach a simple application, but I'm seeing a ttl set to zero but
still a date 5 minutes into the future.
finalize_headers => {
now => "Sun Dec 2 20:00:00 2007",
response_cookie => [
"foo_cookie=4c280674aa273f6b6f624b812938f8dc42208506",
"path=/",
"expires=Sun, 02-Dec-2007 20:05:00 GMT",
],
session => {
__created => 1196625501,
__time_to_live => 0,
__updated => 1196625534,
hello => "howdy",
},
},
}
See attached for app to play with.
--
Bill Moseley
moseley at hank.org
-------------- next part --------------
package Foo;
use strict;
use warnings;
use Catalyst::Runtime;
use Catalyst (
'Cache', # Configurable cache system
'Cache::Store::FastMmap', # Since FastMmap doesn't conform to Cache standards
'Session', # Session Management
'Session::Store::Cache', # Use the cache to store sessions
'Session::State::Cookie', # And use cookies for state.
'Session::DynamicExpiry' # To alter the cookie session time per-session.
);
my $cookie_name = 'foo_cookie';
__PACKAGE__->config(
name => 'Foo',
session => {
cookie_name => $cookie_name,
cookie_expires => 300, # Use session cookies by default
expires => 120, # How long to keep sessions/cooke
},
cache => {
backends => {
default => {
class => 'Cache::FastMmap',
expire_time => 300,
share_file => '/tmp/Foo_share_file',
},
},
},
);
__PACKAGE__->setup;
sub default : Private {
my ( $self, $c ) = @_;
$c->session->{hello} = 'howdy'; # Force cookie
warn "--- in default -- with sid = " . $c->sessionid . "\n";
my $param = $c->req->parameters->{date} || 0;
if ( $param eq 'y' ) {
$c->res->body( 'cookie should have date' );
$c->session_time_to_live( 300 );
}
elsif ( $param eq 'n' ) {
delete $c->session->{remember_me};
$c->res->body( 'remember me deleted -- session cookie' );
$c->session_time_to_live( 0 );
}
else {
$c->res->body( 'should be no change' );
}
}
sub update_session_cookie {
my $c = shift;
warn "--- in update_session_cookie\n";
return $c->NEXT::update_session_cookie( @_ );
}
sub calculate_session_cookie_expires {
my $c = shift;
warn "--- in calculate_session_cookie_expires\n";
return $c->NEXT::calculate_session_cookie_expires( @_ );
}
sub dispatch {
my $c = shift;
warn "--- in dispatch --\n";
$c->NEXT::dispatch;
}
sub xdispatch {
my $c = shift;
warn "--- in dispatch --\n";
my $session_expires = defined $c->session_expires ? $c->session_expires : 'not set';
my $calculate = 'skipped'; # $c->calculate_session_cookie_expires || 'not set';
for ( $session_expires, $calculate ) {
next unless $_ && /\d+/;
$_ = scalar gmtime $_;
}
my $cookie = $c->req->cookie( $cookie_name ) ? $c->req->cookie( $cookie_name )->value : 'no cookie provided';
$c->stash->{stuff}{path} = $c->req->path;
$c->stash->{stuff}{dispatch} = {
parameters => $c->req->parameters,
request_cookie => $cookie,
sessionid => $c->sessionid || 'none',
now => scalar gmtime,
session_expires => $session_expires,
remember_me => $c->session->{remember_me} || '0',
calculate => $calculate,
};
$c->NEXT::dispatch;
}
sub finalize_headers {
my $c = shift;
warn "--- in finailze_headers --\n";
$c->NEXT::finalize_headers( @_ );
my $cookie = $c->res->header( 'set-cookie' );
$cookie = [ split /;\s*/, $cookie ] if $cookie;
$c->stash->{stuff}{finalize_headers} = {
response_cookie => $cookie,
session => $c->session,
now => scalar gmtime,
};
$c->log->_dump( $c->stash->{stuff} );
}
1;
More information about the Catalyst
mailing list