PHP使用Redis实现Session共享的实现示例


Posted in PHP onMay 12, 2019

前言

小型web服务, session数据基本是保存在本地(更多是本地磁盘文件), 但是当部署多台服务, 且需要共享session, 确保每个服务都能共享到同一份session数据.

redis 数据存储在内存中, 性能好, 配合持久化可确保数据完整.

设计方案

1. 通过php自身session配置实现

# 使用 redis 作为存储方案
session.save_handler = redis
session.save_path = "tcp://127.0.0.1:6379"
# 若设置了连接密码, 则使用如下
session.save_path = "tcp://127.0.0.1:6379?auth=密码"

测试代码

<?php
ini_set("session.save_handler", "redis");
ini_set("session.save_path", "tcp://127.0.0.1:6379");

session_start();
echo "<pre>";
$_SESSION['usertest'.rand(1,5)]=1;
var_dump($_SESSION);

echo "</pre>";

输出 ↓

array(2) {
  ["usertest1"]=>
  int(88)
  ["usertest3"]=>
  int(1)
}
usertest1|i:1;usertest3|i:1;

评价

  • 优点: 实现简单, 无需修改php代码
  • 缺点: 配置不支持多样化, 只能应用于简单场景

2. 设置用户自定义会话存储函数

通过 session_set_save_handler() 函数设置用户自定义会话函数.

session_set_save_handler ( callable $open , callable $close , callable $read , callable $write , callable $destroy , callable $gc [, callable $create_sid [, callable $validate_sid [, callable $update_timestamp ]]] ) : bool
  
# >= php5.4
session_set_save_handler ( object $sessionhandler [, bool $register_shutdown = TRUE ] ) : bool

在配置完会话存储函数后, 再执行 session_start() 即可.

具体代码略, 以下提供一份 Memcached 的(来自Symfony框架代码):

<?php

/*
 * This file is part of the Symfony package.
 *
 * (c) Fabien Potencier <fabien@symfony.com>
 *
 * For the full copyright and license information, please view the LICENSE
 * file that was distributed with this source code.
 */

namespace Symfony\Component\HttpFoundation\Session\Storage\Handler;

/**
 * MemcacheSessionHandler.
 *
 * @author Drak <drak@zikula.org>
 */
class MemcacheSessionHandler implements \SessionHandlerInterface
{
  /**
   * @var \Memcache Memcache driver.
   */
  private $memcache;

  /**
   * @var int Time to live in seconds
   */
  private $ttl;

  /**
   * @var string Key prefix for shared environments.
   */
  private $prefix;

  /**
   * Constructor.
   *
   * List of available options:
   * * prefix: The prefix to use for the memcache keys in order to avoid collision
   * * expiretime: The time to live in seconds
   *
   * @param \Memcache $memcache A \Memcache instance
   * @param array   $options An associative array of Memcache options
   *
   * @throws \InvalidArgumentException When unsupported options are passed
   */
  public function __construct(\Memcache $memcache, array $options = array())
  {
    if ($diff = array_diff(array_keys($options), array('prefix', 'expiretime'))) {
      throw new \InvalidArgumentException(sprintf(
        'The following options are not supported "%s"', implode(', ', $diff)
      ));
    }

    $this->memcache = $memcache;
    $this->ttl = isset($options['expiretime']) ? (int) $options['expiretime'] : 86400;
    $this->prefix = isset($options['prefix']) ? $options['prefix'] : 'sf2s';
  }

  /**
   * {@inheritdoc}
   */
  public function open($savePath, $sessionName)
  {
    return true;
  }

  /**
   * {@inheritdoc}
   */
  public function close()
  {
    return $this->memcache->close();
  }

  /**
   * {@inheritdoc}
   */
  public function read($sessionId)
  {
    return $this->memcache->get($this->prefix.$sessionId) ?: '';
  }

  /**
   * {@inheritdoc}
   */
  public function write($sessionId, $data)
  {
    return $this->memcache->set($this->prefix.$sessionId, $data, 0, time() + $this->ttl);
  }

  /**
   * {@inheritdoc}
   */
  public function destroy($sessionId)
  {
    return $this->memcache->delete($this->prefix.$sessionId);
  }

  /**
   * {@inheritdoc}
   */
  public function gc($maxlifetime)
  {
    // not required here because memcache will auto expire the records anyhow.
    return true;
  }

