欢迎您访问程序员文章站本站旨在为大家提供分享程序员计算机编程知识!
您现在的位置是: 首页

项目部署:flask+gunicorn/uwsgi/mod_wsgi+nginx/apache

程序员文章站 2022-06-11 14:43:05
...

flask应用程序

#flask_test.py
import os
from urllib.request import urlretrieve
import logging
from logging.handlers import RotatingFileHandler
from flask import Flask, request, jsonify
import requests
import json
import time

def generate_log(log_dir):
    if not os.path.exists(log_dir):
        os.makedirs(log_dir)
    now_time = time.strftime('%Y-%m-%d-%H-%M-%S')
    formatter_base = '%(asctime)s: %(levelname)s %(message)s'
    logging.basicConfig(level=logging.DEBUG)
    formatter = logging.Formatter(formatter_base)
    Rthandler = RotatingFileHandler(filename='%s' % os.path.join(log_dir, now_time + '.log'), \
    maxBytes=50 * 1024 * 1024, backupCount=1)
    Rthandler.setLevel(logging.DEBUG)
    Rthandler.setFormatter(formatter)
    logging.getLogger('').addHandler(Rthandler)


app = Flask(__name__)
generate_log('/mnt/disk2/xxx/work/test/log/')
@app.route('/Test', methods=['GET', 'POST'])


def test():
    try:
        strs = request.values.get('strs')
    except Exception as e:
        return jsonify({'result': 'ERR', 'message' : 'hello %s faild: %s' % (strs, e)})
    return jsonify({'result': 'OK', 'message' : 'hello %s ' % strs})
if __name__ == '__main__':
    app.run(host='0.0.0.0', port='7000')

flask+gunicorn+nginx方式

  • 安装
# nginx
apt-get install nginx #安装
apt-get remove nginx #卸载
# uwsgi
pip3 install gunicorn --user #安装
pip3 uninstall gunicorn #卸载
  • 创建flask应用程序
  • 创建gunicorn配置文件
    在项目目录下创建gunicorn的配置文件config.py
# config.py
import os
import gevent.monkey
gevent.monkey.patch_all()

import multiprocessing

debug = True

bind = '0.0.0.0:7000'
pidfile = 'log/gunicorn.pid'
accesslog = 'log/access.log'
errorlog = 'log/error.log'
capture_output = True
loglevel = 'warring'

daemon = True #后台启动
reload = True

#workers = multiprocessing.cpu_count()
workers = 1
worker_class = 'gevent'
x_forwarded_for_header = 'X-FORWARDED-FOR'
  • 启动gunicorn
# 添加配置文件后的启动方式
gunicorn -c config.py flask_test:app
  • 通过端口号查看程序是否启动
fuser -v -n tcp 端口号 #查看端口号
fuser -k 端口号/tcp  #关闭端口号

  • 测试gunicorn
    浏览器中输入http://10.27.1.20:7000/Test?strs=gunicorn-flask,如果返回{"message":"hello gunicorn-flask ","result":"OK"}则成功。

  • 创建nginx配置文件
    在/etc/nginx/sites-enabled/目录下创建nginx_gunicorn文件,并写入以下内容。

vim nginx_gunicorn #创建文件
server{
    listen 8002 default_server;
    listen [::]:8002 default_server;
    server_name 10.27.1.20;
    location / {
        proxy_pass http://127.0.0.1:7000;
        proxy_set_header Host $host;
        proxy_set_header X-Forwarded-For $proxy_add_x_forwarded_for;
    }
}
  • 启动nginx
cd /etc/sbin
./nginx -t #测试配置
./nginx #启动
./nginx -s reload #重新加载
./nginx -s stop #停止

  • 查看进程是否起来
fuser -v -n tcp 端口号 #查看端口号
fuser -k 端口号/tcp  #关闭端口号

  • 测试nginx
    浏览器中输入http://10.27.1.20:8002/Test?strs=nginx-gunicorn-flask,如果返回{"message":"hello nginx-gunicorn-flask ","result":"OK"}则成功。

