一种轻量的openresty路由设计
在使用openresty开发接口的过程会发现一个问题,那就是接口的地址问题怎么解决,最好一个接口地址对应一个lua文件,也可以在nginx.conf 配置中使用content_by_lua 来编写接口逻辑,显然后者并不合适团队开发,为了解决这个问题,所以出现了很多类似的框架,一个比较好用的就是lusty框架,他可以将url中的某段值自动定义成变量,但是耦合性有点高,当多个接口站点部署在同一个nginx上时,你只能通过修改lusty的目录结构和app.lua文件,显然这不是我想要的结果,在网上找到一段很犀利的ngx配置,简单粗暴,但非常有效。

但出于安全性考虑,决定给访问的接口地址加个白名单功能,不在白名单的地址不允许访问。
将白名单功能抽象成一个app_route.lua文件,在初始化的时候需要载入一个白名单列表,具体的ngx配置如下:

这里加载了一个对应目录的route_config.lua,由于这个config文件内容较小,所以我把内容直接列了出来:
--白名单列表
local whitelist = {
'test1',
'user/login',
'user/register'
}
--路由重写列表
local rewritelist = {
['user/([-_a-zA-Z0-9]+)/login'] = 'user/login',
['user/([a-zA-Z0-9]+)/register'] = 'user/register'
}
return {
whitelist = whitelist,
rewritelist = rewritelist
}
然后在content_by_lua_file 前面加这么一句代码:

