第11章 LAMP架构企业实战

1.1 LAMP架构企业实战

Linux下LAMP(Linux+Apache+MySQL/MariaDB+Perl/PHP/Python)是一组用来搭建动态网站的开源软件架构,本身是各自独立的软件服务,放在一起使用,拥有了越来越高的兼容度,共同组成了一个强大的Web应用程序平台。

本章向读者介绍互联网主流企业架构LAMP应用案例、PHP解释性语言详解、LAMP组合通信原理、LAMP企业源码架设、LAMP拓展及使用Redis提升LAMP性能优化等。

1.2 LAMP企业架构简介

随着开源潮流的蓬勃发展,开放源代码的LAMP已经与J2EE和.Net商业软件形成三足鼎立之势,并且该软件开发的项目在软件方面的投资成本较低,因此受到整个IT界的关注。LAMP架构受到大多数中小企业的运维、DBA、程序员的青睐,Apache默认只能发布静态网页,而LAMP组合可以发布静态+PHP动态页面。

静态页面通常指不与数据库发生交互的页面,是一种基于w3c规范的一种网页书写格式,是一种统一协议语言,所以称之为静态网页。静态页面被设计好之后,一般很少去修改,不随着浏览器参数改变而内容改变,需注意的是动态的图片也是属于静态文件。从SEO角度来讲,HTML页面更有利于搜索引擎的爬行和收录。常见的静态页面以.html、.gif、.jpg、.jpeg、.bmp、.png、.ico、.txt、.js、.css等结尾。

动态页面通常指与数据库发生交互的页面,内容展示丰富,功能非常强大,实用性广。从SEO角度来讲,搜索引擎很难全面的爬行和收录动态网页,因为动态网页会随着数据库的更新、参数的变更而发生改变,常见的动态页面以.jsp、.php、.do、.asp、.cgi、.apsx等结尾。

1.3 Apache与PHP工作原理

LAMP企业主流架构最重要的三个环节,一是Apache WEB服务器,二是PHP(PHP: Hypertext Preprocessor),三是MYSQL数据库。

Apache WEB服务器主要是基于多模块工作,依赖PHP SAPI处理方式中的PHP_MODULE去解析PHP结尾的文件,如图12-1所示:

图12-1 Apache+PHP mod工作原理

PHP是一种适用于web开发的动态语言,PHP语言内核基于C语言实现包含大量组件的软件框架,是一种功能强大的解释型脚本语言。PHP底层运行机制如图12-2所示:

图12-2 PHP底层处理机制

PHP底层工作原理包括4个部分:

  • Zend引擎,属于PHP内核部分,它负责将PHP代码解析为可执行opcode的处理并实现相应的处理方法、实现基本的数据结构、内存分配及管理、提供了相应的api方法供外部调用,是一切的核心,所有的外围功能均围绕Zend实现。
  • Extensions,围绕着Zend引擎,Extensions通过组件的方式提供各种基础服务,各种内置函数、标准库等都是通过Extension来实现。
  • Sapi,服务端应用编程接口(Server Application Programming Interface,Sapi),sapi通过一系列钩子函数,基于SAPI可以让PHP与外部进行数据交互。
  • 常见的SAPI编程接口处理方法包括:apache2handler:以apache作为webserver,采用MOD_PHP模式运行时候的处理方式;cgi:webserver和PHP直接的另一种交互方式,FastCGI协议;cli:命令行调用的应用模式。
  • APP代码应用,又称之为PHP代码程序,基于sapi接口生成不同的应用模式,从而被PHP引擎解析。

当用户在浏览器地址中输入域名或者域名+PHP页面,向HTTP WEB服务器Apache发起HTTP请求,WEB服务器接受该请求,并根据其后缀判断如果请求的页面是以.php结尾,WEB服务器从硬盘或者内存中取出该PHP文件,将其发送给PHP引擎程序。

PHP引擎程序将会对WEB服务器传送过来的文件进行扫描并根据命令从后台读取、处理数据、并动态地生成相应的HTML页面。然后PHP引擎程序将生成的HTML页面返回给WEB服务器,最终WEB服务器将HTML页面返回给客户端浏览器,浏览器基于MIME类型进行解析展示给用户页面。

1.4 LAMP企业安装配置

构建LAMP架构有两种方法,一是使用YUM在线安装,另外一种是基于LAMP源码编译安装,YUM在线安装方法如下:

yum install httpd httpd-devel mysql mysql-server mysql-devel php php-devel php-mysql -y

service httpd restart

service mysqld restart

YUM方式安装简单、快捷,但如果需要添加扩展的功能和模块,需使用源码包的方式来编译安装LAMP。如下为LAMP源码编译安装的步骤:

  1. Apache WEB安装,先安装apr、apr-utils库包。

yum install apr-devel apr-util-devel -y;

cd /usr/src ;

wget http://mirror.bit.edu.cn/apache/httpd/httpd-2.2.31.tar.gz

tar xzf httpd-2.2.31.tar.gz

cd httpd-2.2.31

./configure –prefix=/usr/local/apache –enable-so –enable-rewrite

make

make install

  1. MYSQL数据库安装,基于MYSQL5.5编译安装,通过cmake、make、make install三个步骤实现。

wget http://down1.chinaunix.net/distfiles/mysql-5.5.20.tar.gz

yum install cmake make ncurses-devel ncurses -y

cmake . -DCMAKE_INSTALL_PREFIX=/usr/local/mysql55 \

-DMYSQL_UNIX_ADDR=/tmp/mysql.sock \

-DMYSQL_DATADIR=/data/mysql \

-DSYSCONFDIR=/etc \

-DMYSQL_USER=mysql \

-DMYSQL_TCP_PORT=3306 \

-DWITH_XTRADB_STORAGE_ENGINE=1 \

-DWITH_INNOBASE_STORAGE_ENGINE=1 \

-DWITH_PARTITION_STORAGE_ENGINE=1 \

-DWITH_BLACKHOLE_STORAGE_ENGINE=1 \

-DWITH_MYISAM_STORAGE_ENGINE=1 \

-DWITH_READLINE=1 \

-DENABLED_LOCAL_INFILE=1 \

-DWITH_EXTRA_CHARSETS=1 \

-DDEFAULT_CHARSET=utf8 \

-DDEFAULT_COLLATION=utf8_general_ci \

-DEXTRA_CHARSETS=all \

-DWITH_BIG_TABLES=1 \

-DWITH_DEBUG=0

make

make install