flask+uwsgi+nginx方式

  • 安装
# nginx
apt-get install nginx #安装
apt-get remove nginx #卸载
# uwsgi
pip3 install uwsgi --user #安装
pip3 uninstall uwsgi #卸载

  • 创建flask应用程序
  • 创建uwsgi配置文件
    在项目目录下创建uwsgi的配置文件uwsgi.ini,跟flask的启动脚本放在同一目录下。
[uwsgi]
#使用nginx时需要该关键字
#socket = 0.0.0.0:7000
#不使用nginx是需要该关键字
http = 0.0.0.0:7000 
pythonpath = /mnt/disk2/xxx/work/xxx/
module = flask_test:app
#起用process manager,管理worker进程,worker进程都是这个master进程的子进程
master = true
# 进程
processes = 2
# 每个worker进程中创建两个线程
threads = 2
#不设置该关键字,请求超过4k就会报错
buffer-size = 65536
#使进程在后台运行,并将日志打到指定的日志文件或udp服务器
daemonize = ./log/uwsgi.log
#指定pid文件
pidfile = ./log/uwsgi.pid
#设置最大日志文件大小
log-maxsize = 50000000
#禁用请求日志记录
#disable-logging = true 
#只在开发时使用,监控项目的py文件的mtime来出发重载,py-autoreload表示多长时间检测一次,单位秒
python-autoreload = 1 
#在每个worker而不是master中加载应用,默认为false,表示先加载应用,再fork出worker,这样可以让work尽量共用内存,只有当写时才copy。
#由于先加载再fork,单有些东西是不支持fork的,比如socket连接,所以lazy-apps=false时,不要在加载应用时自动创建数据连接等
lazy-apps = true 
#为每个工作进程设置请求数的上限,当一个工作进程处理的请求数达到这个值,那么该工作进程就会被回收重用(重启),可以使用这个选项俩默默对抗内存泄露。
max-requests = 5000

  • 启动uwsgi
    uwsgi.ini在项目目录下,所以在项目目录下运行下面的命令。
uwsgi --ini uwsgi.ini #启动
uwsgi -d --ini uwsgi.ini #后台启动
uwsgi --reload ./log/uwsgi.pid #重启
uwsgi --stop ./log/uwsgi.pid #停止
  • 通过端口号查看程序是否启动
fuser -v -n tcp 端口号 #查看端口号
fuser -k 端口号/tcp  #关闭端口号

  • 测试uwsgi
    在uwsgi.ini中配置http方式才可以用浏览器访问,sock方式不可以。
    浏览器中输入http://10.27.1.20:7000/Test?strs=uwsgi-flask,如果返回{"message":"hello uwsgi-flask ","result":"OK"}则成功。

  • 创建nginx配置文件
    在/etc/nginx/sites-enabled/目录下创建nginx_uwsgi文件,并写入以下内容。

vim nginx_uwsgi #创建文件
server{
    listen 8001 default_server;
    listen [::]:8001 default_server;
    server_name 10.27.1.20;
    location / {
        include uwsgi_params;
        uwsgi_pass 127.0.0.1:7000;

    }
}

  • 启动nginx
cd /etc/sbin
./nginx -t #测试配置
./nginx #启动
./nginx -s reload #重新加载
./nginx -s stop #停止

  • 查看进程是否起来
fuser -v -n tcp 端口号 #查看端口号
fuser -k 端口号/tcp  #关闭端口号

  • 测试nginx
    浏览器中输入http://10.27.1.20:8001/Test?strs=nginx-uwsgi-flask,如果返回{"message":"hello nginx-uwsgi-flask ","result":"OK"}则成功。

flask+mod_wsgi+apache方式

  • 安装
