这里打算使用数据库来保存session,应该说用数据库来保存是更加有效而且更方便共享的一种方法。
首先,说明下session_set_save_handler()里面的每个函数。
记住一点:session数据都是在你的代码运行完后才写入代码的
php代码
- <?function open($save_path, $session_name)
- {
- //打开session文件,用来设计保存路径,一般直接return true 就好了
- //在session_start()中会调用到。
- }
- function close()
- {
- //关闭session连接
- }
- function read($id)
- {
- //读取session数据,在session_start()中调用。
- }
- function write($id, $sess_data)
- {
- //写session到文件或者数据库
- //记住$_SESSION['var']='test'这种对session赋值并不调用该方法。该方法是在代码结束后或者调用session_write_close()调用的时候才运行的。
- }
- function destroy($id)
- {
- //注销session,删除一条session记录
- }
- function gc($maxlifetime)
- {
- //删除过时的session记录
- }
- ?>
然后,使用mysql来保存。详细了解了每个函数的作用,这样用数据库来保存就很简单了。这里我给一个例子。
mysql_session.php
PHP代码
- <?
- /**
- *CREATE TABLE `session` (
- `sid` char(32) NOT NULL,
- `expiry` int(10) NOT NULL,
- `value` mediumtext NOT NULL,
- PRIMARY KEY (`sid`)
- ) ENGINE=MyISAM DEFAULT CHARSET=latin1;
- *
- */
- function init_db(){
- $db["host"]='localhost';//
- $db["database"]="pcti";
- $db["user"]="root";
- $db["password"]="admin";
- $db=new PDO('mysql:host='.$db['host'].';dbname='.$db['database'],$db['user'],$db['password']);
- $db->query("set names 'utf8'");
- return $db;
- }
- class session{
- private $db;
- function __construct($db){
- $this->db=$db;
- }
- public function open($save_path,$session_name){
- return true;
- }
- public function close(){
- $this->db=null;
- return true;
- }
- public function read($sid){
- $rs=$this->db->query('select * from session where sid=''.$sid.''');
- foreach ($rs as $row){
- return $row['value'];
- }
- return null;
- }
- public function write($sid,$value){
- if(is_null($old_value=$this->read($sid))){
- //insert
- return $this->db->query("insert into session (sid,expiry,value)values('".$sid."','".time()."','".$value."')");
- }else{
- //update
- return $this->db->query("update session set expiry='".time()."',value='".$old_value.$value."' where sid='".$sid."'");
- }
- }
- public function destroy($sid){
- return $this->db->query('delete from session where sid=''.$sid.''');
- }
- public function gc($max_life_time){
- return $this->db->query('delete from session where expiry+'.$max_life_time.'<'.time());
- }
- }
- $session=new session(init_db());
- session_set_save_handler(array($session,'open'),
- array($session,'close'),
- array($session,'read'),
- array($session,'write'),
- array($session,'destroy'),
- array($session,'gc'));
- session_start();
- ?>
里面有相应的创建数据库的语句。
然后写一个测试文件看看。
创建session:mysql_session_test.php
<?
include('mysql_session.php');
$_SESSION['test']='mysql session test';
?> <a href="mysql_session_check.php">next</a>
运行下,然后看看数据库中是不是多了条记录?呵呵,如果是,恭喜测试成功。
查看session:mysql_session_check.php
<?
include('mysql_session.php');
print_r($_SESSION);
?><a href="mysql_session_exit.php">exit</a>
注销session测试:mysql_session_exit.php
<?
include('mysql_session.php');
session_destroy();
header('location:mysql_session_check.php');
?>
呵呵,再次测试都没有问题。测试环境winxp+php5.2+apache 2.2 +mysql 5.0
总结
之前我完全脱离PHP内置的session机制,使用数据库和cookie来模拟。现在发现直接使用自定义session更加简单,方便。但两者之间谁更加可取还有待商榷。



