mini web框架示例
web框架:
使用web框架专门负责处理用户的动态资源请求,这个web框架其实就是一个为web服务器提供服务的应用程序

什么是路由?
路由就是请求的url到处理函数的映射,也就是说提前把请求的URL和处理函数关联好
管理路由可以使用一个路由列表进行管理

web.py文件:
importsocketimportosimportthreadingimportsysimportframework#http协议的web服务器类classHttpWebServer(object):def__init__(self,port):#创建tcp服务端套接字tcp_server_socket=socket.socket(socket.AF_INET,socket.SOCK_STREAM)#设置端口号复用,程序退出端口号立即释放tcp_server_socket.setsockopt(socket.SOL_SOCKET,socket.SO_REUSEADDR,True)#绑定端口号tcp_server_socket.bind(("",port))#设置监听tcp_server_socket.listen(128)#把tcp服务器的套接字作为web服务器对象的属性self.tcp_server_socket=tcp_server_socket#处理客户端请求@staticmethoddefhandle_client_request(new_socket):#接收客户端的请求信息recv_data=new_socket.recv(4096)#判断接收的数据长度是否为0iflen(recv_data)==0:new_socket.close()return#对二进制数据进行解码recv_content=recv_data.decode("utf-8")print(recv_content)#对数据按照空格进行分割request_list=recv_content.split("",maxsplit=2)#获取请求的资源路径request_path=request_list[1]print(request_path)#判断请求的是否是根目录,如果是根目录设置返回的信息ifrequest_path=="/":request_path="/index.html"#判断是否是动态资源请求,以后把后缀是.html的请求任务是动态资源请求ifrequest_path.endswith(".html"):"""动态资源请求"""#动态资源请求找web框架进行处理,需要把请求参数给web框架#准备给web框架的参数信息,都要放到字典里面env={"request_path":request_path,#传入请求头信息,额外的参数可以在字典里面在进行添加}#使用框架处理动态资源请求,#1.web框架需要把处理结果返回给web服务器,#2.web服务器负责把返回的结果封装成响应报文发送给浏览器status,headers,response_body=framework.handle_request(env)print(status,headers,response_body)#响应行response_line="HTTP/1.1%s\r\n"%status#响应头response_header=""forheaderinheaders:response_header+="%s:%s\r\n"%header#响应报文response_data=(response_line+response_header+"\r\n"+response_body).encode("utf-8")#发送响应报文数据给浏览器new_socket.send(response_data)#关闭连接new_socket.close()else:"""静态资源请求"""#1.os.path.exits#os.path.exists("static/"+request_path)#2.try-excepttry:#打开文件读取文件中的数据,提示:这里使用rb模式,兼容打开图片文件withopen("static"+request_path,"rb")asfile:#这里的file表示打开文件的对象file_data=file.read()#提示:withopen关闭文件这步操作不用程序员来完成,系统帮我们来完成exceptExceptionase:#代码执行到此,说明没有请求的该文件,返回404状态信息#响应行response_line="HTTP/1.1404NotFound\r\n"#响应头response_header="Server:PWS/1.0\r\n"#读取404页面数据withopen("static/error.html","rb")asfile:file_data=file.read()#响应体response_body=file_data#把数据封装成http响应报文格式的数据response=(response_line+response_header+"\r\n").encode("utf-8")+response_body#发送给浏览器的响应报文数据new_socket.send(response)else:#代码执行到此,说明文件存在,返回200状态信息#响应行response_line="HTTP/1.1200OK\r\n"#响应头response_header="Server:PWS/1.0\r\n"#响应体response_body=file_data#把数据封装成http响应报文格式的数据response=(response_line+response_header+"\r\n").encode("utf-8")+response_body#发送给浏览器的响应报文数据new_socket.send(response)finally:#关闭服务于客户端的套接字new_socket.close()#启动服务器的方法defstart(self):#循环等待接受客户端的连接请求whileTrue:#等待接受客户端的连接请求new_socket,ip_port=self.tcp_server_socket.accept()#代码执行到此,说明连接建立成功sub_thread=threading.Thread(target=self.handle_client_request,args=(new_socket,))#设置成为守护主线程sub_thread.setDaemon(True)#启动子线程执行对应的任务sub_thread.start()defmain():##获取终端命令行参数#params=sys.argv#iflen(params)!=2:#print("执行的命令格式如下:python3xxx.py9000")#return#####判断第二个参数是否都是由数字组成的字符串#ifnotparams[1].isdigit():#print("执行的命令格式如下:python3xxx.py9000")#return#####代码执行到此,说明命令行参数的个数一定2个并且第二个参数是由数字组成的字符串#port=int(params[1])#创建web服务器web_server=HttpWebServer(8000)#启动服务器web_server.start()#判断是否是主模块的代码if__name__=='__main__':main()framework.py文件:"""web框架的职责专门负责处理动态资源请求"""importtimeroute_list=[]#定义带有参数的装饰器defroute(path):defdecorator(func):#装饰器执行的时候就需要把路由添加到路由列表里route_list.append((path,func))definner():result=func();returnresultreturninnerreturndecorator#获取首页数据@route("/index.html")defindex():#状态信息status="200OK"#响应头信息response_header=[("Server","PWS/1.1")]#1.打开指定模板文件,读取模板文件中的数据withopen("template/index.html","r",encoding='utf-8')asfile:file_data=file.read()#2.查询数据库,模板里面的模板变量替换成以后从数据库里查询的数据#web框架处理后的数据#获取当前时间,模拟数据库内容data=time.ctime()response_body=file_data.replace("{%content%}",data)#这里返回的是元组returnstatus,response_header,response_body#获取个人中心数据@route("/center.html")defcenter():#状态信息status="200OK"#响应头信息response_header=[("Server","PWS/1.1")]#1.打开指定模板文件,读取模板文件中的数据withopen("template/center.html","r",encoding='utf-8')asfile:file_data=file.read()#2.查询数据库,模板里面的模板变量替换成以后从数据库里查询的数据#web框架处理后的数据#获取当前时间,模拟数据库内容data=time.ctime()response_body=file_data.replace("{%content%}",data)#这里返回的是元组returnstatus,response_header,response_body#处理没有找到的动态资源defnot_found():#状态信息status="404NotFound"#响应头信息response_header=[("Server","PWS/1.1")]#web框架处理后的数据data="notfound"#这里返回的是元组returnstatus,response_header,data#处理动态资源请求defhandle_request(env):#获取动态的请求资源路径request_path=env["request_path"]print("动态资源请求的地址:",request_path)#判断请求的动态资源路径,选择指定的函数处理对应的动态资源请求forpath,funcinroute_list:ifrequest_path==path:result=func()returnresultelse:result=not_found()returnresult#ifrequest_path=="/index.html":##获取首页数据#result=index()##把处理后的结果返回给web服务器使用,让web服务器拼接响应报文时使用#returnresult#elifrequest_path=="/center.html":##个人中心#result=center()#returnresult#else:##没有动态资源数据,返回404状态信息#result=not_found()##把处理后的结果返回给web服务器使用,让web服务器拼接响应报文时使用#returnresultif__name__=="__main__":print(route_list)
framework.py文件:
"""web框架的职责专门负责处理动态资源请求"""
import time
route_list=[]
#定义带有参数的装饰器
def route(path):def decorator(func):#装饰器执行的时候就需要把路由添加到路由列表里route_list.append((path, func))def inner():result=func();return resultreturn innerreturn decorator# 获取首页数据
@route("/index.html")
def index():# 状态信息status = "200 OK"# 响应头信息response_header = [("Server", "PWS/1.1")]# 1.打开指定模板文件,读取模板文件中的数据with open("template/index.html","r",encoding='utf-8') as file:file_data=file.read()# 2.查询数据库,模板里面的模板变量替换成以后从数据库里查询的数据# web框架处理后的数据# 获取当前时间,模拟数据库内容data = time.ctime()response_body=file_data.replace("{%content%}",data)# 这里返回的是元组return status, response_header, response_body#获取个人中心数据
@route("/center.html")
def center():# 状态信息status = "200 OK"# 响应头信息response_header = [("Server", "PWS/1.1")]# 1.打开指定模板文件,读取模板文件中的数据with open("template/center.html","r",encoding='utf-8') as file:file_data=file.read()# 2.查询数据库,模板里面的模板变量替换成以后从数据库里查询的数据# web框架处理后的数据# 获取当前时间,模拟数据库内容data = time.ctime()response_body=file_data.replace("{%content%}",data)# 这里返回的是元组return status, response_header, response_body# 处理没有找到的动态资源
def not_found():# 状态信息status = "404 Not Found"# 响应头信息response_header = [("Server", "PWS/1.1")]# web框架处理后的数据data = "not found"# 这里返回的是元组return status, response_header, data# 处理动态资源请求
def handle_request(env):# 获取动态的请求资源路径request_path = env["request_path"]print("动态资源请求的地址:", request_path)# 判断请求的动态资源路径,选择指定的函数处理对应的动态资源请求for path, func in route_list:if request_path == path:result = func()return resultelse:result = not_found()return result# if request_path == "/index.html":# # 获取首页数据# result = index()# # 把处理后的结果返回给web服务器使用,让web服务器拼接响应报文时使用# return result# elif request_path=="/center.html":# #个人中心# result=center()# return result# else:# # 没有动态资源数据, 返回404状态信息# result = not_found()# # 把处理后的结果返回给web服务器使用,让web服务器拼接响应报文时使用# return result
if __name__=="__main__":print(route_list)
相关文章:
mini web框架示例
web框架: 使用web框架专门负责处理用户的动态资源请求,这个web框架其实就是一个为web服务器提供服务的应用程序 什么是路由? 路由就是请求的url到处理函数的映射,也就是说提前把请求的URL和处理函数关联好 管理路由可以使用一个…...
基于C#开发web网页管理系统模板流程-主界面统计功能完善
点击返回目录-> 基于C#开发web网页管理系统模板流程-总集篇-CSDN博客 前言 紧接上篇->基于C#开发web网页管理系统模板流程-主界面管理员入库和出库功能完善_c#web程序设计-CSDN博客 统计功能是管理系统很常见的功能,例如仓库管理系统要统计某时间段的出入库以…...
chromedriver114以后版本下载地址汇总chromedriver所有版本下载地址汇总国内源下载
谷歌浏览器版本经常会升级,chromedriver 也得下载匹配的版本 chromedriver 114以前版本下载地址https://registry.npmmirror.com/binary.html?pathchromedriver/ 但是自从115版本及其以后网站就找不到了,因此整理了截止2024年6月16日前所有在windows x6…...
x86计算机的启动初期流程 Linux 启动流程
x86计算机的启动初期流程 CPU: step1,加点开机,cpu自己初始化 step2,cpu 从物理地址 0xFFFFFFF0h 取指令执行;此处存放BIOS代码,这些代码可以是由主板自动从 EEPROM中拷贝至此内存地址处;即下…...
P450Rdb: CYP450数据库--地表最强系列--文献精读24
P450Rdb: A manually curated database of reactions catalyzed by cytochrome P450 enzymes P450Rdb: 一个人工整理的细胞色素P450酶催化反应数据库 http://www.cellknowledge.com.cn/p450rdb/ 还有一篇类似CYP450综述-20年-地表最强系列-文献精读-4 要点: P450…...
ubuntu 22.04下载和安装
ubuntu镜像: https://www.releases.ubuntu.com/22.04/ 然后下载vmwareworkstation16 密钥 ZF3R0-FHED2-M80TY-8QYGC-NPKYF...
Fegin如何传参form-data文件
Form-data传输file参数,这个大家都比较清楚,那么针对于Fegin参数file参数该如何操作呢!下面截图来找到对应的参数关系。 一、之前我们在postMan中是这种传参的,那么如果使用Feigin来传输文件File 二、在Fegin中传form-data参数&a…...
解决 Visual C++ 17.5 __cplusplus 始终为 199711L 的问题
目录 软件环境问题描述查阅资料解决问题参考文献 软件环境 Visual Studio 2022, Visual C, Version 17.5.4 问题描述 在应用 https://github.com/ToniLipponen/cpp-sqlite 的过程中,发现源代码文件 sqlite.hpp 中,有一处宏,和本项目的 C L…...
Mac M3 Pro安装Hadoop-3.3.6
1、下载Hadoop安装包 可以到官方网站下载,也可以使用网盘下载 官网下载地址:Hadoop官网下载地址 网盘地址:https://pan.baidu.com/s/1p4BXq2mvby2B76lmpiEjnA?pwdr62r提取码: r62r 2、解压并添加环境变量 # 将安装包移动到指定目录 mv …...
mac下Xcode在iphone真机上测试运行iOS软件
最近一个需求需要在iPhone真机上测试一个视频直播的项目。 需要解决如何将项目 app 安装到真机上 在进行真机调试。 安装Xcode 直接在App Store上搜索Xcode安装即可。 关键是要安装Simulator。项目需要安装iOS17.5但是由于安装包太大,并且网络不稳定的原因。在Xco…...
Mysql(一):深入理解Mysql索引底层数据结构与算法
众所众知,MySql的查询效率以及查询方式,基本上和索引息息相关,所以,我们一定要对MySql的索引有一个具体到数据底层上的认知。 这一次也是借着整理的机会,和大家一起重新复习一下MySql的索引底层。 本节也主要有一下的…...
WebMvcConfigurer配置不当导致鉴权失败
最近同事说他们有个新需求,需要对接口进行加解密,所以他给项目配置了一个拦截器,但这个拦截器直接导致了所有接口鉴权失败,每次调用接口都是提示没有session信息。 公司内的所有java项目是公用同一套基础依赖,所以我也…...
微信小程序毕业设计-实验室管理系统项目开发实战(附源码+论文)
大家好!我是程序猿老A,感谢您阅读本文,欢迎一键三连哦。 💞当前专栏:微信小程序毕业设计 精彩专栏推荐👇🏻👇🏻👇🏻 🎀 Python毕业设计…...
C#:lock锁与订单号(或交易号)的生成
在弄电商类网站的时候,往往是根据年月日时分秒的格式生成订单号(yyyyMMddHHmmss),为了解决并发性,就直接在生成订单号的区域块加上lock。 static void Main(string[] args){for(int i0; i<100; i){//GetRandomTime(…...
计算机图形学入门11:图形管线与着色器
1.什么是图形管线 把场景中的物体经过一系列的处理,最后一张图像的形式在屏幕上显示出来,这一系列过程就是图形管线(Graphics Pipeline),也叫实时渲染管线(Real-time Rendering Pipeline)。如下图所示,为整个渲染管线的过程。 渲染…...
正解 x86 Linux 内存管理
1,机器解析的思路 发现网络上大量的教程,多是以讹传讹地讲解 Linux 内存管理; 都是在讲: 逻辑地址 -> 线性地址 -> 物理地址 这个转换关系是怎么发生的。 上面这个过程确实是程序运行时地址的翻译顺序; …...
springboot读取配置时,读取到了系统环境变量
在Spring Boot应用中,读取配置通常通过application.properties或application.yml文件进行。不过,Spring Boot也支持从系统环境变量读取配置,这使得应用可以在不同的环境中灵活配置。下面详细介绍如何在Spring Boot中读取系统环境变量。 1. 配…...
平均召回(Average Recall,AR)概述
平均召回(Average Recall,AR)概述 在深度学习中,平均召回(Average Recall, AR)是一个衡量模型在不同阈值下的召回率的综合指标,特别常用于目标检测任务。召回率(Recall)…...
WWDC 2024 回顾:Apple Intelligence 的发布与解析
一年一度的苹果全球开发者大会(WWDC)如期而至,2024 年的 WWDC 再次成为科技界的焦点。本次发布会中,苹果正式推出了他们在 AI 领域的全新战略——Apple Intelligence。这一全新概念旨在为用户打造“强大、易用、全面、个性化、注重…...
[Cloud Networking] SPDY 协议
文章目录 1. 背景2. SPDY 之前3. SPDY 项目目标4. SPDY 功能特点4.1 SPDY基本功能4.2 SPDY高级功能 1. 背景 TCP是通用的、可靠的传输协议,提供保证交付、重复抑制、按顺序交付、流量控制、拥塞避免和其他传输特性。 HTTP是提供基本请求/响应语义的应用层协议。 不…...
基于距离变化能量开销动态调整的WSN低功耗拓扑控制开销算法matlab仿真
目录 1.程序功能描述 2.测试软件版本以及运行结果展示 3.核心程序 4.算法仿真参数 5.算法理论概述 6.参考文献 7.完整程序 1.程序功能描述 通过动态调整节点通信的能量开销,平衡网络负载,延长WSN生命周期。具体通过建立基于距离的能量消耗模型&am…...
转转集团旗下首家二手多品类循环仓店“超级转转”开业
6月9日,国内领先的循环经济企业转转集团旗下首家二手多品类循环仓店“超级转转”正式开业。 转转集团创始人兼CEO黄炜、转转循环时尚发起人朱珠、转转集团COO兼红布林CEO胡伟琨、王府井集团副总裁祝捷等出席了开业剪彩仪式。 据「TMT星球」了解,“超级…...
生成 Git SSH 证书
🔑 1. 生成 SSH 密钥对 在终端(Windows 使用 Git Bash,Mac/Linux 使用 Terminal)执行命令: ssh-keygen -t rsa -b 4096 -C "your_emailexample.com" 参数说明: -t rsa&#x…...
全面解析各类VPN技术:GRE、IPsec、L2TP、SSL与MPLS VPN对比
目录 引言 VPN技术概述 GRE VPN 3.1 GRE封装结构 3.2 GRE的应用场景 GRE over IPsec 4.1 GRE over IPsec封装结构 4.2 为什么使用GRE over IPsec? IPsec VPN 5.1 IPsec传输模式(Transport Mode) 5.2 IPsec隧道模式(Tunne…...
什么是Ansible Jinja2
理解 Ansible Jinja2 模板 Ansible 是一款功能强大的开源自动化工具,可让您无缝地管理和配置系统。Ansible 的一大亮点是它使用 Jinja2 模板,允许您根据变量数据动态生成文件、配置设置和脚本。本文将向您介绍 Ansible 中的 Jinja2 模板,并通…...
JVM虚拟机:内存结构、垃圾回收、性能优化
1、JVM虚拟机的简介 Java 虚拟机(Java Virtual Machine 简称:JVM)是运行所有 Java 程序的抽象计算机,是 Java 语言的运行环境,实现了 Java 程序的跨平台特性。JVM 屏蔽了与具体操作系统平台相关的信息,使得 Java 程序只需生成在 JVM 上运行的目标代码(字节码),就可以…...
(一)单例模式
一、前言 单例模式属于六大创建型模式,即在软件设计过程中,主要关注创建对象的结果,并不关心创建对象的过程及细节。创建型设计模式将类对象的实例化过程进行抽象化接口设计,从而隐藏了类对象的实例是如何被创建的,封装了软件系统使用的具体对象类型。 六大创建型模式包括…...
02.运算符
目录 什么是运算符 算术运算符 1.基本四则运算符 2.增量运算符 3.自增/自减运算符 关系运算符 逻辑运算符 &&:逻辑与 ||:逻辑或 !:逻辑非 短路求值 位运算符 按位与&: 按位或 | 按位取反~ …...
node.js的初步学习
那什么是node.js呢? 和JavaScript又是什么关系呢? node.js 提供了 JavaScript的运行环境。当JavaScript作为后端开发语言来说, 需要在node.js的环境上进行当JavaScript作为前端开发语言来说,需要在浏览器的环境上进行 Node.js 可…...
Selenium 查找页面元素的方式
Selenium 查找页面元素的方式 Selenium 提供了多种方法来查找网页中的元素,以下是主要的定位方式: 基本定位方式 通过ID定位 driver.find_element(By.ID, "element_id")通过Name定位 driver.find_element(By.NAME, "element_name"…...
