您当前的位置:首页 > 电脑百科 > 程序开发 > 框架

Flask框架及其应用

时间:2021-03-03 10:03:05  来源:  作者:

Flask介绍

对于Flask大家很熟悉了,现在主流Python的web框架,除了Django就数Flask了。

Django不用多说,集合了orm、template模板引擎、后台管理系统、参数验证、路由系统、用户认证和其他一些工具的,方便快速建站,主要构建了ORM和复写ADMIN模块,就可以快速生成网站和后台增上改查和一些其他的定制化开发。

Flask是一个轻量级的可定制框架,使用Python语言编写,较其他同类型框架更为灵活、轻便、安全且容易上手。它可以很好地结合MVC模式进行开发,开发人员分工合作,小型团队在短时间内就可以完成功能丰富的中小型网站或Web服务的实现。另外,Flask还有很强的定制性,用户可以根据自己的需求来添加相应的功能,在保持核心功能简单的同时实现功能的丰富与扩展,其强大的插件库可以让用户实现个性化的网站定制,开发出功能强大的网站。

笔者更倾向于Flask这个框架,因为它更加透明,更能掌控项目的质量。

使用过的插件

Flask的插件管理是一个很不错的特性,我们利用它可以在启动web服务之前加载我们所需要的插件,一下是笔者经常用到的:

  • flask-restful

flask的restapi开发框架,有参数校验,路由拦截等功能。

  • flask-sqlalchemy

Sqlalchemy的flask插件,这个插件作者扩展了针对与session中的query的分页功能,可以使用SQLALCHEMY_BINDS进行多个数据库的绑定,可以配置连接池,连接池过期时间。

  • MySQLclient或者pymysql

Sqlalchemy连接mysql的引擎,不过pymysql需要加入一句话:

  import pymysql
  pymysql.install_as_MySQLdb()
  • marshmallow

Sqlalcemy序列化数据利器,可以使用它针对query返回的QuerySet结果集合进行序列化成dict 数据。

  • flask-cors

开发API会遇到跨域访问的问题,可以就是客户端OPTIONS的请求,先探知服务器允不允许跨域访问,允许会返回header中允许那些方法进行请求服务器(GET、POST、DELETE、PUT等),这个插件可以通过简单的配置,让您的服务允许跨域访问,不过在生产环境,还是推荐使用Nginx的好,能够使用lua语言进行更加严格的控制。

  • flask-login或者flask-jwt-extended

这两个都是用户认证用到的插件,使用session控制,选择flask-login,使用jwt使用flask-jwt-extended。

Flask框架

下面简单说一下flask的框架,flask框架是基于Werkzeug和Jinja2两大基础框架,Werkzeug是基于WSGI协议的框架,已经有了基本的路由、数据结构、请求和响应等功能,在此之上Flask扩展了一些特性:

  • request

Flask利用Werkzeug的Local、LocalStack和LocalProxy,实现了AppContext和RequestContext的线程或者协程安全功能,也就是:

  1. 当请求过来,Flask将app_context和request,这两个对象压入一个线程号或者协程号对应的栈中,说白了就是dict字典,线程或者携程号有get_indent内置方法获得
  2. 请求过程中,由栈弹出上次压入栈中的app_context和request
  3. 请求结束释放空间

另外说明flask-sqlalchemy利用线程或者携程号有get_indent,可以使用scope_session功能,将session隔离,它是线程或者协程安全的,也和flask的请求保持一致。

  • endpoint

使得每个view方法,有个名称,这个名称是唯一的,它能够通过这个名称找到这个视图方法,也就能够获得路由。

这里数据结构简单地说就是一个map类型,一个名称唯一对应一个视图方法,不允许相同的endpoint出现,这个应用在使用url_for这个方法上:

  1. 程序中使用url_for进行路由跳转
  2. template模板总是用url_for查找对应的路由

这样可以灵活根据名称去使用路由,而不是硬编码到程序中非常死板,如果说我们修改了一个url的地址,只是微小的修改,其他引用这个路由的地方也需要修改,我们可能忘记了使用它的地方,这时url_for非常好的解决了这个问题。

  • extentions

扩展应用,提供了两种方式,一种是直接加载,之类用生成对象例如CORS(flask_app),也可以懒加载,在创建应用之前定义对象,创建flask_app时加载插件,例如flask-sqlalchemy

from flask import Flask
from flask_sqlalcemy import Sqlalchemy

db = Sqlalchemy()

def create_app():
    """
    创建Flask app
    """
    f_app = Flask()
    f_app.config.from_object("core.settings")
    db.init_app(app=f_app)
    return f_app

这样的形式,我们可以使用全局这个db对象了。

开发项目目录结构

