1 预备知识

http(超文本传输协议)与www(World Wide Web,万维网 ) 的工作流
网页(文字、图像、声音、视频….) HTML文档(CSS,Javascript…) .html
网站,网站是一组相关网页文件(包含网页的媒体素材文件)组成的集合,它的表现形式一个文件夹(目录)
Web服务器(程序)
WWW采用的是B(Browser,浏览器(客户端))/S(Server,Web服务器)工作模式。
URL 统一资源定位器
Python Web程序设计基础 - 图1
常见的Web服务器软件:Windows操作系统:IIS(微软) Apahce Nginx …..
Linux操作系统:Apahce Nginx …..

2.使用Python自带的Web服务器程序

Python自带的Web服务器程序通常用于Web应用开发中的测试用途,不用作生产环境下部署。

2.1 准备网站根目录和网页

创建网站根目录e:\wwwroot.
在网站根目录中创建网页index.html,代码如下:

  1. <html>
  2. <head>
  3. <title>测试用的网站首页</title>
  4. </head>
  5. <body>
  6. <h1>测试网站的首页!!</h1>
  7. </body>
  8. </html>

2.2 启动Python自带的Web服务器程序

python -m http.server 8001
此时,服务会监听 0.0.0.0:8001。
帮助: server.py [-h] [—cgi] [—bind ADDRESS] [—directory DIRECTORY] [port]
如果不指定directory,则默认当前目录。

2.3 在客户端使用浏览器访问Web站点

在客户端浏览器的地址栏中输入http://网址:端口/index.html

3 Python的CGI编程

3.1 CGI基础

3.1.1 CGI(通用网关接口)简介

Web 最初目的是在全球范围内对文档进行在线存储和归档(大多用于教学和科研)。这些文件通常用静态文本表示,一般是 HTML。随着因特网和 Web 服务的发展,除了浏览之外,还需要处理用户的输入。
现在服务器的处理过程一般是:第一步Web服务器从客户端接受到请求(GET或POST),并调用相应的程序;然后等待HTML页面,与此同时客户端也在等待;当应用程序处理完成,会将动态生成的HTML页面返回服务器端;然后服务器再将这个结果返回给用户。
Python Web程序设计基础 - 图2
创建 HTML 的 CGI 应用程序通常是用高级编程语言来实现的,可以接受、处理用户数据,向服务器端返回 HTML 页面。在接触 CGI 之前,需要告诫的是,一般生产环境的 Web应用都不再使用 CGI 了。 如今 Web 服务器典型的部件有 Apache 和集成的数据库访问部件(MySQL 或者 PostgreSQL)、Java(Tomcat)、PHP和各种动态语言(如 Python 或 Ruby)模块,以及 SSL/security。
Web 服务器将根据 CGI 程序的类型决定数据向 CGI 程序的传送方式,一般是通过标准输入/输出流和环境变量来与 CGI 程序间传递数据。如下图所示:
image.png
CGI 程序通过标准输入(STDIN)和标准输出(STDOUT)来进行输入输出。此外 CGI 程序还通过环境变量来得到输入,操作系统提供了许多环境变量,它们定义了程序的执行环境,应用程序可以存取它们。Web 服务器和 CGI 接口又另外设置了一些环境变量,用来向 CGI 程序传递一些重要的参数。

