<?php
/**
* ÐлаÑÑ UserSession.
*
* @package energine
* @subpackage core
* @author dr.Pavka
* @copyright ColoCall 2006
* @version $Id: UserSession.class.php,v 1.7 2007/12/17 14:16:03 pavka Exp $
*/
//require_once('core/framework/DBWorker.class.php');
/**
* ÐлаÑÑ ÑпÑÐ°Ð²Ð»ÐµÐ½Ð¸Ñ ÑеанÑами полÑзоваÑелей.
*
* @package energine
* @subpackage core
* @final
*/
final class UserSession extends DBWorker {
/**
* ÐÐ¼Ñ ÑеанÑа по-ÑмолÑаниÑ.
*/
const DEFAULT_SESSION_NAME = 'NRGNSID';
/**
* ÐеÑоÑÑноÑÑÑ Ð²Ñзова ÑбоÑÑика мÑÑоÑа.
* ÐÑÑиÑлÑеÑÑÑ ÐºÐ°Ðº DEFAULT_PROBABILITY / session.gc_divisor (defaults to 100).
* ÐапÑимеÑ, 10 / 100 ознаÑÐ°ÐµÑ 10%-веÑоÑÑноÑÑÑ Ð²Ñзова СÐ.
*/
const DEFAULT_PROBABILITY = 10;
/**
* @access private
* @var string иденÑиÑикаÑÐ¾Ñ ÑеанÑа
*/
private $phpSessId;
/**
* @access private
* @var int иденÑиÑикаÑÐ¾Ñ ÑеанÑа в ÐÐ
*/
private $id = false;
/**
* ÐÑли пеÑиод Ð¼ÐµÐ¶Ð´Ñ Ð·Ð°Ð¿ÑоÑами пÑевÑÑÐ°ÐµÑ ÑÑÑ Ð²ÐµÐ»Ð¸ÑинÑ, ÑÐµÐ°Ð½Ñ ÑÑановиÑÑÑ Ð½ÐµÐ´ÐµÐ¹ÑÑвиÑелÑнÑм.
*
* @var int вÑÐµÐ¼Ñ Ð¾Ð¶Ð¸Ð´Ð°Ð½Ð¸Ñ
* @access private
*/
private $timeout;
/**
* ÐÑполÑзÑеÑÑÑ Ð´Ð»Ñ Ð½Ð°ÑÑÑойки вÑемени жизни cookie и ÑбоÑки мÑÑоÑа.
*
* @var int макÑималÑное вÑÐµÐ¼Ñ Ð¶Ð¸Ð·Ð½Ð¸ ÑеанÑа
* @access private
*/
private $lifespan;
/**
* @access private
* @static
* @var UserSession единÑй Ð´Ð»Ñ Ð²Ñей ÑиÑÑÐµÐ¼Ñ ÑкземплÑÑ ÐºÐ»Ð°ÑÑа UserSession
*/
private static $instance;
/**
* @access private
* @var string полÑзоваÑелÑÑкий агенÑ
*/
private $userAgent;
/**
* @access private
* @var string Ð¸Ð¼Ñ ÑеанÑа
*/
private $name;
/**
* @access private
* @var string Ð¸Ð¼Ñ ÑаблиÑÑ ÑеанÑов в ÐÐ
*/
private $tableName;
/**
* ÐонÑÑÑÑкÑÐ¾Ñ ÐºÐ»Ð°ÑÑа.
*
* @access private
* @return void
*/
public function __construct() {
parent::__construct();
$this->timeout = $this->getConfigValue('session.timeout');
$this->lifespan = $this->getConfigValue('session.lifespan');
$this->userAgent = isset($_SERVER['HTTP_USER_AGENT'])?$_SERVER['HTTP_USER_AGENT']:'ROBOT';
$this->name = self::DEFAULT_SESSION_NAME;
$this->tableName = 'share_session';
ini_set('session.gc_probability', self::DEFAULT_PROBABILITY);
// ÑÑÑанавливаем обÑабоÑÑики ÑеанÑа
session_set_save_handler(
array(&$this, 'open'),
array(&$this, 'close'),
array(&$this, 'read'),
array(&$this, 'write'),
array(&$this, 'destroy'),
array(&$this, 'gc')
);
//register_shutdown_function('session_write_close');
session_name($this->name);
// ÑÑÑанавливаем вÑÐµÐ¼Ñ Ð¶Ð¸Ð·Ð½Ð¸ cookie
session_set_cookie_params($this->lifespan, $this->getConfigValue('site.root'));
// пÑовеÑÑем ÑÑÑеÑÑвование cookie и коÑÑекÑноÑÑÑ ÐµÐ³Ð¾ даннÑÑ
if (isset($_COOKIE[$this->name])) {
$this->phpSessId = $_COOKIE[$this->name];
// пÑовеÑÑем, дейÑÑвиÑелен ли ÑекÑÑий ÑеанÑ
$res = $this->dbh->selectRequest(
"SELECT session_id FROM {$this->tableName}".
' WHERE session_native_id = %s'.
' AND (NOW() - session_created) < %s'.
' AND (NOW() - session_last_impression) <= %s'.
' AND session_user_agent = %s',
$this->phpSessId,
$this->lifespan,
$this->timeout,
$this->userAgent
);
$response = Response::getInstance();
if (is_array($res)) {
$response->setCookie(
$this->name,
$this->phpSessId,
(time() + $this->lifespan),
$this->getConfigValue('site.root')
);
}
else {
$this->dbh->modify(QAL::DELETE, $this->tableName, null, "session_native_id = '{$this->phpSessId}'");
// ÑдалÑем cookie ÑеанÑа
$response = Response::getInstance();
$response->deleteCookie($this->name, $this->getConfigValue('site.root'));
}
}
session_start();
}
/**
* ÐозвÑаÑÐ°ÐµÑ ÐµÐ´Ð¸Ð½Ñй Ð´Ð»Ñ Ð²Ñей ÑиÑÑÐµÐ¼Ñ ÑкземплÑÑ ÐºÐ»Ð°ÑÑа UserSession.
*
* @access public
* @static
* @return UserSession
*/
public static function getInstance() {
if (!isset(self::$instance)) {
self::$instance = new UserSession;
}
return self::$instance;
}
/**
* ÐÑкÑÑÐ²Ð°ÐµÑ ÑеанÑ.
*
* @access public
* @param string $savePath
* @param string $sessionName
* @return boolean
*/
public function open($savePath, $sessionName) {
return true;
}
/**
* ÐакÑÑÐ²Ð°ÐµÑ ÑеанÑ.
*
* @access public
* @return bool
*/
public function close() {
return true;
}
/**
* ЧиÑÐ°ÐµÑ Ð´Ð°Ð½Ð½Ñе ÑеанÑа.
* ÐоÑколÑÐºÑ Ð´Ð°Ð½Ð½Ñй меÑод вÑзÑваÑÑÑ ÑÑÐ°Ð·Ñ Ð¶Ðµ поÑле ÑÑÑановки
* иденÑиÑикаÑоÑа ÑеанÑа, он иÑполÑзÑеÑÑÑ Ð²Ð¼ÐµÑÑо меÑода open.
*
* @access public
* @param string иденÑиÑикаÑÐ¾Ñ ÑеанÑа
* @return mixed
*/
public function read($phpSessId) {
$result = '';
$this->phpSessId = $phpSessId;
$res = $this->dbh->select(
$this->tableName,
array('session_id', 'session_data'),
array('session_native_id' => $this->phpSessId)
);
// еÑли ÑказаннÑй ÑÐµÐ°Ð½Ñ ÑÑÑеÑÑвÑÐµÑ Ð² ÐÐ
if (is_array($res)) {
$res = $res[0];
$this->id = $res['session_id'];
$result = $res['session_data'];
}
// еÑли Ñакого ÑеанÑа в ÐРне ÑÑÑеÑÑвÑеÑ
else {
// Ñоздаем новÑÑ Ð·Ð°Ð¿Ð¸ÑÑ ÑеанÑа
$this->id = $this->dbh->modifyRequest(
"INSERT INTO {$this->tableName} (session_native_id, session_created, session_user_agent) VALUES(%s, NOW(), %s)",
$this->phpSessId, $this->userAgent
);
}
return $result;
}
/**
* ÐапиÑÑÐ²Ð°ÐµÑ Ð´Ð°Ð½Ð½Ñе ÑеанÑа.
*
* @access public
* @param string иденÑиÑикаÑÐ¾Ñ ÑеанÑа
* @param mixed даннÑе
* @return mixed
*/
public function write($phpSessId, $data) {
if ($this->id) {
$this->dbh->modify(QAL::UPDATE, $this->tableName, array('session_data' => $data), array('session_id' => $this->id));
}
return true;
}
/**
* УниÑÑÐ¾Ð¶Ð°ÐµÑ ÑеанÑ.
*
* @access public
* @param string иденÑиÑикаÑÐ¾Ñ ÑеанÑа
* @return bool
*/
public function destroy($phpSessId) {
return $this->dbh->modify(QAL::DELETE, $this->tableName, null, array('session_native_id' => $phpSessId));
}
/**
* СбоÑÑик мÑÑоÑа.
*
* @access public
* @param int макÑималÑное вÑÐµÐ¼Ñ Ð¶Ð¸Ð·Ð½Ð¸ ÑеанÑа
* @return bool
*/
public function gc($maxLifeTime) {
$this->dbh->modify(QAL::DELETE, $this->tableName, null, "(NOW() - session_created) > {$this->lifespan} AND (NOW() - session_last_impression) > {$this->timeout}");
return true;
}
/**
* СÑаÑÑÑÐµÑ ÑеанÑ.
*
* @access public
* @return void
*/
public function start() {
if ($this->phpSessId) {
$this->dbh->modifyRequest("UPDATE {$this->tableName} SET session_last_impression = NOW() WHERE session_native_id = %s", $this->phpSessId);
}
}
/**
* ÐозвÑаÑÐ°ÐµÑ Ð¸Ð´ÐµÐ½ÑиÑикаÑÐ¾Ñ ÑеанÑа.
*
* @access public
* @return int
*/
public function getID() {
return $this->id;
}
}