在虛擬機中安裝CentOS并通過nginx+uwsgi部署django應用
virtualbox的安裝
首先搜索并下載deb包,注意下載本機對應的版本。這里推薦一下deb安裝包的軟件gdebi,安裝及使用:
~$ sudo apt install gdebi
~$ gdebi package.deb
CentOS安裝及配置
CentOS安裝及網絡配置
在bash中運行:
~$ virtualbox
在界面中點擊新建
- 虛擬電腦名稱和系統類型,輸入名稱,系統Linux,版本選擇Red Hat;
- 內存大小,不要少于1G;
- 虛擬硬盤,建議
創建
; - 虛擬硬盤文件類型,默認的VDI即可;
- 存儲在物理硬盤,根據需求選擇容量,點擊
創建
。
點擊顯示
,選擇下載好的iso文件,點擊啟動
,選擇install即可安裝。選擇剛才分配的硬盤,進行新建用戶、密碼等操作,等待安裝,完成后點擊reboot重啟進入系統。
為了實現主機對虛擬機的訪問,需要修改網絡類型為“橋接網卡(Bridged Adapter)”。(也可以選擇Host-only Adapter模式,具體配置請自行搜索。)在進入系統之后如果無法上網,進入以下目錄:
~$ /etc/sysconfig/network-scripts
然后修改ifcfg文件中的ONBOOT為yes即可。
更新及修改yum源
墻內訪問yum源的速度很慢,我們來修改下yum源。這里直接用網易鏡像站點中的配置文件。
- 進入yum配置文件目錄
~$ cd /etc/yum.repos.d/
- 為防止出意外,先將原來的源文件備份
~$ mv CentOS-Base.repo CentOS-Base.repo.bak
- 下載163的配置
- 改名
~$ mv CentOS6-Base-163.repo CentOS-Base.repo
- 更新數據庫
~$ yum update
這樣就可以訪問到163鏡像了。
系統升級及安裝基礎軟件包(部分可省略)
系統升級,以下命令按順序執行
~$ yum clean all && yum makecache
~$ yum -y install epel-release # 此命令是安裝yum源的擴展,必選
~$ yum -y update
安裝基礎包
~$ yum -y install sudo vim
~$ yum -y install zlib-devel bzip2-devel ncurses-devel openssl-devel
~$ yum -y install make gcc-c++ cmake bison-devel swig patch sqlite-devel
~$ yum -y install readline readline-devel rsync nload ntp ntpdate wget
~$ yum -y install net-tools telnet libjpeg-devel
配置django運行環境
安裝pip
運行命令:
~$ yum install python-pip
~$ pip install --upgrade pip #直接安裝的pip版本較舊,應該先升級一下
如果提示找不到pip源,需要首先安裝源擴展包epel-release
~$ yum install epel-release
跟yum一樣的問題,最好更新一下pip的源,提升下載速度,我這里更改為douban的鏡像。首先在主目錄下新建 .pip目錄:
~$ mkdir /etc/.pip
在此目錄下新建pip.conf文件并寫入以下內容:
[global]
trusted-host = pypi.douban.com
index-url = http://pypi.douban.com/simple
保存重啟bash即可。
安裝django、擴展及MariaDB數據庫
如果要在虛擬環境中運行,應當先安裝virtualenv然后啟動相應環境,我這里直接安裝在系統中了。
~$ yum install python-devel #python開發依賴包,大家熟悉的python-dev在centOS上的的馬甲 - -
~$ pip install django
運行
~$ pip install MySQL-python #連接python與mysql的工具
出現錯誤提示mysql_config不存在,所以要先安裝MariaDB才可以。
運行以下命令:
~$ yum install mariadb-server mariadb-client
然后就出現錯誤了,提示找不到mariadb-client。谷歌原因,是因為yum源的問題,需要手動添加。
~$ cd /etc/yum.repos.d/
~$ vim MariaDB.repo
然后寫入以下內容:
[mariadb]
name = MariaDB
baseurl = http://yum.mariadb.org/10.1/centos7-amd64
gpgkey=https://yum.mariadb.org/RPM-GPG-KEY-MariaDB
gpgcheck=1
根據系統的不同,或者要安裝選定版本MariaDB,具體內容會有區別。可以訪問MariaDB官網,根據自己的情況選擇然后就可以自動生成了。
然后運行:
~$ yum install MariaDB-server MariaDB-client
就會成功安裝了。接著設置root用戶密碼:
~$ mysql_secure_installation
又報錯。。。can't connect to local mysql server through socket '/var/run/mysql/mysql.sock',檢索發現是mysql服務未開啟,囧
~$ service mysql start
然后就可以重復上一條命令來設置root密碼了。
然后安裝mysqldb:
~$ pip install MySQL-python
結果還是報錯。。繼續檢索,發現是沒有安裝MariaDB開發環境:
~$ yum install MariaDB-devel # mysql-dev在MariaDB的馬甲
然后再運行,問題解決。總結一下,正確的安裝順序應當是python-devel> django > MariaDB(包括sever,client,devel缺一不可)> MySQL-python。
新建django項目并連接MariaDB數據庫
首先進入MariaDB中新建好數據庫(注意編碼格式),可以采用如下sql語句:
~$ CREATE DATABASE your_database_name DEFAULT CHARACTER SET utf8 COLLATE utf8_general_ci;
接著新建一個django項目,并用來嘗試連接MariaDB。
~$ django-admin startproject mysite
然后在mysite>mysite目錄下setting.py中修改DATABASES部分為剛才創建的數據庫。
DATABASES = {
'default': {
'ENGINE': 'django.db.backends.mysql',
'NAME': 'your_database_name',
'USER': 'root',
'PASSWORD': 'your_password',
'HOST': 'localhost',
'PORT': '',
}
}
然后啟動查看是否連接成功。可以通過alt+fn命令另行啟動一個窗口,然后登錄同用戶,再用w3m訪問端口。
安裝uwsgi并測試django項目
安裝uwsgi:
~$ pip install uwsgi
然后cd到mysite主目錄下執行:
~$ uwsgi --http :8000 --module mysite.wsgi
如果未看到報錯信息,并且可以通過127.0.0.1:8000訪問說明我們打通了這個環節:
~$ the web client <-> uWSGI <-> Django
接下來先讓我們安裝nginx。
nginx安裝與配置
~$ yum install nginx
~$ service nginx start
然后我們訪問127.0.0.1:80,如果顯示nginx的默認頁面,就說明nginx運行成功,我們打通了以下環節:
~$ the web client <-> the web server
接著我們就可以在nginx的conf中配置我們的網站了。首先我們查看nginx默認設置文件:
~$ vim /etc/nginx/nginx.conf
可以看到這么一行:
~$ include /etc/nginx/conf.d/*.conf
說明nginx能夠讀取在此目錄下的conf文件,所以我們選擇把配置文件放到這里。(這里不同的版本可能有所不同,請自己查看nginx能夠自動讀取的配置方式。)
所以我們在此目錄下新建一個文件,就叫他mysite_nginx.conf好了,內容這么填:
~$ upstream django {
server 127.0.0.1:8001; # 作為nginx與uwsgi的socket通信端口
}
server {
listen 8000; #監聽端口
server_name your_ip; #本機ip;
charset utf-8;
client_max_body_size 75M;
location /staic {
alias /path/to/your/mysite/static;
}
location / {
uwsgi_pass django;
include /etc/nginx/uwsgi_params;
}
}
然后重啟nginx服務,接著遇到錯誤,查看錯誤日志(需要管理員權限):
~$ vim /var/log/nginx/error.log
內容為無法bind到0.0.0.0:8000端口,谷歌之,原來是因為SELinux未關閉
~$ setenforce 0 # 臨時關閉
重啟nginx服務,成功。所以我們可以將接其設為永久關閉:
修改/etc/selinux/config 文件
將SELINUX=enforcing改為SELINUX=disabled
重啟機器即可
還碰到一個坑就是在重啟nginx服務的時候會碰到:找不到nginx.service的錯誤,手動添加一份即可,具體內容可以谷歌。
接下來我們就可以用socket的方式啟動uwsgi啦:
~$ uwsgi --socket :8001 --module mysite.wsgi
如果不提示錯誤,然后訪問127.0.0.1:8000能出現熟悉的It worked
頁面,那我們就打通了如下環節:
~$ the web client <-> the web server <-> the socket <-> uWSGI <-> django
勝利就在眼前了,接下來我們把socket連接方式由端口變為文件形式,首先編輯我們創建的mysite_nginx.conf文件:
刪除掉:server 127.0.0.1:8001;
然后修改為: server unix:///path/to/your/mysite/mysite.sock;
mysite.sock文件需要我們手動創建,內容為空即可。然后訪問127.0.0.1:8000,不出意外的話。。。會得到一個502錯誤。查看nginx錯誤日志,會發現這么一句:
~$ connect() to unix:///path/to/your/mysite/mysite.sock failed (13: Permission
denied)
這條錯誤的意思是我們的nginx應用沒有訪問這個sock文件的權限,運行命令:
~$ uwsgi --socket mysite.sock --module mysite.wsgi --chmod-socket=664
然后應該就可以從127.0.0.1:8000訪問到我們的應用啦。
接著我們把相關設置寫到一個ini文件里然后運行就可以了。新建mysite_uwsgi.ini,內容如下:
~$ [uwsgi]
chdir = /path/to/your/project
module = project.wsgi
master = true
processes = 4
socket = /path/to/your/project/mysite.sock
chmod-socket = 664
vacuum = true
然后運行:
~$ uwsgi --ini mysite_uwsgi.ini
然后訪問本機的8000端口檢查是否成功。
防火墻設置及外網訪問
首先,我們要把本機ip(或者域名)添加到django中settings.py文件ALLOWED_HOSTS里面。
接著,我們需要關閉防火墻,鍵入以下命令:
~$ systemctl stop firewalld.service
如果我們要關閉主機的firewalld.service自啟,可以這么做:
~$ systemctl disabled firewalld.service
然后就可以在虛擬機外通過 http://your_ip:8000 訪問到了。
番外篇
將nginx及uwsgi服務設置為開機自啟動
當我們試圖用systemctl命令管理nginx或者uwsgi程序的時候,會提示類似錯誤:
Failed to nginx.service: Unit nginx.service failed to load: No such file or directory.
這條錯誤信息的意思是systemctl在目錄下面找不到 *.service 文件,所以就無法管理啦。(這樣的錯誤是由于我們是用pip安裝的nginx或者uwsgi,如果用yum安裝就不會有這樣的問題……但是卻有其他地方需要配置,本文就不說啦。)我們可以手動創建一個:
~$ vim /etc/systemd/system/nginx.service
輸入:
[Unit]
Description = The NGINX HTTP and reverse proxy server
After = syslog.target network.target remotes-fs.target nss-lookup.target
[Service]
Type = forking
PIDFile = /run/nginx.pid
ExecStartPre = /usr/sbin/nginx -t # 在程序啟動前做conf的語法檢查
ExecStart = /usr/sbin/nginx #程序啟動命令
ExecReload = /bin/kill -s HUP $MAINPID
ExecStop = /bin/kill -s QUIT $MAINPID
PrivateTmp = true
[Install]
WantedBy = multi-user.target
再創建uwsgi.service:
~$ vim /etc/systemd/system/nginx.service
[Unit]
Description=uWSGI
after=syslog.target
[Service]
ExecStart=/usr/bin/uwsgi --ini /etc/uwsgi/your_uwsgi.ini
Restart=always
KillSignal=SIGQUIT
Type=notify
StandardError=syslog
NotifyAccess=all
[Install]
WantedBy=multi-user.target
然后就可以通過systemctl命令管理了,啟動:
~$ sudo systemctl start nginx
~$ sudo systemctl start uwsgi
開啟自啟:
~$ sudo systemctl enable nginx
~$ sudo systemctl enable uwsgi
uwsgi的emperor模式
uwsgi還有一個emperor模式,能夠‘監控’uwsgi配置文件中的設置。首先創建目錄:
~$ mkdir /etc/uwsgi
~$ mkdir /etc/uwsgi/vassals
然后在目錄下新建文件emperor.ini,內容如下:
[uwsgi]
emperor = /etc/uwsgi/vassals
uid = root
logto = /tmp/uwsgi.log
這時候記得把/etc/systemd/system/uwsgi.service文件中ExecStart修改為emperor.ini文件。然后我們可以創建超鏈接到vassals文件夾中,‘皇帝’就會給我們把各個配置管理起來了。
~$ ln -s /path/to/your/mysite_uwsgi.ini /etc/uwsgi/vassals/
最后,可以用命令:
~$ systemctl status uwsgi
查看運行狀況。
nginx的權限管理
我們知道,nginx會直接訪問系統中的靜態文件等,所以需要給其訪問系統資源的權限。要實現這一點,我們之前的做法是修改nginx.conf文件中的user選項,把當前用戶或者root用戶添加進去:
~$ vim /etc/nginx/nginx.conf
然后在首行添加當前用戶:
user your_user nginx;
然而這樣存在一定的安全隱患。最安全的做法是把nginx用戶添加到當前用戶的附加群組中,然后修改相應文件的權限:
~$ usermod -a -G your_user nginx
~$ chmod 710 /home/your_user