3.1.2 CGI 应用程序

  • CGI 应用程序和典型的应用程序有些不同,主要的区别在于输入、输出以及用户和程序交互方面。
  • CGI应用程序的输入是从Web 客户端获得的用户提供的表单数据,而不是从服务器或者硬盘上获得;
  • CGI应用程序的输出将会发送回连接的 Web 客户端,而不是发送到屏幕、GUI窗口或者硬盘上。这些返回的数据必须是具有一系列有效头文件的 HTML 标签数据;
  • CGI应用程序中,用户与脚本之间没有任何交互。所有的交互都将发生在 Web 客户端(基于用户的行为)、Web 服务器端和 CGI 应用程序间。

    3.1.3 CGI 模块

    cgi 模块中有个主要类:FieldStorage 类,其完成了所有的工作。Python CGI脚本启动的时候实例化这个类,实例化完成后,其中会包含一个类似字典的对象,它具有一系列键值对,键是通过表单传入的表单条目的名字,值则包含相应的数据。
    这些值可以是以下三种对象之一:
    1.FieldStorage对象;
    2.另一个名为MiniFieldStorage 类的类似实例,用在没有文件上传或 mulitple-part 格式数据的情况下;
    3.它们还可以是这些对象的列表。当表单中的某个字段有多个输入值时就会产生这种对象。

    3.1.3 cgitb 模块

    Web 服务器在收到无法理解的响应时,会抛弃这个响应,返回“500 错误”。500 是一个HTTP 响应编码,它表示发生了一个内部服务器错误。一般是服务器所执行的应用程序发生了错误。此时在浏览器中给出的提示消息没什么用,要么是空白,要么显示“内部服务器错误”或类似消息。
    当 Python 程序在命令行或集成开发环境(IDE)中运行时,发生的错误会生成回溯消息,指出错误发生的位置,在浏览器中不会显示回溯消息。若想在浏览器中看到的是 Web 应用程序的回溯信息,而不是“内部服务器错误”,可以使用 cgitb 模块。其使用方法只需要将下面代码插入CGI程序中并调用:
    import cgitb cgitb.enable()

    3.2 构建CGI应用程序

    3.2.1 启动python自带Web服务器

    为了用 Python 进行 CGI 开发,首先需要安装一个 Web 服务器,将其配置成可以处理Python CGI 请求,然后让 Web 服务器访问 CGI 脚本。
    生产环境中的服务器。如果需要一个真正的 Web 服务器,可以下载并安装 Apache、ligHTTPD 或 thttpd。Apache中有许多插件或模块可以处理 Python CGI;
    开发人员服务器。出于学习目的或者想建立小型 Web 站点,使用 Python 自身带的 Web 服务器就已经足够,在Python3中构建步骤如下: :::danger 1.在建好的文件夹下打开cmd窗口,进入网站根目录,python命令窗口下输入:
    python -m http.server —cgi
    2.在该文件夹下建立新文件夹,命名为cgi-bin;
    3.将python脚本放入该文件夹下,就可以在浏览器中输入:http://localhost:8000/cgi-bin/xxx.py来查看。 :::

    3.2.2. 创建静态网页和CGI应用程序

    创建静态网页
    1. <HTML>
    2. <HEAD>
    3. <TITLE> Friends CGI Demo (static screen) </TITLE></HEAD>
    4. <BODY>
    5. <H3>Friends list for: <I>NEW USER</I></H3>
    6. <FORM ACTION="/cgi-bin/friends1.py">
    7. <B>Enter your Name:</B>
    8. <INPUT TYPE=text NAME=person VALUE="NEW USER" SIZE=15>
    9. <P><B>How many friends do you have?</B>
    10. <INPUT TYPE=radio NAME=howmany VALUE="0" CHECKED> 0
    11. <INPUT TYPE=radio NAME=howmany VALUE="10"> 10
    12. <INPUT TYPE=radio NAME=howmany VALUE="25"> 25
    13. <INPUT TYPE=radio NAME=howmany VALUE="50"> 50
    14. <INPUT TYPE=radio NAME=howmany VALUE="100"> 100
    15. <P><INPUT TYPE=submit>
    16. </FORM>
    17. </BODY>
    18. </HTML>
    创建CGI程序 ```python import cgi

reshtml = ‘’’Content-Type: text/html

Friends list for: %s

Your name is: %s

You have %s friends. ‘’’

form = cgi.FieldStorage() who = form[‘person’].value howmany = form[‘howmany’].value print(reshtml % (who, who, howmany))

  1. <a name="EdIlv"></a>
  2. # 4 WSGI(Web服务器网关接口)
  3. <a name="h7qpI"></a>
  4. ## 4.1 WSGI的相关概念
  5. <a name="m2Y33"></a>
  6. ### 4.1.1 什么是WSGI
  7. WSGI,全称Python Web Server Gateway Interface,是在PEP333中(PEP3333进行了补充)定义的一种协议,目的是将http底层和[框架](https://so.csdn.net/so/search?q=%E6%A1%86%E6%9E%B6&spm=1001.2101.3001.7020)层解耦。<br />WSGI协议分为两部分,分别为WSGI Server和WSGI Application,WSGI Server负责接受客户端请求、解析请求、并按照协议规范将请求转发给WSGI Application,同时负责接受WSGI Application的响应并发送给客户端;WSGI Application负责接受由WSGI Server发送过来的请求,实现业务处理逻辑,并将标准的响应发回给WSGI Server:<br />![image.png](https://cdn.nlark.com/yuque/0/2022/png/28265088/1654420375793-96be9567-5d93-4395-b48a-277302acd115.png#clientId=u32ddad5f-0719-4&crop=0&crop=0&crop=1&crop=1&from=paste&height=86&id=u8f3ad2e3&margin=%5Bobject%20Object%5D&name=image.png&originHeight=59&originWidth=439&originalType=url&ratio=1&rotation=0&showTitle=false&size=11193&status=done&style=none&taskId=u7e1d874e-0a0f-4cf0-b07c-ab3b92270ff&title=&width=639)
  8. <a name="cFfCN"></a>
  9. ### 4.1.2 为什么需要WSGI规范
  10. 在Web部署的方案上,有一个方案是目前应用最广泛的:
  11. - 首先,部署一个Web服务器专门用来处理HTTP协议层面相关的事情,比如如何在一个物理机上提供多个不同的Web服务(单IP多域名,单IP多端口等)这种事情。
  12. - 然后,部署一个用各种语言编写(Java, PHP, Python, Ruby等)的应用程序,这个应用程序会从Web服务器上接收客户端的请求,处理完成后,再返回响应给Web服务器,最后由Web服务器返回给客户端。
  13. 那么,要采用这种方案,Web服务器和应用程序之间就要知道如何进行交互。为了定义Web服务器和应用程序之间的交互过程,就形成了很多不同的规范。这种规范里最早的一个是CGI。后来又出现了很多这样的规范。比如改进CGI性能的FastCGI,Java专用的Servlet规范,还有Python专用的WSGI规范等。提出这些规范的目的就是为了定义统一的标准,提升程序的可移植性。在WSGI规范的最开始的PEP-333中一开始就描述了为什么需要WSGI规范。
  14. <a name="jUQNH"></a>
  15. ### 4.1.3 WSGI 是怎么工作的
  16. 在WSGI中定义了两个角色,Web服务器端称为server或者gateway,应用程序端称为application或者framework(因为WSGI的应用程序端的规范一般都是由具体的框架来实现的)。我们下面统一使用server和application这两个术语。<br />server端会先收到用户的请求,然后会根据规范的要求调用application端,如下图所示:<br />![20210407151724353.png](https://cdn.nlark.com/yuque/0/2022/png/28265088/1654434907302-87e5b422-6c10-4880-96b1-f2a7ca2656e5.png#clientId=u5c53bedf-404f-4&crop=0&crop=0&crop=1&crop=1&from=paste&height=142&id=u2bcafa93&margin=%5Bobject%20Object%5D&name=20210407151724353.png&originHeight=198&originWidth=812&originalType=binary&ratio=1&rotation=0&showTitle=false&size=46209&status=done&style=none&taskId=ucb57d375-161a-4d47-8dd5-c3dd617320c&title=&width=581)<br />调用的结果会被封装成HTTP响应后再发送给客户端。<br />要使用WSGI,需要分别实现server角色和application角色。<br />Application端的实现一般是由Python的各种框架来实现的,比如Django, web.py等,一般开发者不需要关心WSGI的实现,框架会会提供接口让开发者获取HTTP请求的内容以及发送HTTP响应;
  17. :::info
  18. WSGI web服务器和应用程序<br />WSGI web服务器
  19. - 本质上是一个TCP服务器,监听在特定的端口上。
  20. - 支持HTTP协议,能够解析HTTP请求报文,能够按HTTP协议将响应数据封装为报文并返回给浏览器。
  21. - 实现了WSGI协议,该协议约定了和应用程序之间的接口,即url到app之间的映射。
  22. WSGI应用程序
  23. - 遵从WSGI协议。
  24. - 本身是一个可调用对象。
  25. - 调用start_response,返回响应头部。
  26. - 返回包含正文的可迭代对象。
  27. :::
  28. Server端的实现会比较复杂一点,这个主要是因为软件架构的原因。一般常用的Web服务器,如Apache和nginx,都不会内置WSGI的支持,而是通过扩展来完成。比如Apache服务器,会通过扩展模块mod_wsgi来支持WSGI。Apache和mod_wsgi之间通过程序内部接口传递信息,mod_wsgi会实现WSGI的server端、进程管理以及对application的调用。Nginx上一般是用proxy的方式,用nginx的协议将请求封装好,发送给应用服务器,比如uWSGI,应用服务器会实现WSGI的服务端、进程管理以及对application的调用。<br />![20210407151737245.png](https://cdn.nlark.com/yuque/0/2022/png/28265088/1654434978667-2f3dbade-5508-4e88-9b9c-5067a2d966f6.png#clientId=u5c53bedf-404f-4&crop=0&crop=0&crop=1&crop=1&from=paste&height=408&id=uaf6954d0&margin=%5Bobject%20Object%5D&name=20210407151737245.png&originHeight=1004&originWidth=1910&originalType=binary&ratio=1&rotation=0&showTitle=false&size=123032&status=done&style=none&taskId=u7b955164-8153-47f8-a09b-f203db073ca&title=&width=776)
  29. <a name="TQgKx"></a>
  30. ## 4.2 体验WSGI的简单实现
  31. 实现一个遵循WSGI的简单应用
  32. ```python
  33. def application(environ,start_response):
  34. start_response(status,response_headers)
  35. return [response_body]

