nginx+lua+redis实现灰度发布:

灰度发布是指在黑白之间能够平滑过渡的一种方式

AB test就是一种灰度发布方式,让一部分用户继续用A,一部分用户开始用B,如果用户对B没有什么反对意见,那么逐步扩大范围,把所有用户都迁移到B上面 来。灰度发布可以保证整体系统的稳定,在初始灰度的时候就可以发现、调整问题,以保证其影响度。

灰度发布可以保证应用系统的稳定,降低产品升级影响的用户范围;也可以按照一定的策略让部分用户提前参与产品测试,从而提早获取到用户的反馈,完善应用功能

原理:使用nginx做负载均衡和反向代理,nginx内嵌lua模块,解析并执行lua编写的脚本逻辑,可以通过lua解析cookie以及访问redis,而一些灰度发布分流的策略就是放在redis里通过cookie关联

执行过程:

  • 当用户请求到达前段代理服务nginx,內嵌的lua模块解析nginx配置文件中的lua脚本代码
  • lua变量获取到客户端的ip地址,去查询redis缓存内是否有该建值,如果有返回值执行@client_test,否则执行@client
  • location @client_test把请求转发给部属了new版代码服务器,location@client把请求转发给部属了normal版代码的服务器,localtion@client把请求转发给部属了normal版本代码的服务器,服务器返回结果。整个过程完成

安装配置过程详解:

  1. 安装nginx
安装依赖包:
yum -y install gcc gcc-c++ autoconf libjpeg libjpeg-devel libpng libpng-devel freetype freetype-devel libxml2 libxml2-devel zlib zlib-devel glibc glibc-devel glib2 glib2-devel bzip2 bzip2-devel ncurses ncurses-devel curl curl-devel e2fsprogs e2fsprogs-devel krb5 krb5-devel libidn libidn-devel openssl openssl-devel openldap openldap-devel nss_ldap openldap-clients openldap-servers make pcre-devel yum -y install gd gd2 gd-devel gd2-devel lua lua-devel yum –y install memcached

下载lua模块、lua-memcache操作库文件和nginx包

wget https://github.com/simpl/ngx_devel_kit/archive/v0.2.18.tar.gz

wget https://github.com/chaoslawful/lua-nginx-module/archive/v0.8.5.tar.gz

wget https://github.com/agentzh/lua-resty-memcached/archive/v0.11.tar.gz

wget http://nginx.org/download/nginx-1.4.2.tar.gz

tar xvf nginx-1.4.2.tar.gz

cd nginx-1.4.2/

./configure --prefix=/soft/nginx/ --with-http_gzip_static_module --add-module=/root/ngx_devel_kit-0.2.18/  --add-module=/root/lua-nginx-module-0.8.5/

make

make install

拷贝lua的memcached操作库文件

tar xvf v0.11.tar.gz

cp -r lua-resty-memcached-0.11/lib/resty/ /usr/lib64/lua/5.1/

配置nginx

#vim /soft/nginx/conf/nginx.conf

worker_processes  1;

events {

    worker_connections  1024;

}

