Python Web一些常用部署过程

0x00 一个Python Web项目的大致模块划分

我自己的web项目,大致分成(一些和部署无关的模块隐藏)

- app  # flask app
    - app  # web后台的内容
    - master  # celery 任务调度的任务分配节点(处理任务初始化和回调)
    - node  # 具体任务调度执行的节点
    - manager.py  # web后台的管理器,wsgi的载体
    - celery_worker.py  # celery的管理器
    - .env  # 一些敏感的配置参数,输入到环境变量中,部署在不同位置不同,比如node节点不需要访问web后台的数据库
    - gunicorn.py  # gunicorn的配置
- manager  # 前端vue
    - .env  # vue的环境变量配置
- supervisor.d  # supervisor的配置
- nginx.conf  # nginx的配置

0x01 web app/gunicorn本身的部署

我常用flask,这里以flask为例子,开发的使用使用的pyenv-virtualenv,生产部署也可以使用或者直接用python -n venv,只要有一个虚拟环境就可以

维护一份requirements.txt,以前会使用pipenv,但是安装依赖慢,老是出问题,就算了,自己维护,开发时候添加什么库加上去

修改.env中的各种配置

配置gunicorn.py

import multiprocessing

# 工作模式
worker_class = 'gevent'

# 并行工作进程数
workers = 4  # multiprocessing.cpu_count()

# 指定每个工作者的线程数
# threads = 2

# 监听地址
bind = '127.0.0.1:5000'

# 设置守护进程
daemon = 'false'

# 设置最大并发量
worker_connections = 10000

# 设置进程文件目录
# pidfile = '/var/run/gunicorn.pid'

# 设置访问日志和错误日志路径
accesslog = './gunicorn_access.log'
errorlog = './gunicorn_error.log'

# 设置日志记录水平
loglevel = 'warning'

# preload_app = True

我自己使用的是这一份配置,可以在gunicorn文档中寻找需要的参数

运行

# 不管用什么工具,切换的venv,这里省略
$ pip install -r requirements.txt
# 初始化flask环境,deploy,数据库创建等操作,这里省略
$ guncorn -c gunicorn.py manager:app

这里注意部署时候是nginx对外转发,所以监听端口还是对内

0x02 celery

如有需要celery的master和node节点的requirements也需要单独维护,配置也需要单独改

# 不管用什么工具,切换的venv,这里省略
$ pip install -r requirements.txt
# celery如果有什么需要初始化的环境,或者依赖的flask需要,也deploy一下
$ celery -A celery_worker.celery worker -B -l INFO -Q master -n master  # 开启master节点,因为是配置了路由和节点名为master,所以加了-Q和-n参数,-B是因为有定时任务
$ celery -A celery_worker.celery worker -l INFO -Q node -n node  # 开启node节点,同样配置了路由和节点名为node,所以加了-Q和-n参数
$ celery flower -A celery_worker.celery --basic-auth=username:password  # 配置celery flower,默认为555端口,可以配置,注意设置用户名和密码,url前缀方便nginx配置

celery和celery-flower可以到他们到官方文档中查看,还有很多配置,celery-flower还描述了nginx如何配置

0x03 前端vue

修改.env的配置信息,在开发环境本地编译

$ npm run build

将生成的dist文件部署到nginx部署的对应目录下,之后通过nginx的配置来进行操作就可以了

0x04 nginx

server {
    listen       8000;
    server_name  localhost;
    index index.html;
    root /Users/milkfr/ATField/manager/dist;
    location ^~ /celery/ {
        rewrite ^/celery/(.*)$ /$1 break;
        proxy_pass http://127.0.0.1:5555;
        proxy_set_header Host $host;
        proxy_set_header X-Forwarded-For $proxy_add_x_forwarded_for;
    }
    location ^~ /api {
        proxy_pass http://127.0.0.1:5000;
        proxy_set_header Host $host;
        proxy_set_header X-Forwarded-For $proxy_add_x_forwarded_for;
    }
    location / {
        try_files $uri $uri/ /index.html;
    }
}

这里配置了前端、app和celery-flower的重定向,其他可以根据nginx的配置按需增加

0x05 supervisor

可以使用supervisor进行进程管理

app进程

