缓存架构设计(三)----docker+openresty+lua+redis

目录

一、nginx分发层到应用层

1、目录结构如下

2、分发层配置文件

2.1)简单配置并验证

 二、lua连接redis集群

1、下载redis集群包

2、源码目录通过make生成.so文件,通过lua_package_cpath加载.so文件 (我的下载的文件放在/docker/cache/project/code/nginx/application/common目录下)

3、定时获取集群信息,动态获取集群地址

三、使用OpenResty 组件管理工具


一、nginx分发层到应用层

通过调用本身的 nginx hash 分发模块分发到应用层并且实现动态负载均衡,并且在应用层当中调用 php-fpm
 

1、目录结构如下

 

2、分发层配置文件

2.1)简单配置并验证

2.2)动态负载均衡配置

  • 分发层配置文件

  • 搭建consul容器
#拉取consul镜像
docker pull consul

#启动容器consul服务
docker run -d -p 8700:8500 -h node1 --name node1 consul agent -server -bootstrap-expect=1 -node=node1 -client 0.0.0.0 -ui

#如果非容器consul启动使用以下命令
consul agent -server -bootstrap-expect 1 -data-dir /tmp/consul -node=ali_1 -bind=172.27.0.8 -ui -client 0.0.0.0

#启动consul服务
curl -X PUT -d '{"weight":1,"max_fails":2,"fail_timeout":10}' http://127.0.0.1:8700/v1/kv/upstreams/servers/外网IP地址:映射端口
docker pull consul 镜像

 

创建consul容器

 

浏览器访问情况
添加8002/8003
浏览器访问查看服务器

 

 二、lua连接redis集群

1、下载redis集群包

redis集群包地址 https://github.com/steve0511/resty-redis-cluster

2、源码目录通过make生成.so文件,通过lua_package_cpath加载.so文件 (我的下载的文件放在/docker/cache/project/code/nginx/application/common目录下)

 

3、定时获取集群信息,动态获取集群地址

通过在进程启动的时候定时获取 redis 连接地址 , 在使用时获取内存内的 redis 集群地址
curl -X PUT -d 'redis集群外网访问ip地址:redis集群外网映射端口' http://127.0.0.1:8700/v1/kv/redis-cluster-1/

应用层配置文件

如果配置路径没问题,(由于暂时还没有任何文件)浏览器访问结果如下:

三、使用OpenResty 组件管理工具

很多开发语言 / 环境都会提供配套的包管理工具,例如 npm/Node.js cpan/Perl gem/Ruby 等,它们可以方便地安装功能组件,辅助用户的开发工作,节约用户的时间和经理。OpenResty 也有功能类似的工具,名叫 opm
 
OpenResty 维护一个官方组件库( opm.openresty.org ,opm 就是库的客户端,可以把组件库里的组件下载到本地,并管理本地的组件列表。
 
opm 的用法很简单,常用的命令有:
 
search:以关键字搜索关键的组件。

get:安装功能组件(注意不是 install)。

info:显示已安装组件的详细信息。

list:列出所有本地已经安装的组件。

upgrad:更新某个已安装组件。

update:更新所有已安装组件。

remove:移除某个已安装组件。

opm 默认的操作目录是 “/usr/local/openresty/site”,但是也可以在命令行参数 “--install-dir=PATH” 安装到其他目录,或者用参数 “–cwd” 安装到当前目录的 "./resty_module/" 目录里。

注意:要使用opm我们的环境当中还缺少一个依赖 yum install perl-Digest-MD5 -y  
容器应用层里安装

安装lua_resty_consul 工具包

https://github.com/hamishforbes/lua-resty-consul

#在应用层首先安装依赖包
 yum install perl-Digest-MD5 -y

#将hamishforbes/lua-resty-consul安装到/usr/local/openresty/lualib/project/common下
opm --install-dir=/usr/local/openresty/lualib/project/common get hamishforbes/lua-resty-consul

应用层nginx.conf

user  root;
worker_processes  2;
daemon off;#避免nginx在后台运行
#error_log  logs/error.log;
#error_log  logs/error.log  notice;
#error_log  logs/error.log  info;

#pid        logs/nginx.pid;


events {
   worker_connections  20480;#单个进程允许的客户端最大连接数
}


http {
    include       mime.types;
    #default_type  application/octet-stream;
    lua_code_cache off; #关闭代码缓存上线后去掉
    #log_format  main  '$remote_addr - $remote_user [$time_local] "$request" '
    #                  '$status $body_bytes_sent "$http_referer" '
    #                  '"$http_user_agent" "$http_x_forwarded_for"';

    #access_log  logs/access.log  main;

    sendfile        on;
    #tcp_nopush     on;

    #keepalive_timeout  0;
    keepalive_timeout  65;

    gzip  on;
	
	lua_package_path "/usr/local/openresty/lualib/project/common/lualib/?.lua;;/usr/local/openresty/lualib/project/common/resty-redis-cluster/lib/?.lua;;";
	lua_package_cpath "/usr/local/openresty/lualib/project/common/resty-redis-cluster/src/?.so;;";
    
	lua_shared_dict redis_cluster_slot_locks 100k;
	lua_shared_dict redis_cluster_addr 20k;

	init_worker_by_lua_file /usr/local/openresty/lualib/project/init.lua;
	server {
        listen       80;
        location / {
            #root   /var/www/html;
			content_by_lua_file /usr/local/openresty/lualib/project/application.lua;
			#index index.php index.html index.htm;
			#autoindex on;
        }

        error_page   500 502 503 504  /50x.html;
        location = /50x.html {
            root   html;
        }

        location ~ \.php/?.* {
            root           /var/www/html;#php-fpm容器中的路径,不是nginx路径
            fastcgi_pass   114.67.105.89:9002;#对应容器的端口
            fastcgi_index  index.php;
            #为php-fpm指定的根目录
            fastcgi_param  SCRIPT_FILENAME $document_root$fastcgi_script_name; #加了这一项
            #定义变量$path_info,存放pathinfo信息
            set $path_info "";
            if ($fastcgi_script_name ~ "^(.+?\.php)(/.+)$") {
                #将文件地址赋值给变量 $real_script_name
                set $real_script_name $1;
                #将文件地址后的参数赋值给变量 $path_info
                set $path_info $2;
            }
            #配置fastcgi的一些参数
            fastcgi_param SCRIPT_NAME $real_script_name;
            fastcgi_param PATH_INFO $path_info;
            include        /usr/local/openresty/nginx/conf/fastcgi_params;
       }
    }
}

 application.lua文件

    local redis_list = {}
    local ngx_re_split = require("ngx.re").split
    local ip_addr = ngx.shared.redis_cluster_addr:get("redis_addr")
    local ip_addr_table = ngx_re_split(ip_addr,",")
    for key,value in ipairs(ip_addr_table) do
        local ip_addr = ngx_re_split(value,":")
        redis_list[key] = {ip=ip_addr[1],port=ip_addr[2]}
      --  ngx.print(value)
    end
    local config = {
        name = "testCluster",                   --rediscluster name
        serv_list = redis_list,
        keepalive_timeout = 60000,              --redis connection pool idle timeout
        keepalive_cons = 1000,                  --redis connection pool size
        connection_timout = 1000,               --timeout while connecting
        max_redirection = 5,                    --maximum retry attempts for redirection,
        auth = "binleen"                           --set password while setting auth
    }
    local redis_cluster = require "rediscluster"
    local red_c = redis_cluster:new(config)
    local v, err = red_c:get("name")
    if err then
         ngx.log(ngx.ERR, "err: ", err)
    else
         ngx.say(v)
    end

init.lua文件

--启动器当中获取redis集群表
    local delay = 5
    local handler
    handler = function (premature)
      local resty_consul = require('resty.consul')
      local consul = resty_consul:new({
              host            = "114.67.105.89",
              port            = 8700,
              connect_timeout = (60*1000), -- 60s
              read_timeout    = (60*1000), -- 60s
          })
      local res, err = consul:list_keys("redis-cluster") -- Get all keys
      if not res then
          ngx.log(ngx.ERR, err)
          return
      end
      local keys = {}
      if res.status == 200 then
          keys = res.body
      end
      local ip_addr = ''
      for key,value in ipairs(keys) do
          local res, err = consul:get_key(value)
          if not res then
              ngx.log(ngx.ERR, err)
              return
          end
          if table.getn(keys) == key then
              ip_addr = ip_addr..res.body[1].Value
          else
              ip_addr = ip_addr..res.body[1].Value..","
          end
          ngx.shared.redis_cluster_addr:set("redis_addr",ip_addr)
      end
    end
   if( 0 == ngx.worker.id() ) then
        --第一次立即执行 ngx.timer.at:只执行一次
         local ok, err = ngx.timer.at(0, handler)
         if not ok then
           ngx.log(ngx.ERR, "第一次执行错误: ", err)
             return
         end
        --第二次定时执行
        local ok, err = ngx.timer.every(delay, handler)
        if not ok then
          ngx.log(ngx.ERR, "定时执行错误: ", err)
          return
        end
    end

 

  • 0
    点赞
  • 2
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值