Jump to content

[SOLVED] Storing sessions in the database


codebyren

Recommended Posts

Hi.

 

I am trying to store session data in the database using a certain bit of code (below) but it seems that my variable for holding the database connection ($sdbc) is not being maintained from one of the set_session_save_handler() functions to the next.  Can anyone see what I am doing wrong? I get the following errors:

 

Warning: mysqli_real_escape_string() expects parameter 1 to be mysqli, null given in C:\Program Files\xampplite\htdocs\sandbox\dbtest\test.php on line 61

 

Warning: mysqli_real_escape_string() expects parameter 1 to be mysqli, null given in C:\Program Files\xampplite\htdocs\sandbox\dbtest\test.php on line 62

 

Warning: mysqli_query() expects parameter 1 to be mysqli, null given in C:\Program Files\xampplite\htdocs\sandbox\dbtest\test.php on line 63

 

Warning: mysqli_affected_rows() expects parameter 1 to be mysqli, null given in C:\Program Files\xampplite\htdocs\sandbox\dbtest\test.php on line 64

 

Warning: mysqli_close() expects parameter 1 to be mysqli, null given in C:\Program Files\xampplite\htdocs\sandbox\dbtest\test.php on line 32

 

The code I'm using is:

<?php # test.php

/*
 *	This page creates the functional interface 
 *	for storing session data in the database.
 *	Also starts the session.	
 */

# To do:
# ======
# ... get it working
# implement better error handling than die()

// Global used for the database connection in all database functions 
$sdbc = NULL;

// This function opens the database connection
function open_session() {

global $sdbc;

$sdbc = mysqli_connect('localhost', 'root', '', 'project01')
	OR die('Cannot connect to the database: ' . mysqli_connect_error());
return true;
}


// This function closes the database connection
function close_session() {

global $sdbc;
return mysqli_close($sdbc);
}


// This function fetches session data
// This function takes one arguments (Session ID)
function read_session($sid) {

global $sdbc;
$q = sprintf('SELECT data FROM sessions WHERE id="%s"', mysqli_real_escape_string($sdbc, $sid));
$r = mysqli_query($sdbc, $q);

if (mysqli_num_rows($r) == 1) {

	list($data) = mysqli_fetch_array($r, MYSQLI_NUM); // Or mysqli_fetch_row($r) ... ?
	return $data;
}
else {
	return '';
}
}


// This funtion writes session data
// This function takes two arguments (Session ID, Session Data)
function write_session($sid, $data) {

global $sdbc;
$q = sprintf('REPLACE INTO sessions (id, data) VALUES ("%s", "%s")', 
	mysqli_real_escape_string($sdbc, $sid), 
	mysqli_real_escape_string($sdbc, $data));
$r = mysqli_query($sdbc, $q);
return mysqli_affected_rows($sdbc);
}


// This function destroys the session data
// This function takes one argument (Session ID)
function destroy_session($sid) {

global $sdbc;
$q = sprintf('DELETE FROM sessions WHERE id="%s"', mysqli_real_escape_string($sdbc, $sid));
$r = mysqli_query($sdbc, $q);
$_SESSION = array();
return mysqli_affected_rows($sdbc);
}


// This function cleans old session data
// This function takes one parameter (expiration in seconds)
function clean_session($expire) {

global $sdbc;
$q = sprintf('DELETE FROM sessions WHERE DATE_ADD(last_accessed, INTERVAL %d SECOND) < NOW()', (int) $expire);
$r = mysqli_query($sdbc, $q);
return mysqli_affected_rows($sdbc);
}

# **************************** #
# ***** END OF FUNCTIONS ***** #
# **************************** #

// Declare the functions to use for session handling
session_set_save_handler('open_session', 'close_session', 'read_session', 'write_session', 'destroy_session', 'clean_session');

// Start the session
session_start();
?>

 

Thanks for any help.

Link to comment
https://forums.phpfreaks.com/topic/172333-solved-storing-sessions-in-the-database/
Share on other sites

Based on the line numbers, the errors occurred during write/close. You might want to read this section in the session_set_save_handler() section of the documentation -

Warning

As of PHP 5.0.5 the write and close handlers are called after object destruction and therefore cannot use objects or throw exceptions. The object destructors can however use sessions.

 

It is possible to call session_write_close() from the destructor to solve this chicken and egg problem.

 

Thank you.

 

Amazing how when you don't understand something you think it doesn't apply to you...

 

Unfortunately I'm still kinda lost as to what it means by calling session_write_close() from the destructor though.  My understanding is that close_session() is my destructor in this case.  Wouldn't this destructor only be called after write_session() - which is apparently getting called after object destruction in the first place (hence the problem...).

 

Think I might rewrite this session handler into an object approach later so I can define the destructor etc. myself.  For now, adding session_write_close(); to the footer of my page seems to be working.  Guess it forces the call to write_session() and close_session() before object destruction.

 

Thanks again.

mysqli is a class, even if you call it using procedural style function calls. When php exits, all the class destructors are called, which ends all your mysqli database connections. Then the session write and close handlers are called.

 

To the best of my knowledge, there is no raw mysqli destructor that you can modify, so you would need to wrap/extend the mysqli class with your own class in order to define a destructor that you can place the session_write_close() in so that it would automatically get called at the correct time.

Archived

This topic is now archived and is closed to further replies.

×
×
  • Create New...

Important Information

We have placed cookies on your device to help make this website better. You can adjust your cookie settings, otherwise we'll assume you're okay to continue.