http {

    include       mime.types;

    default_type  application/octet-stream;

    sendfile        on;

    keepalive_timeout  65;

    proxy_next_upstream     error timeout;

    proxy_redirect          off;

    proxy_set_header        Host $host;

    proxy_set_header        X-Real-IP $http_x_forwarded_for;

    proxy_set_header        X-Forwarded-For $proxy_add_x_forwarded_for;

    client_max_body_size    100m;

    client_body_buffer_size 256k;

    proxy_connect_timeout   180;

    proxy_send_timeout      180;

    proxy_read_timeout      180;

    proxy_buffer_size       8k;

    proxy_buffers           8 64k;

    proxy_busy_buffers_size 128k;

    proxy_temp_file_write_size 128k;

     upstream client {

        server   192.168.200.29:80;

    }

    upstream client_test {

        server   192.168.200.29:81;

    }

    server {

        listen       80;

        server_name  localhost;

       location / {

       content_by_lua '

            clientIP = ngx.req.get_headers()["X-Real-IP"]

            if clientIP == nil then

                clientIP = ngx.req.get_headers()["x_forwarded_for"]

            end

            if clientIP == nil then

                clientIP = ngx.var.remote_addr

            end

                local memcached = require "resty.memcached"

                local memc, err = memcached:new()

                if not memc then

                    ngx.say("failed to instantiate memc: ", err)

                    return

                end

                local ok, err = memc:connect("127.0.0.1", 11211)

                if not ok then

                    ngx.say("failed to connect: ", err)

                    return

                end

                local res, flags, err = memc:get(clientIP)

                if err then

                    ngx.say("failed to get clientIP ", err)

                    return

                end

                if  res == "" then

                    ngx.exec("@client_test")

                    return

                end

                 ngx.exec("@client")

               ';

       }

       location @client{

           proxy_pass http://client;

       }

       location @client_test{

           proxy_pass http://client_test;

       }

    location /hello {

        default_type 'text/plain';

        content_by_lua 'ngx.say("hello, lua")';

    }

    location = /50x.html {

        root   html;

    }

   }

}

检测配置文件:

/usr/local/nginx/sbin/nginx -t

出现ok显示成功

启动nginx

/usr/local/nginx/sbin/nginx

启动memchaed服务

chkconfig --level 2345 memcached on

/etc/init.d/memcached start|stop

测试lua模块是否运行正常

telnet localhost 11211

Trying ::1...

Connected to localhost.

Escape character is '^]'.

set 192.168.68.211 0 3600 1

STORED

get 192.168.68.211

VALUE 192.168.68.211 9 1

END

quit

注意:

set后第一个值为key值。

192.168.68.211这是key值是需要灰度测试的IP地址;

0 表示一个跟该key有关的自定义数据;

3600 表示该key值的有效时间;

1 表示key所对应的value值的字节数。

下面访问Nginx,效果符合预期,我的IP已经在memcached中存储值,所以请求转发给执行灰度测试代码的主机。

访问http://测试服务器ip地址/hello  如果显示lua表示安装成功

在另一台测试机(这里是192.168.200.29)设置两个虚拟主机,一个用80端口是执行正常代码,一个是81端口执行灰度测试代码。

在memcached中以你的客户机IP地址为key,value值为1。这里我的IP是192.168.68.211.

从memcached删除我的主机IP值。

再次请求Nginx,请求转发给执行正常代码内容的主机。

整个配置并不复杂,整个判断过程对服务的影响非常小。如果需要使用这个系统最好自己看看lua脚本。

