Django/Nginx/uWSGI — проверка CSRF не удалась

Я пытаюсь аутентифицировать себя на своем сервере, выполнив запрос POST с использованием модуля запросов python.

К сожалению, у меня следующая ошибка:

  Forbidden (403)
  CSRF verification failed. Request aborted.

Я пробовал конфигурацию Nginx других людей (см. здесь, здесь или здесь), но запрос по-прежнему не выполняется. Я не знаком с этой задачей. Может кто-нибудь помочь мне понять мою ошибку, пожалуйста?

Код с запросами на стороне клиента

import requests

username_django = 'username'
password_django = 'password'
server_django_ca = '/path/to/ca.pem'
login_url = 'https://login_url'
api_url = 'https://api_url'

def get_django_authentication_token(
    login_url, 
    username, 
    password,
    server_django_ca
):
    #hilens.info('NOW AUTHENTICATING USER')
    request_session = requests.Session()
    request_session.headers.update({'referer': 'HiLens'})
    response = request_session.get(
        login_url,
        verify=server_django_ca
    )

    token = response.cookies['csrftoken']
    print(f'Token 1 = {token}')
    
    headers =  {'X-CSRFToken': token}

    # THIS REQUESTS FAILS - returns a csrf verification failed
    login_response = request_session.post(
        login_url,
        data={
            'username':username,
            'password':password,
            'next':'/ihm_maquette/set_hi_lens_detection'},
        verify=server_django_ca,
        headers = headers
    )

    print(login_response.text)
    
    token = request_session.cookies['csrftoken']
    print(f'Token 2 = {token}')

    if login_response.status_code == 200:
        #hilens.info('AUTHENTICATION WORKED')
        return request_session, token
    else:
        print('Login response error')


def send_post_request_to_django(
    username_django,
    password_django,
    login_url, 
    api_url,
    server_django_ca,
    bboxes
):

    datas = {}

    for bbox in bboxes:
        label = int(bbox[4])
        if label == 0:
            datas['label'] = 'No Mask' 
        elif label == 1:
            datas['label'] = 'Wearing Mask'

    request_session, token = get_django_authentication_token(
        login_url, 
        username_django, 
        password_django, 
        server_django_ca
    )

    if request_session:    

        headers =  {'X-CSRFToken': token}

        #hilens.info('NOW SENDING POST REQUEST')
        post_request = request_session.post(
            api_url,
            datas,
            verify=server_django_ca,
            headers=headers
        )

        return post_request

if __name__ == '__main__':
    response = send_post_request_to_django(
        username_django,
        password_django,
        login_url, 
        api_url,
        server_django_ca,
        []
    )
    print(response)

prod_settings.py

SESSION_COOKIE_AGE = 14400
SESSION_COOKIE_SECURE = True
CSRF_COOKIE_SECURE = True

SECURE_SSL_REDIRECT = True
SECURE_PROXY_SSL_HEADER = ('HTTP_X_FORWARDED_PROTO', 'https')
SECURE_REDIRECT_EXEMPT = [r'.*conveyor\/get_conveyor_status.*']
SECURE_REFERRER_POLICY = 'strict-origin'

Конфигурация Nginx

upstream django {
    server unix:///tmp/uwsgi.sock; # for a file socket
    #server 127.0.0.1:8001; # for a web port socket (we'll use this first)
}

server {
        listen 443 ssl default_server;
        listen [::]:443 ssl default_server;

        add_header Strict-Transport-Security "max-age=31536000; always"; 

        proxy_set_header X-Forwarded-Proto $scheme;

        # Sélection de la chaine complète de certification (concaténation du certificat SSL du domaine, du certificat SSL intermédiaire puis de la racine)
        ssl_certificate /path/to/certificate.pem;
        
        # Sélection de la clé privée associée au certificat SSL du domaine
        ssl_certificate_key  /path/to/key.pem;

        server_name _;

        #location / {
                # First attempt to serve request as file, then
                # as directory, then fall back to displaying a 404.
        #       try_files $uri $uri/ =404;
        #}

        location /static {
            alias /home/cloud/django/static/; 
        }

        location /uploads {
            alias /home/cloud/django/uploads/; 
        }
    
    # Finally, send all non-media requests to the Django server.
        location / {
            include     /home/cloud/django-demos-cic/uwsgi_params;
            proxy_set_header Host $http_host;
            proxy_set_header X-Real-IP $remote_addr;
            proxy_set_header X-Forwarded-For $proxy_add_x_forwarded_for;
            proxy_set_header X-Forwarded-Proto $scheme;
            # proxy_set_header X-Forwarded-Proto https;
            proxy_set_header X-Forwarded-Host   $host:$server_port;
            proxy_set_header X-Forwarded-Port   $server_port;

            proxy_redirect off;
            #proxy_pass   http://django;
            uwsgi_pass  django;
        }

}


person Welyweloo    schedule 04.08.2021    source источник
comment
вы используете шаблон django?   -  person Amin    schedule 05.08.2021