#1
  1. No Profile Picture
    Contributing User
    Devshed Newbie (0 - 499 posts)

    Join Date
    Aug 2002
    Posts
    47
    Rep Power
    16

    reading existing session, problem


    I have created a very simple session example using CGI::Session. Which creates a session, writes a name to it and stores the session ID in a cookie. The initial page writes the cookie and creates the session successfully (have verified this), and will also allow access to the session info.

    However when i try and re call that information on a new page the session fails to recognise the exisitng session and sets up a new one, obviously defeating the whole point of using a session.

    The code i am using to create and re call the session on both pages is:

    #!/usr/bin/perl -w

    use CGI::Session qw/-api3/;

    use CGI qw(:standard escapeHTML);

    my $cgi = new CGI;

    my $session = new CGI::Session(undef, $cgi, {Directory=>"/tmp"});

    On the first page this is fine and creates the session, while on the second page this code doesnt locate the existing session and creates a new session. Any help or pointers would be much appreciated. I am beginning to think perhaps it may have something to do with my server, rather than the code.

    Thanks

    Buttie
  2. #2
  3. No Profile Picture
    A Member
    Devshed Newbie (0 - 499 posts)

    Join Date
    Dec 2002
    Location
    dk
    Posts
    267
    Rep Power
    19
    Try:
    Code:
    my $q = CGI->new;
    my $sid = $q->cookie("CGISESSID") || $q->param('CGISESSID') || undef;
    
    my $session = new CGI::Session(undef, $sid, {Directory=>'/tmp'});
    Basically that is the "long" way of doing what you had. However, it seems to work for me. You are checking for the session id in a cookie or query string. If there is one it will match the existing session else create a new one.

    Hope this helps
    Rob

    BTW: Does anyone know how NOT to create a new session if there is no session id found? ie prompt for a login instead...
  4. #3
  5. No Profile Picture
    Contributing User
    Devshed Newbie (0 - 499 posts)

    Join Date
    Aug 2002
    Posts
    47
    Rep Power
    16
    Thanks rob46 but i have all ready tried the longer version (was where i started) but with little joy. Produces the same result of not seeing the existing session and creating a new one instead.

    I presumed it was because it wasnt seeing the session id in the cookie or the query string, but i could actually print the CGISESID to the page so it wasnt that it couldnt get that info. Therefore i can only presume it cant match that session Id against the session id being held in the file on the server.

    I know the session file exists (have viewed it and its contents) so this means it must be looking for it in the wrong place or not looking for it all? Fair assumption? or does the problem lie within the code?

    Buttie
  6. #4
  7. No Profile Picture
    A Member
    Devshed Newbie (0 - 499 posts)

    Join Date
    Dec 2002
    Location
    dk
    Posts
    267
    Rep Power
    19
    Well your code looks fine as its straight out the examples on CPAN.
    I have to agree that it seems like it can't find an existing ID.

    Make sure that when you login (and create a new session):
    1 - the session is written to the file
    2 - the id has been sent via cookie or url.

    It wouldn't suprise me if no cookie has been set. Although if a cookie isn't sent it should send the ID via the query string. This has never worked for me though.

    Check the cookies is being baked
    Code:
      my $cookie = $q->cookie(CGISESSID => $session->id);
     
      print $q->redirect(-location=>'index.pl', -cookie => $cookie);
    Rob
  8. #5
  9. No Profile Picture
    Contributing User
    Devshed Newbie (0 - 499 posts)

    Join Date
    Aug 2002
    Posts
    47
    Rep Power
    16
    Cheers Rob

    Yeah the cookie is sitting there nice and pretty, with all the relevant info.

    However dont whether the session writing is working perfectly, the session is viewable on the server sometimes then other times it is not. However the session id is obtainable every time which would suggest that it is creating the session every time, other wise it would not be able to grab a session id or create the cookie?

    This is why i was thinking maybe some issue with the server.
  10. #6
  11. 11
    Devshed Demi-God (4500 - 4999 posts)

    Join Date
    Jul 2001
    Location
    Lynn, MA
    Posts
    4,635
    Rep Power
    86
    1) You have to manually put the session id in the query string. CGI::Session isn't magic.

    2) There's something wrong with your code, somewhere. I say this because I use CGI::Session (with a MySQL data store, but it shouldn't matter) in a number of apps and it works flawlessly.

    You aren't trying to set and retrieve a cookie on the same transaction, are you? This is impossible. It takes two transactions: one to set, on to retrieve.

    What's "-api3" ? I don't see it in the docs for the newest version.

    Read the docs again. By sending "undef" as the first argument to the new constructor, you're saying that you want to regenerate a new session everytime. Read CGI::Session::Cookbook and the CGI::Session docs proper.

    Here's some working code cut directly from an app of mine that uses CGI::Session::MySQL.

    Sorry about the extra verbosity- This is from an app where I was originally using my own sessioning system, and then upgraded to CGI::Session.

    Code:
    sub _initialize_session{
        my $self=shift;
        my $q=$self->query();
        my $dbh=$self->param('dbh');
        my $session_check=$q->cookie('sessionid') || $q->param('sessionid');
        # If there's a session parameter,  make sure it's a valid one.  If not,  then don't start a session and 
        # set them up as anonymous users.
        if (($session_check)) {
    #	my $sessionid = $q->param('sessionid') || $q->cookie('sessionid');
    	my $session = CGI::Session::MySQL->new($session_check,
    					       {
    						Handle=>$dbh,
    						LockHandle=>$dbh
    					       }
    					      ) 
    	  or die($CGI::Session::errstr);
    	my $sessionid=$session->id();
    
    	if (($sessionid ne $session_check)) {
    	    $self->param('accesslevels' => ['public']);
    	    $self->param('accesslevels_hash'=>{'public'=>1});
    	    $self->param('accesslevels_cache'=>'public');
    	    $self->param('firstname' => 'Anonymous');
    	    return $self->redirect_to_login('old_cookie','yes');
    	}
    	$self->param('sessionid'=>$sessionid);
    	$self->param('session'=>$session);
    	$self->param('accesslevels_hash'=>$session->param('accesslevels_hash'));
    	$self->param('accesslevels' => $session->param('accesslevels'));
    	$self->param('accesslevels_cache'=>$session->param('accesslevels_cache'));
    	$self->param('top_cats_cache_time'=>$session->param('top_cats_cache_time'));
    	$self->param('show_cat_cache_time'=>$session->param('show_cat_cache_time'));
    	$self->param('firstname' => $session->param('firstname'));
    	$self->param('logged_into_forum' => $session->param('logged_into_forum'));
    	$self->param('program' => $session->param('program'));
    	$self->param('username' => $session->param('username'));
        } else {
    	$self->param('accesslevels' => ['public']);
    	$self->param('accesslevels_hash'=>{'public'=>1});
    	$self->param('firstname' => 'Anonymous');
    	$self->param('accesslevels_cache'=>'public');
    	$self->param('top_cats_cache_time'=>$self->param('public_top_cats_cache_time'));
    	$self->param('show_cat_cache_time'=>$self->param('public_show_cat_cache_time'));
        }
    }
    ########################################
  12. #7
  13. No Profile Picture
    Contributing User
    Devshed Newbie (0 - 499 posts)

    Join Date
    Aug 2002
    Posts
    47
    Rep Power
    16
    Thanks for the input Hero Zzyzzx.

    1) I appreciate you need to manually insert the query string. If you mean in the url or the cookie then i have tried both methods, and get the same result from both.

    2) I think you are right that there is problem with my code somewhere. However on full inspection of all the CPAN documentation it is not apparent (I will prevail some how!).

    regarding -api3 (from CPAN session tutorial):
    "The syntax of the CGI::Session 3.x has changed from previous releases. But we still keep supporting the old syntax for backward compatibility. To help us do this, you will always need to 'use' CGI::Session with "-api3" switch. It tells the library that you will be using the new syntax."

    The undef you refer to, the first argument to the new constructor, according to the documentation refers to the storage of the session and if it's undef, the library will use the default driver, which is File.

    I will take a closer look at the documentation and your code sample
  14. #8
  15. No Profile Picture
    Contributing User
    Devshed Newbie (0 - 499 posts)

    Join Date
    Aug 2002
    Posts
    47
    Rep Power
    16
    Just a quick update:
    I tried the same exact scripts under a different server environment and it worked first time. Having looked closely at where the other server was saving the session files i found it to be very unpredicatble from script call to the next. Sometimes saving the sessid in the place i would expect other times not doing so at all. So the script couldnt locate the sessid file and therefore created a new session. I am presuming it is a server issue that i will look into a lot closer.

    Thanks for the pointers.

IMN logo majestic logo threadwatch logo seochat tools logo