Django:它是一个开放源代码的Web应用框架,由Python写成。Django
是基于Python的web框架中最有代表性的一位。许多成功的网站和APP都基于Django
。此外,它的数据库默认设置为SQLite
,无需另外安装,除非你要用其他数据库。
Nginx:它是一款轻量级的Web 服务器/反向代理服务器及电子邮件(IMAP/POP3)代理服务器。优点:轻量,占有内存少,并发能力强。
WSGI(补充):它的全称是Web Server Gateway Interface
,WSGI
不是服务器,python模块,框架,API或者任何软件。WSGI
只是一种规范,描述web server如何与web application通信,在此可理解为描述Nginx服务器与Django项目间的通信。要实现WSGI
协议,必须同时实现web server和web application。
uwsgi:与WSGI
一样是一种通信协议,是uWSGI
服务器的独占协议。它与mod_wsgi
相比的优点为:超快的性能。低内存占用(实测为apache2的mod_wsgi的一半左右)。多app管理。
pip install Django
如果你遇到了python2
和python3
多版本管理的问题,比如pip
安装时它没有将Django安装到你所希望的python版本下,可以先读下我的这一篇博文:使用virtualenv创建各版本python的虚拟环境
sudo apt-get update
sudo apt-get install nginx
sudo /etc/init.d/nginx start # start nginx
注意要先执行
sudo apt-get update
,这条命令是同步 /etc/apt/sources.list 中列出的源的索引文件,相当于获取软件最新的状态,这样才能获取到最新的软件包。不执行update,有可能会提示无法定位到nginx。
安装完成后,用电脑的浏览器访问服务器的公网ip地址,如果出现Nginx的欢迎页面(如下),则表示nginx运行正常。
果然我这里没那么顺利,出现了异常,无法访问到该ip(也许是被墨菲定律眷顾吧= =!)。
因此下边开始异常解决。如果在你的服务器上运行正常,则nginx运行正常,点击跳过异常解决部分。
以下将按照这两个猜想进行排查
netstat -nap | grep 80
其中:
netstat:查看网络系统的状态信息;
-a或–all:显示所有连线中的Socket;
-n或–numeric:直接使用ip地址,而不通过域名服务器;
-p或–programs:显示正在使用Socket的程序识别码和程序名称;
#查看ubuntu的ufw防火墙状态
ufw status
了解到阿里云服务器有一个安全组规则设置,其作用可类比防火墙,可以控制端口的开放与关闭。
前往阿里云服务器的管理控制台,点击自己的云服务器–>更多–>网络和安全组–>安全组配置–>配置规则,发现规则里没有对外开放80端口。至此,问题原因已经被找出。
理所当然地,我们应该设置对外开放80端口。选择添加安全组规则
,并如下图填写。
其中授权对象的0.0.0.0/0表示允许或拒绝所有的ip访问。我们搭建的个人服务器当然是希望让更多的人访问,因此选择允许所有ip。
配置完成后,再次在浏览器中访问服务器的公网ip,可以看到上述的Welcome to nginx!。
sudo pip install uwsgi --upgrade
经过上面的步骤,我们已经搭建好了需要的软件和环境。作为web server
的nginx
也运行良好,现在它只是不知道该如何处理不同的url请求,这就要求我们将nginx、uwsgi、django项目通过配置文件关联起来。
接下来我们就开始逐一配置。
为了方便测试,我使用的是通过django-admin startproject mysite
生成的一个模板项目工程“mysite”。
如果你对django创建app项目还不太了解,这里给出官方教程链接:https://docs.djangoproject.com/en/2.1/intro/tutorial01/ 。如果你对英语感到陌生,不用担心,在官方教程右下角可以将语言切换至中文。
项目工程mysite放置在/var/www
目录下,www目录结构如下所示,比如settings.py
文件的全路径为/var/www/mysite/mysite/settings.py
。
.
├── html
│ └── index.nginx-debian.html
└── mysite
├── *uwsgi.ini
├── *run.log
├── manage.py
├── mysite
│ ├── __init__.py
│ ├── settings.py
│ ├── urls.py
│ └── wsgi.py
└── *static
└── *admin
#注:带*的表示我们即将要创建的文件
接下来,我们要部署静态文件,即把Django的静态文件(CSS, JavaScript, Images等)收集到一个static
文件夹中。这步不需要你手动执行,你只需要打开上述settings.py
文件,加入一行:
STATIC_ROOT = os.path.join(BASE_DIR, "static/")
并且
#找到下面这一行
#ALLOWED_HOSTS = []
#换成
ALLOWED_HOSTS = ['你的公网IP', 'localhost', '127.0.0.1']
其中你的公网IP
请替换成实际的IP地址,这样才能通过公网访问到django应用。
然后执行:
#此命令在外部的mysite文件夹下执行
python manage.py collectstatic
为什么要创建这个static文件夹?为什么我网站的admin后台管理页面样式全没了?
你可能已经通过
manage.py
来运行过django项目,并且访问过默认生成的admin
后台管理界面,彼时理所当然是有样式的。
如果不创建static
文件夹,当使用公网ip访问admin
时,客户端将无法获取到django
内置的这些静态文件,就会出现样式全无的情况,也就是第二个问题的原因。
vim /etc/nginx/sites-available/default
别看这个default文件写了很多东西,其实带#
的都是注释,把注释拿开后,我们关注的只有:
server {
listen 80 default_server;
listen [::]:80 default_server;
root /var/www/html;
# Add index.php to the list if you are using PHP
index index.html index.htm index.nginx-debian.html;
server_name 119.23.69.193; #第一处修改,此处改为你的服务器的公网IP
location / {
#以下3行是第二处修改
include /etc/nginx/uwsgi_params; #uwsgi_params是我们需要用到的文件
uwsgi_pass 127.0.0.1:8000; #将请求交由uwsgi处理,并传到127.0.0.1:8000
#try_files $uri $uri/ =404;
}
#####################第三处修改begin
location /static {
alias /var/www/mysite/static; #请替换成自己实际的静态文件目录
#这里会将请求转换成对alias指定的路径下的文件访问
}
#####################第三处修改end
}
请把你default文件按如上进行修改,总共有三处,请仔细查看。另外,请不要盲目复制粘贴!
对于上述参数,现给出部分参数解释如下:
listen 80 default_server;
:listen,即监听指令,此处监听80端口,且后面有一个参数 default_server。Nginx 的虚拟主机是通过HTTP请求中的Host值来找到对应的虚拟主机配置,如果找不到呢?那 Nginx 就会将请求送到监听了 default_server 的 节点来处理。
location / {}
:表示捕捉server_name的根请求,比如我服务器的根URLhttp://119.23.69.193/
。同理,/static
为http://119.23.69.193/static
。
uwsgi_pass 127.0.0.1:8000;
:将请求转至本机的8000端口,不用担心阿里云安全组规则的设置,因为是本地的。
这份配置文件告诉nginx从文件系统里寻找static文件,并且将一些需要django代码介入的行为交由uwsgi来管理。也就是实现了从nginx–>uwsgi。
修改完成后,别忘了重启nginx:
sudo service nginx restart
接下来,在外部的mysite(/var/www/mysite/)
新建一个uwsgi.ini文件和一个run.log文件,即我在www目录结构下提到的带*
文件。
然后我们将以下内容添加进这个空的uwsgi.ini文件:
[uwsgi]
chdir = /var/www/mysite
module = mysite.wsgi
socket = 127.0.0.1:8000
master = true
daemonize = /var/www/mysite/run.log
disable-logging = true
pythonpath = /root/py3env/lib/python3.5/site-packages
chdir:它是你的项目的根目录,请自行替换成你自己的;
moudule 是你的入口wsgi模块,将mysite替换成你自己的项目名称;
socket 是通信端口设置;
master = true 表示以主进程模式运行;
daemonize 是你的日志文件目录,这个路径就是刚刚新建的run.log文件的路径;
disable-logging = true 表示不记录正常信息,只记录错误信息;
pythonpath 是你python的包的路径。由于我们使用了virtualenv环境,所以这里必须设置,请替换成你的实际路径。否则会报错:ImportError:No module named django.core.wsgi。
最后,不要忘记使得ini文件生效:
#在/var/www/mysite/目录下执行
uwsgi --ini uwsgi.ini
可以使用uwsgi --python-version
命令查看uwsgi对应的python
,如果不是virtualenv里的那个版本,请自行修正好。可参考:http://blog.51cto.com/leizhu/2065394
#如果要重载init文件,需要如下操作
#查看到占用8000端口的当前的uwsgi
netstat -nap | grep 8000
#kill掉当前的uwsgi
kill -9 进程号
#再次运行
uwsgi --ini uwsgi.ini
至此,就完成了nginx–>uwsgi->django项目的配置。其中nginx到uwsgi是通过本地端口8000来完成的,nginx进行转交,uwsgi来监听,最后导入相应的django模块。
We’re done! 现在,你可以通过ip访问你的网站啦,比如我的:http://119.23.69.193/ 、又或者admin后台管理。
其实还是踩了蛮多坑才能写完这篇博文的哈哈哈哈,希望能对你有帮助呀!有什么问题欢迎留言询问。
我查看了下run.log,发现程序给出了不少调整和优化建议,看来之后要研究下这块,立个flag吧hhh!