A-A+

PHP将SESSION会话数据保存到Mysql数据库

2012年06月07日 PHP技术文章 评论 2 条 阅读 363 views 次

在共享的主机服务器上,所有的网站都在使用同样的临时目录,这就意味着多个程序都在同一个位置进行文件的读取 操作,那么我们就可以利用技术编写一个程序来读取这个临时目录所有的数据,很显然,这样对于安全来讲是很不安全的,如果有多台服务器,那么共享临时会话信息就很困难了。

有时候我们需要长期进行保存 SESSION 会话数据,这样显然将 SESSION 缓存保存在临时文件是没有任何优势的,而且随着 SESSION 会话文件的增多,也会增加服务器本身的负担,夏日博客之前有维护过几十个网站,光是 SESSION 的会话信息就占用硬盘资源十几个G,可想而知,这么多的缓存读取会占用多少服务器的资源,而且十几个G里面也很难慎选出有用的SESSION会话信息,有的网站 SESSION 会话没有设置到期时间,那么就会保留很长时间,对于服务器性能的优化是很不利的。

而解决 SESSION 会话的问题最好的方案无非是利用 PHP 将 SESSION 会话保存到数据库了,作为独立网站的 SESSION 会话状态,和其它网站的临时目录会话分隔开,不仅安全性会提高许多,而且也提高程序的规范性,使得网站的 SESSION 会话能够统一进行管理操作。

PHP 将 SESSION 会话数据保存到 Mysql 数据库,只需要一个 SESSION 的会话类即可,我们将其要实现的方法封装到一起,比如 打开会话,关闭会话,读取会话,写入会话,销毁会话,过期会话的收集,会话收理等等,这些都是平时我们常用的会话功能,无非就是将这些功能进行了封装,进行了统一的管理,并且将 SESSION 会话信息统一写入到了 数据库中,实现本功能共需要有 3 个文件,(1),一个 SESSION 的会话类,(2) Mysql 数据库。(3) 实例调用的文件

一,SESSION 会话类:session.inc.php

<?php   
$sdbc = null; //保存数据库连接   
  
/*定义打开会话的函数*/  
function open_session(){   
 global $sdbc;   
 $sdbc = mysql_connect('localhost', 'root', '43291600') or die
('Cannot connect to the database');   
 if(is_resource($sdbc)){   
  mysql_select_db('test', $sdbc);   
  //mysql_query('SET NAMES "UTF8"', $sdbc);   
  return true;   
 }   
 return false;   
}   
  
/*定义关闭回话的函数*/  
function close_session(){   
 global $sdbc;   
 return mysql_close($sdbc);   
}   
  
/*定义读取会话数据函数*/  
function read_session($sid){   
 global $sdbc;   
 $q = sprintf('Select `s_data` FROM `session` Where `s_id`="%s"'
, $sid);   
 $r = mysql_query($q, $sdbc);   
    
 if(mysql_num_rows($r) == 1){   
  list($data) = mysql_fetch_array($r, MYSQL_NUM);   
  return $data;   
 }else return '';   
}   
  
/*定义写入会话数据函数*/  
function write_session($sid, $data){   
 global $sdbc;   
 $q = sprintf('REPLACE INTO `session` (`s_id`, `s_data`) VALUES 
("%s", "%s")', $sid, mysql_real_escape_string($data, $sdbc));   
 $r = mysql_query($q, $sdbc);   
 return mysql_affected_rows($sdbc);   
}   
  
/*定义销毁会话数据函数*/  
function destroy_session($sid){   
 global $sdbc;   
 $q = sprintf('Delete FROM `session` Where `s_id`="%s"', $sid);   
 $r = mysql_query($q, $sdbc);   
 $_SESSION = array();   
 return mysql_affected_rows($sdbc);   
}   
  
/*定义垃圾收集函数*/  
function clean_session($expire){   
 global $sdbc;   
 $q = sprintf('Delete FROM `session` Where DATE_ADD(s_time, INTERVAL 
%d SECOND) < NOW()', (int)$expire);   
 $r = mysql_query($q, $sdbc);   
 return mysql_affected_rows($sdbc);   
}   
  
/*使用会话处理函数*/  
session_set_save_handler('open_session', 'close_session', 'read
_session'
, 'write_session', 'destroy_session', 'clean_session');   
session_start();   
?>

二,Mysql 数据库,保存会话状态

-- phpMyAdmin SQL Dump
-- version 2.10.3
-- http://www.phpmyadmin.net
--
-- 主机: localhost
-- 生成日期: 2010 年 05 月 26 日 06:54
-- 服务器版本: 5.0.51
-- PHP 版本: 5.2.6

SET SQL_MODE="NO_AUTO_VALUE_ON_ZERO";

--
-- 数据库: `test`
--
Create DATABASE `test` DEFAULT CHARACTER SET utf8 COLLATE utf8_unicode_ci;
USE `test`;

-- --------------------------------------------------------

--
-- 表的结构 `session`
--

Create TABLE `session` (
`s_id` char(32) collate utf8_unicode_ci NOT NULL,
`s_data` text collate utf8_unicode_ci,
`s_time` timestamp NOT NULL default CURRENT_TIMESTAMP on updat
e CURRENT_TIMESTAMP,
PRIMARY KEY (`s_id`)
) ENGINE=MyISAM DEFAULT CHARSET=utf8 COLLATE=utf8_unicode_ci;

三,实例调用文件:demo.php

<?php   
require('session.inc.php'); //引入session.inc文件   
  
if(emptyempty($_SESSION)){   
 $_SESSION&#91;'name'&#93; = 'admin';   
 $_SESSION&#91;'age'&#93; = 23;   
 echo '<p>Session data stored</p>';   
}   
  
if(isset($_GET['logout'])){   
 session_destroy();   
 echo '<p>Session destroyed.</p>';   
}else echo '<a href="demo.php?logout=true">Log Out</a>';   
  
echo '<p>Session Data:<pre>'.print_r($_SESSION, 1).'</pre></p>';   
?>
标签:

2 条留言  访客:2 条  博主:0 条

  1. 王先森

    不知道博主有没有试试,运行后会报错,写入和关闭的时候 global $sdbc; 获取不到 值为null

    • smiling

      是否是数据库字段类型的问题。

给我留言