前言

nginx默认不读取请求体的数据,但可以通过$request_body内置变量来获取。$request_body存在内存中,如果它的字节大小超过nginx配置的client_body_buffer_size的值,nginx就会把请求体存放到临时文件中。此时数据就不在内存中了,这会导致$request_body为空。

同步非阻塞方式获取请求体

ngx.req.read_body

含义:同步读取客户端请求体,且不会阻塞nginx的事件循环。使用此指令后,就可以通过ngx.req.get_body_data来获取请求体的数据了。但如果使用临时文件来存放请求体,就需要先使用函数ngx.req.get_body_file来获取临时文件名,再读取临时文件中的请求体数据。

环境:rewrite_by_lua*access_by_lua*content_by_lua*

ngx.req.get_body_data

含义:执行ngx.req.read_body指令后,可以使用本指令在内存中获取请求体数据,结果会返回一个lua的字符串类型的数据。如果要获取table类型的数据,则需要使用ngx.req.get_post_args

环境:rewrite_by_lua*access_by_lua*content_by_lua*log_by_lua*

ngx.req.get_post_args

含义:读取包含当前请求在内的所有post请求的查询参数,返回一个table类型的数据

环境:rewrite_by_lua*access_by_lua*content_by_lua*log_by_lua*header_filter_by_lua*body_filter_by_lua*

ngx.req.get_body_file

含义:获取存放请求体的临时文件名。如果请求体被存放在内存中,获取的值就是nil。

示例

获取string类型的请求体

location /testlua {
client_max_body_size 10k;
client_body_buffer_size 1k;
content_by_lua_block {
local ngx = require "ngx";
ngx.req.read_body() -- 开启读取请求体模式
local data = ngx.req.get_body_data() -- 获取内存中的请求体
if data then
ngx.print(string.format("data: %s, type: %s",data,type(data)))
return
else
local file = ngx.req.get_body_file() -- 如果内存中没有, 则到临时文件中读取
if file then
ngx.say("body is in file ", file)
else
ngx.say("no body found")
end
end
}
}

请求测试

curl -i http://192.168.1.111/testlua -d 'test=123&a=qwe&b=zxc'

HTTP/1.1 200 OK
Server: openresty
Date: Sun, 28 May 2023 10:05:51 GMT
Content-Type: application/octet-stream
Transfer-Encoding: chunked
Connection: keep-alive data: test=123&a=qwe&b=zxc, type: string

获取table类型的请求体

location /testlua {
client_max_body_size 10k;
client_body_buffer_size 1k;
content_by_lua_block {
local ngx = require "ngx";
ngx.req.read_body() -- 开启读取请求体模式
local args, err = ngx.req.get_post_args() -- 获取内存中的请求体
if args then
for k,v in pairs(args) do
if type(v) == "table" then
ngx.say(k, ": ", table.concat(v, ", "))
else
ngx.say(k, ": ", v)
end
end
else
local file = ngx.req.get_body_file() -- 如果内存中没有, 则到临时文件中读取
if file then
ngx.say("body is in file ", file)
else
ngx.say("no body found")
end
end
}
}

请求测试

curl -i http://192.168.1.111/testlua -d 'test=123&a=qwe&b=zxc'

HTTP/1.1 200 OK
Server: openresty
Date: Sun, 28 May 2023 10:37:48 GMT
Content-Type: application/octet-stream
Transfer-Encoding: chunked
Connection: keep-alive a: qwe
b: zxc
test: 123

参考

  • 《Nginx实战:基于lua语言的配置、开发与架构详解》