  /**
   * Return a Memcache instance
   *
   * @return \Memcache
   */
  protected function getMemcache()
  {
    return $this->memcache;
  }
}

以上就是本文的全部内容,希望对大家的学习有所帮助,也希望大家多多支持三水点靠木。

PHP 相关文章推荐
利用PHP实现与ASP Banner组件相似的类
Oct 09 PHP
php 多个submit提交表单 处理方法
Jul 07 PHP
PHP base64编码后解码乱码的解决办法
Jun 19 PHP
php中cookie实现二级域名可访问操作的方法
Nov 11 PHP
详细解读PHP中接口的应用
Aug 12 PHP
php投票系统之增加与删除投票(管理员篇)
Jul 01 PHP
修改Laravel5.3中的路由文件与路径
Aug 10 PHP
ThinkPHP框架分布式数据库连接方法详解
Mar 14 PHP
thinkphp 抓取网站的内容并且保存到本地的实例详解
Aug 25 PHP
PHP给源代码加密的几种方法汇总(推荐)
Feb 06 PHP
php删除一个路径下的所有文件夹和文件的方法
Feb 07 PHP
解决thinkPHP 5 nginx 部署时,只跳转首页的问题
Oct 16 PHP
如何让PHP编码更加好看利于阅读
May 12 #PHP
Yii2处理密码加密及验证的方法
May 12 #PHP
php和asp语法上的区别总结
May 12 #PHP
Laravel推荐使用的十个辅助函数
May 10 #PHP
PHP下载大文件失败并限制下载速度的实例代码
May 10 #PHP
PHP 7.4 新语法之箭头函数实例详解
May 09 #PHP
PHP文件类型检查及fileinfo模块安装使用详解
May 09 #PHP
You might like
php 从数据库提取二进制图片的处理代码
2009/09/09 PHP
如何让搜索引擎抓取AJAX内容解决方案
2014/08/25 PHP
PHP Hash算法:Times33算法代码实例
2015/05/13 PHP
php通过exif_read_data函数获取图片的exif信息
2015/05/21 PHP
ThinkPHP 5.1 跨域配置方法
2019/10/11 PHP
基于PHP实现用户在线状态检测
2020/11/10 PHP
起点页面传值js,有空研究学习下
2010/01/25 Javascript
setTimeout的延时为0时多个浏览器的区别
2012/05/23 Javascript
Javascript生成json的函数代码(可以用php的json_decode解码)
2012/06/11 Javascript
jquery中交替点击事件toggle方法的使用示例
2013/12/08 Javascript
把文本中的URL地址转换为可点击链接的JavaScript、PHP自定义函数
2014/07/29 Javascript
jQuery中end()方法用法实例
2015/01/08 Javascript
js实现禁止中文输入的方法
2015/01/14 Javascript
快速学习AngularJs HTTP响应拦截器
2015/12/31 Javascript
jQuery实现可展开折叠的导航效果示例
2016/09/12 Javascript
JavaScript和jQuery获取input框的绝对位置实现方法
2016/10/13 Javascript
AngularJS extend用法详解及实例代码
2016/11/15 Javascript
node.js express中app.param的用法详解
2017/07/16 Javascript
从零开始学习搭建React脚手架项目
2018/08/23 Javascript
关于angular浏览器兼容性问题的解决方案
2020/07/26 Javascript
基于vue.js仿淘宝收货地址并设置默认地址的案例分析
2020/08/20 Javascript
Python EOL while scanning string literal问题解决方法
2020/09/18 Python
Python发送以整个文件夹的内容为附件的邮件的教程
2015/05/06 Python
Ubuntu16.04/树莓派Python3+opencv配置教程(分享)
2018/04/02 Python
Python饼状图的绘制实例
2019/01/15 Python
Python微医挂号网医生数据抓取
2019/01/24 Python
pytorch 实现张量tensor,图片,CPU,GPU,数组等的转换
2020/01/13 Python
Python基于stuck实现scoket文件传输
2020/04/02 Python
中学生英语演讲稿
2014/04/26 职场文书
庆国庆活动总结
2014/08/28 职场文书
个人遵守党的政治纪律情况对照检查材料思想汇报
2014/09/25 职场文书
特此通知格式
2015/04/27 职场文书
入党积极分子考察意见
2015/06/02 职场文书
2016教师廉洁从教心得体会
2016/01/13 职场文书
2019终止劳动合同协议书最新范本!
2019/07/09 职场文书
Golang二维数组的使用方式
2021/05/28 Golang