当前位置: 首页>>技术教程>>正文


django – 权限被拒绝-Nginx和uwsgi套接字

, , ,

问题描述

好吧,我目前正在尝试使用nginx和uwsgi使我的django应用程序得到服务。我当前正在使用安装了uwsgi的虚拟环境。但是,我目前在尝试访问该页面时收到502错误的网关错误。

我遇到的错误。

2014/02/27 14:20:48 [crit] 29947#0: *20 connect() to unix:///tmp/uwsgi.sock failed (13: Permission denied) while connecting to upstream, client: 144.136.65.176, server: domainname.com.au, request: "GET /favicon.ico HTTP/1.1", upstream: "uwsgi://unix:///tmp/uwsgi.sock:", host: "www.domainname.com.au"

这是我的nginx.conf

    # mysite_nginx.conf

# the upstream component nginx needs to connect to
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)
}

# configuration of the server
server {
    # the port your site will be served on
    listen      80;
    # the domain name it will serve for
    server_name .domainname.com.au; # substitute your machine's IP address or FQDN
    charset     utf-8;

    # max upload size
    client_max_body_size 75M;   # adjust to taste

    # Django media
    location /media  {
        alias /home/deepc/media;  # your Django project's media files - amend as required
    }

    location /static {
        alias /home/deepc/static; # your Django project's static files - amend as required
    }

    # Finally, send all non-media requests to the Django server.
    location / {
        uwsgi_pass  django;
        include     /home/deepc/.virtualenvs/dcwebproj/dcweb/uwsgi_params; # the uwsgi_params file you installed
    }
}

这是我的uwsgi.ini文件

[uwsgi]
socket=/tmp/uwsgi.sock
chmod-socket=644
uid = www-data
gid = www-data

chdir=/home/deepc/.virtualenvs/dcwebproj/dcweb
module=dcweb.wsgi:application
pidfile=/home/deepc/.virtualenvs/dcwebproj/dcweb.pid
vacuum=true

从我在Google上阅读的内容来看,它与www-data组和/tmp /目录存在权限问题。但是,我对此并不陌生,并尝试将文件夹的权限级别更改为无效。有人可以指出我正确的方向吗?这是权限问题。

将sock文件放在tmp目录中也是可以的做法吗?

谢谢

最佳思路

我认为您只需要将套接字文件更改为666(www-data可以使用664),或者将其删除并再次运行uwsgi服务器。

在我的uwsgi.ini中:

chmod-socket = 664
uid = www-data
gid = www-data

次佳思路

哇,这个问题几乎要花我一整天!

我使用uwsgi 2.0.14, nginx 1.10.1, django 1.10

综上所述,最重要的是确保以下两个用户都对socket文件具有rwx权限:

  1. nginx的用户;

  2. uWSGI的用户;

因此,您可以一一检查它们。


