Skip to content

Instantly share code, notes, and snippets.

@stut
Created May 31, 2016 20:32
Show Gist options
  • Save stut/4ddadbc6a8261f4ce258a57c6e234428 to your computer and use it in GitHub Desktop.
Save stut/4ddadbc6a8261f4ce258a57c6e234428 to your computer and use it in GitHub Desktop.
/***********************************************************************
MySQL Session class
This class encapsulates everything needed to store your PHP sessions
in a MySQL database. To use it simply call Session::start() instead
of session_start().
You'll need a table like this in your database. You can change the
name but the fields should remain as they are defined here.
CREATE TABLE `sessions` (
`id` varchar(50) NOT NULL,
`name` varchar(50) NOT NULL,
`expires` int(10) unsigned NOT NULL default '0',
`data` text,
PRIMARY KEY (`id`, `name`)
) TYPE=InnoDB;
***********************************************************************/
class Session
{
protected $_lifetime = 900;
protected $_db = false;
protected $_table = 'sessions';
protected $_name = 'phpsess';
static public function start($host = 'localhost', $username = 'root', $password = '', $db = 'sessionstore', $table = 'sessions', $_lifetime = 0)
{
// Create the object
$GLOBALS['_SESSION_OBJ_'] = new self($host, $username, $password, $db, $table, $lifetime);
// Hook up the handler
session_set_save_handler(
array($GLOBALS['_SESSION_OBJ_'], 'open'),
array($GLOBALS['_SESSION_OBJ_'], 'close'),
array($GLOBALS['_SESSION_OBJ_'], 'read'),
array($GLOBALS['_SESSION_OBJ_'], 'write'),
array($GLOBALS['_SESSION_OBJ_'], 'destroy'),
array($GLOBALS['_SESSION_OBJ_'], 'gc')
);
// Start the session
session_start();
}
private function __construct($host = 'localhost', $username = 'root', $password = '', $db = 'sessionstore', $table = 'sessions', $_lifetime = 0)
{
// By default we use the session _lifetime in php.ini, but this can be overridden in code
$this->_lifetime = ($_lifetime == 0 ? get_cfg_var('session.gc_max_lifetime') : $_lifetime);
// This is the table where session data is to be stored
$this->_table = $table;
// Now we connect to the database, throwing expections if anything fails
$this->_db = @mysql_connect($host, $username, $password);
if ($this->_db === false)
throw new Exception('Failed to connect to the session store', 1);
if (false === @mysql_select_db($db, $this->_db))
throw new Exception('Failed to select session store', 2);
}
public function open($path, $name)
{
// Store the session name for future use, we don't have any use for the path
$this->_name = $name;
// Everything is OK if we have a connection to the database
return ($this->_db !== false);
}
public function close()
{
// Run the garbage collector 10% of the time
if (rand(1, 10) == 5) {
$this->gc($this->_lifetime);
}
// Close the database connection
return @mysql_close($this->_db);
}
public function read($id)
{
// By default we return nothing
$retval = '';
// Try to read an entry from the database
$result = mysql_query('select data from `'.$this->_table.'` where id = "'.mysql_real_escape_string($id, $this->_db).'" and name = "'.mysql_real_escape_string($this->_name, is->_db).'" and expires > '.time().' order by expires desc', $this->_db);
if ($result !== false and mysql_num_rows($result) > 0) {
// Found one, get it
$retval = mysql_result($result, 0, 0);
}
return $retval;
}
public function write($id, $data)
{
$retval = false;
// Build the query. We use the MySQL ON DUPLICATE KEY feature to do an insert/update in one query.
$sql = 'insert into `'.$this->_table.'` set ';
$sql.= 'id = "'.mysql_real_escape_string($id, $this->_db).'", ';
$sql.= 'name = "'.mysql_real_escape_string($this->_name, $this->_db).'", ';
$sql.= 'expires = '.(time() + $this->_lifetime).', ';
$sql.= 'data = "'.mysql_real_escape_string($data, $this->_db).'" ';
$sql.= 'on duplicate key update expires = values(expires), data = values(data)';
// Run it and return true if it was successful
$result = mysql_query($sql, $this->_db);
if ($result !== false and mysql_affected_rows($this->_db) > 0) {
$retval = true;
}
@mysql_free_result($result);
return $retval;
}
public function destroy($id)
{
// Remove this session from the database
$result = mysql_query('delete from `'.$this->_table.'` where id = "'.mysql_real_escape_string($id, $this->_db).'" and name = "'.mysql_real_escape_string($this->_name, s->_db).'"', $this->_db);
if ($result !== false and mysql_affected_rows($this->_db) > 0) {
return true;
}
return false;
}
public function gc($_lifetime)
{
// Remove any sessions that have expired
$result = mysql_query('delete from `'.$this->_table.'` where expires < '.time(), $this->_db);
return ($result === false ? 0 : mysql_affected_rows($this->_db));
}
}
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment