2017-05-21 4 views
0

Ich habe ein neues Django 1.11-Projekt mit einer App, einem Modell und einem Admin-Panel gestartet. Lokal funktioniert alles. Wenn ich es auf Amazon EC2 ausstelle und versuche, mich beim Admin-Panel anzumelden, erhalte ich eine 403 (CSRF-Verifizierung fehlgeschlagen. Anfrage abgebrochen.). Ich sehe das in meinem Debug-Log:Django CSRF Überprüfung für Admin-Panel fehlgeschlagen

[WARNING] 2017-05-21 11:23:52,142 csrf 14263 140377210439424 Forbidden (Referer checking failed - Referer is insecure while host is secure.): /admin/login/

ich mit Chrome Netzwerk-Dienstprogramm überprüft die Anforderung, und ich bemerkte, dass in meinem Request Header Ich habe:

Cookie:csrftoken=hFhzOJPMOhkNWWWfRtlMOEum9jXV8XXWnOtw3OwZm2En9JUqYRVq632xyZfwSpzU

während in meinem Formular Data I haben:

csrfmiddlewaretoken:RHNpPfOHhg42FZnXmn9PZgNm3bN40C41XQZm4kvUP1oCSMl8tLJthFlxsR5FK4GZ

Sollten diese zwei sein t er gleich? In meinem Verständnis tun sie das, aber wenn ich das gleiche in meiner lokalen Umgebung versuche, sehe ich, dass sie auch nicht gleich sind, aber dort funktioniert es gut und ich bekomme das gleiche Token zurück in den Antwort-Header, wie es in der Anfrage gesendet wurde Kopfzeile, also nehme ich an, dass sie nicht genau gleich sein müssen? Hinweis: Ich habe momentan keine sichere Verbindung (https), arbeite aber daran, nachdem dies behoben wurde.

ich bereits versucht,/überprüft Folgendes:

Andere Antworten, die ich auf SO gefunden erwähnen, dass Sie etwas in der Form tun müssen, selbst, aber dies ist eine Form aus dem Django Framework .

Zusätzliche Informationen

Meine nginx Konfiguration von /etc/nginx/nginx.conf:

user www-data; 
worker_processes auto; 
pid /run/nginx.pid; 

events { 
    worker_connections 768; 
    # multi_accept on; 
} 

http { 

    ## 
    # Basic Settings 
    ## 

    sendfile on; 
    tcp_nopush on; 
    tcp_nodelay on; 
    keepalive_timeout 65; 
    types_hash_max_size 2048; 
    # server_tokens off; 

    # server_names_hash_bucket_size 64; 
    # server_name_in_redirect off; 

    include /etc/nginx/mime.types; 
    default_type application/octet-stream; 

    ## 
    # SSL Settings 
    ## 

    ssl_protocols TLSv1 TLSv1.1 TLSv1.2; # Dropping SSLv3, ref: POODLE 
    ssl_prefer_server_ciphers on; 

    ## 
    # Logging Settings 
    ## 

    access_log /var/log/nginx/access.log; 
    error_log /var/log/nginx/error.log; 

    ## 
    # Gzip Settings 
    ## 

    gzip on; 
    gzip_disable "msie6"; 

    # gzip_vary on; 
    # gzip_proxied any; 
    # gzip_comp_level 6; 
    # gzip_buffers 16 8k; 
    # gzip_http_version 1.1; 
    # gzip_types text/plain text/css application/json application/javascript text/xml application/xml application/xml+rss text/javascript; 

    ## 
    # Virtual Host Configs 
    ## 

    include /etc/nginx/conf.d/*.conf; 
    include /etc/nginx/sites-enabled/*; 
} 

Meine Seite spezifische Konfiguration von /etc/nginx/sites-enabled/MyDjangoService:

upstream MyDjangoService_wsgi_server { 
    # fail_timeout=0 means we always retry an upstream even if it failed 
    # to return a good HTTP response (in case the Unicorn master nukes a 
    # single worker for timing out). 

    server unix:/webapps/MyDjangoService/run/gunicorn.sock fail_timeout=0; 
} 

server { 
    listen  80; 
    server_name MyDjangoService; 

    client_max_body_size 4G; 

    access_log /webapps/MyDjangoService/logs/nginx_access.log; 
    error_log /webapps/MyDjangoService/logs/nginx_error.log; 

    location /static/ { 
     alias /webapps/MyDjangoService/static/; 
    } 

    location /media/ { 
     alias /webapps/MyDjangoService/media/; 
    } 

    location/{ 
     if (-f /webapps/MyDjangoService/maintenance_on.html) { 
      return 503; 
     } 

     proxy_set_header X-Forwarded-For $proxy_add_x_forwarded_for; 
     proxy_set_header X-Forwarded-Proto https; 
     proxy_set_header Host $http_host; 
     proxy_redirect off; 

     # Try to serve static files from nginx, no point in making an 
     # *application* server like Unicorn/Rainbows! serve static files. 
     if (!-f $request_filename) { 
      proxy_pass http://MyDjangoService_wsgi_server; 
      break; 
     } 
    } 

    # Error pages 
    error_page 500 502 504 /500.html; 
    location = /500.html { 
     root /webapps/MyDjangoService/django/src/MyDjangoService/templates/; 
    } 

    error_page 503 /maintenance_on.html; 
    location = /maintenance_on.html { 
     root /webapps/MyDjangoService/; 
    } 
} 
+1

Django 1.10 und höher Pads das Token mit einem zufälligen Zeichenfolge zum Schutz gegen [VERLETZUNG Angriffe] (https://en.wikipedia.org/wiki/BREACH), so Sie werden nicht gleich sein, selbst wenn sie korrekt sind. Django sollte Ihnen einen Grund geben warum die CSRF-Prüfung fehlgeschlagen ist, können Sie den genauen Fehler anzeigen? Wenn 'DEBUG' deaktiviert ist, sollte Django immer noch den genauen Fehler protokollieren. Überprüfen Sie daher Ihre Protokolle, wenn Sie sich nicht sicher sind. – knbk

+0

Danke. Ich habe den Fehler aus dem Debug-Protokoll zur Frage hinzugefügt. 'Forbidden (Referer-Überprüfung fehlgeschlagen - Referer ist unsicher, während der Host sicher ist.) – physicalattraction

+1

Es scheint, als würde Django fälschlicherweise annehmen, dass es auf https läuft, aber die Referer-URL http verwendet. Können Sie die relevante Server-Konfiguration und Ihren' SECURE_PROXY_SSL_HEADER' anzeigen Einstellung? – knbk

Antwort

1

Ihr Problem ist in der folgenden Zeile:

 proxy_set_header X-Forwarded-Proto https; 

Hier setzen Sie unbedingt den Header X-Forwarded-Proto auf den Wert https. Ihr WSGI-Server interpretiert dies so, dass Ihre Site hinter https ausgeführt wird. Django führt dann eine strenge Referrer-Prüfung durch und sieht, dass das Protokoll in der Referrer-Domain http statt https ist. Da dies ein Sicherheitsproblem sein kann, weist Django die Anfrage zurück.

Sie sollten diese Zeile entweder entfernen oder ändern, um den richtigen Wert zu verwenden.Sie können die $scheme Variable für diesen Einsatz:

proxy_set_header X-Forwarded-Proto $scheme; 
Verwandte Themen