FreeBSD 部署 Flask 應用 (HTTPS+Gunicorn)


1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
# 記錄相關
Flask + Supervisor + Gunicorn + Gevent + SSL (HTTPS)

# 切到應用目錄
cd /home/user/example.com

# 解決 SqlAlchemy Fallback 到 pysqlite2 時找到套件的問題
cd /usr/ports/databases/sqlite3 && make distclean && make config && make install clean && cd -

# 安裝 libevent 庫,解決 gevent 無法安裝問題
cd /usr/ports/devel/libevent && make install clean && cd -

setenv CFLAGS "-I /usr/local/include"
setenv LDFLAGS "-L /usr/local/lib/"

# 建立套件環境
easy_install -U virtualenv
virtualenv --no-site-package --python=/usr/local/bin/python2.7 venv
source venv/bin/activate.csh

# 安裝依賴套件
pip install -r requirements.txt

# 移除設定的編譯參數
unsetenv CFLAGS
unsetenv LDFLAGS

# 測試執行是否成功
gunicorn wsgi:app -c project_name/configs/gunicorn.py

# 加入到 Supervisor 控制
vim /usr/local/etc/supervisord.conf

[program:project_nameapp]
command=/home/user/example.com/venv/bin/gunicorn wsgi:app -c project_name/configs/gunicorn.py
directory=/home/user/example.com
autostart=true
startsecs=5
user=user
redirect_stderr=true
stdout_logfile=/var/run/supervisor/project_nameapp.log

# 重新加載設定
supervisorctl reread
supervisorctl reload

# 查看啟動情況
/var/run/supervisor/project_nameapp.log

# 編輯 Nginx
vim /usr/local/nginx/conf/vhosts/example.com.conf

upstream project_name_app {
server 127.0.0.1:8080 fail_timeout=0;
}

server {
listen 80;
server_name example.com;

rewrite ^/(.*) https://$server_name/$1 permanent;
}

server {
listen 443;

ssl on;
ssl_certificate /usr/local/nginx/conf/ssls/example.com.bundled.crt;
ssl_certificate_key /usr/local/nginx/conf/ssls/example.com.key;
ssl_session_timeout 5m;

charset utf-8;
server_name example.com;

location /robots.txt {
alias /home/user/example.com/project_name/statics/robots.txt;
}

location / {
proxy_set_header X-Forwarded-For $proxy_add_x_forwarded_for;
proxy_set_header Host $http_host;
proxy_set_header X-Real-IP $remote_addr;
proxy_set_header X-Scheme $scheme;
proxy_redirect off;

proxy_pass http://project_name_app;
}

location ~ /\.ht {
deny all;
}
}