[nginx]lua读取请求体的更多相关文章

  1. nginx读取请求体

    请求体的读取一般发生在nginx的content handler中,一些nginx内置的模块,比如proxy模块,fastcgi模块,uwsgi模块等,这些模块的行为必须将客户端过来的请求体(如果有的 ...

  2. nginx请求体读取

    上节说到nginx核心本身不会主动读取请求体,这个工作是交给请求处理阶段的模块来做,但是nginx核心提供了ngx_http_read_client_request_body()接口来读取请求体,另外 ...

  3. 【精选】Nginx模块Lua-Nginx-Module学习笔记(一)Nginx Lua API 接口详解

    源码地址:https://github.com/Tinywan/Lua-Nginx-Redis 一.介绍 各种* _by_lua,* _by_lua_block和* _by_lua_file配置指令用 ...

  4. post请求体过大导致ngx.req.get_post_args()取不到参数体的问题

    http://nginx.org/en/docs/http/ngx_http_core_module.html#client_body_buffer_size 该地址对于client_body_buf ...

  5. Nginx模块Lua-Nginx-Module学习笔记(一)Nginx Lua API 接口详解

    源码地址:https://github.com/Tinywan/Lua-Nginx-Redis 一.介绍 各种* _by_lua,* _by_lua_block和* _by_lua_file配置指令用 ...

  6. openresty(nginx+lua)初识

    1.新增项目配置文件: vim /usr/example/example1.conf --将以下内容加入example1.conf server { listen 80; server_name _; ...

  7. http 请求体数据--ngx

    HTTP包体的长度有可能非常大,不同业务可能对包体读取 处理不相同, 比如waf, 也许会读取body内容或者只是读取很少的前几十字节.所以根据不同业务特性,对http body 数据包处理方式不同, ...

  8. 从Excel获取请求体

    Excel文件 .py文件---------------------- import xlrdimport re def fetch_body(path,sheet,name,adict):     ...

  9. Spring Cloud Gateway 之获取请求体(Request Body)的几种方式

    Spring Cloud Gateway 获取请求体 一.直接在全局拦截器中获取,伪代码如下 private String resolveBodyFromRequest(ServerHttpReque ...

  10. Asp.Net Core上传大文件请求体限制设置

    IIS进程内部署时 1. Web.Config的<system.webServer>节点下增加 <security> <requestFiltering> < ...

随机推荐

  1. mapper中sql返回类型是integer,但是sql查询结果是null,报错

    1.出问题代码 当sql返回结果为null时报错    org.apache.ibatis.binding.BindingException: Mapper method 'com.yswl.scie ...

  2. #Power Query 分组依据,数据的分类汇总

    一:概述 Power Query中的分组依据,类似于Excel中的分类汇总功能,可以按照某一分类对某列数据或某几列数据进行去重操作和聚合计算(求和.计数.求平均.非重复行计数等),并在去重的过程中将其 ...

  3. 2023-05-12:存在一个由 n 个节点组成的无向连通图,图中的节点按从 0 到 n - 1 编号, 给你一个数组 graph 表示这个图, 其中,graph[i] 是一个列表,由所有与节点 i

    2023-05-12:存在一个由 n 个节点组成的无向连通图,图中的节点按从 0 到 n - 1 编号, 给你一个数组 graph 表示这个图, 其中,graph[i] 是一个列表,由所有与节点 i ...

  4. phpstudy-sqlilabs-less-11

    题目:POST - Error Based - Single quotes- String 基于错误的单引号post型字符变形的注入 看到有个账密输入口第一反应尝试post注入 打开post data ...

  5. SpringIOC个人笔记

    上一章讲解了SpringBoot中的 AutoConfiguration自动装配,而这一章就来讲讲自动装配时会用到的Spring三大特性之一的IOC控制反转. ​ 使用过Spring的人都熟知,Spr ...

  6. 2015年蓝桥杯C/C++大学B组省赛真题(加法变乘法)

    题目描述: 我们都知道:1+2+3+ ... + 49 = 1225 现在要求你把其中两个不相邻的加号变成乘号,使得结果为2015 比如: 1+2+3+...+10*11+12+...+27*28+2 ...

  7. windows下搭建docker容器环境

    下载Docker Desktop https://www.docker.com/ 安装Docker Desktop(软件默认安装c盘,若要安装到其他盘,在安装之前创建软连接再进行安装) 在自定义磁盘中 ...

  8. MySQL全面瓦解30:备份与恢复

    合辑地址:MySQL全面瓦解 1 为什么需要数据库备份 灾难恢复:当发生数据灾难的时候,需要对损坏的数据进行恢复和还原 需求的变更或者回滚:当需求发生变更,或者需要回滚到之前的版本时,数据库备份也显得 ...

  9. http_basic认证(401)爆破

    Http Basic认证(401)爆破 hydra,burpsuit 在thm:https://tryhackme.com/room/toolsrus 遇到了这个问题,但这个用的工具是hydra,想起 ...

  10. JavaWeb编程面试题——MyBatis

    引言 面试题==知识点,这里所记录的面试题并不针对于面试者,而是将这些面试题作为技能知识点来看待.不以刷题进大厂为目的,而是以学习为目的.这里的知识点会持续更新,目录也会随时进行调整. 关注公众号:编 ...