python web开发
# WSGI原理
WSGI(Web Server Gateway Interface) ,作为一个规范,定义了Web服务器如何与Python应用程序进行交互,使得使用Python写的Web应用程序可以和Web服务器对接起来。
为什么需要WSGI 在Web部署的方案上,有一个方案是目前应用最广泛的:
- 首先,部署一个Web服务器专门用来处理HTTP协议层面相关的事情,比如如何在一个物理机上提供多个不同的Web服务(单IP多域名,单IP多端口等)这种事情。
- 然后,部署一个用各种语言编写(Java, PHP, Python, Ruby等)的应用程序,这个应用程序会从Web服务器上接收客户端的请求,处理完成后,再返回响应给Web服务器,最后由Web服务器返回给客户端。
那么 Web Server 和 Application 之间就要知道如何进行交互。为了定义Web服务器和应用程序之间的交互过程,就形成了很多不同的规范。比如改进CGI性能的FasgCGI,Java专用的Servlet规范,还有Python专用的WSGI规范等。提出这些规范的目的就是为了定义统一的标准,提升程序的可移植性。
WSGI (Web Server Gateway lnterface) 主要规定了服务器端和应用程序间的接口
Web Server:主要负责HTTP协议请求和响应,但不一定支持WSGI接口访问. 接收来自客户端的HTTP,然后将请求交给Web Application
Web Application:根据请求来调用相应的处理逻辑,生成response;通过Web Server把response发送给客户端
Server端将http请求相关信息、wsgi变量以及一些服务端环境变量添加到environ
传给Application端,Application端处理完所需信息后将http状态码和header通过start_response
回调函数传给Server端,而http响应body则以返回值的形式传给服务端。 见wsgiref.simple_server
源码,参数app为可调用对象,请求处理交由WSGIRequestHandler
可调用对象: 函数、类(callable)、实例instance
def make_server( host, port, app, server_class=WSGIServer, handler_class=WSGIRequestHandler):
"""Create a new WSGI server listening on `host` and `port` for `app`"""
server = server_class((host, port), handler_class)
server.set_app(app)
return server
2
3
4
5
def demo_app(environ,start_response):
from io import StringIO
stdout = StringIO()
print("Hello world!", file=stdout)
print(file=stdout)
h = sorted(environ.items())
for k,v in h:
print(k,'=',repr(v), file=stdout)
start_response("200 OK", [('Content-Type','text/plain; charset=utf-8')])
return [stdout.getvalue().encode("utf-8")]
2
3
4
5
6
7
8
9
10
# wsgi服务器wsgiref
app中需要准备内容,在return之前,需要使用start_response函数准备状态码和响应头的数据。 return可迭代对象,元素是内容的一 部分,bytes类型,参考wsgiref.simple_server.demo_app
函数
wsgiref是Python提供的一个WSGI参考实现库,不适合生产环境使用。wsgiref.simple_server
模块实现一个简单的WSGI HTTP服务器
# WSGI server in Python
from wsgiref.simple_server import make_server
# 方式一:函数形式 httpd= make_server("127.0.0.1",8081, app);
def app(environ, start_response):
response_body = ['%s: %s' % (key, value)
for key, value in sorted(environ.items())]
response_body = '\n'.join(response_body)
status = '200 OK'
response_headers = [('Content-Type', 'text/plain'), ('Content-Length', str(len(response_body)))]
start_response(status, response_headers)
return [response_body.encode('utf8')]
# 方式二:类形式,需为可迭代对象 httpd= make_server("127.0.0.1",8081, MyApp);
class MyApp():
def __init__(self, environ, start_response):
self.environ = environ
self.start_response = start_response
def __iter__(self): #需返回可迭代对象 iter(...)
self.start_response("200 OK", [('Content-Type', 'text/plain'),('Content-Type','text/plain; charset=utf-8')])
yield from ["类形式".encode()];
#方式三:实例形式,callabe httpd= make_server("127.0.0.1",8081, App());
class App():
def __call__(self, environ, start_response):
start_response("200 OK", [('Content-Type', 'text/plain'), ('Content-Type', 'text/plain; charset=utf-8')])
return ["类实例形式".encode()];
httpd = make_server('localhost',8080,application)
# 请求处理完退出,执行一次
#httpd.handle_request()
httpd.serve_forever()
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
# WSGI 服务器作用
- 监听HTTP服务端口 (TCPServer,默认端口80)
- 接收浏览器端的HTTP请求并解析封装成environ环境数据
- 负责调用应用程序,将environ数据和start response方法两个实参传入给Application
- 将应用程序返回的正文封装成HTTP响应报文返回浏览器端
# Django 入门与进阶(上)
01-Django介绍,开发环境准备
django-admin startproject mysite
cd mysite
python manage.py startapp blog
# 将应用添加到setting.py文件的INSTALLED_APPS 变量中, 'blog.apps.BlogConfig',
python manage.py runserver
2
3
4
5
02-Pycharm,创建第一个项目,Django工作流程 03-URL路由系统:配置、URL正则表达式匹配 04-视图:HttpRequest详解1 05-视图:HttpRequest详解2,HttpResponse详解 06-模板:变量、标签、过滤器、继承、导入等
参考: django4.0基础教程:通过指令创建django项目和应用-django教程-Django社区,Django中文网! (opens new window)
Django 文档 | Django 文档 | Django (djangoproject.com) (opens new window)
# 05 第二阶 Django 入门与进阶(下)
01-数据模型:ORM、Model,ORM基本增删改查 02-数据模型:内置管理后台,配置MySQL数据库 03-数据模型:QuerySet序列化,一对一关系模型 04-数据模型:一对多、多对多关系模型 05-多对多关系模型2,内置用户认证系统 06-auth模块、Session与Cookie应用,CSRF防御
# 前端基础 HTML\CSS\JS
01-HTML:基本概念,常用标签 02-CSS:基本使用,常用选择器、常用样式属性2 03-javaScript:基本使用,事件,选择器 04-JavaScript:数据类型,流程控制,表单验证 05-JavaScript:函数,定时器,正则表达式 06-jQuery:基本使用,选择器,常见HTML操作 07-jQuery:前端与后端数据交互 Ajax
# 前端UI框架 Layui
01-Layui介绍,基本使用,后台布局,栅格系统 02-卡片面板,按钮,表单,上传文件 03-数据表格,弹出框
# Web项目实战案例 K8s Dashboard(上)
01-项目概述,API介绍,K8s认证方式 02-K8s API使用案例,K8s平台登录页面认证实现 03-K8s管理平台布局.mp41 o8 E6 [7 q) w/ K 04-前后端开发功能:NS、PV、Node、DP
# Web项目实战案例 K8s Dashboard(中)
01-前后端开发功能:DS、STS、Pod 02-前后端开发功能:SVC、ING、PVC、CM、Se 03-前后端开发功能:初步优化 04-前后端开发功能:创建资源K8s资源 05-前后端开发功能:查看YAML 06前后端开发功能:Node详情页 07前后端开发功能:DP详情页和Pod日志 08-前后端开发功能:容器终端
# Web项目实战案例 K8s Dashboard(下)
01-前后端开发功能:仪表盘 02-生产环境部署Django项目
【No1728】python web运维开发中级视频教程
网盘链接:https://pan.baidu.com/s/1sRoaoHjDZL_5vnwCGyQuCg 提取密码:403x 解压密码:www.javaxxz.com_*UH&5Gj
# flask
Flask是一个Python编写的Web 微框架,让我们可以使用Python语言快速实现一个网站或Web服务。本文参考自Flask官方文档,大部分代码引用自官方文档。
# 安装
pip install flask
编程快速入门 http://docs.jinkan.org/docs/flask/quickstart.html#quickstart 在项目根目录下构建
- webapp包目录,存放flask代码,包内有_init_.py文件
- templates目录,存放模板文件
- static目录,存放is、css等静态文件。其下建立js目录,放入jquery、echarts的is文件
- app.py,入口文件
# Flask实例的源码:
class Flask(_PackageBoundObject):
def __init__(self, import_name, # 指定应用的名字和工程目录,默认为__name__
static_path=None, # 是静态文件存放的路径,会赋值给static_url_path参数
static_url_path=None, # 设置静态文件路由的前缀,默认为“/static”
static_folder='static', # 静态文件的存放目录, 默认值为"static"
template_folder='templates', # 模板文件的存放目录,默认值为"templates"
instance_path=None, # 设置配置文件的路径,在instance_relative_config=True情况下生效
instance_relative_config=False # 设置为True表示配置文件相对于实例路径而不是根路径
root_path=None) # # 应用程序的根路径
2
3
4
5
6
7
8
9
10
from webapps import app
if __name__=="__main__":
app.run(debug=True,port=5000) #调试模式,热启动
2
3
# 蓝图
Flask中,基本上都是route装饰器和视图函数的映射,如果函数很多,代码组织结构会非常乱。蓝图Blueprint,就是Flask中模块化的技术
Blueprint构造参数
- name,蓝图名字,注册在app的蓝图字典中用的key
- import_name,用来计算蓝图模块所在的路径,一般写
__name__
- root_path,指定蓝图模块所在的路径,如果为None,使用import_name计算得到
- template folder
- 相对于蓝图的root_path,假设就是books.py的目录path1,那么上面的模板文件路径0path1/temp/xxx.html
- 模板是一批搜索路径,会依次搜索这些模板路径,找到第一个返回。如果在找到本蓝图模板之前,有一个同名的模板,那么本蓝图模板文件就不能被找到了
- url_prefix,指定本蓝图模块的路径前缀。app.register_hlueprint注册蓝图时,也可以对当前蓝图指定url_prefix,它将覆盖蓝图中的定义
from flask import Blueprint, Flask, Request, Response, jsonify, render_template, request, redirect, url_for
book = Blueprint("book",__name__, url_prefix="/book", template_folder="tpl/book");
@book.route('/saveUI')
def saveUI():
return render_template("saveUI.html"); # 模板默认在templates目录下找
2
3
4
5
6
7
import io
import flask
from flask import Flask, Request, Response, jsonify, render_template, request, redirect, url_for
# 初始化应用,指定模板目录template_folder、静态目录static_folder,见构造init方法
app:Flask = Flask(import_name=__name__, static_url_path="/", template_folder="templates") # 静态默认访问/static
# 添加模块
from .book import book
app.register_blueprint(book); # url_prefix路径前缀,会覆盖模块里
2
3
4
5
6
7
8
9
10
# jinja2模板
pip install Jinja2
<h2>九九乘法表:</h2>
{% for i in range(1,10) %}
{% for j in range(1,10) %}
{{i}} X {{ j }} = {{"%s"|format( i*j) }} <br/>
{% if j%9==0 %}
<br/>
{% endif %}
{% endfor %}
{% endfor %}
2
3
4
5
6
7
8
9
10
# 过滤器
变量可以通过 过滤器 修改。过滤器与变量用管道符号( |
)分割,并且也 可以用圆括号传递可选参数。多个过滤器可以链式调用,前一个过滤器的输出会被作为 后一个过滤器的输入。
例如 会移除 name 中的所有 HTML 标签并且改写 为标题样式的大小写格式。过滤器接受带圆括号的参数,如同函数调用。这个例子会 把一个列表用逗号连接起来:
。
# 代码提示和高亮
参考: