njs是一个烂,烂,烂的东西,文件上传方面一坨屎
上传吧,客户端好好的,动不动0字节
然后多方求证,甚至还翻找了issue,终于让我找到了 解决方法
句法: client_body_in_file_only on | clean | off;
默认: 客户端主体在文件中仅关闭;
语境:http
,server
,location
决定 nginx 是否应将整个客户端请求主体保存到文件中。此指令可以在调试期间使用,或者在使用变量$request_body_file
或 模块 ngx_http_perl_module的$r->request_body_file
方法时使用。
当设置为该值时on
,请求处理后不会删除临时文件。
该值clean
将导致请求处理后留下的临时文件被删除。
先设置 client_body_in_file_only: clean
然后加大缓冲区
client_max_body_size 256m;
client_body_buffer_size 128m;
注意量力而行,比如我的服务器(光猫)内存只有512m
~ $ cat /proc/meminfo
MemTotal: 470944 kB
接下来是判断body在文件中还是在Buffer内
Buffer:
try{
// 内容不在内存中
if(h.requestBuffer && h.requestBuffer.length == 0) throw 0;
// 直接使用h.requestBuffer
// ......
}catch(_e){
// 尝试读取文件
const file = h.variables.request_body_file;
if(!file) return h.return(500, 'Body read failed');
const body = await fs.promises.open(file, 'r');
// 使用body
// ......
}
文本:
let text = '';
try {
// 在Buffer内:直接可以使用
if (!h.requestText) throw 1;
text = h.requestText;
} catch (_e) {
// 在文件中:打开
const file = h.variables.request_body_file;
if (!file) return h.return(500, 'Body read failed');
text = (await fs.promises.readFile(file)).toString('utf8');
}
// 使用text
// ......
本文由 zlh 创作,采用 知识共享署名4.0 国际许可协议进行许可。
本站文章除注明转载/出处外,均为本站原创或翻译,转载前请务必署名。
[...]详情请参看我的这篇踩坑文章 https://hi.imzlh.top/2024/07/09.cgi 总之,这是Nginx的Buffer,而客户端的上传如果大于client_body_buffer_size会被写入文件并暴露在变量中 h.variables.request_body_file[...]