OpenResty通过lua代码进行新旧接口转发

依赖:http、cjson

http.lua、http_connect.lua、http_headers.lua
这些文件拷贝到/usr/local/openresty/lualib/resty/

nginx中的设置
nginx.conf

   lua_package_path "/usr/local/nginx/lua/?.lua;;";  
   lua_package_cpath "/usr/local/openresty/lualib/?.so;;"; 
   lua_shared_dict dis_cache 10m; #启用nginx共享缓存

http项目 server 配置

1、请求跳转关系,经过验证后将跳转关系写入nginx共享缓存。
这个可以定时执行,或变更跳转关系后,主动刷新。

   location /get_nginx_uris/test{
            content_by_lua  '
             local getNginxUris = require("GetNginxUris")
             local httpUrl = "http://127.0.0.1:8106/rest/system/listForNginx.htm"
             local tempFileName = "/usr/local/nginx/nginx_uris_test.txt"
             local finalFileName = "/usr/local/nginx/etc/test.json"
             local resBody = getNginxUris.getUriConfig(httpUrl,tempFileName,finalFileName)
             ngx.say(resBody)
            ';
   }

为实现跳转,需要有三个location

        #入口
        location /member/ {
               proxy_pass http://172.1.15.16:8090/member/;
               rewrite_by_lua_file lua/UrlRedirect.lua;
        }
        #没有跳转关系,进入
        location @old_member {
               proxy_pass http://172.1.15.16:8090;
        }
        #--新项目,有跳转关系,且指定@to_new_member的跳转到这
        location @to_new_member {
               proxy_pass http://172.1.15.18:8500;
        }

lua代码1、地址跳转关系
GetNginxUris.lua文件,目的: 获得新旧地址跳转关系数据,并将关系存入nginx缓存

local http = require "resty.http"
local cjson = require ("cjson")
local urlMapping = require("UrlMapping")

local getNginxUris={}

--请求地址,返回响应
-- 参数 httpUrl 请求url
function getNginxUris.getResponse(httpUrl)
    local httpc = http.new()
    local res, err = httpc:request_uri(httpUrl, {
        method = "get"
    })
    if not res then
        ngx.log(ngx.WARN,"failed to request: ", err)
        return 'notok'
    else
        ngx.status = res.status
        if ngx.status ~= 200 then
            ngx.log(ngx.WARN,"非200状态,ngx.status:"..ngx.status)
            return 'notok'
        else 
            local resStr = res.body
            return resStr
        end
    end
end

-- 根据地址请求转发配置,通过验证后,存入本地etc配置文件
-- 参数 httpUrl 请求地址
-- 参数 tempFileName 临时文件 
-- 参数 finalFileName 最终文件
function getNginxUris.getUriConfig(httpUrl,tempFileName,finalFileName)
    local moduleKey = ngx.var.host
    local resBody = getNginxUris.getResponse(httpUrl)
    if(resBody == nil ) then
        ngx.log(ngx.ERR,"failed to request: "..httpUrl)
    elseif(resBody == 'notok') then
        ngx.log(ngx.ERR,"failed to request: "..notok)
    else
        local resJson = cjson.encode(resBody)
        local file = io.open(tempFileName, "w");
        assert(file);
        file:write(resBody);
        file:close();

        urlMapping.loadJsonConf(tempFileName)
        local urlRelation = urlMapping.getUrlRelation()
        local tableSize = urlMapping.getTableLen(urlRelation)
        if( tableSize ==nil )
        then
           ngx.log(ngx.ERR,"&&&&&&&&&&&&---缓存失败---&&&&&&&&&&&"..tableSize)
        else 
           getNginxUris.saveToNginxCache(moduleKey,urlRelation,tableSize)
           getNginxUris.newContentFile(finalFileName,resBody)
           ngx.log(ngx.ERR,"**************---缓存成功---****************"..tableSize)
        end
    end
    return resBody
end

-- 将结果保存到文件
-- 参数 saveFileName 文件名
-- 参数 resBody 内容
function getNginxUris.newContentFile(saveFileName,resBody)
    local file = io.open(saveFileName, "w");
    assert(file);
    file:write(resBody);
    file:close();
end

-- 保存到nginx缓存
function getNginxUris.saveToNginxCache(moduleKey,urlRelation,tableSize)
    local cache_ngx = ngx.shared.dis_cache; 
    cache_ngx:set(moduleKey.."-size", tableSize,0); 
    for k, v in pairs(urlRelation) do
        for k1, v1 in pairs(v) do
         local cacheKey = moduleKey.."-"..k1;
         cache_ngx:set(cacheKey, v1,0);
        end
     end
end

return getNginxUris

lua代码2、地址关系解析工具
UrlMapping.lua

local cjson = require ("cjson")
local urlMapping={}
local urlRelation={}

function urlMapping.getUrlRelation()
    return urlRelation;
 end

function urlMapping.getTableLen(t)
    local leng=0
    for k, v in pairs(t) do
      leng=leng+1
    end
    return leng;
 end

 function urlMapping.printTable(t)
    for k, v in pairs(t) do
       for k1, v1 in pairs(v) do
        print(k1,v1)
       end
    end
 end

 function urlMapping.trim(str)
    str = string.gsub(str, "^[%s]*(.-)[%s]*$", "%1")
    return str
 end

 function urlMapping.split(fullString, separator)
    local nFindStartIndex = 1
    local nSplitIndex = 1
    local nSplitArray = {}
    while true do
      local nFindLastIndex = string.find(fullString, separator, nFindStartIndex)
      if not nFindLastIndex then
        nSplitArray[nSplitIndex] = string.sub(fullString, nFindStartIndex, string.len(fullString))
        break
      end
      nSplitArray[nSplitIndex] = string.sub(fullString, nFindStartIndex, nFindLastIndex - 1)
      nFindStartIndex = nFindLastIndex + string.len(separator)
      nSplitIndex = nSplitIndex + 1
    end
    return nSplitArray
  end

 function urlMapping.getLines(filename)
    local indx = 0
    for line in io.lines(filename) do
        indx = indx + 1
        local sepIndex = string.find(line, "=", 1)
        if(sepIndex ~= nil)
        then
            local key = string.sub(line, 0 ,sepIndex-1)
            key = urlMapping.trim(key)
            local commentFlag = string.sub(key,0, 1)
            if(commentFlag ~= '#')
            then
                local value = string.sub(line,sepIndex+1,string.len(line))
                value = urlMapping.trim(value)
                urlRelation[key] = value
                print("key="..key,"value="..urlRelation[key])
            end
        end
    end
    return indx, urlRelation --returns number of lines and line table
end

function urlMapping.readJsonFile(filename)
    local file = io.open(filename,"r")
    local json = file:read("*a");
    file:close()
    return json
end

function urlMapping.loadConf(filename)
    local tableSize = urlMapping.getTableLen(urlRelation)
    if (tableSize==0) 
    then
        urlMapping.getLines(filename)
    end
end

function urlMapping.loadJsonConf(filename)
    local tableSize = urlMapping.getTableLen(urlRelation)
    if (tableSize==0)
    then
        local jsonString = urlMapping.readJsonFile(filename)
        urlRelation = cjson.decode(jsonString)
        print(type(urlRelation))
        urlMapping.printTable(urlRelation)
    end
end
function urlMapping.getURL(uri)
    for k, v in pairs(urlRelation) do
        if(type(v)== 'table')
        then
            for k1, v1 in pairs(v) do
                if(k1 == uri)
                then
                    return v1
                end
            end
        else
            return urlRelation[uri]
        end
     end
    -- return urlRelation[uri]
end

return urlMapping

lua代码3、根据地址关系进行跳转的核心代码
UrlRedirect.lua


local request_method = ngx.var.request_method

local methodType = ngx.HTTP_GET
local headers = ngx.req.get_headers()
local cookie = headers.cookie

local body = {
   url = ngx.var.uri,
   query = ngx.req.get_uri_args(),
   type = request_method,
   post = nil
}

if "POST" == request_method then 
   ngx.req.read_body()
   body.post = ngx.req.get_post_args()
   methodType = ngx.HTTP_POST
end

-- 从nginx缓存中获得跳转地址设置

local moduleKey = ngx.var.host
local cacheKey = moduleKey.."-"..body.url;
local cache_ngx = ngx.shared.dis_cache; 
-- local redirect_uri = urlMapping.getURL(cacheKey)
local redirect_uri = cache_ngx:get(cacheKey)

--根据跳转设置进行转发处理 

if (redirect_uri ~= nil)
then
  local urlArray = urlMapping.split(redirect_uri,",@")
  redirect_uri = urlArray[1]
  local arraySize = urlMapping.getTableLen(urlArray)
  if(arraySize<=1)
  then
    -- 内部跳转
    ngx.log(ngx.ERR,"++++++++++++111111++++++++++++")
     ngx.log(ngx.ERR," redirect-yes url= "..redirect_uri)
     ngx.exec(redirect_uri, body.query)
  else
    -- 转到指定location
     local anotherLocation = urlArray[2]
     ngx.log(ngx.ERR,"++++++++++++222222++++++++++++")
     ngx.log(ngx.ERR,"another Location="..anotherLocation," redirect-no url= "..redirect_uri)
     ngx.req.set_uri(redirect_uri, false)
     ngx.exec("@"..anotherLocation)
  end
else
   -- 转到默认location
   ngx.log(ngx.ERR,"++++++++++++33333++++++++++++")
   ngx.log(ngx.ERR," redirect-no url= "..body.url)
   ngx.exec("@old_member")
end

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

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

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

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值