标签 Flask 下的文章

安装

这里直接使用包管理器提供的版本,不过建议大家使用pip来安装,会少一些坑:

(Debian/Ubuntu) apt-get install uwsgi uwsgi-plugin-python3

或使用pip安装

pip3 install uwsgi

试试看

[demo.py]
from flask import Flask

app = Flask(__name__)

@app.route("/")
def hello_world():
    return "<p>Hello, World!</p>"

终端执行:

uwsgi --http-socket 0.0.0.0:8088 --manage-script-name --mount /=demo:app --plugin python3
(如果你是通过pip安装的,可不加 --plugin python3)
uwsgi --http-socket 0.0.0.0:8088 --manage-script-name --mount /[path]=demo:app --plugin python3

访问:

http://localhost:8088/[path]

部署

通常情况下我们的应用是按照工厂模式所编写的,使用我们需要新建一个文件来暴露出app对象:

from application import create_app
app = create_app()
if __name__ == "__main__":
    app.run()

下面来编写一个配置文件,便于配置修改:

[config.ini]

[uwsgi]
# 使用http协议
# http = 0.0.0.0:8081
# 指定工作用户(组)
uid = www-data
gid = www-data
# 主进程,由本进程派生子进程
master = true
# 工作目录
chdir = /var/application
# 插件(使用pip安装的可省略)
plugins = python3
# 入口文件
wsgi-file = app.py
# 指定入口文件的Flask对象
callable = app
# 指定uwsgi的socket路径
socket = /tmp/application.sock
# 进程数
processes = 2
# 线程数
threads = 4
# 缓冲区大小
buffer-size = 32768

配置Nginx

server {
    listen 80 default_server;
    listen [::]:80 default_server;

    root /var/www/html;

    index index.html index.htm index.nginx-debian.html;

    server_name _;

    # location = /[path] { rewrite ^ /[path]/; }
    location / { try_files $uri @uwsgi; }
    location @uwsgi {
        include uwsgi_params;
        uwsgi_pass unix:/tmp/application.sock;
    }
}

uwsgi后台运行,你可以直接在命令后加-d,但我这里是新建了个服务:

[/etc/systemd/system/uwsgi.service]

[Unit]
Description=uwsgi application

[Service]
User=www-data
Group=www-data
Type=simple
WorkingDirectory=/var/application
ExecStart=/usr/bin/uwsgi /var/application/config.ini

[Install]
WantedBy=multi-user.target

接下来就是设置开机启动了:

(sudo) systemctl enable uwsgi
(启动)
(sudo) systemctl start uwsgi

常见问题

  1. Nginx报5XX错误
    检查你的uwsgi的运行用户,务必保证你创建的socketNginx有权限读写的。
  2. uwsgino app loaded. going in full dynamic mode
    这个用pip安装的不会出现,需要添加python3插件

更多

https://uwsgi-docs.readthedocs.io/en/latest/
http://nginx.org/en/docs/http/ngx_http_uwsgi_module.html

Flask-Mail是Flask的邮件扩展,能让我们以简单的方式方式邮件。

安装

pip3 install flask_mail

配置

MAIL_SERVER : 服务器地址,默认为 ‘localhost’
MAIL_PORT : 服务器端口,默认为 25
MAIL_USE_TLS : 使用TLS,默认为 False
MAIL_USE_SSL : 使用SSL,默认为 False
MAIL_DEBUG : 是否打开Debug,默认为 app.debug
MAIL_USERNAME : 用户名,默认为 None
MAIL_PASSWORD : 密码(授权码),默认为 None
MAIL_DEFAULT_SENDER : 默认发送者,默认为 None
MAIL_MAX_EMAILS : 重新连接前发送邮件最大数目,默认为 None
MAIL_SUPPRESS_SEND : 启用发送(True为不发送),默认为 app.testing
MAIL_ASCII_ATTACHMENTS : 附件文件名转换为ASCII,默认为 False

示例(同步)

from flask import Flask
from flask_mail import Mail,Message
app = Flask(__name__)

#app.config['MAIL_DEBUG'] = True
app.config['MAIL_SUPPRESS_SEND'] = False
app.config['MAIL_SERVER'] = 'smtp.qq.com'
app.config['MAIL_PORT'] = 465
app.config['MAIL_USE_SSL'] = True
app.config['MAIL_USERNAME'] = '你的邮箱'
app.config['MAIL_PASSWORD'] = '密码(授权码)'
app.config['MAIL_DEFAULT_SENDER'] = '发件人邮箱'
mail = Mail(app)