我们可以借鉴django的目录形式进行组织项目的框架,例如:

Flask框架及其应用

 

core文件夹基本这个样子,app 是项目Flask应用初始化,settings是配置信息,应用是user和config等,static存放静态文件,templates是模板目录,requirements.txt里面配置依赖,run.py是调试使用的启动入口。

特别的一个应用目录为:

Flask框架及其应用

 

其中,__init__.py是module的文件,dbis.py里面都是面向数据操作的方法,models.py里面都是ORM的定义,urls.py里面是路由配置,validators.py存放参数校验方法,views.py存放视图方法,serializers.py存放序列化的方法,dbi_services.py存放构造views.py中使用的数据类型。

我们如何将他们和Flask的应用联系起来呢,可以进行如下操作:

生成Flask的应用代码:

import os
from flask_sqlalchemy import SQLAlchemy
from flask_bootstrap import Bootstrap
from flask_url.conf import FlaskUrlConf
from flask_wtf.csrf import CSRFProtect
from flask import Flask

db = SQLAlchemy()


def create_app(import_name):
    """
    创建Flask应用
    :param import_name: [str]  模块名称
    :return:
    """
    f_app = Flask(import_name)
    # 根据环境变量加载配置信息
    env_dict = {
        "DEV": "core.dev_settings",
        "ONLINE": "core.online_settings"
    }
    env = os.environ.get("PRO_ENV", "DEV")
    f_app.config.from_object(env_dict.get(env, "core.dev_settings"))
    FlaskUrlConf(app=f_app)
    db.init_app(app=f_app)
    CSRFProtect(app=f_app)
    print(f_app.url_map)
    return f_app


app = create_app(__name__)

其中使用了FlaskUrlConf(app=f_app)这个,是我自己构造的一个插件,贴出这段代码:

from flask import Flask
from flask.blueprints import Blueprint
from flask_url.utils import get_mod_attr


def path(rule, endpoint, view_func, **options):
    return Url(rule=rule, endpoint=endpoint, view_func=view_func, **options)


class Url:
    rule = None
    endpoint = None
    view_func = None
    options = {}

    def __init__(self, rule, endpoint, view_func, **options):
        self.rule = rule
        self.endpoint = endpoint
        self.view_func = view_func
        self.options = options


class FlaskUrlConf:

    def __init__(self, app: Flask = None):
        if app:
            self.init_app(app=app)

    def init_app(self, app: Flask):
        install_apps = app.config.get("INSTALL_APPS", [])
        for app_str in install_apps:
            mod_path = f"{app_str}.urls"
            try:
                urls = get_mod_attr(mod_path, "urls")
                b = Blueprint(import_name=mod_path, name=app_str)
                for url in urls:
                    if isinstance(url, Url):
                        b.add_url_rule(
                            rule=url.rule,
                            endpoint=url.endpoint,
                            view_func=url.view_func,
                            **url.options
                        )
                app.register_blueprint(b)
            except ImportError as e:
                app.logger.warn(f"Import module {mod_path} err {e}")
            except IndexError as e:
                app.logger.warn(f"Split module {mod_path} attr error {e}")
            except AttributeError as e:
                app.logger.warn(f"Get attr from url module {mod_path}, error {e}")

其核心思想是通过INSTALL_APPS这个配置,将各级模块儿应用下的urls.py中的urls列表进行加载,urls.py示例:

from flask_url.conf import path
from article import views


urls = [
    path(rule="/article/page/<int:a_id>/", view_func=views.get_article, endpoint="page")
]

那我们就完成了MVC的项目目录结构的搭建。

部署

最后我们再来谈一下flask应用的部署,我们可以使用gunicorn或者uwsgi进行部署,通过nginx进行代理即可。

uwsgi配置示例:

uwsgi]
uid = root
gid = root

master = true
processes = 1
listen = 10
socket = 127.0.0.1:9000
pidfile = /uwsgi.pid	# 你的路径
vacuum = true
daemonize = /uwsgi.log # 你的日志路径
chdir = ${你的项目路径}
home=${你的env的路径}
buffer-size = 32768  # 可以修改允许最大交换数据
module = core.wsgi  # 你的 wsgi模块路径
callable = app # 选择你的应用,Flask的应用
http-websockets = true # 是否启用web socket
gevent = 10   # 启用协程
async = 10   

nginx配置示例

server {
        listen       8888;
        charset UTF-8;


        location ^~ /api/ {
                include uwsgi_params;
                uwsgi_pass http://127.0.0.1:9000;
                client_max_body_size 100m;
        }
}

以上是总结的一些内容跟大家分享,由于篇幅有限有些细节没有说清,大家可以在评论区提问。希望大家多多支持。



