静态资源:每次请求返回固定不变的内容。
动态资源:请求时 即时生成的内容。
服务器 : 会用 别人写好的 性能强大的服务器程序,例如 Nagix
Web框架: 为了 方便开发,会有个框架,例如 Django和Flask
WSGI:允许 开发者将 服务器和框架 分开,将二者可以混合匹配。一种约定,实现二者的解耦。
会调用 框架里的 application函数,带着两个参数,(字典,服务器中的一个函数名),然后框架调用服务器中的这个函数并把header传过去。当application执行完,会把body也传给服务器。
服务器把 WSGI返回的 header 和 body 和起来返回给 浏览器。
运行时指定 端口 和 框架。
服务器代码示例: 改为类的形式实现
# coding=utf-8
import socket
import re
import time
import miniFramwork
class WSGIService:
def __init__(self):
self.tcp_server_socket = socket.socket(socket.AF_INET, socket.SOCK_STREAM)
self.tcp_server_socket.bind(("", 7891))
# 3.变为 监听套接字,等待 客户端发送请求 来激活阻塞,可以指定能够接受的最大连接数
self.tcp_server_socket.listen(128)
self.tcp_server_socket.setblocking(False)
self.client_socket_list = list()
def service_high(self,new_socket, request):
# 1. 接受浏览器发来的请求,并解析
# request = new_socket.recv(1024).decode("utf-8")
request_lines = request.decode("utf-8").splitlines()
print("=" * 30)
print(request_lines)
ret = re.match(r"[^/]+(/[^ ]*)", request_lines[0])
if ret:
file_name = ret.group(1)
if file_name == "/":
file_name = "/index.html"
# 返回 HTTP 格式的数据给 浏览器
if not file_name.endswith('.py'):
try:
f = open("../../frontEnd" + file_name, 'rb')
except:
response = "HTTP/1.1 404 NOT FOUND\r\n"
response += "Content-Length:%d\r\n" % len("---- file not find----")
response += "\r\n"
response += "---- file not find----"
new_socket.send(response.encode("utf-8"))
else:
response_body = f.read()
f.close()
response_header = "HTTP/1.1 200 OK\r\n"
response_header += "Content-Length:%d\r\n" % len(response_body)
response_header += "\r\n"
response = response_header.encode("utf-8") + response_body
new_socket.send(response)
else:
env = {}
env['PATH_INFO'] = file_name
response_body = miniFramwork.application(env,self.start_response)
response_header = "HTTP/1.1 %s\r\n" % self.headers
# 这个地方要 加个 encode('utf-8') ,因为传来的有汉字,编码要统一才可以辨识出准确的字符个数
response_header += "Content-Length:%d\r\n" % len(response_body.encode('utf-8'))
# response_header += "Content-Length:%d\r\n" % len(response_body)
for temp in self.headers:
response_header += "%s:%s\r\n" % (temp[0],temp[1])
response_header += '\r\n'
response = response_header + response_body
new_socket.send(response.encode('utf-8'))
def run_forever(self):
while True:
try:
new_socket, client_addr = self.tcp_server_socket.accept()
except Exception as ret:
time.sleep(2)
print("---没有新客户到来,继续监听")
else:
print("如果没有上个异常,就是来了新的客户端的访问")
new_socket.setblocking(False) # 设置套接字为非阻塞的方式
self.client_socket_list.append(new_socket)
for client_socket in self.client_socket_list:
try:
recv_data = client_socket.recv(1024*1024)
except Exception as ret:
print("客户的数据还没有发送过来")
else:
if recv_data:
print("客户端发来了数据")
# 进行数据的处理。。。可以调用service_client
self.service_high(client_socket, recv_data)
else:
# 客户端调用close,发来了空的数据
self.client_socket_list.remove(client_socket)
client_socket.close()
def start_response(self,status,headers):
self.status = status
self.headers = headers
if __name__ == '__main__':
wsgi = WSGIService()
wsgi.run_forever()
框架代码:
# coding=utf-8
""""
框架与服务器分开,这个相当于 框架
对于 寻找静态资源时,是按照 服务器所在的目录为根目录的
"""
import time
def index():
# 要读取 html文件的内容,用rb , 再用decode把bytes转为字符串
with open('../../frontEnd/index.html','rb') as f:
return f.read().decode()
def login():
return "这是登录页面jfjdjsdjf"
def application(env, start_response):
start_response("200 OK", [('Content-Type', 'text/html;charset=utf-8')])
file_name = env['PATH_INFO']
if file_name == '/index.py':
return index()
elif file_name == '/login.py':
return login()
else:
return 'Hello World! %s 你好啊' % time.ctime()
静态URL:
动态URL:
伪静态URL:
url的 棉麻和解码 :