@app.route('/')
def index():
    msg = Message(subject="标题",sender="发送者邮箱",recipients=[接收者邮箱1,接收者邮箱2...])
    #发送HTML或文本信息
    msg.html = '<h1>hello</h1>'
    #msg.body = 'hello'
    #发送
    mail.send(msg)
    return 'index'

if __name__ == '__main__':
    app.run('0.0.0.0',8080)

异步解决

#省略上面的配置和路由
#(下面代码在路由中)
from threading import Thread
from flask import current_app
def send_mail(app,msg):
    #应用上下文管理器
    with app.app_context():
        mail.send(msg)
#启用线程来异步发送,传入app实例与msg对象
thr = Thread(target = send_mail, args = [app,msg])
thr.start()

在工厂模式下没有app实例怎么办,只需要在线程启动前添加这样一行来获取:

app = current_app._get_current_object()

关于current_app._get_current_object()的讨论:
https://segmentfault.com/q/1010000005865632/a-1020000005865704
Flask_Mail中文文档:
http://www.pythondoc.com/flask-mail/index.html

相关内容

摄像头视频流

示例

传输一个mp4流,使游览器播放:

from flask import Flask,Response
app = Flask(__name__)
def Video_stream(file):
        with open(file,'rb') as f:
                data = f.read(5120) #每次读取5120字节
                while data:
                        print len(data),'-',
                        yield data
                        data = f.read(5120)
@app.route('/')
def index():
        return Response(Video_stream('./test.mp4'),mimetype='video/mp4') #Content-Type:video/mp4
if __name__ == '__main__':
        app.run(host='0.0.0.0',port='80',debug=True)

常用流媒体标头

mp3 = "audio/mpeg"
mp4 = "video/mp4"
mp4v = "video/mp4"
mpeg = "video/mpeg"
mpg = "video/mpeg"
wav  = "audio/x-wav"
webm = "video/webm"
wma = "audio/x-ms-wma"
wmv = "video/x-ms-wmv"
wmx = "video/x-ms-wmx"

部署指南

为了适应高并发,https支持(比如gevent就不支持)等条件时,往往会加入中间件,比如Nginx,把这些流媒体交给Nginx处理,可以 减轻Flask应用应用的压力,提高效率。

老物搬运。
画面比在Linux桌面运行的流畅很多,也许是Opencv的cv2.imshow()会不断产生新窗口导致的卡顿,因为我关不掉窗口,它会一直产生新的。

Camera.py

#coding=utf-8
import cv2
class Camera():
    def __init__(self,Camera_id):
        self.video = cv2.VideoCapture(Camera_id)
        self.face_cascade = cv2.CascadeClassifier('./haarcascade_frontalface_default.xml')
    def __del__(self):
        self.video.release()
    def get_img(self):
        success,image = self.video.read()
        gray = cv2.cvtColor(image,cv2.COLOR_BGR2GRAY)
        faces = self.face_cascade.detectMultiScale(gray, 1.3, 5)
        for (x,y,w,h) in faces:
            cv2.rectangle(image,(x,y),(x+w,y+h),(255,0,0),2)
        ret,jpeg = cv2.imencode('.jpg', image) #将image对象转为jpeg格式
        return jpeg.tobytes() #转字节

main.py

from flask import Flask,Response
from Camera import Camera
app = Flask(__name__)
@app.route('/')
def index():
    return '<h3 style="text-align:center"><img src="/video" width="60%"></h3>'

def Video_stream(camera):
    while True:
        img = camera.get_img()
        yield (b'--frame\r\n'b'Content-Type: image/jpeg\r\n\r\n' + img + b'\r\n\r\n') #生成器

@app.route('/video')
def video():
    return Response(Video_stream(Camera(0)), mimetype='multipart/x-mixed-replace; boundary=frame') #合成响应,返回一个自定义标头和图片数据

if __name__ == '__main__':
    app.run(host='0.0.0.0',port=80)

1.安装pyOpenSSL库

pip install pyOpenSSL
(仅pip)

2.修改原有代码

端口改为443,在原有参数上加上ssl_context=('证书路径','私钥路径')即可

app.run(host='0.0.0.0',port=443,ssl_context=('/root/certificate.crt', '/root/private.key'))

Flask 是 Python 的一款轻量化Web框架,使用Flask可以快速完成Web应用的开发。

1 安装

Pip 方式:

pip install flask

Apt方式:

sudo apt-get install python-flask

在pip安装不了时使用apt强制安装

2 一个最小的应用

from flask import Flask #引用
app = Flask(__name__)

@app.route('/') #路由
def hello_world():
    return 'Hello World!' #返回

if __name__ == '__main__':
    app.run(host='0.0.0.0',port=80) #全IP访问,80端口