#apache2
apt-get install apache2
apt-get remove apache2
#mod_wsgi
apt-get install libapache2-mod-wsgi #python2
apt-get install libapache2-mod-wsgi-py3 #python3
  • 创建flask应用程序
  • 创建.wsgi配置文件
    在项目test目录下创建mod_wsgi.wsgi,因为test目录在非root用户下,需要用chmod 777 mod_wsgi.wsgi命令将mod_wsgi.wsgi文件改成可读可写模式,是root用户下,apache运行后能调用该文件。
#mod_wsgi.wsgi
#!/usr/bin/python3

import sys
import os
import logging
import site

logging.basicConfig(level=logging.DEBUG, stream=sys.stderr)
site.addsitedir('/home/xxx/.local/lib/python3.5/site-packages')
sys.path.insert(0, '/mnt/disk2/xxx/work/test')

#logging.info(sys.path)

#import torch
#logging.debug(torch.__version__)

#def application(environ,start_response):
#    status='200 OK'
#    output=b'Hello wsgi!'
#    print(environ['wsgi.errors'], sys.path)
#    print (environ['wsgi.errors'], sys.prefix)
#    print (environ['wsgi.errors'], sys.executable)
#    response_headers=[('Content-type','text/plain'),
#                       ('Content-Length',str(len(output)))]
#    start_response(status,response_headers)
#    return[output]


from test_hello import app as application

  • 创建apache2配置文件
    在/etc/apache2/sites-available/目录下创建flask_app.conf配置文件,在该文件中同样需要对mod_wsgi.wsgi文件、项目test目录、日志test/log目录设置可读写权限,并且还需要用命令chmod 777 xxx修改可读写权限。
#flask_app.conf
WSGIPythonHome /home/xxx/.local/lib/python3.5/site-packages
ServerName 10.27.1.20
Listen 7000
<VirtualHost *:7000>
    ServerAdmin [email protected]
    WSGIDaemonProcess test python-path=/mnt/disk2/xxx/work/test:/home/xxx/.local/lib/python3.5/site-packages python-home=/home/xxx/.local/lib/python3.5/site-packages display-name=%{GROUP}

    WSGIScriptAlias / /mnt/disk2/xxx/work/test/mod_wsgi.wsgi process-group=test application-group=%{GLOBAL}
    <Directory /home/xxx/.local/lib/python3.5/site-packages/>
    Require all granted
    </Directory>
    <Directory /mnt/disk2/xxx/work/test/>
        WSGIScriptReloading On
        Require all granted
        <Files mod_wsgi.wsgi>
            Require all granted
        </Files>
    </Directory>

    <Directory /mnt/disk2/xxx/work/test/log/>
    Require all granted
    </Directory>
    LogLevel debug
    ErrorLog /mnt/disk2/xxx/work/test/log/apache_error.log
    CustomLog /mnt/disk2/xxx/work/test/log/apache_access.log combined
</VirtualHost>


  • 启动站点配置文件
    可在任意目录下启动
a2ensite flask_app.conf # **站点
a2dissite flask_app.conf # 屏蔽站点
  • 启动mod_wsgi
    可在任意目录下启动
a2enmod wsgi # 查看是否启动
a2dismod wsgi # 禁用
  • 启动apache服务
apache2ctl start # 启动
apache2ctl configtest #检测配置
apache2ctl restart # 重启
apache2ctl reload # 重新加载站点
apache2ctl stop # 关闭
  • 通过端口号查看服务是否运行
    关闭该端口网络站点和wsgi都会被关闭。
fuser -v -n tcp 7000 # 查看端口服务
fuser -k 7000/tcp #关闭端口,关闭该端口网络站点和wsgi都会被关闭
  • 测试
    浏览器中输入http://10.27.1.20:7000/Test?strs=apache-wsgi-flask,如果返回{"message":"hello apache-wsgi-flask ","result":"OK"}则成功。

参考资料
项目部署:flask+mod_wsgi+apache
项目部署:nginx+uwsgi+flask
深度学习多线程部署—学习笔记
Flask—学习笔记