将源码安装的Mysql数据库服务设置为系统服务,可以使用chkconfig管理,并启动MYSQL数据库:

cd /usr/local/mysql55/

\cp support-files/my-large.cnf /etc/my.cnf

\cp support-files/mysql.server /etc/init.d/mysqld

chkconfig –add mysqld 
chkconfig –level 35 mysqld on

mkdir -p /data/mysql

useradd mysql

/usr/local/mysql55/scripts/mysql_install_db –user=mysql –datadir=/data/mysql/ –basedir=/usr/local/mysql55/

ln -s /usr/local/mysql55/bin/* /usr/bin/

service mysqld restart

  1. PHP服务安装,PHP需与Apache、MySQL进行整合,如图12-3所示,参数命令如下:

cd /usr/src

wget http://mirrors.sohu.com/php/php-5.3.28.tar.bz2

tar jxf php-5.3.28.tar.bz2

cd php-5.3.28 ;

./configure –prefix=/usr/local/php5 –with-config-file-path=/usr/local/php5/etc –with-apxs2=/usr/local/apache2/bin/apxs –with-mysql=/usr/local/mysql55/

make

make install

图12-3 LAMP源码编译整合

  1. Apache+PHP源码整合

为了能让Apache发布PHP页面,需要将PHP安装完成后的libphp5.so模块与Apache进行整合,vim httpd.conf编辑配置文件,加入如下代码:

LoadModule      php5_module modules/libphp5.so

AddType application/x-httpd-php .php

DirectoryIndex   index.php index.html index.htm

  1. 测试Apache+PHP环境

创建PHP测试页面,在/usr/local/apache/htdocs目录下创建index.php测试页面,执行如下命令自动创建:

cat >/usr/local/apache/htdocs/index.php<<EOF

<?php

phpinfo();

?>

EOF

重新启动Apache服务,浏览器输入 Apache WEB的IP访问,如图12-4所示,即代表LAMP源码环境整合成功。

图12-4 Apache+PHP测试页面

  1. Discuz PHP论坛安装

LAMP源码整合完毕之后,Dicuz官网下载Discuz开源PHP软件包,将软件包解压并发布在Apache Htdocs发布目录,代码如下:

cd /usr/src ;

wget http://download.comsenz.com/DiscuzX/3.1/Discuz_X3.1_SC_UTF8.zip

unzip Discuz_X3.1_SC_UTF8.zip -d /usr/local/apache/htdocs/

cd /usr/local/apache/htdocs/;\mv upload/* .

chmod 757 -R data/ uc_server/ config/ uc_client/

通过浏览器访问Apache WEB IP,如图12-5所示,选择“我同意”

图12-5 Discuz安装界面一

进入如图12-6界面,数据库安装,如果不存在则需要新建数据库并授权。

图12-6 Discuz安装界面二

MYSQL数据库命令行中创建PHP连接MYSQL的用户及密码,命令如下:

create database discuz charset=utf8;

grant all on discuz.* to root@’localhost’ identified by “123456”;

单击下一步,直至安装完成,浏览器自动跳转至如图12-7所示界面:

图12-7 Discuz安装界面三

1.5 LAMP企业架构拓展实战

如上LAMP服务均安装至单台服务器,随着用户访问量不断的增加,单台服务器压力逐渐增加,那如何优化LAMP架构,如何拆分LAMP架构呢,怎么把Apache和MySQL分开放在不同的机器呢。

LAMP架构拆分的目的在于缓解单台服务器的压力,可以将PHP、MYSQL单独安装至多台服务器,本节将实现LAP+MySQL的架构,也即是把MYSQL单独拆分出去。部署方法有两种:

  1. YUM安装LAMP多机方案

在Apache WEB服务器只需只需如下代码:

yum install httpd httpd-devel php-devel php php-mysql -y

在MYSQL数据库服务器只需只需如下代码:

yum install mysql-server mysql mysql-devel mysql-libs -y

  1. 源码安装LAMP多机方案

源码安装LAMP多机方式,Apache WEB服务与MYSQL数据库服务分别部署在不同的服务器即可,PHP与Apache服务部署在一台服务器,PHP编译参数时加入如下代码进行LAMP的整合,mysqlnd为PHP远程连接MYSQL数据库服务器的一种方式:

./configure –prefix=/usr/local/php5 \

–with-mysql=mysqlnd  –with-mysqli=mysqlnd  –with-pdo-mysql=mysqlnd \

–with-apxs2=/usr/local/apache2/bin/apxs

make

make install

1.6 LAMP+Redis企业实战

LAMP在企业生产环境中,除了将MYSQL单独部署在其他服务器、由于MYSQL数据库压力会很大,还会对MYSQL实现主从复制及读写分离,同时会对PHP网站进行调优,通常PHP的优化手段包括:PHP代码本身优化、PHP配置文件优化、为PHP添加缓存模块,将PHP网站数据存入缓存等。

1.7 Redis入门简介

Redis是一个开源的使用ANSI  C语言编写、支持网络、可基于内存亦可持久化的日志型、Key-Value数据库,并提供多种语言的API。Redis是一个key-value存储系统。

和Memcached缓存类似,Redis支持存储的value类型相对更多,包括string(字符串)、list(链表)、set(集合)、zset(有序集合)和hash(哈希类型)。

Redis是一种高级key-value数据库,它跟memcached类似,不过Redis的数据可以持久化,而且支持的数据类型很丰富,有字符串,链表,集 合和有序集合。支持在服务器端计算集合的并,交和补集(difference)等,还支持多种排序功能。Redis也被看成是一个数据结构服务器。

Redis很大程度补偿了memcached这类key/value存储的不足,在部分场合可以对关系数据库起到很好的补充作用。Redis提供了Java,C/C++,C#,PHP,JavaScript,Perl,Object-C,Python,Ruby,Erlang等客户端,方便易用,得到IT人的青睐。

Redis支持主从同步,数据可以从主服务器向任意数量的从服务器上同步,从服务器可以是关联其他从服务器的主服务器。这使得Redis可执行单层树复制,由于完全实现了发布/订阅机制,使得从数据库在任何地方同步树时,可订阅一个频道并接收主服务器完整的消息发布记录,同步对读取操作的可扩展性和数据冗余很有帮助。

目前使用Redis的互联网企业有:京东、百度、腾讯、阿里巴巴、新浪、图吧、研修网等等,如表12-1所示,为目前主流数据库简单功能对比:

名称

数据库类型

数据存储选项

操作类型

备注

Redis

内存存储,Nosql数据库

支持字符串、列表、集合、散列表、有序集合

增、删、修改、更新

支持分布式集群、主从同步及高可用、单线程

Memcached

内存缓存数据库,键值对

键值之间的映射

增、删、修改、更新

支持多线程

MySQL

典型关系数据库,RDBMS

数据库由多表主成,每张表包含多行

增、删、修改、更新

支持ACID性质

PostgreSQL

典型关系数据库,RDBMS

数据库由多表主成,每张表包含多行

增、删、修改、更新

支持ACID性质

MongoDB

硬盘存储,Nosql数据库

数据库包含多个表

增、删、修改、更新

主从复制,分片,副本集、空间索引

表12-1 常见数据库功能对比

1.8 LAMP+Redis工作机制

LAMP+Redis工作机制:用户通过浏览器访问LAMP网站,并以用户名和密码登录到网站,默认Redis缓存中没有该用户名和密码对应列表,PHP程序会读取MYSQL数据库中的用户名和密码,然后将用户名和密码缓存至Redis中,下次用户通过浏览器再次使用同样的用户名和密码登录网站,PHP无需从数据库中读取该用户和密码信息,而是直接优先从Redis缓存中读取并返回,从而减轻MYSQL数据库的压力。

Redis除了可以缓存用户名、密码,还可以换成PHP论坛各种数据,例如用户帖子、用户动态等等,如图12-8所示:

图12-8 LAMP+Redis架构流程图

要实现将LAMP PHP网站相关数据存入Redis,需要一台Redis服务器、PHP-redis连接驱动、PHP代码连接修改等。

1.9 LAMP+Redis操作案例

LAMP PHP连接Redis,首先需安装Redis服务器,安装连接驱动,然后修改PHP网站配置文件,具体操作步骤如下:

  1. LAMP+Redis实战环境配置

LAMP服务器: 192.168.149.128

Redis主库: 192.168.149.129

Redis从库: 192.168.149.130

  1. 192.168.149.129服务器安装部署Redis服务,代码如下

wget http://download.redis.io/releases/redis-2.8.13.tar.gz

tar zxf redis-2.8.13.tar.gz

cd redis-2.8.13

make PREFIX=/usr/local/redis install

cp redis.conf /usr/local/redis/

将/usr/local/redis/bin/目录加入至环境变量配置文件/etc/profile末尾,然后Shell终端执行source /etc/profile让环境变量生效。

export PATH=/usr/local/redis/bin:$PATH

Nohup后台启动及停止Redis服务命令:

nohup /usr/local/redis/bin/redis-server /usr/local/redis/redis.conf &

/usr/local/redis/bin/redis-cli -p 6379 shutdown

  1. 安装PHP-Redis连接驱动

要确保PHP能够连接Redis缓存服务器,需添加PHP Redis扩展程序,也即是添加PHP安ext扩展模块,添加方法如下:

wget https://github.com/phpredis/phpredis/archive/3.1.2.tar.gz

tar xzf 3.1.2.tar.gz

/usr/local/php5/bin/phpize

cd phpredis-3.1.2/

./configure –with-php-config=/usr/local/php5/bin/php-config –enable-redis

make

make install

修改vim /usr/local/php5/lib/php.ini配置文件,添加redis.so模块,代码如下:

extension_dir = “/usr/local/php5/lib/php/extensions/no-debug-zts-20090626”

extension=redis.so

重启Apache服务,写入phpinfo测试页面,通过浏览器访问,如图12-9所示,检查到存在Redis模块即可:

图12-9 PHP Redis模块添加

  1. LAMP+Redis缓存测试

登录192.168.149.128 WEB服务器,修改Discuz PHP网站发布/usr/local/apache2/htdcos目录全局配置文件config_global.php,查找CONFIG MEMORY段,将redis server后改为Redis主服务器的IP 192.168.149.129即可,如图12-10所示:

图12-10 PHP Redis配置文件修改

通过浏览器访问Apache PHP论坛网站,同时登陆Redis服务器,执行命令redis-cli进入Redis命令行,运行命令KEYS *,如图12-11所示,存在以IOKLAN开头的key,则证明Redis成功缓存LAMP+Discuz网站信息数据。

图12-11 Redis缓存LAMP KEYS数据

  1. 测试Redis缓存是否生效

访问LAMP+Discuz网站,创建论坛测试用户jfedu666,密码jfedu666,此时用户数据第一次注册,用户名和密码会写入到MySQL数据库表中,同时会写入该数据也会写入到Redis缓存,如图12-12(a)、12-12(b)、12-12(c)所示:

图12-12(a) 创建论坛用户和密码

图12-12(b) MySQL数据库用户查询

图12-12(c) Redis缓存测试案例

将jfedu666从MySQL Discuz库pre_common_member中删除,通过该用户依然可以正常登录WEB网站,则证明此时数据读取的是Redis缓存服务器,如图12-13(a)、12-13(b)、12-13(c)所示:

图12-13(a) 删除数据库用户和密码

图12-13(b) 用户名和密码登录discuz论坛

图12-13(c) 用户名和密码登录discuz论坛

1.10 Redis配置文件详解

Redis是一个内存数据库,附Redis.conf常用参数的详解,后面章节会继续深入讲解。

# daemonize no Linux Shell终端运行redis,改为yes即后台运行Redis服务;

daemonize yes

# 当运行多个 redis 服务时,需要指定不同的pid文件和端口

pidfile /var/run/redis_6379.pid

# 指定redis运行的端口,默认是 6379

port 6379

# 在高并发的环境中,为避免慢客户端的连接问题,需要设置一个高速后台日志

tcp-backlog 511

# 指定redis只接收来自于该 IP 地址的请求,如果不进行设置,那么将处理所有请求

# bind 192.168.1.100 10.0.0.1

# bind 127.0.0.1

#设置客户端连接时的超时时间,单位为秒。当客户端在这段时间内没有发出任何指令,那么关闭该连接;

timeout 0

# 在Linux 上,指定值(秒)用于发送 ACKs 的时间。注意关闭连接需要双倍的时间。默认为 0 。

tcp-keepalive 0

# Redis总共支持四个日志级别: debug 、 verbose 、 notice 、 warning ,默认为 verbose

# debug 记录很多信息,用于开发和测试

# varbose 有用的信息,不像 debug 会记录那么多

# notice 普通的 verbose ,常用于生产环境

# warning 只有非常重要或者严重的信息会记录到日志

loglevel notice

#配置 log 文件地址

#默认值为 stdout ,标准输出,若后台模式会输出到 /dev/null 。

logfile /var/log/redis/redis.log

#可用数据库数

#默认值为16 ,默认数据库为0,数据库范围在 0- ( database-1 )之间

databases 16

#数据写入磁盘快照设置

#保存数据到磁盘,格式如下 :

#save <seconds> <changes>

#指出在多长时间内,有多少次更新操作,就将数据同步到数据文件 rdb 。

#相当于条件触发抓取快照,这个可以多个条件配合

#比如默认配置文件中的设置,就设置了三个条件

#save 900 1 900 秒内至少有 1 个 key 被改变

#save 300 10 300 秒内至少有 300 个 key 被改变

#save 60 10000 60 秒内至少有 10000 个 key 被改变

# save 900 1

# save 300 10

# save 60 10000

# 后台存储错误停止写。

stop-writes-on-bgsave-error yes

# 存储至本地数据库时(持久化到 rdb 文件)是否压缩数据,默认为 yes

rdbcompression yes

# 本地持久化数据库文件名,默认值为 dump.rdb

dbfilename dump.rdb

# 工作目录

# 数据库镜像备份的文件放置的路径。

# 这里的路径跟文件名要分开配置是因为 redis 在进行备份时,先会将当前数据库的状态写入到一个临时文件中,等备份完成,

# 再把该该临时文件替换为上面所指定的文件,而这里的临时文件和上面所配置的备份文件都会放在这个指定的路径当中。

# AOF 文件也会存放在这个目录下面

# 注意这里必须制定一个目录而不是文件

dir /var/lib/redis/

################################# 复制 #################################

# 主从复制 . 设置该数据库为其他数据库的从数据库 .

# 设置当本机为 slav 服务时,设置 master 服务的 IP 地址及端口,在 Redis 启动时,它会自动从 master 进行数据同步

# slaveof <masterip><masterport>

# 当 master 服务设置了密码保护时 ( 用 requirepass 制定的密码 )

# slave 服务连接 master 的密码

# masterauth <master-password>

# 当从库同主机失去连接或者复制正在进行,从机库有两种运行方式:

# 1) 如果 slave-serve-stale-data 设置为 yes( 默认设置 ) ,从库会继续响应客户端的请求

# 2) 如果 slave-serve-stale-data 是指为 no ,出去 INFO 和 SLAVOF 命令之外的任何请求都会返回一个

# 错误 “SYNC with master in progress”

slave-serve-stale-data yes

# 配置 slave 实例是否接受写。写 slave 对存储短暂数据(在同 master 数据同步后可以很容易地被删除)是有用的,但未配置的情况下,客户端写可能会发送问题。

# 从 Redis2.6 后,默认 slave 为 read-only

slaveread-only yes

# 从库会按照一个时间间隔向主库发送 PINGs. 可以通过 repl-ping-slave-period 设置这个时间间隔,默认是 10 秒

# repl-ping-slave-period 10

# repl-timeout 设置主库批量数据传输时间或者 ping 回复时间间隔,默认值是 60 秒

# 一定要确保 repl-timeout 大于 repl-ping-slave-period

# repl-timeout 60

# 在 slave socket 的 SYNC 后禁用 TCP_NODELAY

# 如果选择“ yes ” ,Redis 将使用一个较小的数字 TCP 数据包和更少的带宽将数据发送到 slave , 但是这可能导致数据发送到 slave 端会有延迟 , 如果是 Linux kernel 的默认配置,会达到 40 毫秒 .

# 如果选择 “no” ,则发送数据到 slave 端的延迟会降低,但将使用更多的带宽用于复制 .

repl-disable-tcp-nodelay no

# 设置复制的后台日志大小。

# 复制的后台日志越大, slave 断开连接及后来可能执行部分复制花的时间就越长。

# 后台日志在至少有一个 slave 连接时,仅仅分配一次。

# repl-backlog-size 1mb

# 在 master 不再连接 slave 后,后台日志将被释放。下面的配置定义从最后一个 slave 断开连接后需要释放的时间(秒)。

# 0 意味着从不释放后台日志

# repl-backlog-ttl 3600

# 如果 master 不能再正常工作,那么会在多个 slave 中,选择优先值最小的一个 slave 提升为 master ,优先值为 0 表示不能提升为 master 。

slave-priority 100

# 如果少于 N 个 slave 连接,且延迟时间 <=M 秒,则 master 可配置停止接受写操作。

# 例如需要至少 3 个 slave 连接,且延迟 <=10 秒的配置:

# min-slaves-to-write 3

# min-slaves-max-lag 10

# 设置 0 为禁用

# 默认 min-slaves-to-write 为 0 (禁用), min-slaves-max-lag 为 10

################################## 安全 ###################################

# 设置客户端连接后进行任何其他指定前需要使用的密码。

# 警告:因为 redis 速度相当快,所以在一台比较好的服务器下,一个外部的用户可以在一秒钟进行 150K 次的密码尝试,这意味着你需要指定非常非常强大的密码来防止暴力破解

# requirepass jfedu

# 命令重命名 .

# 在一个共享环境下可以重命名相对危险的命令。比如把 CONFIG 重名为一个不容易猜测的字符。

# 举例 :

# rename-command CONFIG b840fc02d524045429941cc15f59e41cb7be6c52

# 如果想删除一个命令,直接把它重命名为一个空字符 “” 即可,如下:

# rename-command CONFIG “”

###################################约束###################################

#设置同一时间最大客户端连接数,默认无限制,

#Redis 可以同时打开的客户端连接数为 Redis 进程可以打开的最大文件描述符数,

#如果设置 maxclients 0 ,表示不作限制。

#当客户端连接数到达限制时, Redis 会关闭新的连接并向客户端返回 max number of clients reached 错误信息

# maxclients 10000

# 指定 Redis 最大内存限制, Redis 在启动时会把数据加载到内存中,达到最大内存后, Redis 会按照清除策略尝试清除已到期的 Key

# 如果 Redis 依照策略清除后无法提供足够空间,或者策略设置为 ”noeviction” ,则使用更多空间的命令将会报错,例如 SET, LPUSH 等。但仍然可以进行读取操作

# 注意: Redis 新的 vm 机制,会把 Key 存放内存, Value 会存放在 swap 区

# 该选项对 LRU 策略很有用。

# maxmemory 的设置比较适合于把 redis 当作于类似 memcached 的缓存来使用,而不适合当做一个真实的 DB 。

# 当把 Redis 当做一个真实的数据库使用的时候,内存使用将是一个很大的开销

# maxmemory <bytes>

# 当内存达到最大值的时候 Redis 会选择删除哪些数据?有五种方式可供选择

# volatile-lru -> 利用 LRU 算法移除设置过过期时间的 key (LRU: 最近使用 Least RecentlyUsed )

# allkeys-lru -> 利用 LRU 算法移除任何 key

# volatile-random -> 移除设置过过期时间的随机 key

# allkeys->random -> remove a randomkey, any key

# volatile-ttl -> 移除即将过期的 key(minor TTL)

# noeviction -> 不移除任何可以,只是返回一个写错误

# 注意:对于上面的策略,如果没有合适的 key 可以移除,当写的时候 Redis 会返回一个错误

# 默认是 : volatile-lru

# maxmemory-policy volatile-lru

# LRU 和 minimal TTL 算法都不是精准的算法,但是相对精确的算法 ( 为了节省内存 ) ,随意你可以选择样本大小进行检测。

# Redis 默认的灰选择 3 个样本进行检测,你可以通过 maxmemory-samples 进行设置

# maxmemory-samples 3

############################## AOF###############################

# 默认情况下, redis 会在后台异步的把数据库镜像备份到磁盘,但是该备份是非常耗时的,而且备份也不能很频繁,如果发生诸如拉闸限电、拔插头等状况,那么将造成比较大范围的数据丢失。

# 所以 redis 提供了另外一种更加高效的数据库备份及灾难恢复方式。

# 开启 append only 模式之后, redis 会把所接收到的每一次写操作请求都追加到 appendonly.aof 文件中,当 redis 重新启动时,会从该文件恢复出之前的状态。

# 但是这样会造成 appendonly.aof 文件过大,所以 redis 还支持了 BGREWRITEAOF 指令,对 appendonly.aof 进行重新整理。

# 你可以同时开启 asynchronous dumps 和 AOF

appendonly no

# AOF 文件名称 ( 默认 : “appendonly.aof”)

# appendfilename appendonly.aof

# Redis 支持三种同步 AOF 文件的策略 :

# no: 不进行同步,系统去操作 . Faster.

# always: always 表示每次有写操作都进行同步 . Slow, Safest.

# everysec: 表示对写操作进行累积,每秒同步一次 . Compromise.

# 默认是 “everysec” ,按照速度和安全折中这是最好的。

# 如果想让 Redis 能更高效的运行,你也可以设置为 “no” ,让操作系统决定什么时候去执行

# 或者相反想让数据更安全你也可以设置为 “always”

# 如果不确定就用 “everysec”.

# appendfsync always

appendfsync everysec

# appendfsync no

# AOF 策略设置为 always 或者 everysec 时,后台处理进程 ( 后台保存或者 AOF 日志重写 ) 会执行大量的 I/O 操作

# 在某些 Linux 配置中会阻止过长的 fsync() 请求。注意现在没有任何修复,即使 fsync 在另外一个线程进行处理

# 为了减缓这个问题,可以设置下面这个参数 no-appendfsync-on-rewrite

no-appendfsync-on-rewrite no

# AOF 自动重写

# 当 AOF 文件增长到一定大小的时候 Redis 能够调用 BGREWRITEAOF 对日志文件进行重写

# 它是这样工作的: Redis 会记住上次进行些日志后文件的大小 ( 如果从开机以来还没进行过重写,那日子大小在开机的时候确定 )

# 基础大小会同现在的大小进行比较。如果现在的大小比基础大小大制定的百分比,重写功能将启动

# 同时需要指定一个最小大小用于 AOF 重写,这个用于阻止即使文件很小但是增长幅度很大也去重写 AOF 文件的情况

# 设置 percentage 为 0 就关闭这个特性

auto-aof-rewrite-percentage 100

auto-aof-rewrite-min-size 64mb

######## # LUA SCRIPTING #########

# 一个 Lua 脚本最长的执行时间为 5000 毫秒( 5 秒),如果为 0 或负数表示无限执行时间。

lua-time-limit 5000

################################LOW LOG################################

# Redis Slow Log 记录超过特定执行时间的命令。执行时间不包括 I/O 计算比如连接客户端,返回结果等,只是命令执行时间

# 可以通过两个参数设置 slow log :一个是告诉 Redis 执行超过多少时间被记录的参数 slowlog-log-slower-than( 微妙 ) ,

# 另一个是 slow log 的长度。当一个新命令被记录的时候最早的命令将被从队列中移除

# 下面的时间以微妙为单位,因此 1000000 代表一秒。

# 注意指定一个负数将关闭慢日志,而设置为 0 将强制每个命令都会记录

slowlog-log-slower-than 10000

# 对日志长度没有限制,只是要注意它会消耗内存

# 可以通过 SLOWLOG RESET 回收被慢日志消耗的内存

# 推荐使用默认值 128 ,当慢日志超过 128 时,最先进入队列的记录会被踢出

slowlog-max-len 128

1.11 Redis常用配置

Redis缓存服务器命令行中常用命令如下:

Redis CONFIG 命令格式如下:

redis 127.0.0.1:6379> CONFIG GET|SET CONFIG_SETTING_NAME

CONFIG GET * 获取Redis服务器所有配置信息;

CONFIG SET loglevel “notice” 设置Redis服务器日志级别;

CONFIG SET requirepass “jfedu”

AUTH jfedu

redis-cli -h host -p port -a password 远程连接redis数据库;

CLIENT GETNAME 获取连接的名称;

CLIENT SETNAME 设置当前连接的名称;

CLUSTER SLOTS 获取集群节点的映射数组;

COMMAND 获取Redis命令详情数组;

COMMAND COUNT 获取 Redis 命令总数;

COMMAND GETKEYS 获取给定命令的所有键;

TIME 返回当前服务器时间;

CONFIG GET parameter 获取指定配置参数的值;

CONFIG SET parameter value 修改redis 配置参数,无需重启;

CONFIG RESETSTAT 重置 INFO 命令中的某些统计数据;

DBSIZE 返回当前数据库的 key 的数量;

DEBUG OBJECT key 获取 key 的调试信息;

DEBUG SEGFAULT 让Redis服务崩溃;

FLUSHALL 删除所有数据库的所有key;

FLUSHDB 删除当前数据库的所有key;

ROLE 返回主从实例所属的角色;

SAVE 异步保存数据到硬盘;

SHUTDOWN 异步保存数据到硬盘,并关闭服务器;

SLOWLOG 管理 redis 的慢日志;

SET keys values 设置key为jfedu,值为123;

DEL jfedu 删除key及值;

INFO CPU 查看服务器CPU占用信息;

KEYS jfedu 查看是存在jfedu的key;

KEYS * 查看Redis所有的KEY;

CONFIG REWRITE 启动 Redis时所指定的redis.conf 配置文件进行改写;

INFO [section] 获取Redis服务器的各种信息和统计数值;

SYNC 用于复制功能(replication)的内部命令;

SLAVEOF host port 指定服务器的从属服务器(slave server);

MONITOR 实时打印出Redis服务器接收到的命令,调试用;

LASTSAVE 返回最近一次Redis成功将数据保存到磁盘上的时间;;

CLIENT PAUSE timeout 指定时间内终止运行来自客户端的命令;

BGREWRITEAOF 异步执行一个 AOF(AppendOnly File) 文件重写操作;

BGSAVE 后台异步保存当前数据库的数据到磁盘。

1.12 Redis集群主从实战

为了提升redis高可用性,我们除了备份redis dump数据之外,还需要创建redis主从架构,可以利用从将数据库持久化(数据持久化通俗讲就是把数据保存到磁盘上,保证不会因为断电等因素丢失数据。

Redis需要经常将内存中的数据同步到磁盘来保证持久化。redis支持两种持久化方式,一种是 Snapshotting(快照)也是默认方式,另一种是Append-only file(缩写aof)的方式。)

Redis主从复制,当用户往Master端写入数据时,通过Redis Sync机制将数据文件发送至Slave,Slave也会执行相同的操作确保数据一致;且实现Redis的主从复制非常简单。同时slave上还可以开启二级slave,三级slave从库,跟MySQL的主从类似。

Redis主从配置非常简单,只需要在Redis丛库192.168.149.130配置中设置如下指令,slaveof表示指定主库的IP,192168.149.129为master服务器,6379为master服务器Redis端口,配置方法如下:

  1. 192.168.149.129 Redis主库redis.conf配置文件如下:

daemonize no

pidfile /var/run/redis.pid

port 6379

tcp-backlog 511

timeout 0

tcp-keepalive 0

loglevel notice

logfile “”

databases 16

save 900 1

save 300 10

save 60 10000

stop-writes-on-bgsave-error yes

rdbcompression yes

rdbchecksum yes

dbfilename redis.rdb

dir /data/redis/

slave-serve-stale-data yes

slave-read-only yes

repl-disable-tcp-nodelay no

slave-priority 100

appendonly no

appendfilename “appendonly.aof”

appendfsync everysec

no-appendfsync-on-rewrite no

auto-aof-rewrite-percentage 100

auto-aof-rewrite-min-size 64mb

lua-time-limit 5000

slowlog-log-slower-than 10000

slowlog-max-len 128

latency-monitor-threshold 0

notify-keyspace-events “”

hash-max-ziplist-entries 512

hash-max-ziplist-value 64

list-max-ziplist-entries 512

list-max-ziplist-value 64

set-max-intset-entries 512

zset-max-ziplist-entries 128

zset-max-ziplist-value 64

hll-sparse-max-bytes 3000

activerehashing yes

client-output-buffer-limit normal 0 0 0

client-output-buffer-limit slave 256mb 64mb 60

client-output-buffer-limit pubsub 32mb 8mb 60

hz 10

aof-rewrite-incremental-fsync yes

  1. 192168.149.130 Redis丛库redis.conf配置文件如下:

daemonize no

pidfile /var/run/redis.pid

port 6379

slaveof 192.168.149.129 6379

tcp-backlog 511

timeout 0

tcp-keepalive 0

loglevel notice

logfile “”

databases 16

save 900 1

save 300 10

save 60 10000

stop-writes-on-bgsave-error yes

rdbcompression yes

rdbchecksum yes

dbfilename redis.rdb

dir /data/redis/

slave-serve-stale-data yes

slave-read-only yes

repl-disable-tcp-nodelay no

slave-priority 100

appendonly no

appendfilename “appendonly.aof”

appendfsync everysec

no-appendfsync-on-rewrite no

auto-aof-rewrite-percentage 100

auto-aof-rewrite-min-size 64mb

lua-time-limit 5000

slowlog-log-slower-than 10000

slowlog-max-len 128

latency-monitor-threshold 0

notify-keyspace-events “”

hash-max-ziplist-entries 512

hash-max-ziplist-value 64

list-max-ziplist-entries 512

list-max-ziplist-value 64

set-max-intset-entries 512

zset-max-ziplist-entries 128

zset-max-ziplist-value 64

hll-sparse-max-bytes 3000

activerehashing yes

client-output-buffer-limit normal 0 0 0

client-output-buffer-limit slave 256mb 64mb 60

client-output-buffer-limit pubsub 32mb 8mb 60

hz 10

aof-rewrite-incremental-fsync yes

  1. 重启Redis主库、丛库服务,在Redis主库创建key及values,登录Redis丛库查看,如图12-14(a)、12-14(b)所示:

图12-14(a) Redis主库创建key

图12-14(b) Redis从库获取key值

1.13 Redis数据备份与恢复

Redis所有数据都是保存在内存中,Redis数据备份可以定期的通过异步方式保存到磁盘上,该方式称为半持久化模式,如果每一次数据变化都写入aof文件里面,则称为全持久化模式。同时还可以基于Redis主从复制实现Redis备份与恢复。

半持久化RDB模式

半持久化RDB模式也是Redis备份默认方式,是通过快照(snapshotting)完成的,当符合在Redis.conf配置文件中设置的条件时Redis会自动将内存中的所有数据进行快照并存储在硬盘上,完成数据备份。

Redis进行RDB快照的条件由用户在配置文件中自定义,由两个参数构成:时间和改动的键的个数。当在指定的时间内被更改的键的个数大于指定的数值时就会进行快照。在配置文件中已经预置了3个条件:

save 900 1 #900秒内有至少1个键被更改则进行快照;

save 300 10 #300秒内有至少10个键被更改则进行快照;

save 60 10000 #60秒内有至少10000个键被更改则进行快照。

默认可以存在多个条件,条件之间是“或”的关系,只要满足其中一个条件,就会进行快照。 如果想要禁用自动快照,只需要将所有的save参数删除即可。Redis默认会将快照文件存储在Redis数据目录,默认文件名为:dump.rdb文件,可以通过配置dir和dbfilename两个参数分别指定快照文件的存储路径和文件名。也可以在Redis命令行执行config get dir获取Redis数据保存路径,如图12-15(a)、12-15(b)所示:

图12-15(a) 获取Redis数据目录

图12-15(b) Redis数据目录及dump.rdb文件

Redis实现快照的过程,Redis使用fork函数复制一份当前进程(父进程)的副本(子进程),父进程继续接收并处理客户端发来的命令,而子进程开始将内存中的数据写入硬盘中的临时文件,当子进程写入完所有数据后会用该临时文件替换旧的RDB文件,至此一次快照操作完成。

执行fork的时操作系统会使用写时复制(copy-on-write)策略,即fork函数发生的一刻父子进程共享同一内存数据,当父进程要更改其中某片数据时,操作系统会将该片数据复制一份以保证子进程的数据不受影响,所以新的RDB文件存储的是执行fork一刻的内存数据。

Redis在进行快照的过程中不会修改RDB文件,只有快照结束后才会将旧的文件替换成新的,也就是说任何时候RDB文件都是完整的。这使得我们可以通过定时备份RDB文件来实 现Redis数据库备份。

RDB文件是经过压缩(可以配置rdbcompression参数以禁用压缩节省CPU占用)的二进制格式,所以占用的空间会小于内存中的数据大小,更加利于传输。除了自动快照,还可以手动发送SAVE和BGSAVE命令让Redis执行快照,两个命令的区别在于,前者是由主进程进行快照操作,会阻塞住其他请求,后者会通过fork子进程进行快照操作。

Redis启动后会读取RDB快照文件,将数据从硬盘载入到内存,根据数据量大小与结构和服务器性能不同,通常将一个记录一千万个字符串类型键、大小为1GB的快照文件载入到内存中需花费20~30秒钟。

通过RDB方式实现持久化,一旦Redis异常退出,就会丢失最后一次快照以后更改的所有数据。此时需要开发者根据具体的应用场合,通过组合设置自动快照条件的方式来将可能发生的数据损失控制在能够接受的范围。

全持久化AOF模式

如果数据很重要无法承受任何损失,可以考虑使用AOF方式进行持久化,默认Redis没有开启AOF(append only file)方式的全持久化模式。

在启动时Redis会逐个执行AOF文件中的命令来将硬盘中的数据载入到内存中,载入的速度相较RDB会慢一些,开启AOF持久化后每执行一条会更改Redis中的数据的命令,Redis就会将该命令写入硬盘中的AOF文件。AOF文件的保存位置和RDB文件的位置相同,都是通过dir参数设置的,默认的文件名是appendonly.aof,可以通过appendfilename参数修改该名称。

Redis允许同时开启AOF和RDB,既保证了数据安全又使得进行备份等操作十分容易。此时重新启动Redis后Redis会使用AOF文件来恢复数据,因为AOF方式的持久化可能丢失的数据更少,可以在redis.conf中通过appendonly参数开启Redis AOF全持久化模式:

appendonly yes

appendfilename appendonly.aof

auto-aof-rewrite-percentage 100

auto-aof-rewrite-min-size 64mb

appendfsync always

#appendfsync everysec

#appendfsync no

Redis AOF持久化参数配置详解:

appendonly yes #开启AOF持久化功能;

appendfilename appendonly.aof #AOF持久化保存文件名;

appendfsync always #每次执行写入都会执行同步,最安全也最慢;

#appendfsync everysec #每秒执行一次同步操作;

#appendfsync no #不主动进行同步操作,而是完全交由操作系统来做,每30秒一次,最快也最不安全;

auto-aof-rewrite-percentage 100 #当AOF文件大小超过上一次重写时的AOF文件大小的百分之多少时会再次进行重写,如果之前没有重写过,则以启动时的AOF文件大小为依据;

auto-aof-rewrite-min-size 64mb #允许重写的最小AOF文件大小配置写入AOF文件后,要求系统刷新硬盘缓存的机制。

1.14 Redis主从复制备份

通过持久化功能,Redis保证了即使在服务器重启的情况下也不会损失(或少量损失)数据。但是由于数据是存储在一台服务器上的,如果这台服务器的硬盘出现故障,也会导致数据丢失。

为了避免单点故障,我们希望将数据库复制多个副本以部署在不同的服务器上,即使只有一台服务器出现故障其他服务器依然可以继续提供服务,这就要求当一台服务器上的数据库更新后,可以自动将更新的数据同步到其他服务器上,Redis提供了复制(replication)功能可以自动实现同步的过程。通过配置文件在Redis从数据库中配置文件中加入slaveof master-ip master-port即可,主数据库无需配置。

Redis主从复制优点及应用场景, WEB应用程序可以基于主从同步实现读写分离以提高服务器的负载能力。在常见的场景中,读的频率一般比较大,当单机Redis无法应付大量的读请求时,可以通过复制功能建立多个从数据库,主数据库只进行写操作,而从数据库负责读操作,还可以基于LVS+keepalived+Redis对Redis实现均和高可用。

从数据库持久化持久化通常相对比较耗时,为了提高性能,可以通过复制功能建立一个(或若干个)从数据库,并在从数据库中启用持久化,同时在主数据库禁用持久化。

当从数据库崩溃时重启后主数据库会自动将数据同步过来,所以无需担心数据丢失。而当主数据库崩溃时,需要在从数据库中使用SLAVEOF NO ONE命令将从数据库提升成主数据库继续服务,并在原来的主数据库启动后使用SLAVE OF命令将其设置成新的主数据库的从数据库,即可将数据同步回来。

1.15 LAMP企业架构读写分离

LAMP+Discuz+Redis缓解了MYSQL的部分压力,但是如果访问量非常大,Redis缓存中第一次没有缓存数据,会导致MYSQL数据库压力增大,此时可以基于分库、分表、分布式集群、或者读写分离来分担MYSQL数据库的压力,以读写分离为案例,来实现分担MYSQL数据库的压力。

MYSQL读写分离的原理其实就是让Master数据库处理事务性增、删除、修改、更新操作(CREATE、INSERT、UPDATE、DELETE),而让Slave数据库处理SELECT操作,MYSQL读写分离前提是基于MYSQL主从复制,这样可以保证在Master上修改数据,Slave同步之后,WEB应用可以读取到Slave端的数据。

实现MYSQL读写分离可以基于第三方插件,也可以通过开发修改代码实现,具体实现的读写分离的常见方式有如下四种:

  • MySQL-Proxy读写分离;
  • Amoeba读写分离;
  • Mycat读写分离;
  • 基于程序读写分离(效率很高,实施难度大,开发改代码)

Amoeba是以MySQL为底层数据存储,并对WEB、APP应用提供MySQL协议接口的proxy。它集中地响应WEB应用的请求,依据用户事先设置的规则,将SQL请求发送到特定的数据库上执行,基于此可以实现负载均衡、读写分离、高可用性等需求。

Amoeba相当于一个SQL请求的路由器,目的是为负载均衡、读写分离、高可用性提供机制,而不是完全实现它们。用户需要结合使用MySQL的 Replication等机制来实现副本同步等功能。

Mysql-Proxy是MySQL官方提供的mysql中间件服务,支持无数客户端连接,同时后端可连接若干台Mysql-Server服务器,MYSQL-Proxy自身基于MySQL协议,连接MYSQL-Proxy的客户端无需修改任何设置, 跟正常连接MYSQL Server没有区别,无需修改程序代码。

MySQL Proxy是App应用(客户端)与MYSQL Server之间的一个连接代理,MySQL Proxy负责将APP应用的SQL请求根据转发规则,转发至相应的后端数据库,基于lua脚本,可以实现复杂的连接控制和过滤,从而实现数据读写分离和负载均衡的需求。

Mysql-Proxy允许用户指定Lua脚本对SQL请求进行拦截,对请求进行分析与修改,还允许用户指定Lua脚本对服务器的返回结果进行修改,加入一些结果集或者去除一些结果集,对SQL的请求通常为读请求、写请求,基于Lua脚本,可以实现将SQL读请求转发至后端Slave服务器,将SQL写请求转发至后端Master服务器。

如图12-16所示,为MYSQL-PROXY读写分离架构图,通过架构图可以清晰看到SQL请求整个流向的过程。

timg?image&quality=80&size=b9999_10000&sec=1495011244752&di=c4b62ae85985158fbf86dd23507d8704&imgtype=0&src=http%3A%2F%2Fs3

图12-16 MYSQL-Proxy读写分离流程

Mysql-Proxy读写分离架构实战配置,如图12-17所示,两台WEB通过MYSQL-Proxy连接后端1.14和1.15 MYSQL服务器。

图12-17 MYSQL-Proxy实施架构图

构建Mysql读写分离架构首先需要将两台MYSQL服务器配置为主从复制(前文已存在,此处省略配置),配置完毕后,在192.168.1.16服务器上安装Mysql-Proxy服务即可,配置步骤如下:

  1. 下载MYSQL-Proxy软件版本,解压并重命名至/usr/local/mysql-proxy,命令如下:

wget http://ftp.ntu.edu.tw/pub/MySQL/Downloads/MySQL-Proxy/mysql-proxy-0.8.4-linux-el6-x86-64bit.tar.gz

useradd -r mysql-proxy

tar zxvf mysql-proxy-0.8.4-linux-el6-x86-64bit.tar.gz -C /usr/local

mv /usr/local/mysql-proxy-0.8.4-linux-el6-x86-64bit /usr/local/mysql-proxy

  1. 环境变量配置文件/etc/profile中加入如下代码保存退出,然后执行source /etc/profile使环境变量配置生效即可:

export PATH=$PATH:/usr/local/mysql-proxy/bin/

  1. 启动MYSQL-Proxy中间件,命令如下:

mysql-proxy –daemon –log-level=debug –user=mysql-proxy –keepalive –log-file=/var/log/mysql-proxy.log –plugins=”proxy” –proxy-backend-addresses=”192.168.1.162:3306″ –proxy-read-only-backend-addresses=”192.168.1.163:3306″ –proxy-lua-script=”/usr/local/mysql-proxy/share/doc/mysql-proxy/rw-splitting.lua” –plugins=admin –admin-username=”admin” –admin-password=”admin” –admin-lua-script=”/usr/local/mysql-proxy/lib/mysql-proxy/lua/admin.lua”

  1. Mysql-Proxy的相关参数详解如下:

–help-all :获取全部帮助信息;

–proxy-address=host:port :代理服务监听的地址和端口,默认为4040;

–admin-address=host:port :管理模块监听的地址和端口,默认为4041;

–proxy-backend-addresses=host:port :后端mysql服务器的地址和端口;

–proxy-read-only-backend-addresses=host:port :后端只读mysql服务器的地址和端口;

–proxy-lua-script=file_name :完成mysql代理功能的Lua脚本;

–daemon :以守护进程模式启动mysql-proxy;

–keepalive :在mysql-proxy崩溃时尝试重启之;

–log-file=/path/to/log_file_name :日志文件名称;

–log-level=level :日志级别;

–log-use-syslog :基于syslog记录日志;

–plugins=plugin :在mysql-proxy启动时加载的插件;

–user=user_name :运行mysql-proxy进程的用户;

–defaults-file=/path/to/conf_file_name :默认使用的配置文件路径,其配置段使用[mysql-proxy]标识;

–proxy-skip-profiling :禁用profile;

–pid-file=/path/to/pid_file_name :进程文件名;

  1. MYSQL-Proxy启动后,在服务器端查看端口,其中4040为proxy代理端口用于WEB应用连接,4041位管理端口用于SA或者DBA管理,如图12-48所示:

图12-48 MYSQL-Proxy启动端口

  1. 基于4041端口MySQL-Proxy查看读写分离状态,登录4041管理端口,命令如下:

mysql -h192.168.1.16 -uadmin -p -P 4041

  1. 以4041管理口登录,然后执行select命令,如图12-18所示state均为up状态,type类型为rw、ro,则证明读写分离状态成功。如果状态为unknown未知状态,可以4040端口登录执行:show databases;命令,直到state变成up状态为止。

select * from backends;

图12-18 MYSQL-Proxy读写分离状态

  1. 读写分离数据测试,以3306端口登录到从库,进行数据写入和测试,在丛库上创建jfedu_test测试库,并写入内容,如图12-19所示:

图12-19 MYSQL-Proxy读写分离测试

  1. 读写分离数据测试,以4040代理端口登录,执行如下命令,可以查看到数据即证明读写分离成功。

mysql -h192.168.1.16 -uroot -p123456 -P4040 -e “select * from jfedu_test.t1;”

  1. 登录Apache WEB服务器,修改Discuz PHP网站发布/usr/local/apache2/htdcos目录全局配置文件config_global.php,查找dbhost段,将192.168.1.16 改成192.168.1.16:40404,如图12-20所示:

图12-20 MYSQL-Proxy读写分离测试