如何在多个Memcached的服务器共享PHP会议上的Ubuntu 14.04

Memcached的可以更快速地处理会话,更快的用户体验。本教程介绍了如何让用户维护多个负载平衡服务器的单个会话共享多个云服务器会话。

介绍

Memcached是一个分布式对象缓存系统,它将信息存储在内存中,而不是存储在磁盘上,以便更快地访问。 PHP的Memcache模块可用于处理会话,否则会存储在文件系统上。 在Memcached中存储PHP会话具有能够将其分发到运行Memcached的多个云服务器的优点,从而保持会话冗余。

如果没有此Memcached设置,如果您的应用程序在多个服务器上进行负载平衡,则有必要在负载均衡器上配置会话粘性。 这保持了用户体验,并防止他们突然注销。 配置Memcached以处理会话将确保Memcached池中的所有云服务器具有相同的会话数据集,从而无需使用一个服务器保持会话。

先决条件

本教程假定您熟悉Ubuntu中设置LAMP服务器
这样的设置将利用3Droplet与Ubuntu的14.04图像。

Droplet1

  • 名称:lamp01
  • 公共IP:1.1.1.1
  • 私人IP:10.1.1.1

Droplet2

  • 名称:lamp02
  • 公共IP:2.2.2.2
  • 私人IP:10.2.2.2

Droplet3

  • 名称:lamp03
  • 公共IP:3.3.3.3
  • 私人IP:10.3.3.3

确保专用网络建立Droplet时复选框被选中。 另外,请记下私有IP地址,因为我们以后需要它们。

在所有三个服务器上安装LAMP。

首先,更新存储库并安装Apache。

apt-get update
apt-get install apache2

安装PHP和Apache的mod_php扩展。

apt-get install php5 libapache2-mod-php5 php5-mcrypt

欲了解更多信息,请参阅这篇文章

第一步 - 安装Memcache软件包

lamp01,安装Memcached的守护进程和PHP的内存缓存模块。

apt-get install php5-memcache memcached

PHP有两个包:php5-memcache和php5-memcached(注意结尾处的“d”)。 我们将使用第一个包(memcache),因为它更轻,没有任何依赖。 阅读之间的比较的memcache和memcached的

Memcached服务只侦听localhost(127.0.0.1)。 这必须更改为接受来自专用网络的连接。

nano /etc/memcached.conf

找到以下行:

-l 127.0.0.1

更改它以侦听此服务器的私有IP地址。

-l 10.1.1.1

重新启动memcached服务。

service memcached restart

重复其他两台服务器上执行这些步骤,取代127.0.0.1与适当的私有IP地址。

lamp02

-l 10.2.2.2

lamp03

-l 10.3.3.3

重新启动memcached第二两个服务器上的服务。

第二步 - 将Memcache设置为PHP的会话处理程序

lamp01,打开php.ini文件进行编辑。

nano /etc/php5/apache2/php.ini

该文件位于/etc/php5/fpm/php.ini对PHP-FPM安装。

查找以下配置指令:

session.save_handler =
session.save_path =

修改它们以使用Memcache,如下所示。 使用所有这三个私有IP地址的session.save_path

session.save_handler = memcache
session.save_path = 'tcp://10.1.1.1:11211,tcp://10.2.2.2:11211,tcp://10.3.3.3:11211'

您可能需要注释session.save_path通过在开始移除分号。 记住每个IP地址后输入端口号11211,因为这的Memcached端口上侦听。

在其他两个服务器上添加完全相同的设置。

lamp02:

session.save_handler = memcache
session.save_path = 'tcp://10.1.1.1:11211,tcp://10.2.2.2:11211,tcp://10.3.3.3:11211'

lamp03:

session.save_handler = memcache
session.save_path = 'tcp://10.1.1.1:11211,tcp://10.2.2.2:11211,tcp://10.3.3.3:11211'

此配置必须在所有Droplets上完全相同,以便会话共享正常工作。

第三步 - 配置会话冗余的Memcache

lamp01,编辑memcache.ini文件。

nano /etc/php5/mods-available/memcache.ini

将以下配置指令添加到此文件的末尾。

memcache.allow_failover=1
memcache.session_redundancy=4

所述memcache.session_redundancy指令必须等于memcached的服务器+ 1会话信息被复制到所有服务器的数量。 这是由于一个在PHP错误

这些指令启用会话故障转移和冗余,因此PHP写的会话信息以指定的所有服务器session.save_path ; 类似于RAID-1设置。

根据所使用的内容重新启动Web服务器或PHP FPM守护程序。

service apache2 reload

重复上准确和lamp02这些lamp03步骤。

第四步 - 测试会话冗余

要测试此设置,请在所有Droplet上创建以下PHP脚本。

/var/www/html/session.php