[program:atfield_app]
command=/Users/milkfr/.pyenv/versions/3.8.0/envs/atfield-master-venv/bin/gunicorn -c gunicorn.py manager:app      ; the program (relative uses PATH, can take args)
;process_name=%(program_name)s ; process_name expr (default %(program_name)s)
;numprocs=1                    ; number of processes copies to start (def 1)
directory=/Users/milkfr/ATField/master                ; directory to cwd to before exec (def no cwd)
;priority=999                  ; the relative start priority (default 999)
autostart=true                ; start at supervisord start (default: true)
startsecs=1                   ; # of secs prog must stay up to be running (def. 1)
startretries=3                ; max # of serial start failures when starting (default 3)
autorestart=unexpected        ; when to restart if exited after running (def: unexpected)
user=milkfr                   ; setuid to this UNIX account to run the program
;redirect_stderr=true          ; redirect proc stderr to stdout (default false)
stdout_logfile=/Users/milkfr/ATField/master/app.log         ; stdout log path, NONE for none 
;stdout_logfile_maxbytes=50MB   ; max # logfile bytes b4 rotation (default 50MB)
;stdout_logfile_backups=10     ; # of stdout logfile backups (0 means none, default 10)
;environment=A="1",B="2"       ; process environment additions (def no adds)

flower进程

[program:celery_flower]
command=/Users/milkfr/.pyenv/versions/3.8.0/envs/atfield-master-venv/bin/celery flower -A celery_worker.celery --basic_auth=username:password --url_prefix=celery   ; the program (relative uses PATH, can take args)
;process_name=%(program_name)s ; process_name expr (default %(program_name)s)
;numprocs=1                    ; number of processes copies to start (def 1)
directory=/Users/milkfr/ATField/master                ; directory to cwd to before exec (def no cwd)
;priority=999                  ; the relative start priority (default 999)
autostart=true                ; start at supervisord start (default: true)
startsecs=1                   ; # of secs prog must stay up to be running (def. 1)
startretries=3                ; max # of serial start failures when starting (default 3)
autorestart=unexpected        ; when to restart if exited after running (def: unexpected)
user=milkfr                   ; setuid to this UNIX account to run the program
;redirect_stderr=true          ; redirect proc stderr to stdout (default false)
stdout_logfile=/Users/milkfr/ATField/master/celery_flower.log         ; stdout log path, NONE for none 
;stdout_logfile_maxbytes=50MB   ; max # logfile bytes b4 rotation (default 50MB)
;stdout_logfile_backups=10     ; # of stdout logfile backups (0 means none, default 10)
;environment=A="1",B="2"       ; process environment additions (def no adds)

master进程

[program:celery_master]
command=/Users/milkfr/.pyenv/versions/3.8.0/envs/atfield-master-venv/bin/celery -A celery_worker.celery worker -B -l INFO -Q master -n master      ; the program (relative uses PATH, can take args)
;process_name=%(program_name)s ; process_name expr (default %(program_name)s)
;numprocs=1                    ; number of processes copies to start (def 1)
directory=/Users/milkfr/ATField/master                ; directory to cwd to before exec (def no cwd)
;priority=999                  ; the relative start priority (default 999)
autostart=true                ; start at supervisord start (default: true)
startsecs=1                   ; # of secs prog must stay up to be running (def. 1)
startretries=3                ; max # of serial start failures when starting (default 3)
autorestart=unexpected        ; when to restart if exited after running (def: unexpected)
user=milkfr                   ; setuid to this UNIX account to run the program
;redirect_stderr=true          ; redirect proc stderr to stdout (default false)
stdout_logfile=/Users/milkfr/ATField/master/celery_master.log         ; stdout log path, NONE for none 
;stdout_logfile_maxbytes=50MB   ; max # logfile bytes b4 rotation (default 50MB)
;stdout_logfile_backups=10     ; # of stdout logfile backups (0 means none, default 10)
;environment=A="1",B="2"       ; process environment additions (def no adds)

node进程

[program:celery_node]
command=/Users/milkfr/.pyenv/versions/3.8.0/envs/atfield-master-venv/bin/celery -A celery_worker.celery worker -l INFO -Q node -n node      ; the program (relative uses PATH, can take args)
;process_name=%(program_name)s ; process_name expr (default %(program_name)s)
;numprocs=1                    ; number of processes copies to start (def 1)
directory=/Users/milkfr/ATField/master                ; directory to cwd to before exec (def no cwd)
;priority=999                  ; the relative start priority (default 999)
autostart=true                ; start at supervisord start (default: true)
startsecs=1                   ; # of secs prog must stay up to be running (def. 1)
startretries=3                ; max # of serial start failures when starting (default 3)
autorestart=unexpected        ; when to restart if exited after running (def: unexpected)
user=milkfr                   ; setuid to this UNIX account to run the program
;redirect_stderr=true          ; redirect proc stderr to stdout (default false)
stdout_logfile=/Users/milkfr/ATField/master/celery_node.log         ; stdout log path, NONE for none 
;stdout_logfile_maxbytes=50MB   ; max # logfile bytes b4 rotation (default 50MB)
;stdout_logfile_backups=10     ; # of stdout logfile backups (0 means none, default 10)
;environment=A="1",B="2"       ; process environment additions (def no adds)
坚持原创技术分享,您的支持将鼓励我继续创作!