我如何强制nginx在缓存文件夹中保存响应,并使用来自上游服务器的标头?

时间:2017-02-15 11:00:28

标签: django caching nginx

我为我的API使用Django REST Framework,将nginx用作反向代理,使用redis缓存一些静态api数据。
我尝试使用Cache-Control: max-ageLast-Modify标头实施缓存 简而言之,它看起来像这样:

class SomeViewSet(viewsets.ModelViewSet):
    ....
    def list(self, request, *args, **kwargs):
        queryset = self.get_queryset()
        cache_key = self._get_cache_key() # get a key for reddis
        response = self._get_data_from_cache(cache_key) # get a data from reddis
        if response:
            # If data in redis return Response with a same Last-Modify
            # and 'Cache-Control': 'max-age=120'
            return response

        # Setting up new value for this viewset in a reddis
        serializer = self.get_serializer(queryset, many=True)
        now = datetime.datetime.now()
        cache.set(cache_key, [now, serializer.data])
        return Response(serializer.data, headers={'Last-Modified': now, 'Cache-Control': 'max-age=120'})

它的工作方式与我预期的一样,浏览器缓存数据的时间为120秒,当客户端使用If-Modified-Since标头检查内容时。 但是,当我设置max-age标头时,nginx会将其保存在缓存文件夹中,并且无需点击服务器即可为所有客户端提供服务。
这是我从本地机器测试nginx配置:

upstream django {
  server 127.0.0.1:8002; 
}

proxy_cache_path /home/ivan/projects/kors/test_prod/cache levels=1:2 keys_zone=my_cache:10m max_size=10g inactive=60m use_temp_path=off;

server {
    listen      8000;
    server_name 127.0.0.1; #
    charset     utf-8;
    client_max_body_size 75M;

location /media  {
    alias /path/to/media; 
    expires 1y;
    log_not_found off;
    access_log off;
}
location /static {
    alias /path/to/static; 
    expires 1y;
    log_not_found off;
    access_log off;
}

location / {
    uwsgi_pass  django;
    include     /path/to/uwsgi_params; 
    uwsgi_param Host $host;
    uwsgi_param X-Real-IP $remote_addr;
    uwsgi_param X-Forwarded-For $proxy_add_x_forwarded_for;
    uwsgi_param X-Forwarded-Proto $http_x_forwarded_proto;

    proxy_cache my_cache;
    }
}

考虑一下这篇文章nginx-caching-guide

  

NGINX如何确定是否缓存某些东西?
  默认情况下,NGINX尊重源服务器的Cache-Control标头。它不会缓存响应,缓存控制设置为Private,No-Cache或No-Store或响应头中的Set-Cookie。 NGINX仅缓存GET和HEAD客户端请求。您可以按照以下答案中的描述覆盖这些默认值。

我认为Cache-Contol: max-age标题会强制nginx将json保存在缓存文件夹中 文件夹已创建,但此处没有数据,我的所有来自不同浏览器的请求都在命中服务器 我错过了什么?或者也许我完全被误解为使用nginx进行缓存的概念?

1 个答案:

答案 0 :(得分:1)

首先,你在标题中添加Cache-Control: max-age并不能告诉nginx对它做任何事情。客户端管理如何处理标头以及如何处理后续请求。

你可能是一个网址的nginx响应缓存。不要看到你的nginx配置有问题。

uwsgi_cache_path /home/ivan/projects/kors/test_prod/cache levels=1:2 keys_zone=my_cache:10m max_size=10g inactive=60m use_temp_path=off;

location / {

    include     /path/to/uwsgi_params; 
    uwsgi_param Host $host;
    uwsgi_param X-Real-IP $remote_addr;
    uwsgi_param X-Forwarded-For $proxy_add_x_forwarded_for;
    uwsgi_param X-Forwarded-Proto $http_x_forwarded_proto;

    uwsgi_cache my_cache;
    uwsgi_pass  django;
}

此后你需要使用uwsgi缓存模块。

请参阅此处http://nginx.org/en/docs/http/ngx_http_uwsgi_module.html