如上所示,满足的条件有:

  • 该应用必须是一个可调用对象,无论是函数、方法还是一个实现了call 方法的对象;
  • 应用必须接收两个参数,一般用environ和start_response,这两个参数都是由服务器传递进来;前一个是字典,包含了HTTP请求的一些字段(CGI字段);后一个是回调函数,由此应用调用,给Web服务器返回HTTP状态码和其他头部,状态码应为string,而头部应为由二元tuple组成的 list;
  • 最后该应用需要返回一个HTTP body,是一个bytes组成的可迭代对象(如list)。

按照这样的接口规范,现在来写一个返回 “Hello World” 的Web应用:

  1. from wsgiref.simple_server import make_server
  2. def application(environ,start_response):
  3. if environ["REQUEST_METHOD"] == "GET": # 判断请求方法是否是GET
  4. start_response('200 OK',[('Content-Type', 'text/html')]) # 回调
  5. return [b'<h1>Hello World!This is a example of WSGI!</h1>'] # 返回一个可迭代对象
  6. httpd=make_server('127.0.0.1',port=9005,app=application)
  7. if __name__ == "__main__":
  8. httpd.serve_forever()

在浏览器中使用http://127.0.0.1:9005 打得开Web页面。

5 Web应用开发框架Django简介

5.1 Web应用框架简介

