Lua

4.1k 词

名称

ngx_http_lua_module - 将Lua的功能嵌入到Nginx HTTP服务器中。

这个模块没有与Nginx源码一起发布。详见安装介绍

内容列表

状态

已经发布。

版本

此文档基于2017年4月8日发布的ngx_lua v0.10.8

概要

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
# 设置纯lua外部库的搜索路径 (';;' 是默认路径):
lua_package_path '/foo/bar/?.lua;/blah/?.lua;;';
# 设置用C实现的Lua外部库的搜索路径 (也可以用 ';;'):
lua_package_cpath '/bar/baz/?.so;/blah/blah/?.so;;';
server {
location /lua_content {
# MIME type determined by default_type:
default_type 'text/plain';
content_by_lua_block {
ngx.say('Hello,world!')
}
}
location /nginx_var {
# MIME type determined by default_type:
default_type 'text/plain';
# try access /nginx_var?a=hello,world
content_by_lua_block {
ngx.say(ngx.var.arg_a)
}
}
location = /request_body {
client_max_body_size 50k;
client_body_buffer_size 50k;
content_by_lua_block {
ngx.req.read_body() -- explicitly read the req body
local data = ngx.req.get_body_data()
if data then
ngx.say("body data:")
ngx.print(data)
return
end
-- body may get buffered in a temp file:
local file = ngx.req.get_body_file()
if file then
ngx.say("body is in file ", file)
else
ngx.say("no body found")
end
}
}
# transparent non-blocking I/O in Lua via subrequests
# (well, a better way is to use cosockets)
location = /lua {
# MIME type determined by default_type:
default_type 'text/plain';
content_by_lua_block {
local res = ngx.location.capture("/some_other_location")
if res then
ngx.say("status: ", res.status)
ngx.say("body:")
ngx.print(res.body)
end
}
}
location = /foo {
rewrite_by_lua_block {
res = ngx.location.capture("/memc",
{ args = { cmd = "incr", key = ngx.var.uri } }
)
}
proxy_pass http://blah.blah.com;
}
location = /mixed {
rewrite_by_lua_file /path/to/rewrite.lua;
access_by_lua_file /path/to/access.lua;
content_by_lua_file /path/to/content.lua;
}
# use nginx var in code path
# CAUTION: contents in nginx var must be carefully filtered,
# otherwise there'll be great security risk!
location ~ ^/app/([-_a-zA-Z0-9/]+) {
set $path $1;
content_by_lua_file /path/to/lua/app/root/$path.lua;
}
location / {
client_max_body_size 100k;
client_body_buffer_size 100k;
access_by_lua_block {
-- check the client IP address is in our black list
if ngx.var.remote_addr == "132.5.72.3" then
ngx.exit(ngx.HTTP_FORBIDDEN)
end
-- check if the URI contains bad words
if ngx.var.uri and
string.match(ngx.var.request_body, "evil")
then
return ngx.redirect("/terms_of_use.html")
end
-- tests passed
}
# proxy_pass/fastcgi_pass/etc settings
}
}

回到内容列表

描述

通过标准的Lua5.1解释器或者LuaJIT2.0/2.1以及借助Nginx的子请求,此模块将Lua嵌入到Nginx中,允许将强大的Lua线程集成到Nginx事件模块中。

Apcache’s mod_luaLighttpd’s mod_magnet不同的是,使用此模块执行Lua代码,在网络传输中完全是非阻塞的,只要使用此模块提供的Nginx API for Lua来处理上游服务的请求,例如MySQL, PostgreSQL, Memcached,Redis 或上游Http web服务。

至少以下Lua库和Nginx模块可以和ngx_lua模块一起使用:

通过ngx.location.capture或者ngx.location.capture_multi,几乎所有的Ngnix模块都可以与ngx_lua模块一起使用,但是我们建议使用lua-resty-*代替创建子请求去访问Nginx upstream模块,因为前者更加灵活且存储效率更高。

在一个单独的nginx worker进程中,所有的请求共享一个Lua解释器或LuaJIT实例,但是请求上下文却是使用轻量级的Lua协程隔离。

被加载的Lua模块保持在nginx worker级别使得只占用极小内存,即使在重负载下也是如此。

这个模块被插入NGINX的“http”子系统,所以它仅仅支持Http家族中的晚期通信协议(例如HTTP0.9/1.0/1.1/2.0,WebSockets等等)。如果你想使用TCP协议与晚期版本客户端通信,你应该使用兼容Lua APi的ngx_stream_lua模块。

回到TOC

典型应用

仅仅列举一些:

  • 使用Lua处理各种nginx upstream输出(代理,dirzzle, postgres,redis, memcached,等等)
  • 在请求真正到达upstream后端之前,使用处理任意复杂的访问控制和安全检查
  • 使用随意方式操纵响应头
  • 从外部存储(例如redis, memcached,mysql,postgresql)获取后端信息,从而即时根据那些信息来选择访问哪个upstream后端
  • 在一个content handler中使用同步方式编写任意复杂的web应用,但是仍然使用非阻塞方式访问数据库后端和其他存储。
  • 使用Lua在重写阶段做非常复杂的URL调度
  • 使用Lua为Nginx的子请求和任意的location实现高级的缓存机制。

作为模块,他允许将Nginx内的各种元素聚集在一起,并将Lua的优势暴露给用户,这种可能性是无限的。该模块提供了脚本的全部灵活性,同时在cpu时间以及内存占用方面,提供了与C语言同等级别的性能水平。当LusJIT2.x可用后尤其是如此。

而其他的脚本语言通常难以实现此性能级别。

Lua状态(Lua虚拟机实例)跨所有请求共享,通过一个单独的nginx worker进程处理以最小化内存占用。

回到TOC

Nginx兼容性

该模块最新的版本兼容一下Nginx版本:

  • 1.11.x (last tested: 1.11.2)
  • 1.10.x
  • 1.9.x (last tested: 1.9.15)
  • 1.8.x
  • 1.7.x (last tested: 1.7.10)
  • 1.6.x

Nginx cores低于1.6.0(包含)版本不再支持。

回到TOC

安装