通过uWSGI来运行Python应用

uWSGI是一个Web服务器,它实现了WSGI协议,在Nginx中使用HttpUwsgiModule提供服务。WSGI是一种网关接口,是Web服务器与Web应用之间通讯的一种规范。uWSGI是由Python实现的Web容器,对Django、Flask等有较好的兼容性;因为本质上来说uwsgi是python的一个模块,所以uwsgi可以使用pip install uwsgi来安装。

uWSGI一般用来负载Flask项目,因为虽然可以使用Python直接来负载Flask项目,但是始终还存在并发、异步等众多问题。所以开发好的项目使用Web容器来发布是比较正确且通用的做法。

配置uWSGI需要在项目根目录中放置一个.ini或者是.yml格式的配置文件。例如有以下项目根文件。

from flask import Flask
app = Flask(__name__)

@app.route("/")
def hello():
	return "Hello world."

if __name__ == "__main__":
	app.run(host="0.0.0.0", port=8080)

这里要注意,app.run()只应该在测试时使用,而不是在发布时使用,所以需要将其写入判断中,防止uWSGI运行app.run()方法。下面以.ini配置文件为例来配置uWSGI。

# 配置文件名称为uwsgi.ini
[uwsgi]
# 设定项目所在的目录
chdir=/Home/user/webservice/site
# 设定virtualenv的环境目录,也就是python可执行文件所在目录
home=/Home/user/webservice/site/venv
# 指定主模块名称
module=hello
# 指定代表主应用的变量名称
callable=app
# 是否允许主线程存在
master=true
# 开启进程数量
processes=2
# 指定项目执行的端口号,配合Nginx时只用socket,自己执行时使用http配置
# IP地址可以省略
http-socket=127.0.0.1:3230
# 指定服务器退出时清理环境
vacuum=true
# 指定服务器后台运行时的日志记录
daemonize=/Home/user/log/uwsgi_log.log
pidfile=/Home/user/log/uwsgi.pid.log
# 动态监控指定目录中的文件变化,有变化则自动重启
touch-reload=/Home/user/webservice/site/

配置文件书写好后,就可以使用uwsgi --ini /path/to/uwsgi.ini来启动uWSGI服务了。如果需要连续监控项目的变化,可以使用uwsgi --emperor /path/to/project/来启动应用。如果不使用连续监控,则可以使用以下命令来对uWSGI进行控制。

  • uwsgi uwsgi.ini --daemonize,后台启动
  • uwsgi --stop uwsgi.pid,停止服务
  • uwsgi --reload uwsgi.pid,无缝重启服务

对于Nginx来说,需要配置反向代理,将请求转移至uWSGI来执行。

server {
	listen 80;
	server_name localhost;
	location / {
		include uwsgi_params;
		# uwsgi.ini中http-socket的配置
		uwsgi_pass 127.0.0.1:3230;
		# 项目中venv的位置
		uwsgi_param UWSGI_PYHOME /Home/user/webservice/site/venv;
		# 项目根目录
		uwsgi_param UWSGI_CHDIR /Home/user/webservice/site;
		# 启动项目的主程序
		uwsgi_param USWSGI_SCRIPT hello:app
	}
}