首先,您可以通过刷新网址(例如http://192.168.201.210:8024/morning/)来检查Web服务器nginx是否具有权限,而无需运行uwsgi。如果看到/var/log/nginx/error.log没有这样的文件或目录,如下所示:

2016/10/14 16:53:49 [crit] 17099#0: *19 connect() to unix:///usr/share/nginx/html/test/helloworld.sock failed (2: No such file or directory) while connecting to upstream, client: 192.168.201.140, server: belter-tuesday.com, request: "GET /morning/ HTTP/1.1", upstream: "uwsgi://unix:///usr/share/nginx/html/test/helloworld.sock:", host: "192.168.201.210:8024"

只需创建一个名为helloworld.sock的文件,然后刷新url并再次检查日志文件,如果您在日志文件中看到“权限被拒绝”,如下所示:

2016/10/14 17:00:45 [crit] 17099#0: *22 connect() to unix:///usr/share/nginx/html/test/helloworld.sock failed (13: Permission denied) while connecting to upstream, client: 192.168.201.140, server: belter-tuesday.com, request: "GET /morning/ HTTP/1.1", upstream: "uwsgi://unix:///usr/share/nginx/html/test/helloworld.sock:", host: "192.168.201.210:8024"

这意味着Web服务器nginx不具有读取,写入和执行的所有权限。因此,您可以授予对此文件的权限:

sudo chmod 0777 helloworld.sock

然后,刷新URL并再次检查日志文件,如果您在日志文件中看到“连接被拒绝”,如下所示:

2016/10/14 17:09:28 [error] 17099#0: *25 connect() to unix:///usr/share/nginx/html/test/helloworld.sock failed (111: Connection refused) while connecting to upstream, client: 192.168.201.140, server: belter-tuesday.com, request: "GET /morning/ HTTP/1.1", upstream: "uwsgi://unix:///usr/share/nginx/html/test/helloworld.sock:", host: "192.168.201.210:8024"

这是一个好兆头,表示您的Web服务器nginx从现在起拥有使用helloworld.sock文件的权限。


接下来运行uwsgi并检查uwsgi的用户是否具有使用helloworld.sock的权限。首先,删除我们之前创建的文件helloworld.sock

运行uwsgi:uwsgi --socket /usr/share/nginx/html/test/helloworld.sock --wsgi-file wsgi.py

如果看到 bind():权限被拒绝[core /socket.c第230行],则表明uwsgi没有绑定helloworld.sock的权限。这是目录test的父目录helloworld.sock的问题。

sudo chmod 0777 test/

现在,您可以成功运行uwsgi

但是也许您仍然看到502 Bad Gateway,这很糟糕,我整天都看过。如果再次检查error.log文件,您将再次看到此信息:

2016/10/14 17:33:00 [crit] 17099#0: *28 connect() to unix:///usr/share/nginx/html/test/helloworld.sock failed (13: Permission denied) while connecting to upstream, client: 192.168.201.140, server: belter-tuesday.com, request: "GET /morning/ HTTP/1.1", upstream: "uwsgi://unix:///usr/share/nginx/html/test/helloworld.sock:", host: "192.168.201.210:8024"

怎么了???

查看helloworld.sock文件的详细信息,可以看到:

srwxr-xr-x. 1 belter mslab       0 Oct 14 17:32 helloworld.sock

uWSGI自动授予此文件755权限。

您可以通过添加--chmod-socket来更改它:

uwsgi --socket /usr/share/nginx/html/test/helloworld.sock --wsgi-file wsgi.py --chmod-socket=777

好!最后,您可以看到:


带走消息:

  1. uwsgi_params文件的位置并不重要;

  2. 由于我的nginx用户和uwsgi用户不同,甚至不在同一组,因此我需要给helloworld.sock及其父目录test/授予777权限;

  3. 如果将helloworld.sock文件放在主目录中,则始终会得到“拒绝权限”。

  4. 您需要在两个位置设置socket文件路径,一个在nginx conf文件中,对我来说是helloworld_nginx.conf;运行uwsgi时一个。

  5. 检查SELinux

这是我的helloworld_nginx.conf文件:

# helloworld_nginx.conf
upstream django {
    server unix:///usr/share/nginx/html/test/helloworld.sock; # for a file socket
    # server 127.0.0.1:5902; # for a web port socket (we'll use this first)
}

# configuration of the server
server {
    # the port your site will be served on
    listen      8024;
    # the domain name it will serve for
    server_name .belter-tuesday.com; # substitute your machine's IP address or FQDN
    charset     utf-8;

    # max upload size
    client_max_body_size 75M;   # adjust to taste

    # Finally, send all non-media requests to the Django server.
    location /morning {
        include     uwsgi_params;
        uwsgi_pass  django;
    }
}

第三种思路

在CentOS上,我尝试了所有这些方法,但是仍然没有用。最后,我找到了这篇文章:

https://www.nginx.com/blog/nginx-se-linux-changes-upgrading-rhel-6-6/

对于开发机器,我们只需运行:

semanage permissive -a httpd_t

但是对于真正的生产服务器,我还没有弄清楚。您可能需要尝试上述文章中描述的其他方法。

参考资料

本文由Ubuntu问答整理, 博文地址: https://ubuntuqa.com/article/10628.html,未经允许,请勿转载。