nginx+lua+redis实现灰度发布_test的更多相关文章

  1. 利用nginx+lua+memcache实现灰度发布

    一.灰度发布原理说明 灰度发布在百度百科中解释: 灰度发布是指在黑与白之间,能够平滑过渡的一种发布方式.AB test就是一种灰度发布方式,让一部分用户继续用A,一部分用户开始用B,如果用户对B没有什 ...

  2. 基于nginx+lua简单的灰度发布系统

    upstream.conf upstream grey_1 { keepalive 1000; server localhost:8020; } upstream grey_2 { keepalive ...

  3. Nginx+Lua+Redis 对请求进行限制

    Nginx+Lua+Redis 对请求进行限制 一.概述 需求:所有访问/myapi/**的请求必须是POST请求,而且根据请求参数过滤不符合规则的非法请求(黑名单), 这些请求一律不转发到后端服务器 ...

  4. Nginx+Lua+Redis整合实现高性能API接口 - 网站服务器 - LinuxTone | 运维专家网论坛 - 最棒的Linux运维与开源架构技术交流社区! - Powered by Discuz!

    Nginx+Lua+Redis整合实现高性能API接口 - 网站服务器 - LinuxTone | 运维专家网论坛 - 最棒的Linux运维与开源架构技术交流社区! - Powered by Disc ...

  5. nginx lua redis 访问频率限制(转)

    1. 需求分析 Nginx来处理访问控制的方法有多种,实现的效果也有多种,访问IP段,访问内容限制,访问频率限制等. 用Nginx+Lua+Redis来做访问限制主要是考虑到高并发环境下快速访问控制的 ...

  6. nginx+lua+redis构建高并发应用(转)

    nginx+lua+redis构建高并发应用 ngx_lua将lua嵌入到nginx,让nginx执行lua脚本,高并发,非阻塞的处理各种请求. url请求nginx服务器,然后lua查询redis, ...

  7. 基于nginx+lua+redis高性能api应用实践

    基于nginx+lua+redis高性能api应用实践 前言 比较传统的服务端程序(PHP.FAST CGI等),大多都是通过每产生一个请求,都会有一个进程与之相对应,请求处理完毕后相关进程自动释放. ...

  8. nginx限制请求之三:Nginx+Lua+Redis 对请求进行限制

    相关文章: <高可用服务设计之二:Rate limiting 限流与降级> <nginx限制请求之一:(ngx_http_limit_conn_module)模块> <n ...

  9. nginx+lua+redis 处理APK包替换

    nginx + lua +redis 安装与使用入门: http://huoding.com/2012/08/31/156 nginx httpEchoModule : http://wiki.ngi ...

随机推荐

  1. 前端 js javascript

    新浪SAE公共资源 推荐指数★★★ 支持https http://lib.sinaapp.com/http://lib.sinaapp.com/js/jquery/2.0.3/jquery-2.0.3 ...

  2. Codeforces Round #595 (Div. 3) 题解

    前言 大家都在洛谷上去找原题吧,洛谷还是不错的qwq A 因为没有重复的数,我们只要将数据排序,比较两两之间有没有\(a_j - a_i == 1 (j > i)\) 的,有则输出 \(2\) ...

  3. mpvue实现微信小程序(欢迎踩坑)

    最近刚使用mpvue完成了微信小程序的开发,写点东西,做个记录. 首先依旧是两个传送门: 微信小程序文档:[https://developers.weixin.qq.com/miniprogram/d ...

  4. Zabbix通过邮件发送Screen图形报表实现

    在使用Zabbix的过程中,我们通常会建立一些需要的Screen图形报表来汇总需要监控的Graph. 而下面的两个脚本,则是通过从Zabbix数据库中获取所有的Screen图形参数,提供Zabbix的 ...

  5. javaSE之运行时异常和编译时异常

    运行时异常继承自RuntimeException; package foundationEnhance; public class Person { private int age; public P ...

  6. 父工程 pom版本

    <!-- 集中定义依赖版本号 --> <properties> <junit.version>4.12</junit.version> <spri ...

  7. DELPHI FMX 同时使用LONGTAP和TAP

    在应用到管理图标时,如长按显示删除标志,单击取消删除标志.在FMX的手势管理中,只有长按LONGTAP,点击TAP则是单独的事件,不能在同事件中管理.在执行LONGTAP后,TAP也会被触发​,解决方 ...

  8. python学习笔记(十八)python操作excel

    python操作excel需要安装通过pip安装xlwt, xlrd这两个模块: pip install xlwt pip insall xlrd 操作excel ,写入excel: import x ...

  9. php strpos()函数 语法

    php strpos()函数 语法 作用:寻找字符串中某字符最先出现的位置.大理石平台怎么选择 语法:strpos(string,find,start) 参数: 参数 描述 string     必需 ...

  10. Linux内核设计与实现 总结笔记(第八章)下半部和推后执行的工作

    上半部分的中断处理有一些局限,包括: 中断处理程序以异步方式执行,并且它有可能打断其他重要代码的执行. 中断会屏蔽其他程序,所以中断处理程序执行的越快越好. 由于中断处理程序往往需要对硬件进行操作,所 ...