Reputation: 1139
I'm writing a web application that needs to make use of module CGI::Session ver 4.35. Upon receiving request from the client with an SESSIONID string
$sid = $cgi->cookie("CGISESSID") || $cgi->param("CGISESSID") || undef;
it tries to recreate the session by passing the $sid as an argument
$session = new CGI::Session($sid) or ($logger->error(CGI::Session->errstr) and die);
If there was an session created with that sid, $session->id
and $sid
are suppose to be the same, but the truth is it's NOT.
This is the statement where I create a completely new session
$session = new CGI::Session("id:md5", undef, {Directory=>$SESSION_DIR})
or ($logger->error(CGI::Session->errstr) and die);
What went wrong here? How am I supposed to use the module CGI::Session correctly?
Upvotes: 1
Views: 2983
Reputation: 13381
I'm the maintainer of CGI::Session. I recommend creating the session the same way in all cases, like this:
$session = CGI::Session->new("id:md5", $cgi, {Directory=>$SESSION_DIR});
This follows the recommended syntax in the docs for new(). I also recommend making sure that you call flush() explicitly near the end of the script. The reason for that is explained more here:
http://metacpan.org/pod/CGI::Session#A-Warning-about-Auto-flushing
Upvotes: 5
Reputation: 21
there really is no need for you to grab the session cookie yourself. If you pass a CGI object instance to CGI::Session it does it for you. So, basically, the above code by jfd can be re-written like this:
my $session = CGI::Session->new( $query );
$self->header_props(-cookie => $session->cookie);
And $query->cookie()
and if/else
blocks are all redundant, because they already exist in CGI::Session's logic!
So the above code checks for client's cookie named CGI::Session->name
(which defaults to CGISESSID
). If it doesn't exist, looks for query parameter in the URL or request's body named CGI::Session->name
(which also defaults to CGISESSID
). If it can get claimed session id it tries to load its data into the session. If the session id cannot be validated (either expired, or forged) it ignores it, and creates a brand new, empty session.
If the session id cannot be found in either cookie nor in URL parameters it creates a new session.
most examples of session management I see out there try to re-invent the session logic inside the code while using CGI::Session. I'm just here to tell you that all that code is completely redundant!!!
Enjoy using CGI::Session!
Upvotes: 2
Reputation: 26
So, I'm not clear why you are creating the session twice? You want to first try and get the sid, and then create the session with it, whether it exists or not. If it doesn't exist, set the cookie. It's been awhile, but I pulled this from an old piece of code...
my $sid = $query->cookie('CGISESSID') || undef;
# grab the session obj, if one already exists otherwise create one
my $session = new CGI::Session( "id:md5", $sid, { Directory => $SESSION_DIR } );
# If there is no user cookie, or it's non existent, we give them a new one
if ( !$sid or $sid ne $session->id ) {
my $cookie = $query->cookie(
-name => 'CGISESSID',
-value => $session->id,
-expires => EXPIRE_TIME
);
$self->header_props( -cookie => $cookie );
}
Upvotes: 0