nginx报错“an upstream response is buffered to a temporary file”

已邀请:

解决办法:

如果是通过fastcgi做的代理,可以可以增加/调整如下到http段,也可以增加到反向代理的server的location段

fastcgi_buffer_size 128k;
fastcgi_buffers 8 128k;


fastcgi_buffers 控制 nginx 最多创建 8 个大小为 128K 的缓冲区

而 fastcgi_buffer_size 则是处理 Response 时第一个缓冲区的大小,不包含在前者中。

所以总计能创建的最大内存缓冲区大小是 8*128K+128K = 1152k。而这些缓冲区是根据实际的 Response 大小动态生成的,并不是一次性创建的。比如一个 256K 的页面,Nginx 会创建 2*128K 共 2 个 buffers。



当 Response 小于等于 

1152k  时,所有数据当然全部在内存中处理。如果 Response 大于 

1152k  呢?fastcgi_temp 的作用就在于此。多出来的数据会被临时写入到文件中,放在这个目录下面。同时你会在 error.log 中看到一条类似 warning。


缓冲区设置的太小的话,Nginx 会频繁读写硬盘,对性能有很大的影响,但也不是越大越好。



如果是proxy方式可以参考如下:


参数释义:

proxy_buffer_size
语法: proxy_buffer_size the_size

默认值: proxy_buffer_size 4k/8k

上下文: http, server, location

该指令设置缓冲区大小,从代理后端服务器取得的第一部分的响应内容,会放到这里.

小的响应header通常位于这部分响应内容里边.

默认来说,该缓冲区大小等于指令 proxy_buffers所设置的;但是,你可以把它设置得更小.

proxy_buffering
语法: proxy_buffering on|off

默认值: proxy_buffering on

上下文: http, server, location

该指令开启从后端被代理服务器的响应内容缓冲.

如果缓冲区开启,nginx假定被代理的后端服务器会以最快速度响应,并把内容保存在由指令proxy_buffer_size 和 proxy_buffers指定的缓冲区里边.

如果响应内容无法放在内存里边,那么部分内容会被写到磁盘上。

如果缓冲区被关闭了,那么响应内容会按照获取内容的多少立刻同步传送到客户端。

nginx不尝试计算被代理服务器整个响应内容的大小,nginx能从服务器接受的最大数据,是由指令proxy_buffer_size指定的.

对于基于长轮询(long-polling)的Comet 应用来说,关闭 proxy_buffering 是重要的,不然异步响应将被缓存导致Comet无法工作

proxy_buffers
语法: proxy_buffers the_number is_size;

默认值: proxy_buffers 8 4k/8k;

上下文: http, server, location

该指令设置缓冲区的大小和数量,从被代理的后端服务器取得的响应内容,会放置到这里. 默认情况下,一个缓冲区的大小等于内存页面大小,可能是4K也可能是8K,这取决于平台。

proxy_busy_buffers_size
语法: proxy_busy_buffers_size size;

默认值: proxy_busy_buffers_size proxy_buffer_size * 2;

上下文: http, server, location, if

TODO: Description.

buffer工作原理
首先第一个概念是所有的这些proxy buffer参数是作用到每一个请求的。每一个请求会安按照参数的配置获得自己的buffer。proxy buffer不是global而是per request的。

proxy_buffering 是为了开启response buffering of the proxied server,开启后proxy_buffers和proxy_busy_buffers_size参数才会起作用。

无论proxy_buffering是否开启,proxy_buffer_size(main buffer)都是工作的,proxy_buffer_size所设置的buffer_size的作用是用来存储upstream端response的header。

在proxy_buffering 开启的情况下,Nginx将会尽可能的读取所有的upstream端传输的数据到buffer,直到proxy_buffers设置的所有buffer们被写满或者数据被读取完(EOF)。此时nginx开始向客户端传输数据,会同时传输这一整串buffer们。同时如果response的内容很大的话,Nginx会接收并把他们写入到temp_file里去。大小由proxy_max_temp_file_size控制。如果busy的buffer传输完了会从temp_file里面接着读数据,直到传输完毕。

一旦proxy_buffers设置的buffer被写入,直到buffer里面的数据被完整的传输完(传输到客户端),这个buffer将会一直处在busy状态,我们不能对这个buffer进行任何别的操作。所有处在busy状态的buffer size加起来不能超过proxy_busy_buffers_size,所以proxy_busy_buffers_size是用来控制同时传输到客户端的buffer数量的。


1. proxy_buffering

语法:proxy_buffering on|off

默认值:proxy_buffering 0n

上下文:http,server,location

该 指令开启从后端被代理服务器的响应内容缓冲。如果缓冲区开启,nginx假定被代理的后端服务器会以最快速度响应,并把内容保存在由指令 proxy_buffer_size 和 proxy_buffers指定的缓冲区里边.如果响应内容无法放在内存里边,那么部分内容会被写到磁盘上。如果缓冲区被关闭了,那么响应内容会按照获取 内容的多少立刻同步传送到客户端。nginx不尝试计算被代理服务器整个响应内容的大小,nginx能从服务器接受的最大数据,是由指令 proxy_buffer_size指定的.对于基于长轮询(long-polling)的Comet 应用来说,关闭 proxy_buffering 是重要的,不然异步响应将被缓存导致Comet无法工作。

2. proxy_buffers

语法:proxy_buffers  数量  大小

默认值:proxy_buffers 8  4k/8k

上下文:http,server,location

该指令设置缓冲区的大小和数量,从被代理的后端服务器取得的响应内容,会放置到这里. 默认情况下,一个缓冲区的大小等于内存页面大小,可能是4K也可能是8K,这取决于平台。

3. proxy_buffer_size

语法:proxy_buffer_size  the size

默认值:proxy_buffer_size 4k/8k

上下文:http,server,location

该指令设置缓冲区大小,从代理后端服务器取得的第一部分的响应内容,会放到这里.小的响应header通常位于这部分响应内容里边.默认来说,该缓冲区大小等于指令 proxy_buffers所设置的;但是,你可以把它设置得更小.

4. proxy_busy_buffers_size

语法:proxy_busy_buffers_size                大小

默认值:proxy_busy_buffers_size  proxy_buffer_size*2

上下文:http,server,location,if

buffer 工作原理

1. 所有的proxy buffer参数是作用到每一个请求的。每一个请求会安按照参数的配置获得自己的buffer。proxy buffer不是global而是per request的。

2. proxy_buffering 是为了开启response buffering of the proxied server,开启后proxy_buffers和proxy_busy_buffers_size参数才会起作用。

3. 无论proxy_buffering是否开启,proxy_buffer_size(main buffer)都是工作的,proxy_buffer_size所设置的buffer_size的作用是用来存储upstream端response的header。

4. 在proxy_buffering 开启的情况下,Nginx将会尽可能的读取所有的upstream端传输的数据到buffer,直到proxy_buffers设置的所有buffer们 被写满或者数据被读取完(EOF)。此时nginx开始向客户端传输数据,会同时传输这一整串buffer们。同时如果response的内容很大的 话,Nginx会接收并把他们写入到temp_file里去。大小由proxy_max_temp_file_size控制。如果busy的buffer 传输完了会从temp_file里面接着读数据,直到传输完毕。

5. 一旦proxy_buffers设置的buffer被写入,直到buffer里面的数据被完整的传输完(传输到客户端),这个buffer将会一直处 在busy状态,我们不能对这个buffer进行任何别的操作。所有处在busy状态的buffer size加起来不能超过proxy_busy_buffers_size,所以proxy_busy_buffers_size是用来控制同时传输到客户 端的buffer数量的。

要回复问题请先登录注册