<?php
    header('Content-Type: text/plain');
    session_start();
    if(!isset($_SESSION['visit']))
    {
        echo "This is the first time you're visiting this server\n";
        $_SESSION['visit'] = 0;
    }
    else
            echo "Your number of visits: ".$_SESSION['visit'] . "\n";

    $_SESSION['visit']++;

    echo "Server IP: ".$_SERVER['SERVER_ADDR'] . "\n";
    echo "Client IP: ".$_SERVER['REMOTE_ADDR'] . "\n";
    print_r($_COOKIE);
?>

此脚本仅用于测试,可在设置Droplet后删除。

在第一个Droplet上使用curl访问此文件,并提取cookie信息。

curl -v -s http://1.1.1.1/session.php 2>&1 | grep 'Set-Cookie:'

这将返回类似以下的输出。

< Set-Cookie: PHPSESSID=8lebte2dnqegtp1q3v9pau08k4; path=/

复制PHPSESSID cookie,并请求发送给使用该cookie的其他Droplet。 如果没有请求1440秒,此会话将被PHP删除,因此请确保您在此时间内完成测试。 阅读关于PHP的session.gc-maxlifetime更多地了解这一点。

curl --cookie "PHPSESSID=8lebte2dnqegtp1q3v9pau08k4" http://1.1.1.1/session.php http://2.2.2.2/session.php http://3.3.3.3/session.php

你会发现会话正在所有的Droplet中进行。

Your number of visits: 1
Server IP: 1.1.1.1
Client IP: 117.193.121.130
Array
(
    [PHPSESSID] => 8lebte2dnqegtp1q3v9pau08k4
)
Your number of visits: 2
Server IP: 2.2.2.2
Client IP: 117.193.121.130
Array
(
    [PHPSESSID] => 8lebte2dnqegtp1q3v9pau08k4
)
Your number of visits: 3
Server IP: 3.3.3.3
Client IP: 117.193.121.130
Array
(
    [PHPSESSID] => 8lebte2dnqegtp1q3v9pau08k4
)

要测试故障转移,停止memcached服务,并在其上访问该文件。

service memcached stop

Droplet透明地使用存储在其他两个服务器上的会话信息。

curl --cookie "PHPSESSID=8lebte2dnqegtp1q3v9pau08k4" http://1.1.1.1/session.php

输出:

Your number of visits: 4
Server IP: 1.1.1.1
Client IP: 117.193.121.130
Array
(
    [PHPSESSID] => 8lebte2dnqegtp1q3v9pau08k4
)

现在,负载均衡器可以配置为均匀分发请求,而不会配置会话粘性的麻烦。

启动memcached一次,一旦你完成测试:

service memcached start

第五步 - 用IPTables安全Memcached

即使Memcached使用专用网络,同一数据中心中的其他DigitalOcean用户也可以连接到您的Droplet,如果他们知道您的私有IP。 因此,我们将建立iptables规则 ,只允许在我们的Memcached池中的云服务器相互通信。

我们在测试会话冗余之后执行此步骤,以便更容易排除如果应用不正确的规则可能出现的问题。

创建与lamp02lamp03的私有IP地址lamp01防火墙规则。

iptables -A INPUT -s 10.2.2.2 -i eth1 -p tcp -m state --state NEW -m tcp --dport 11211 -j ACCEPT
iptables -A INPUT -s 10.3.3.3 -i eth1 -p tcp -m state --state NEW -m tcp --dport 11211 -j ACCEPT

在典型的LAMP服务器上,以下是完整的规则集:

iptables -A INPUT -m state --state RELATED,ESTABLISHED -j ACCEPT
iptables -A INPUT -p tcp -m state --state NEW -m tcp --dport 80 -j ACCEPT
iptables -A INPUT -p tcp -m state --state NEW -m tcp --dport 443 -j ACCEPT
iptables -A INPUT -p tcp -m state --state NEW -m tcp --dport 22 -j ACCEPT
iptables -A INPUT -s 10.2.2.2 -i eth1 -p tcp -m state --state NEW -m tcp --dport 11211 -j ACCEPT
iptables -A INPUT -s 10.3.3.3 -i eth1 -p tcp -m state --state NEW -m tcp --dport 11211 -j ACCEPT
iptables -A INPUT -i lo -j ACCEPT
iptables -A INPUT -p icmp -m icmp --icmp-type 8 -j ACCEPT
iptables -P INPUT DROP

输入与lamp01lamp03的私有IP地址lamp02防火墙规则。

iptables -A INPUT -s 10.1.1.1 -i eth1 -p tcp -m state --state NEW -m tcp --dport 11211 -j ACCEPT
iptables -A INPUT -s 10.3.3.3 -i eth1 -p tcp -m state --state NEW -m tcp --dport 11211 -j ACCEPT

不要与lamp01lamp02的私有IP地址lamp03相同。

iptables -A INPUT -s 10.1.1.1 -i eth1 -p tcp -m state --state NEW -m tcp --dport 11211 -j ACCEPT
iptables -A INPUT -s 10.2.2.2 -i eth1 -p tcp -m state --state NEW -m tcp --dport 11211 -j ACCEPT

重复第4步中的测试,以确认防火墙没有阻止我们的交通。

附加阅读