5.1.1 Web应用框架的简介

  • web应用框架(web application framework),是用于进行web开发的一套软件架构。框架,特指为解决一个开放性问题而设计的具有一定约束性质的支撑结构。
  • 大多数的web框架提供了一套开发和部署网站的方式。为web的行为提供了一套支持支持的方法。
  • 使用web框架,很多的业务逻辑外的功能不需要自己再去完善,而是使用框架已有的功能就可以。

    5.1.2 web应用框架的功能

  • 对于所有的web应用,本质上就是一个socket服务端,web浏览器是客户端。web框架使得在进行web应用开发的时候,减少了工作量。

  • web框架主要用于动态网络开发,动态网络主要是指现在的主要的页面,可以实现数据的交互和业务功能的完善。
  • 使用web框架进行web开发的时候,在进行数据缓存、数据库访问、数据安全校验等方面,不需要自己再重新实现,而是将业务逻辑相关的代码写入框架就可以。也就是说,通过对web框架进行主观上的“缝缝补补”,就可以实现自己进行web开发的需求了。

    5.1.3 Python的主流Web框架

    目前Python主流的框架有Django和Flask等。

  • Django是一个比较重量级的框架,几乎所有的功能都帮助开发者写好了,有时候如果想做一个简单的网站,并不需要太多功能,这时候使用Django的话,就比较不合适,因为在部署网站的时候会导致很多不必要的功能也部署了进来。

  • Flask是一个轻量级的框架,一些核心的功能实现了,但是实现的功能并没有Django那么多,这样可以进行自己的发挥,在Flask的基础上,如果想实现更多的功能,可以很方便地加入。

    5.2 Django的简介

    5.2.1 关于Django

    Python下有许多款不同的 Web 框架。Django是重量级选手中最有代表性的一位。许多成功的网站和APP都基于Django。

  • Django 是一个开放源代码的 Web 应用框架,由 Python 写成。

  • Django 遵守 BSD 版权,初次发布于 2005 年 7 月, 并于 2008 年 9 月发布了第一个正式版本 1.0 。
  • Django 采用了 MVT 的软件设计模式,即模型(Model),视图(View)和模板(Template)。

image.png

5.2.2 MVC 与 MTV模型

