開通網站必須做域名空間營銷方法有哪些方式
開發(fā)自己的 Web 框架
- 開發(fā)Web服務器主體程序
- 開發(fā)Web框架程序
- 使用模板來展示響應內容
- 開發(fā)框架的路由列表功能
- 采用裝飾器的方式添加路由
- 電影列表頁面的開發(fā)案例
接收web服務器的動態(tài)資源請求,給web服務器提供處理動態(tài)資源請求的服務。根據(jù)請求資源路徑的后綴名進行判斷
- 如果請求資源路徑的后綴名是.html則是動態(tài)資源請求,讓web框架程序進行處理。
- 否則是靜態(tài)資源請求,讓web服務器程序進行處理。
開發(fā)Web服務器主體程序
- 接受客戶端 HTTP 請求(底層是 TCP)
- 判斷請求是否是靜態(tài)資源還是動態(tài)資源
- 如果是靜態(tài)資源怎么處理
- 如果是動態(tài)資源怎么處理
- 關閉 Web 服務器
"""
#!/usr/bin/python3
# coding:utf-8
#
# Copyright (C) 2024 - 2024 Jasonakeke, Inc. All Rights Reserved
# @Desc :我們自己開發(fā)的 web 服務器
# @Time : 2024/7/31 22:17
# @Author : Code_By_Jasonakeke
# @Email : 2284037977@qq.com
# @File : my_web.py
# @IDE : PyCharm
"""
from socket import socket, AF_INET, SOCK_STREAM
from threading import Thread
from time import strftime, localtimefrom _socket import SOL_SOCKET, SO_REUSEADDRfrom MyFramework import handle_request# 開發(fā)自己的 web 服務器主類
class MyWebHttpServer(object):def __init__(self, port):# 創(chuàng)建 HTTP 服務器的套接字server_socket = socket(AF_INET, SOCK_STREAM)# 設置端口號復用,出現(xiàn)退出之后,不需要等待幾分鐘,直接釋放端口server_socket.setsockopt(SOL_SOCKET, SO_REUSEADDR, True)server_socket.bind(('', port))server_socket.listen(128)self.server_socket = server_socket# 處理請求的函數(shù)@staticmethoddef hande_browser_request(new_socket):# 接收客戶端的請求recv_data = new_socket.recv(4096)# 如果沒有收到數(shù)據(jù),那么請求無效,關閉套接字,直接退出if len(recv_data) == 0:new_socket.close()return# 對接收的字節(jié)數(shù)據(jù),轉換成字符request_data = recv_data.decode('utf-8')print("瀏覽器請求的數(shù)據(jù):", request_data)request_array = request_data.split(' ', maxsplit = 2)# 得到請求路徑request_path = request_array[1]print("請求路徑是:", request_path)# 如果請求路徑是 /,自動設置為 /index.htmlif request_path == '/':request_path = '/index.html'# 根據(jù)請求路徑來判斷是否是動態(tài)資源函數(shù)靜態(tài)資源if request_path.endswith('.html'):''' 動態(tài)資源的請求 '''# 動態(tài)資源的處理交給 Web 框架來處理,需要把請求參數(shù)傳給 Web 框架,可能會有多個參數(shù),所以采用字典結果params = {'request_path': request_path}# Web 框架處理動態(tài)資源請求之后,返回一個響應response = handle_request(params)new_socket.send(response)new_socket.close()else:''' 靜態(tài)資源的請求 '''# 響應主體頁面response_body = None# 響應頭response_header = Noneresponse_type = 'text/html'# 響應頭第一行response_first_line = None# 其實就是根據(jù)請求路徑讀取 /static/ 目錄中靜態(tài)的文件數(shù)據(jù),響應給客戶端try:# 讀取 static 目錄中的文件數(shù)據(jù),rb 模式是一種兼容模式,可以打開圖片,也可以打開 jswith open('static' + request_path, 'rb') as f:response_body = f.read()if request_path.endswith('.jpg'):response_type = 'image/wbep'response_first_line = 'HTTP/1.1 200 OK\r\n'# 響應頭response_header = ('Content-Length: ' + str(len(response_body)) + '\r\n'+ 'Content-Type: ' + response_type + '; charset=iso-8859-1\r\n'+ 'Date: ' + strftime('%Y-%m-%d %H:%M:%S', localtime()) + '\r\n'+ 'Server: keke\r\n')except Exception as e:# 瀏覽器想讀取的文件可能不存在with open('static/404.html', 'rb') as f:# 響應主體頁面response_body = f.read()response_first_line = 'HTTP/1.1 404 Not Found\r\n'# 響應頭response_header = ('Content-Length: ' + str(len(response_body)) + '\r\n'+ 'Content-Type: ' + response_type + '; charset=iso-8859-1\r\n'+ 'Date: ' + strftime('%Y-%m-%d %H:%M:%S', localtime()) + '\r\n'+ 'Server: keke\r\n')finally:# 組成響應數(shù)據(jù),發(fā)給客戶端response = (response_first_line + response_header + '\r\n').encode('utf-8') + response_bodynew_socket.send(response)# 關閉套接字new_socket.close()# 啟動服務器 ,并且接收客戶端的請求def start(self):# 循環(huán)并且多線程來接收客戶端的請求while True:new_socket, ip_port = self.server_socket.accept()print("客戶端的 ip 和端口是:", ip_port)# 一個客戶端請求交給一個線程處理sub_thread = Thread(target = self.hande_browser_request, args = (new_socket,))# 設置守護線程sub_thread.daemon = Truesub_thread.start()def main():# 創(chuàng)建服務器對象web_server = MyWebHttpServer(8080)# 啟動服務器web_server.start()if __name__ == '__main__':main()
開發(fā)Web框架程序
- 根據(jù)請求路徑,動態(tài)響應對應的數(shù)據(jù)
- 如果請求路徑,沒有對應的響應數(shù)據(jù)也需要返回404頁面
"""
# coding:utf-8
#
# Copyright (C) 2024 - 2024 Jasonakeke, Inc. All Rights Reserved
# @Desc :自定義 Web 框架
# @Time : 2024/8/1 22:07
# @Author : Code_By_Jasonakeke
# @Email : 2284037977@qq.com
# @File : MyFramework.py
# @IDE : PyCharm
"""
from time import strftime, localtime# 處理動態(tài)資源請求
def handle_request(params):request_path = params['request_path']# 當前的請求路徑有與之對應的動態(tài)響應if request_path == '/index.html':response = index()return responseelse:# 沒有動態(tài)資源的數(shù)據(jù),返回 404頁面return page_not_found()# 專門處理 index.html 的請求
def index():data = strftime('%Y-%m-%d %H:%M:%S', localtime())response_body = dataresponse_first_line = 'HTTP/1.1 200 OK\r\n'# 響應頭response_header = ('Content-Length: ' + str(len(response_body)) + '\r\n'+ 'Content-Type: text/html; charset=iso-8859-1\r\n'+ 'Date: ' + strftime('%Y-%m-%d %H:%M:%S', localtime()) + '\r\n'+ 'Server: keke\r\n')response = (response_first_line + response_header + '\r\n' + response_body).encode('utf-8')return response# 處理沒有找到對應的動態(tài)資源
def page_not_found():# 瀏覽器想讀取的文件可能不存在with open('static/404.html', 'rb') as f:# 響應主體頁面response_body = f.read()response_first_line = 'HTTP/1.1 404 Not Found\r\n'# 響應頭response_header = ('Content-Length: ' + str(len(response_body)) + '\r\n'+ 'Content-Type: text/html; charset=iso-8859-1\r\n'+ 'Date: ' + strftime('%Y-%m-%d %H:%M:%S', localtime()) + '\r\n'+ 'Server: keke\r\n')response = (response_first_line + response_header + '\r\n').encode('utf-8') + response_bodyreturn response
使用模板來展示響應內容
- 自己設計一個模板,中有一些地方采用動態(tài)的數(shù)據(jù)替代
- 怎么替代,替代什么數(shù)據(jù)
<!DOCTYPE html>
<html lang="zh-CN"><head><meta charset="utf-8"><meta http-equiv="X-UA-Compatible" content="IE=edge"><meta name="viewport" content="width=device-width, initial-scale=1"><title>首頁 - 電影列表</title><link href="/css/bootstrap.min.css" rel="stylesheet"><script src="/js/jquery-1.12.4.min.js"></script><script src="/js/bootstrap.min.js"></script></head><body><div class="navbar navbar-inverse navbar-static-top "><div class="container"><div class="navbar-header"><button class="navbar-toggle" data-toggle="collapse" data-target="#mymenu"><span class="icon-bar"></span><span class="icon-bar"></span><span class="icon-bar"></span></button><a href="#" class="navbar-brand">電影列表</a></div><div class="collapse navbar-collapse" id="mymenu"><ul class="nav navbar-nav"><li class="active"><a href="">電影信息</a></li><li><a href="">個人中心</a></li></ul></div></div></div><div class="container"><div class="container-fluid"><table class="table table-hover"><tr><th>序號</th><th>名稱</th><th>導演</th><th>上映時間</th><th>票房</th><th>電影時長</th><th>類型</th><th>備注</th><th>刪除電影</th></tr>{%datas%}</table></div></div></body>
</html>
開發(fā)框架的路由列表功能
- 以后開發(fā)新的動作資源的功能只需要增加一個條件判斷分支和一個專門處理的函數(shù)
- 路由:就是請求的 URL 路徑和處理函數(shù)直接的映射
- 路由表
請求路徑 處理函數(shù) /index.html index /userinfo.html user_info
注意:用戶的動態(tài)資源請求通過遍歷路由表找到對應的處理函數(shù)來完成的
"""
#!/usr/bin/python3
# coding:utf-8
#
# Copyright (C) 2024 - 2024 Jasonakeke, Inc. All Rights Reserved
# @Desc :自定義 Web 框架
# @Time : 2024/8/1 22:07
# @Author : Code_By_Jasonakeke
# @Email : 2284037977@qq.com
# @File : MyFramework.py
# @IDE : PyCharm
"""
from time import strftime, localtime# 處理動態(tài)資源請求
def handle_request(params):request_path = params['request_path']for path, func in route_list:if request_path == path:return func()else:return page_not_found()# 當前的請求路徑有與之對應的動態(tài)響應# if request_path == '/index.html':# response = index()# return response# elif request_path == '/userinfo.html':# response = user_info()# return response# else:# return page_not_found()# 專門處理 index.html 的請求
def index():response_body = Nonedate = strftime('%Y-%m-%d %H:%M:%S', localtime())# response_body = datawith open('template/index.html', 'r', encoding = 'utf-8') as f:response_body = f.read()response_body = response_body.replace('{%datas%}', date)response_first_line = 'HTTP/1.1 200 OK\r\n'# 響應頭response_header = 'Server: keke\r\n'response = (response_first_line + response_header + '\r\n' + response_body).encode('utf-8')return response# 處理沒有找到對應的動態(tài)資源
def page_not_found():# 瀏覽器想讀取的文件可能不存在with open('static/404.html', 'rb') as f:# 響應主體頁面response_body = f.read()response_first_line = 'HTTP/1.1 404 Not Found\r\n'# 響應頭response_header = 'Server: keke\r\n'response = (response_first_line + response_header + '\r\n').encode('utf-8') + response_bodyreturn responsedef user_info():response_body = Nonedate = strftime('%Y-%m-%d %H:%M:%S', localtime())# response_body = datawith open('template/user_info.html', 'r', encoding = 'utf-8') as f:response_body = f.read()response_body = response_body.replace('{%datas%}', date)response_first_line = 'HTTP/1.1 200 OK\r\n'# 響應頭response_header = 'Server: keke\r\n'response = (response_first_line + response_header + '\r\n' + response_body).encode('utf-8')return response# 定義路由表
route_list = {('/index.html', index),('/userinfo.html', user_info),
}
采用裝飾器的方式添加路由
- 采用帶參數(shù)的裝飾器
- 在任何一個處理函數(shù)的基礎上增加一個添加路由的功能
"""
#!/usr/bin/python3
# coding:utf-8
#
# Copyright (C) 2024 - 2024 Jasonakeke, Inc. All Rights Reserved
# @Desc :自定義 Web 框架
# @Time : 2024/8/1 22:07
# @Author : Code_By_Jasonakeke
# @Email : 2284037977@qq.com
# @File : MyFramework.py
# @IDE : PyCharm
"""
from functools import wraps
from time import strftime, localtime# 定義路由表
route_list = []# route_list = {
# ('/index.html', index),
# ('/userinfo.html', user_info),
# }# 調用一個帶參數(shù)的裝飾器
def route(request_path):""":param request_path: URL 請求:return:"""def add_route(func):# 添加路由到路由表route_list.append((request_path, func))@wraps(func)def invoke(*arg, **kwargs):# 調用指定的處理函數(shù)并返回return func(*arg, **kwargs)return invokereturn add_route# 處理動態(tài)資源請求
def handle_request(params):request_path = params['request_path']for path, func in route_list:if request_path == path:return func()else:return page_not_found()# 當前的請求路徑有與之對應的動態(tài)響應
# if request_path == '/index.html':
# response = index()
# return response
# elif request_path == '/userinfo.html':
# response = user_info()
# return response
# else:
# return page_not_found()# 專門處理 index.html 的請求
@route('/index.html')
def index():response_body = Nonedate = strftime('%Y-%m-%d %H:%M:%S', localtime())# response_body = datawith open('template/index.html', 'r', encoding = 'utf-8') as f:response_body = f.read()response_body = response_body.replace('{%datas%}', date)response_first_line = 'HTTP/1.1 200 OK\r\n'# 響應頭response_header = 'Server: keke\r\n'response = (response_first_line + response_header + '\r\n' + response_body).encode('utf-8')return response# 處理沒有找到對應的動態(tài)資源
def page_not_found():# 瀏覽器想讀取的文件可能不存在with open('static/404.html', 'rb') as f:# 響應主體頁面response_body = f.read()response_first_line = 'HTTP/1.1 404 Not Found\r\n'# 響應頭response_header = 'Server: keke\r\n'response = (response_first_line + response_header + '\r\n').encode('utf-8') + response_bodyreturn response@route('/userinfo.html')
def user_info():response_body = Nonedate = strftime('%Y-%m-%d %H:%M:%S', localtime())# response_body = datawith open('template/user_info.html', 'r', encoding = 'utf-8') as f:response_body = f.read()response_body = response_body.replace('{%datas%}', date)response_first_line = 'HTTP/1.1 200 OK\r\n'# 響應頭response_header = 'Server: keke\r\n'response = (response_first_line + response_header + '\r\n' + response_body).encode('utf-8')return response
小結:使用帶參數(shù)的裝飾器,可以把路由自動的添加到路由列表中
電影列表頁面的開發(fā)案例
- 查詢數(shù)據(jù)
- 根據(jù)查詢的數(shù)據(jù)得到動態(tài)的內容
"""
#!/usr/bin/python3
# coding:utf-8
#
# Copyright (C) 2024 - 2024 Jasonakeke, Inc. All Rights Reserved
# @Desc :自定義 Web 框架
# @Time : 2024/8/1 22:07
# @Author : Code_By_Jasonakeke
# @Email : 2284037977@qq.com
# @File : MyFramework.py
# @IDE : PyCharm
"""
from functools import wraps
from time import strftime, localtimefrom pymysql import connect# 定義路由表
route_list = []# route_list = {
# ('/index.html', index),
# ('/userinfo.html', user_info),
# }# 調用一個帶參數(shù)的裝飾器
def route(request_path):""":param request_path: URL 請求:return:"""def add_route(func):# 添加路由到路由表route_list.append((request_path, func))@wraps(func)def invoke(*arg, **kwargs):# 調用指定的處理函數(shù)并返回return func(*arg, **kwargs)return invokereturn add_route# 處理動態(tài)資源請求
def handle_request(params):request_path = params['request_path']for path, func in route_list:if request_path == path:return func()else:return page_not_found()# 當前的請求路徑有與之對應的動態(tài)響應
# if request_path == '/index.html':
# response = index()
# return response
# elif request_path == '/userinfo.html':
# response = user_info()
# return response
# else:
# return page_not_found()# 專門處理 index.html 的請求
@route('/index.html')
def index():response_body = None# date = strftime('%Y-%m-%d %H:%M:%S', localtime())# response_body = data# 1.從 MySQL 中查詢數(shù)據(jù)conn = connect(host = '127.0.0.1', port = 3306, user = 'root', password = '123456', database = 'test', charset = 'utf8')cursor = conn.cursor()cursor.execute('select * from t_movies')result = cursor.fetchall()print(result)datas = ''for row in result:datas += '''<tr><td>%s</td><td>%s</td><td>%s</td><td>%s</td><td>%s元</td><td>%s</td><td>%s</td><td>%s</td><td> <input type='button' value='刪除'/></td></tr>''' % rowprint(datas)with open('template/index.html', 'r', encoding = 'utf-8') as f:response_body = f.read()response_body = response_body.replace('{%datas%}', datas)response_first_line = 'HTTP/1.1 200 OK\r\n'# 響應頭response_header = 'Server: keke\r\n'response = (response_first_line + response_header + '\r\n' + response_body).encode('utf-8')return response# 處理沒有找到對應的動態(tài)資源
def page_not_found():# 瀏覽器想讀取的文件可能不存在with open('static/404.html', 'rb') as f:# 響應主體頁面response_body = f.read()response_first_line = 'HTTP/1.1 404 Not Found\r\n'# 響應頭response_header = 'Server: keke\r\n'response = (response_first_line + response_header + '\r\n').encode('utf-8') + response_bodyreturn response@route('/userinfo.html')
def user_info():response_body = Nonedate = strftime('%Y-%m-%d %H:%M:%S', localtime())# response_body = datawith open('template/user_info.html', 'r', encoding = 'utf-8') as f:response_body = f.read()response_body = response_body.replace('{%datas%}', date)response_first_line = 'HTTP/1.1 200 OK\r\n'# 響應頭response_header = 'Server: keke\r\n'response = (response_first_line + response_header + '\r\n' + response_body).encode('utf-8')return response