Nginx - 为什么 uwsgi_cache 不能使用这个 headers?

Nginx - why isn't uwsgi_cache working with this headers?

我正在使用 Nginx + uWsgi + web2py 框架,我想让 Nginx 缓存 web2py 生成的 HTML 响应。

web2py生成的HTMLheaders是这些:

Cache-Control:max-age=300, s-maxage=300, public
Connection:keep-alive
Content-Length:147
Content-Type:text/html; charset=utf-8
Date:Mon, 27 Mar 2017 16:27:54 GMT
Expires:lun, 27 mar 2017 16:32:54 GMT
Server:Rocket 1.2.6 Python/2.7.6
X-Powered-By:web2py

这些是直接使用 web2py 嵌入式服务器提供的。 使用 nginx 和 uwsgi(没有任何缓存配置)服务的相同请求会产生这些 headers:

Cache-Control:max-age=300, s-maxage=300, public
Connection:keep-alive
Content-Encoding:gzip
Content-Type:text/html; charset=utf-8
Date:Mon, 27 Mar 2017 16:31:09 GMT
Expires:lun, 27 mar 2017 16:36:09 GMT
Server:nginx
Transfer-Encoding:chunked
Vary:Accept-Encoding
X-Powered-By:web2py

现在,我想为 nginx 配置实现 uwsgi_cache,我正在尝试这样:

uwsgi_cache_path /tmp/nginx_cache/ levels=1:2 keys_zone=mycache:10m max_size=10g inactive=10m use_temp_path=off;

server {  
    listen 80;
    server_name  myapp.com;
    root /home/user/myapp;

    location / {
        uwsgi_cache mycache;
        uwsgi_cache_valid 200 15m;
        uwsgi_cache_key $request_uri;

        add_header X-uWSGI-Cache $upstream_cache_status;

        expires 1h;

        uwsgi_pass      unix:///tmp/myapp.socket;
        include         uwsgi_params;
        uwsgi_param     UWSGI_SCHEME $scheme;
        uwsgi_param     SERVER_SOFTWARE    nginx/$nginx_version;
    }
}

然而,每次我点击 URL,我都会在响应中得到一个 MISS headers,表明 nginx 没有为来自缓存的请求提供服务:

Cache-Control:max-age=3600
Connection:keep-alive
Content-Encoding:gzip
Content-Type:text/html; charset=utf-8
Date:Mon, 27 Mar 2017 16:37:29 GMT
Expires:Mon, 27 Mar 2017 22:37:29 GMT
Server:nginx
Transfer-Encoding:chunked
Vary:Accept-Encoding
X-Powered-By:web2py
X-uWSGI-Cache:MISS

nginx进程运行为"www-data"user/group。我检查了文件夹 /tmp/nginx_cache/ 的权限,他们没问题:用户有权限读取和写入该文件夹。此外,在 /tmp/nginx_cache/ 中,nginx 创建了一个 "temp" 文件夹,但没有写入缓存文件。

我还尝试将 proxy_ignore_headers 添加到位置块,以指示 nginx 忽略一些 headers,如 Set-Cookie 和 Cache-Control,如下所示:

location / {
        uwsgi_cache mycache;
        uwsgi_cache_valid 200 15m;
        uwsgi_cache_key $scheme$proxy_host$uri$is_args$args;

        add_header X-uWSGI-Cache $upstream_cache_status;

        proxy_ignore_headers X-Accel-Expires Expires Cache-Control Set-Cookie Vary;

        uwsgi_pass      unix:///tmp/myapp.socket;
        include         uwsgi_params;
        uwsgi_param     UWSGI_SCHEME $scheme;
        uwsgi_param     SERVER_SOFTWARE    nginx/$nginx_version;
}

但是,这没有区别:第一个请求未被缓存,所有后续请求都是 MISS,也就是说,它们不是从缓存中提供的。

我发现了类似的 post,回答者指出这可能是(在本例中)web2py 生成的响应 headers 的问题: https://serverfault.com/questions/690164/why-is-this-nginx-setup-not-caching-responses

为什么 nginx 不缓存响应?

我找到了问题的原因:我将 uwsgi_cache_* 指令与 proxy_cache_* 指令混合在一起,它们属于不同的 Nginx 模块。我只是 需要将 proxy_ignore_headers 替换为 uwsgi_ignore_headers

注意proxy_cache module is different than uwsgi_cache,它们有非常相似的指令,但它们是两个不同的模块。