Tags:Flask框架   点击:()  评论:()
声明:本站部分内容及图片来自互联网,转载是出于传递更多信息之目的,内容观点仅代表作者本人,如有任何标注错误或版权侵犯请与我们联系(Email:2595517585@qq.com),我们将及时更正、删除,谢谢。
▌相关推荐
Flask介绍对于Flask大家很熟悉了,现在主流python的web框架,除了Django就数Flask了。Django不用多说,集合了orm、template模板引擎、后台管理系统、参数验证、路由系统、用户认...【详细内容】
2021-03-03  Tags: Flask框架  点击:(231)  评论:(0)  加入收藏
Flask框架作为轻量级Web应用框架,最大的特征是轻便灵活,第三方库的选择面广,容易上手,试错成本低。为了帮助大家学习并掌握Flask框架,本文将会带着大家一步步的完成Flask安装的环...【详细内容】
2020-08-14  Tags: Flask框架  点击:(72)  评论:(0)  加入收藏
开发环境Python版本:3.x包:flask工具:1.Pycharm2.Postman实现目标:开发一个只接受get方法的接口,接受参数为name和age,并返回相应内容。实现代码from flask import Flask,requesti...【详细内容】
2020-05-19  Tags: Flask框架  点击:(56)  评论:(0)  加入收藏
▌简易百科推荐
近日只是为了想尽办法为 Flask 实现 Swagger UI 文档功能,基本上要让 Flask 配合 Flasgger, 所以写了篇 Flask 应用集成 Swagger UI 。然而不断的 Google 过程中偶然间发现了...【详细内容】
2021-12-23  Python阿杰    Tags:FastAPI   点击:(6)  评论:(0)  加入收藏
文章目录1、Quartz1.1 引入依赖<dependency> <groupId>org.quartz-scheduler</groupId> <artifactId>quartz</artifactId> <version>2.3.2</version></dependency>...【详细内容】
2021-12-22  java老人头    Tags:框架   点击:(11)  评论:(0)  加入收藏
今天来梳理下 Spring 的整体脉络啦,为后面的文章做个铺垫~后面几篇文章应该会讲讲这些内容啦 Spring AOP 插件 (了好久都忘了 ) 分享下 4ye 在项目中利用 AOP + MybatisPlus 对...【详细内容】
2021-12-07  Java4ye    Tags:Spring   点击:(14)  评论:(0)  加入收藏
&emsp;前面通过入门案例介绍,我们发现在SpringSecurity中如果我们没有使用自定义的登录界面,那么SpringSecurity会给我们提供一个系统登录界面。但真实项目中我们一般都会使用...【详细内容】
2021-12-06  波哥带你学Java    Tags:SpringSecurity   点击:(18)  评论:(0)  加入收藏
React 简介 React 基本使用<div id="test"></div><script type="text/javascript" src="../js/react.development.js"></script><script type="text/javascript" src="../js...【详细内容】
2021-11-30  清闲的帆船先生    Tags:框架   点击:(19)  评论:(0)  加入收藏
流水线(Pipeline)是把一个重复的过程分解为若干个子过程,使每个子过程与其他子过程并行进行的技术。本文主要介绍了诞生于云原生时代的流水线框架 Argo。 什么是流水线?在计算机...【详细内容】
2021-11-30  叼着猫的鱼    Tags:框架   点击:(21)  评论:(0)  加入收藏
TKinterThinter 是标准的python包,你可以在linx,macos,windows上使用它,你不需要安装它,因为它是python自带的扩展包。 它采用TCL的控制接口,你可以非常方便地写出图形界面,如...【详细内容】
2021-11-30    梦回故里归来  Tags:框架   点击:(26)  评论:(0)  加入收藏
前言项目中的配置文件会有密码的存在,例如数据库的密码、邮箱的密码、FTP的密码等。配置的密码以明文的方式暴露,并不是一种安全的方式,特别是大型项目的生产环境中,因为配置文...【详细内容】
2021-11-17  充满元气的java爱好者  博客园  Tags:SpringBoot   点击:(25)  评论:(0)  加入收藏
一、搭建环境1、创建数据库表和表结构create table account(id INT identity(1,1) primary key,name varchar(20),[money] DECIMAL2、创建maven的工程SSM,在pom.xml文件引入...【详细内容】
2021-11-11  AT小白在线中  搜狐号  Tags:开发框架   点击:(29)  评论:(0)  加入收藏
SpringBoot开发的物联网通信平台系统项目功能模块 功能 说明 MQTT 1.SSL支持 2.集群化部署时暂不支持retain&will类型消 UDP ...【详细内容】
2021-11-05  小程序建站    Tags:SpringBoot   点击:(55)  评论:(0)  加入收藏
最新更新
栏目热门
栏目头条