MVC 模型
MVC 模式(Model–view–controller)是软件工程中的一种软件架构模式,把软件系统分为三个基本部分:模型(Model)、视图(View)和控制器(Controller)。
MVC 以一种插件式的、松耦合的方式连接在一起。

  • 模型(M)- 编写程序应有的功能,负责业务对象与数据库的映射(ORM)。
  • 视图(V)- 图形界面,负责与用户的交互(页面)。
  • 控制器(C)- 负责转发请求,对请求进行处理。

简易图:
image.png
用户操作流程图:
image.png


MTV 模型
Django 的 MTV 模式本质上和 MVC 是一样的,也是为了各组件间保持松耦合关系,只是定义上有些许不同,Django 的 MTV 分别是指:

  • M 表示模型(Model):编写程序应有的功能,负责业务对象与数据库的映射(ORM)。
  • T 表示模板 (Template):负责如何把页面(html)展示给用户。
  • V 表示视图(View):负责业务逻辑,并在适当时候调用 Model和 Template。

除了以上三层之外,还需要一个 URL 分发器,它的作用是将一个个 URL 的页面请求分发给不同的 View 处理,View 再调用相应的 Model 和 Template,MTV 的响应模式如下所示:
简易图:
image.png
用户操作流程图:
image.png
解析:
用户通过浏览器向我们的服务器发起一个请求(request),这个请求会去访问视图函数:

  • a.如果不涉及到数据调用,那么这个时候视图函数直接返回一个模板也就是一个网页给用户。
  • b.如果涉及到数据调用,那么视图函数调用模型,模型去数据库查找数据,然后逐级返回。

视图函数把返回的数据填充到模板中空格中,最后返回网页给用户。

5.3 Django的安装

安装django之前需要先正确安装了Python。
可以使用多种方法安装Django.
pip 命令安装方法
如果还未安装 pip 工具,可查看:Python pip 安装与使用
pip3 install Django -i https://pypi.tuna.tsinghua.edu.cn/simple
-i https://pypi.tuna.tsinghua.edu.cn/simple 指定清华镜像源,下载速度更快。
指定 Django 的下载版本(3.0.6 可以改成你要的版本):
sudo pip3 install Django==3.0.6 -i https://pypi.tuna.tsinghua.edu.cn/simple
如果 pip < 1.4,安装方法如下:
pip install https://www.djangoproject.com/download/1.11a1/tarball/

5.4 体验简单的Django项目

5.4.1 创建与一个新的Django项目

安装 Django 之后,您现在应该已经有了可用的管理工具 django-admin,Windows 如果没有配置环境变量可以用 django-admin
使用 django-admin 来创建 HelloWorld 项目:
django-admin startproject HelloWorld
创建完成后我们可以查看下项目的目录结构

目录说明:

  • HelloWorld: 项目的容器。
  • manage.py: 一个实用的命令行工具,可让你以各种方式与该 Django 项目进行交互。
  • HelloWorld/init.py: 一个空文件,告诉 Python 该目录是一个 Python 包。
  • HelloWorld/asgi.py: 一个 ASGI 兼容的 Web 服务器的入口,以便运行你的项目。
  • HelloWorld/settings.py: 该 Django 项目的设置/配置。
  • HelloWorld/urls.py: 该 Django 项目的 URL 声明; 一份由 Django 驱动的网站”目录”。
  • HelloWorld/wsgi.py: 一个 WSGI 兼容的 Web 服务器的入口,以便运行你的项目。

接下来我们进入 HelloWorld 目录输入以下命令,启动服务器:
python manage.py runserver 0.0.0.0:8000
0.0.0.0 让其它电脑可连接到开发服务器,8000 为端口号。如果不说明,那么端口号默认为 8000。
在浏览器输入你服务器的 ip(这里我们输入本机 IP 地址: 127.0.0.1:8000) 及端口号,如果正常启动,输出结果如下:

5.4.2 视图和 URL 配置

在先前创建的 HelloWorld 目录下的 HelloWorld 目录新建一个 views.py 文件,并输入代码:

  1. from django.http import HttpResponse
  2. def hello(request):
  3. return HttpResponse("Hello world ! ")

接着,绑定 URL 与视图函数。打开 urls.py 文件,删除原来代码,将以下代码复制粘贴到 urls.py 文件中:

  1. from django.urls import re_path as url
  2. from . import views
  3. urlpatterns = [
  4. url(r'^$', views.hello),
  5. ]

整个目录结构如下:
image.png
在浏览器输入你服务器的 ip(这里我们输入本机 IP 地址: 127.0.0.1:8000) 及端口号