前言Nginx与Lua编写脚本的基本构建块是指令。指令用于指定何时运行用户Lua代码以及如何使用结果。下面是显示指令执行顺序的图。
原理:
ngx_lua将Lua嵌入Nginx,可以让Nginx执行Lua脚本,并且高并发、非阻塞的处理各种请求。Lua内建协程,这样就可以很好的将异步回调转换成顺序调用的形式。
ngx_lua在Lua中进行的IO操作都会委托给Nginx的事件模型,从而实现非阻塞调用。开发者可以采用串行的方式编写程序,ngx_lua会自动的在进行阻塞的IO操作时中断,保存上下文;然后将IO操作委托给Nginx事件处理机制,在IO操作完成后,ngx_lua会恢复上下文,程序继续执行,这些操作都是对用户程序透明的。
每个NginxWorker进程持有一个Lua解释器或者LuaJIT实例,被这个Worker处理的所有请求共享这个实例。每个请求的Context会被Lua轻量级的协程分割,从而保证各个请求是独立的。
ngx_lua采用“one-coroutine-per-request”的处理模型,对于每个用户请求,ngx_lua会唤醒一个协程用于执行用户代码处理请求,当请求处理完成这个协程会被销毁。每个协程都有一个独立的全局环境(变量空间),继承于全局共享的、只读的“comman data”。
所以,被用户代码注入全局空间的任何变量都不会影响其他请求的处理,并且这些变量在请求处理完成后会被释放,这样就保证所有的用户代码都运行在一个“sandbox”(沙箱),这个沙箱与请求具有相同的生命周期。
得益于Lua协程的支持,ngx_lua在处理10000个并发请求时只需要很少的内存。根据测试,ngx_lua处理每个请求只需要2KB的内存,如果使用LuaJIT则会更少。所以ngx_lua非常适合用于实现可扩展的、高并发的服务。
1. 安装解压lua
#安装至/usr/local
wget http://luajit.org/download/LuaJIT-2.0.5.tar.gz
tar -zxvf LuaJIT-2.0.5.tar.gz
2.进入该目录执行安装命令
cd LuaJIT-2.0.5
make && make install PREFIX=/usr/local/LuaJIT
3. /etc/profile 文件中加入环境变量
#vi /etc/profile 在最后面加入下面两行配置
export LUAJIT_LIB=/usr/local/LuaJIT/lib
export LUAJIT_INC=/usr/local/LuaJIT
#保存执行命令
source /etc/profile
#路径是上面luajit实际安装路径,路径错误安装nginx的lua模块时会报错找不到luajit库
# source /etc/profile 立刻生效,如果ngixn安装的时候不生效需要重启服务
4.下载ngx_devel_kit模块
wget https://github.com/simpl/ngx_devel_kit/archive/v0.3.0.tar.gz
tar -zxvf v0.3.0.tar.gz
#NDK(nginx development kit)模块是一个拓展nginx服务器核心功能的模块,第三方模块开发
#可以基于它来快速实现。 NDK提供函数和宏处理一些基本任务,减轻第三方模块开发的代码
#量。
5.下载lua-nginx-module模块
wget https://github.com/openresty/lua-nginx-module/archive/v0.10.9rc7.tar.gz
tar -zxvf v0.10.9rc7.tar.gz
#lua-nginx-module 模块使nginx中能直接运行lua
6.再次编译nginx
#增加这两个模块
--add-module=/usr/local/LuaJIT-2.0.5/lua-nginx-module-0.10.9rc7
--add-module=/usr/local/LuaJIT-2.0.5/ngx_devel_kit-0.3.0
通过nginx -V查看之前安装的信息
切换到nginx安装目录下执行编译添加需要安装的模块
./configure --user=nginx --group=nginx --prefix=/usr/local/nginx --add-module=/usr/local/LuaJIT-2.0.5/lua-nginx-module-0.10.9rc7 --add-module=/usr/local/LuaJIT-2.0.5/ngx_devel_kit-0.3.0 --with-stream
如果执行出现以下错误
解决办法:
yum install lua-devel
执行make && make install安装
make && make install
7.安装完成后再次执行查看是否安装成功
nginx -V
如果出现以下错误:
一般是由于编译时没有生成动态链接库,只能手动链接
#查找安装的libluajit-5.1.so.2
find / -name libluajit-5.1.so.2
cat /etc/ld.so.conf
#""里面的路径即时上图动态链接库的路径
echo "/usr/local/LuaJIT/lib" >> /etc/ld.so.conf
ldconfig
如果没有出错,则如下
8. nginx配置文件进行lua的实际使用配置
在对应拦截请求处,新增验证
access_by_lua_block {
local argToken = ngx.var.arg_token;
local headerToken = ngx.var.http_token;
--先验证请求参数中是否含有token
if argToken ~= nil then
if argToken ~= "eyJ0eXAiOicYMJFOlA3qpn0vXjXJD0XWDQ" then
ngx.status = ngx.HTTP_FORBIDDEN
ngx.say("Token失效")
ngx.exit(ngx.HTTP_FORBIDDEN)
end
--如果参数中没有,验证请求头里面是否含有
elseif headerToken ~= nil then
if headerToken ~= "eyJ0eXAiOicYMJFOlA3qpn0vXjXJD0XWDQ" then
ngx.status = ngx.HTTP_FORBIDDEN
ngx.say("Token失效")
ngx.exit(ngx.HTTP_FORBIDDEN)
end
else
print("都没有");
ngx.status = ngx.HTTP_FORBIDDEN
ngx.say("Token不能为空")
ngx.exit(ngx.HTTP_FORBIDDEN)
end
}
重启nginx使得配置文件生效,再去访问页面
就会发现如果不携带token访问页面是访问不了的
携带token才可访问