flask框架-上
flask简介
Flask是一个使用 Python 编写的轻量级 Web 应用框架。其 WSGI 工具箱采用 Werkzeug ,模板引擎则使用 Jinja2 。Flask使用 BSD 授权。
Flask也被称为 “microframework” ,因为它使用简单的核心,用 extension 增加其他功能。Flask没有默认使用的数据库、窗体验证工具。
为什么要从Flask开始学习web框架?
依赖于wsgiref、jianjia2、wsgi、Werkzeug。
"""
1.python语言的灵活性给予了Flask同样的特征;
2.无论是用户画像还是产品推荐,python相比其他语言都有极大的优势;
3.Flask轻便,容易上手,试错成本低
"""
与其他web框架对比
"""(1)Django:比较“重”的框架,同时也是最出名的Python框架。包含了web开发中常用的功能、
组件的框架(ORM、Session、Form、Admin、分页、中间件、信号、缓存、ContenType....),
Django是走大而全的方向,最出名的是其全自动化的管理后台:只需要使用起ORM,做简单的对象定义,它就能自动生成数据库结构、以及全功能的管理后台。
(2)Tornado:大特性就是异步非阻塞、原生支持WebSocket协议;
(3)Flask:如上
(4)Bottle:是一个简单高效的遵循WSGI的微型python Web框架。说微型,是因为它只有一个文件,除Python标准库外,它不依赖于任何第三方模块。
"""
flask安装及使用
目录结构
通过别人的目录大致了解一下flask框架的目录结构
初始化项目
(1)、创建flask实例对象
flask程序必须创建一个程序实例,常用的方法:
这里的app就是一个程序实例,客户端(一般是浏览器)将请求发送给服务端Web服务器,Web服务器再把请求发给Flask实例。
(2)构建实例对象从URL到python函数的映射关系
程序实例需要知道所有URL对应的执行代码,所以要有从URL到python函数的映射关系。处理URL到python函数映射关系的程序一般叫做路由(Router)。
(3)启动服务器
开始测试hello world
最简单的测试
这是flask框架制作的一个最小的应用。使用python运行后访问localhost:5000就能看到网页显示Hello world。
flask模板
Flask的模板功能是基于Jinja2模板引擎实现的。让我们来实现一个例子吧。创建一个新的Flask运行文件(你应该不会忘了怎么写吧),代码如下:
flask启动的本质
flask依赖于两个模块的运行:werkzeug、wsgiref.
wsgiref可以当做独立的server来运行。
from wsgiref.simple_server import make_server def mya(environ, start_response): print(environ) start_response('200 OK', [('Content-Type', 'text/html')]) if environ.get('PATH_INFO') == '/index': with open('index.html','rb') as f: data=f.read() elif environ.get('PATH_INFO') == '/login': with open('login.html', 'rb') as f: data = f.read() else: data=b'<h1>Hello, web!</h1>' return [data] if __name__ == '__main__': myserver = make_server('', 8011, mya) print('监听8011') myserver.serve_forever()
werkzeug是WSGI工具包,它可以作为web框架的底层库
from werkzeug.wrappers import Request, Response @Request.application def hello(request): return Response('Hello World!') if __name__ == '__main__': from werkzeug.serving import run_simple run_simple('localhost', 4000, hello)
结果
flask启动的核心本质
from flask import Flask app=Flask(__name__) # mvc.c CBV @app.route('/')路由 def index(): return "back ok" if __name__ == '__main__': # 本质上run_simple(host,port,app,**options) # app(),对象加().执行__call__ app.run()
默认的启动ip和端口:
flask的四剑客使用
from flask import Flask,render_template,redirect,Response,jsonify app=Flask(__name__) @app.route('/') def text(): # 1直接返回字符串 # return "人生苦短,我学Python" # 2返回html # name_dict = {"name":'Eason'} # return render_template("text.html",name="java",name_dict=name_dict)
#跳转页面 # return redirect("/login") # 返回json数据 name_dict = {{"name":"jack"},{'hobby':"music"}} @app.route('/login') def login(): return "Hello woorld" if __name__ == '__main__': app.run()
html直接支持的字典取值
<!DOCTYPE html> <html lang="en"> <head> <meta charset="UTF-8"> <title>Title</title> </head> <body> <h1>用户列表</h1> <table> {% for k,v in user_dict.items() %} <tr> <td>{{k}}</td> <td>{{v.name}}</td> <td>{{v['name']}}</td> <td>{{v.get('name')}}</td> <td><a href="/detail/{{k}}">查看详细</a></td> </tr> {% endfor %} </body> </html>
flask配置文件的4种方式
只要配置之后,Ctrl+s保存,即可实现重启服务器生效的作用。
from flask import Flask app=Flask(__name__)
#配置文件1,这中方式只能配置两种 # app.debug=True # app.secret_key="123123" #第二种,以字典的形式 # app.config['DEBUG']=True
#第三种,以文件的形式 # app.config.from_pyfile("settings.py") #第四种以类的形式(推荐) settings.py文件下自定义的类。 app.config.from_object('settings.DevelopmentConfig')
@app.route('/login') def login(): print(123) return "ojbk_login" if __name__ == '__main__': app.run()
settings.py
# DEBUG = True class Config(object): DEBUG = False TESTING = False DATABASE_URI = 'sqlite://:memory:' class ProductionConfig(Config): DATABASE_URI = 'mysql://user@localhost/foo' class DevelopmentConfig(Config): DEBUG = True class TestingConfig(Config): TESTING = True
其他配置方式,有哪些配置,了解即可。
{ 2 'DEBUG': get_debug_flag(default=False), 是否开启Debug模式 3 'TESTING': False, 是否开启测试模式 4 'PROPAGATE_EXCEPTIONS': None, 5 'PRESERVE_CONTEXT_ON_EXCEPTION': None, 6 'SECRET_KEY': None, 7 'PERMANENT_SESSION_LIFETIME': timedelta(days=31), 8 'USE_X_SENDFILE': False, 9 'LOGGER_NAME': None, 10 'LOGGER_HANDLER_POLICY': 'always', 11 'SERVER_NAME': None, 12 'APPLICATION_ROOT': None, 13 'SESSION_COOKIE_NAME': 'session', 14 'SESSION_COOKIE_DOMAIN': None, 15 'SESSION_COOKIE_PATH': None, 16 'SESSION_COOKIE_HTTPONLY': True, 17 'SESSION_COOKIE_SECURE': False, 18 'SESSION_REFRESH_EACH_REQUEST': True, 19 'MAX_CONTENT_LENGTH': None, 20 'SEND_FILE_MAX_AGE_DEFAULT': timedelta(hours=12), 21 'TRAP_BAD_REQUEST_ERRORS': False, 22 'TRAP_HTTP_EXCEPTIONS': False, 23 'EXPLAIN_TEMPLATE_LOADING': False, 24 'PREFERRED_URL_SCHEME': 'http', 25 'JSON_AS_ASCII': True, 26 'JSON_SORT_KEYS': True, 27 'JSONIFY_PRETTYPRINT_REGULAR': True, 28 'JSONIFY_MIMETYPE': 'application/json', 29 'TEMPLATES_AUTO_RELOAD': None,
路由系统
@app.route('/xxx/<username>') @app.route('/xxx/<int:id>') @app.route('/xxx/<float:id>') @app.route('/xxx/<path:path>') @app.route('/xxx', methods=['GET', 'POST'])
@app.route本质,源码分析
内部源码add_url_rule,所需要传的参数:view_func、endpoint....
代码演示
from flask import Flask,url_for app=Flask(__name__) app.debug=True @app.route('/login',methods=['POST','GET'],endpoint="test") #decorator def login(nid): print(type(nid),nid) return "obi_login" # rule 就是路由 # enpoint,取别名,如果没有就用当前的函数名 # enpoint,不能重复 # methods=["POST","GET"] # view_func 就是我们enpoint,指向的函数,也就是请求该路由的时候,要响应函数 # app.add_url_rule(rule,'取别名,反向解析,login') app.add_url_rule('/login/<strnig:nid>',view_func=login,endpoint="func",methods=["POST","GET"]) """ 取别名: """ #app01.route('/',endpoint="func") def index(): real_url = url_for("test") return real_url app.add_url_rule('/index',view_func=index,methods=["POST","GET"]) if __name__ == '__main__': app.run()
method=[],如果不传参数,默认是视图类,可以只传POST/GET.
路由默认的转换器,有名分组支持的数据类型
DEFAULT_CONVERTERS = { 'default': UnicodeConverter, 'string': UnicodeConverter, 'any': AnyConverter, 'path': PathConverter, 'int': IntegerConverter, 'float': FloatConverter, 'uuid': UUIDConverter, }
初识flask中的CBV视图
cbv视图类的基本写法
#第一种方法 class IndexView(views.View): methods = ['GET'] decorators = [auth, ] def dispatch_request(self): print('Index') return 'Index!' app.add_url_rule('/index', view_func=IndexView.as_view(name='index'))
#第二种方法(通常使用这种) class IndexView(views.MethodView): methods = ['GET','POST'] #指定可以接收的方法有什么,默认可以不写 decorators = [auth, ] #指定自定义的装饰器 def get(self): return 'Index.GET' def post(self): return 'Index.POST' app.add_url_rule('/index', view_func=IndexView.as_view(name='index'))
总结流程:
1.先从flask中导入views
2.写一个类一定要继承views.MethodView
3.在类中写methods = ['GET','POST'],可以指定可接受的请求类型,默认是两种都行
4.在类中写decorators = [auth,]可以指定装饰器,第一个装饰器是最里层函数依次往外包裹
5.在类中写def get(self):用于获取get请求
6.在类中写def post(self):用于获取post请求
7.添加路由的方法使用
app.add_url_rule('路由', view_func=IndexView.as_view(name='自定义一个端点名字'))
其原理是IndexView.ad_view(name='自定义名字')会返回一个函数,name是为这个函数命名,可以通过这个函数进行分发请求等操作。
#IndexView.as_view(name='index')都views.View里面的as_view的view #为什么要as_view(name='index'), #如果不指定,就都是view #所以必须指定
CBV常用的模式
继承的是:MethodView
登录实现
from flask import Flask,render_template,request,redirect,session,url_for app = Flask(__name__) app.debug = True app.secret_key = 'sdfsdfsdfsdf' USERS = { 1:{'name':'张三','age':18,'gender':'男','text':"道路千万条"}, 2:{'name':'李四','age':28,'gender':'男','text':"安全第一条"}, 3:{'name':'王五','age':18,'gender':'女','text':"行车不规范"}, } @app.route('/detail/<int:nid>',methods=['GET']) def detail(nid): info = USERS.get(nid) return render_template('detail.html',info=info) @app.route('/index',methods=['GET']) def index(): return render_template('index.html',user_dict=USERS) def login(): if request.method == "GET": return render_template('login.html') else: # request.query_string user = request.form.get('user') pwd = request.form.get('pwd') if user == 'cxw' and pwd == '123': url=url_for('index') return redirect(url) # session['user_info'] = user return render_template('login.html', error='用户名或密码错误') app.add_url_rule("/login",view_func=login,methods=["GET","POST"]) if __name__ == '__main__': app.run()
本文来自博客园,作者:游走De提莫,转载请注明原文链接:https://www.cnblogs.com/Gaimo/p/11837344.html