Я устанавливаю некоторые не кэширующие заголовки в промежуточном программном обеспечении Django для управления кешированием запроса xhr. В основном потому, что IE сильно кеширует запросы ajax.
class NeverCacheXhrMiddleware(object):
"""
sets no-cache headers for all xhr requests
xhr requests must send the HTTP_X_REQUESTED_WITH header to
be identified correctly as a xhr request using .is_ajax()
see: http://stackoverflow.com/questions/49547/making-sure-a-web-page-is-not-cached-across-all-browsers
"""
def process_response(self, request, response):
if request.is_ajax():
#add_never_cache_headers(response)
#patch_cache_control(response, no_cache=True)
response['Cache-Control'] = 'no-cache, no-store, must-revalidate'
response['Pragma'] = 'no-cache'
response['Expires'] = '0'
return response
Это отлично работает, когда я развернул свое приложение, используя только Gunicorn в среде разработки. В производственной среде мы также запускаем NGINX перед Gunicorn, и кажется, что NGINX перезаписывает заголовки, установленные Django.
Посмотрите эти снимки экрана, чтобы увидеть, как меняются заголовки:
DEV Env .:
PROD Env. с NGINX:
Есть идеи, что изменить в конфигурации NGINX, чтобы NGINX передавал заголовки, установленные Django?
nginx conf. выглядит так:
events {
worker_connections 1024;
}
http {
include /etc/nginx/mime.types;
default_type application/octet-stream;
log_format main '$remote_addr - $remote_user [$time_local] "$request" '
'$status $body_bytes_sent "$http_referer" '
'"$http_user_agent" "$http_x_forwarded_for"';
sendfile on;
keepalive_timeout 65;
include /path/to/sub_conf/*.conf;
}
Конфигурация сервера nginx. включен через sub conf:
server {
listen 80;
server_name localhost1;
location / {
proxy_pass http://127.0.0.1:8000;
}
}
Видимо вы можете установить proxy_ignore_headers чтобы Nginx не изменял ваши заголовки.
proxy_ignore_headers Cache-Control Expires Pragma;
что может быть самым простым способом исправить это. То, что вы видите, может быть вызвано этой функцией в Nginx:
Change: now nginx does not cache by default backend responses, if they have a "Set-Cookie" header line.
Предположительно, они не сделали этого без какой-либо причины, но я не могу объяснить, почему эта функция была реализована.
Однако, если вы пытаетесь принудительно отключить все кеширование из-за того, что «IE сильно кэширует запрос ajax», у вас может быть лучшее решение, просто добавив уникальный номер к каждому запросу Ajax, что является более устойчивым способом заставить клиентов не кешировать ответы.
Проблема заключалась не в том, что nginx не передавал заголовки, установленные в исходном коде django, а в том, что nginx удалял все клиентские заголовки с подчеркиванием в них.
Поскольку Django ищет HTTP_X_REQUESTED_WITH
заголовок при звонке request.is_ajax()
, запрос никогда не был идентифицирован как запрос ajax, и, следовательно, заголовки без кеширования не были установлены.
def is_ajax(self):
return self.META.get('HTTP_X_REQUESTED_WITH') == 'XMLHttpRequest'
Проблема решена установкой underscores_in_headers
к on
в конфиге nginx. это Почта указал мне в правильном направлении.