KeyError: REQUEST_METHOD с Django + uWSGI + nginx + docker

Я создал django REST-API и хочу развернуть его на своем сервере. Все отлично работает в локальной среде разработки. Но на моем сервере у меня возникает ошибка: nginx не передает uwsgi_params правильно (я думаю).

Ошибка

Мне кажется, что мои настройки работают нормально, так как когда я обращаюсь к своему доменному имени, журналы появляются на сервере. Однако мне кажется, что ошибка заключается в том, что nginx не передает reqeust_method для wsgi в django.

Я нашел другой пост здесь, в котором была та же ошибка, однако, я дважды проверил файл uwsgi_params и он не пустой. Так что у меня нет подсказки.

simuzones_server_web | Traceback (most recent call last):
simuzones_server_web |   File "/home/tx7093/.local/lib/python3.8/site-packages/django/core/handlers/wsgi.py", line 130, in __call__
simuzones_server_web |     request = self.request_class(environ)
simuzones_server_web |   File "/home/tx7093/.local/lib/python3.8/site-packages/django/core/handlers/wsgi.py", line 78, in __init__
simuzones_server_web |     self.method = environ["REQUEST_METHOD"].upper()
simuzones_server_web | KeyError: 'REQUEST_METHOD'
simuzones_server_web | [pid: 11|app: 0|req: 1/1]  () {48 vars in 977 bytes} [Sun Jan 22 13:28:53 2023]   => generated 0 bytes in 5 msecs ( 500) 0 headers in 0 bytes (0 switches on core 0)
simuzones_server_web | Traceback (most recent call last):
simuzones_server_web |   File "/home/tx7093/.local/lib/python3.8/site-packages/django/core/handlers/wsgi.py", line 130, in __call__
simuzones_server_web |     request = self.request_class(environ)
simuzones_server_web |   File "/home/tx7093/.local/lib/python3.8/site-packages/django/core/handlers/wsgi.py", line 78, in __init__
simuzones_server_web |     self.method = environ["REQUEST_METHOD"].upper()
simuzones_server_web | KeyError: 'REQUEST_METHOD'
simuzones_server_web | [pid: 11|app: 0|req: 2/2]  () {44 vars in 855 bytes} [Sun Jan 22 13:28:53 2023]   => generated 0 bytes in 4 msecs ( 500) 0 headers in 0 bytes (0 switches on core 0)

Django app docker

Я создал dockerfile для моего приложения django, который запускает и обслуживает приложение с помощью uwsgi. Докерфайл выглядит следующим образом

FROM python:3.8.15-slim-buster


ARG user
ARG DEBIAN_FRONTEND=noninteractive

ENV PATH="/docker_scripts:/home/${user}/.local/bin:${PATH}"
ENV PYTHONUNBUFFERED 1

...

RUN mkdir /simuzones_server
COPY ./simuzones_server /simuzones_server
WORKDIR /simuzones_server
COPY ./docker_scripts /docker_scripts
RUN chmod +x /docker_scripts/*

RUN mkdir -p /vol/web/media
RUN mkdir -p /vol/web/static

RUN adduser --disabled-login $user
RUN chown -R $user:$user /vol
RUN chmod -R 755 /vol/web

USER $user

COPY requirements.txt /simuzones_server/
RUN /usr/local/bin/python -m pip install --upgrade pip
RUN cd /simuzones_server/
RUN pip install -r requirements.txt

CMD ["entrypoint.sh"]

Файл entrypoint.sh просто запускает сервер uwsgi.

#!/bin/sh

set -e

python manage.py collectstatic --noinput

uwsgi --socket :8000 --master --enable-threads --module simuzones_server.wsgi

Nginx docker

Dockerfile

FROM nginxinc/nginx-unprivileged:1-alpine

COPY ./default.conf /etc/nginx/conf.d/default.conf
COPY ./uwsgi_params /etc/nginx/uwsgi_params

USER root

RUN mkdir -p /vol/static
RUN chmod 755 /vol/static

USER nginx

И файл default.conf

server {
    listen 8080;
    listen [::]:8080;
    server_name simuzones.tk www.simuzones.tk;
    return 301 https://$server_name$request_uri;
}

server {
    # SSL configuration
    listen 443 ssl http2;
    listen [::]:443 ssl http2;
    ssl_certificate      /etc/ssl/cert.pem;
    ssl_certificate_key  /etc/ssl/key.pem;

    server_name simuzones.tk www.simuzones.tk;

    return 200 $request_method;

    location /static {
        alias /vol/static;
    }

    location / {
        include /etc/nginx/uwsgi_params;
        uwsgi_pass web:8000;
    }
}

И файл uwsgi_params на хост-машине (сервере)

uwsgi_param QUERY_STRING $query_string;
uwsgi_param REQUEST_METHOD $request_method;
uwsgi_param CONTENT_TYPE $content_type;
uwsgi_param CONTENT_LENGTH $content_length;
uwsgi_param REQUEST_URI $request_uri;
uwsgi_param PATH_INFO $document_uri;
uwsgi_param DOCUMENT_ROOT $document_root;
uwsgi_param SERVER_PROTOCOL $server_protocol;
uwsgi_param REMOTE_ADDR $remote_addr;
uwsgi_param REMOTE_PORT $remote_port;
uwsgi_param SERVER_ADDR $server_addr;
uwsgi_param SERVER_PORT $server_port;
uwsgi_param SERVER_NAME $server_name;

Докер-композит (если необходимо)

version: '3.7'

services:
  web:
    build:
      args:
        user: tx7093
      context: .
    ports:
      - "8000:8000"
    volumes:
      - ./simuzones_server:/simuzones_server
      - static_data:/vol/web
    container_name: simuzones_server_web
    environment:
      - POSTGRES_DB=${POSTGRES_DB}
      - POSTGRES_USER=${POSTGRES_USER}
      - POSTGRES_PASSWORD=${POSTGRES_PASSWORD}
      - PGDATA=/var/lib/postgresql/data/pgdata
      - DATABASE_URL=${DATABASE_URL}
      - DEBUG=1
      - SECRET_KEY=${SECRET_KEY}
      - ALLOWED_HOSTS=${ALLOWED_HOSTS}
    depends_on:
      - db
  nginx:
    build:
      context: ./nginx
    volumes:
      - static_data:/vol/static
      - /etc/ssl:/etc/ssl
    ports:
      - "8080:8080"
    depends_on:
      - web
  db:
    image: postgres:11.18-bullseye
    environment:
      - POSTGRES_DB=${POSTGRES_DB}
      - POSTGRES_USER=${POSTGRES_USER}
      - POSTGRES_PASSWORD=${POSTGRES_PASSWORD}
      - PGDATA=/var/lib/postgresql/data/pgdata
      - DATABASE_URL=${DATABASE_URL}
    ports:
      - "5432:5432"
    volumes:
      - type: bind
        source: ./tmp/postgres-data
        target: /var/lib/postgresql/data

volumes:
  static_data:

Я хотел бы сказать спасибо заранее, эта проблема занимает у меня несколько дней, и я до сих пор не смог ее решить.

Мне удалось заставить его работать! Основная причина в том, что я не пробросил порт для SSL (443)

Вернуться на верх