cosocket API 还可以用于读取巨大的请求体数据
http://agentzh.org/misc/slides/ngx-openresty-ecosystem/index.html#59
实话是内置的,,,
- 上传可以流式读取
- 下载自然也可以使用相同机制来吼
--
人生苦短, Pythonic! 冗余不做,日子甭过!备份不做,十恶不赦!
俺: http://about.me/zoom.quiet
文字协议: http://creativecommons.org/licenses/by-sa/2.5/cn/
--
邮件自: 列表“openresty”,专用于技术讨论!
发言: 请发邮件到 open...@googlegroups.com
退订: 请发邮件至 openresty+...@googlegroups.com
详情: http://groups.google.com/group/openresty
官网: http://openresty.org/
仓库: https://github.com/agentzh/ngx_openresty
建议: 提问的智慧 http://wiki.woodpecker.org.cn/moin/AskForHelp
在 12-3-11,wd<w...@wdicc.com> 写道:
如果你的数据源是磁盘文件,可以使用类似下面的代码来分块读取文件内容并流式输出给下游 HTTP 连接:
local chunk_size = 4096 -- this is just an example
local file_path = "/tmp/big.txt" -- this is just an example
local f, err = io.open(file_path, "r")
if not f then
ngx.say("failed to open file: ", err)
return
end
while true do
local chunk = f:read(chunk_size)
if not chunk then
break
end
ngx.print(chunk)
ngx.flush(true)
end
see:c30k和nginx的AIO | N.S.thoughts
http://nightsailer.com/2010/12/16/827.html
嗯,是的。我是在想如何利用这个做一个类似于网盘的东西,显然,不能直接提供HTTP下载,要不然,网盘就失去权限控制作用了。
Regards,
-agentzh
- 总之,根据 nginx 的执行阶段来切分
- 只要是作用于不同阶段的模块,就可以串接起来共同作用
- 好在 opernersty 包含了所有主要阶段的处置
- 而且可以通过内部子请求的方式,分裂出新的执行序列来
- 从而可以引入其它模块的能力
嗯嗯嗯,怎么想都感觉,这里有个要命的调试技巧问题:
- 万一将作用同一阶段的不同模块想当然的写到一齐
- 报錯时,是否明确指出为什么?
或是,已经通过模块的命名本身就强烈的暗示只能使用在什么阶段?
> 1. 使用 access_by_lua 在 access 阶段进行权限控制,而 content 阶段仍由 ngx_static 模块提供静态文件服务。
>
> 见 http://wiki.nginx.org/HttpLuaModule#access_by_lua
>
> 关于 nginx 请求处理阶段的概念,可以参见我的 Nginx 教程系列“Nginx 配置指令的执行顺序”:
>
> http://blog.sina.com.cn/s/articlelist_1834459124_2_1.html
>
> 2. 在入口 location 中使用 content_by_lua 进行相关处理,但不直接输出响应,最后再用 ngx.exec()
> 发起内部跳转到一个配置了静态文件服务的 internal location 输出文件内容。
>
> 见 http://wiki.nginx.org/HttpLuaModule#ngx.exec
>
> Regards,
> -agentzh
- 总之,根据 nginx 的执行阶段来切分
- 只要是作用于不同阶段的模块,就可以串接起来共同作用
- 好在 opernersty 包含了所有主要阶段的处置
- 而且可以通过内部子请求的方式,分裂出新的执行序列来
- 从而可以引入其它模块的能力
嗯嗯嗯,怎么想都感觉,这里有个要命的调试技巧问题:
- 万一将作用同一阶段的不同模块想当然的写到一齐
- 报錯时,是否明确指出为什么?
或是,已经通过模块的命名本身就强烈的暗示只能使用在什么阶段?
如果使用lua读写本地文件,那么缓存也能搞定,就是用不上sendfile,性能会差点。貌似
做个sendfile的lua bind是不是可以搞定?
cosocket很强大,如果文件存储在后端,lua模块只用来做porxy,那么完全可以自由拼接
后端的分块存储形成一个文件流给用户。
如果使用lua读写本地文件,那么缓存也能搞定,就是用不上sendfile,性能会差点。貌似
做个sendfile的lua bind是不是可以搞定?
又想了想,用lua读写文件,会阻塞线程。。。能主动yield么,或者改用luaaio?
不过有这种大量io的应用场景不多,呵呵
On Mar 12, 5:14 pm, agentzh <agen...@gmail.com> wrote:
如果你的数据源是磁盘文件,可以使用类似下面的代码来分块读取文件内容并流式输出给下游 HTTP 连接:
local chunk_size = 4096 -- this is just an example
local file_path = "/tmp/big.txt" -- this is just an example
local f, err = io.open(file_path, "r")
if not f then
ngx.say("failed to open file: ", err)
return
end
while true do
local chunk = f:read(chunk_size)
if not chunk then
break
end
ngx.print(chunk)
ngx.flush(true)
end
这个例子中的关键是利用了 ngx.flush 这个接口:
http://wiki.nginx.org/HttpLuaModule#ngx.flush
不过这里需要注意的一个问题是 ngx_lua 对于 HTTP 1.0 是自动对响应体进行全缓存的(为了支持 HTTP 1.0 Keepalive),而目前没有提供配置方式禁止此行为,所以当客户端发起的是 HTTP 1.0 请求,上面的代码并不能实现流式输出。我这两天将实现一个 lua_http10_buffering 配置选项,上面的例子中只要在 nginx.conf 中加上
lua_http10_buffering off;
就不会再有 HTTP 1.0 全缓存输出的行为了。