你会发现白名单功能就这么完成了,而且多次测试后发现单纯的路由查找功能会比lusty快一倍以上。
当然也支持简单的路由重定向功能,本文只是单纯的技术分享,如果你有更好的建议也可以单独讨论。
文本是原创作品,转载记得写明出处
app_route.lua
local _M = { _VERSION = '0.1' }
local mt = { __index = _M}
local tinsert = table.insert
local tconcat = table.concat
local tonumber = tonumber
local function uritoken(uri)
local ret = {}
for token in uri:gmatch("[^/.]+") do
tinsert(ret,token)
end
return ret
end
function _M.new(self,rconfig)
local tab = {}
local routeMap = require(rconfig)
local route_data = {}
local whitelist = routeMap.whitelist
for i=,#whitelist do
local ret = uritoken(whitelist[i])
if #ret > then
tinsert(route_data,tconcat({'^',tconcat(ret,'/'),'$'}))
end
end
local rewritelist = routeMap.rewritelist
local x =
local rewrite_data = {}
local rewrite_urls = {}
for k,v in pairs(rewritelist) do
tinsert(rewrite_data,tconcat({'^(?<z',x,'z>',k,')$'}))
tinsert(rewrite_urls,v)
x = x +
end
tab.rewrite_urls = rewrite_urls
tab.rewrite_pattern = tconcat(rewrite_data,'|')
tab.route_pattern = tconcat(route_data,'|')
return setmetatable(tab, mt)
end
function _M.route_verify(self)
local uri = ngx.var.api_path
local ret = uritoken(uri)
uri = tconcat(ret,'/')
ngx.var.api_path = uri
local m = ngx.re.match(uri,self.route_pattern)
if m == nil then
m = ngx.re.match(uri,self.rewrite_pattern)
if m == nil then
ngx.exit()
else
local locant = ngx.re.match(next(m,#m), "^z(\\d+)z")
ngx.var.api_path = self.rewrite_urls[tonumber(locant[])]
end
end
end
return _M
一种轻量的openresty路由设计的更多相关文章
- flutter最简单轻量便捷的路由管理方案NavRouter
大家好,我是CrazyQ1,今天给大家推荐一个路由管理方案,用的非常不错的,叫nav_router. 项目地址是:https://github.com/fluttercandies/nav_route ...
- 实战ELK(4)Metricbeat 轻量型指标采集器
一.介绍 用于从系统和服务收集指标.从 CPU 到内存,从 Redis 到 Nginx,Metricbeat 能够以一种轻量型的方式,输送各种系统和服务统计数据. 1.系统级监控,更简洁(轻量型指标采 ...
- Metricbeat 轻量型指标采集器
一.介绍 用于从系统和服务收集指标.从 CPU 到内存,从 Redis 到 Nginx,Metricbeat 能够以一种轻量型的方式,输送各种系统和服务统计数据. 1.系统级监控,更简洁(轻量型指标采 ...
- 一种简单,轻量,灵活的C#对象转Json对象的方案(续)
本文参考资料 一种简单,轻量,灵活的C#对象转Json对象的方案 [源码]Literacy 快速反射读写对象属性,字段 一段废话 之前我已经介绍了这个方案的名称为JsonBuilder,这套方案最大的 ...
- 动手打造轻量web服务器(二)路由
tomcat启动慢?自己动手打造轻量web服务器(一) 上篇讲了怎么做一个最简单的web服务器,这篇就是在上篇加上URL路由功能(什么是路由?) 首先,根据http获得请求行 val scanner ...
- 一种简单,轻量,灵活的C#对象转Json对象的方案
简单,是因为只有一个类 轻量,是因为整个类代码只有300行 灵活,是因为扩展方式只需要继承重写某个方法即可 补充:修正无法处理可空值类型的bug 首先我将这个类称之为JsonBuilder,我希望它以 ...
- 基于netty轻量的高性能分布式RPC服务框架forest<上篇>
工作几年,用过不不少RPC框架,也算是读过一些RPC源码.之前也撸过几次RPC框架,但是不断的被自己否定,最近终于又撸了一个,希望能够不断迭代出自己喜欢的样子. 顺便也记录一下撸RPC的过程,一来作为 ...
- Bourbon – 简单轻量的 Sass 混入(Mixins)库
Bourbon 是一个简单易用的 Sass 混入(Mixin)库,无需配置.该混入包含用于支持所有现代浏览器的 CSS3 属性前缀.前缀需要确保在旧的浏览器支持优雅降级.Bourbon 使用 SCSS ...
- Cardinal:一个用于移动项目开发的轻量 CSS 框架
Cardinal 是一个适用于移动项目的 CSS 框架,包含很多有用的默认样式.矢量字体.可重用的模块以及一个简单的响应式模块系统.Cardinal 提供了一种在多种移动设备上实现可伸缩的字体和布局的 ...
随机推荐
- Cas Server中各配置文件介绍
Cas Server中所有的配置文件都是放在WEB-INF目录及其子目录下的. 在WEB-INF/classes下的配置文件有: l cas-theme-default.properties:该文件 ...
- [Webpack 2] Hashing with Webpack for long term caching
Leveraging the browser cache is an important part of page load performance. A great way to utilize t ...
- 采用subversion管理iOS资源
1.装和配置subversionserver 在windows server上安装VisualSVN-Server.下载地址http://www.visualsvn.com/server/downl ...
- 自定义String类,并且实现在STL容器中添加自定义的类型
13.44 编写标准库string类的简化版本,命名String.你的类应该至少有一个默认构造函数和一个接受C风格字符串指针参数的构造函数.使用allocator为你的String类分配所需内存. 1 ...
- LabVIEW设计模式系列——事件结构中值改变事件
标准:1.将具有值改变事件的控件,放置在其事件结构的值改变页面里.
- Unity Panel open & close
Making a Popup and Closable Panel in Unity 5 script: public GameObject thePanel; public open() { the ...
- iOS开发中常用的手势---边缘手势
说明:以下方法是开发中使用的方法,有什么不对的或者好的方法,请多多指教! 此处的边缘手势是用来控制左侧抽屉视图的弹出以及收回. 添加手势 : 页面上有多个手势时需要遵循 UIGestureRecogn ...
- table完美css样式,table的基本样式,table样式
table完美css样式,table的基本样式,table样式 >>>>>>>>>>>>>>>>> ...
- 多线程(Thread),其实很简单!
目录: 1:线程简介 2:怎么操作线程 3:Thread的常用方法 4:简单的获奖机 5:应用程序域 线程:是Windows任务调度的最小单位.线程是程序中的一个执行流,每个线 ...
- 初学HTML5系列三:事件
Window 事件属性 针对 window 对象触发的事件(应用到 <body> 标签): 属性 值 描述 onafterprint script 文档打印之后运行的脚本. onbefor ...