1.瀏覽器向服務端發送請求html
2.服務端接收請求前端
3.服務端返回相應的響應python
4.瀏覽器接收響應 根據特定的規則渲染頁面展現給用戶看mysql
超文本傳輸協議,規定了瀏覽器與服務端之間消息傳輸的數據格式web
1.基於請求響應面試
2.基於TCP/IP之上的做用於應用層的協議sql
3.無狀態(服務端沒法保存用戶的狀態,屢次請求,任然不記住,還如初見)數據庫
4.無鏈接(請求來一次就響應一次,以後就立馬斷開鏈接,二者之間就再也不有任何關係了)express
websocket 至關因而HTTP協議的一個大的補丁 它支持長鏈接django
請求首行(標識HTTP協議版本,當前請求方式)
請求頭(一大堆k,v鍵值對)
請求體(攜帶的是一些敏感信息好比 密碼,身份證號等)
1.響應首行(標識HTTP協議版本,響應狀態碼)
2.響應頭(一大堆k,v鍵值對)
3.響應體(返回給瀏覽器頁面的數據 一般響應體都是html頁面)
用一串簡單的數字來表示一些複雜的轉態或者提示信息
具體表現形式:
1xx:服務端已經成功接收到了你的數據正在處理,你能夠繼續提交額外的數據
2xx:服務端成功響應,你想要的數據(請求成功 200)
3xx:重定向(當你在訪問一個須要登陸以後才能訪問的頁面 你會發現窗口會自動調到登陸頁面 301 302)
4xx:請求錯誤(請求資源不存在404,請求不合法不符合內部規定會權限不夠403)
5xx:服務器內部錯誤(500) 系統崩掉:洪水攻擊 系統癱瘓等
200 返回正常
304 服務端資源無變化,可以使用緩存資源
400 請求參數不合法
401 未認證
403 服務端禁止訪問該資源
404 服務端未找到該資源
500 服務端異常
1.get請求
朝服務端要資源(好比瀏覽器窗口輸入www.baidu.com)
2.post請求
朝服務端提交數據(好比用戶登陸 提交用戶名和密碼)
GET 向服務器獲取指定資源;
POST 向服務器提交數據,數據放在請求體裏
二者最直接的區別,GET請求的參數是放在URL裏的,POST請求參數是放在請求body裏的;
import socket server = socket.socket() #括號內不寫默認是tcp協議 server.bind(("127.0.0.1",8080)) server.listen(5) while True: conn,addr = server.accept() data = conn.recv(1024) conn.send(b"HTTP/1.1 200 OK\r\n\r\n hello world") # 必須遵循HTTP協議 print(data) data = data.decode("utf-8") # "b'GET /login HTTP/1.1\r\nHost:切割獲取客戶端頁面返回的類型login" current_path = data.split("\r\n")[0].splist(' ')[1] print(current_path) if current_path =="/index": with open(r":\python脫產10期視頻\day51\01 純手擼html文件.html",'rb') as f: conn.send(f.read()) elif current_path =='/login': conn.send(b'login') else: conn.send(b"hello world!") conn.close()
經過post請求,指定輸入後綴就能訪問固定存在的資源
data = b'hello world' data = str(data,encoding='utf-8') print(data) data = bytes(data,encoding='utf-8') print(data) "當不知道用encodeing 仍是 incodeing時 考慮加上類型轉"
WSGI(Web Server Gateway Interface)就是一種規範,它定義了使用Python編寫的web應用程序與web服務器程序之間的接口格式,實現web應用程序與web服務器程序間的解耦。
經常使用的WSGI服務器有uwsgi、Gunicorn。而Python標準庫提供的獨立WSGI服務器叫wsgiref,Django開發環境用的就是這個模塊來作服務器
咱們利用wsgiref模塊來替換咱們本身寫的web框架的socket server部分:
""" 根據URL中不一樣的路徑返回不一樣的內容--函數進階版 返回HTML頁面 讓網頁動態起來 wsgiref模塊版 """
基於wsgiref模塊及拆分紅不一樣的文件以後,
加一個功能只須要在兩個地方修改代碼便可
1.urls.py 路由與視圖函數的對應關係
2.views.py 視圖函數
基於wsgiref模塊寫的web代碼演示以下:
from wsgiref.simple_server import make_server from urls import urls from views import * def run(env,response): """ env是請求相關的數據 response是響應相關的數據 """ # print(env) response('200 OK',[]) current_path = env.get('PATH_INFO') # print(current_path) # if current_path == '/index': # return [b'index'] # elif current_path == '/login': # return [b'login'] # 定義一個存儲函數名的標誌位 func = None for url in urls: # 判斷當前url在不在元組內 if url[0] == current_path: # 只要匹配上了 就把url後綴對應的函數名賦值給func func = url[1] # 一旦匹配上 應該馬上退出for循環 節省資源 break # 對變量func作判斷 if func: res = func(env) else: res = errors(env) return [res.encode('utf-8')] if __name__ == '__main__': server = make_server('127.0.0.1',8080,run) # 實時監測127.0.0.1:8080地址 一旦有客戶端來鏈接 會自動加括號調用run方法 server.serve_forever() # 啓動服務端 # 對象加括號調用 觸發--call--
from views import * urls = [ ('/index',index), ('/login',login), ('/reg',reg), ('/get_time',get_time), ('/get_user',get_user), ('/get_db',get_db), ]
def index(env): return 'index' def login(env): return 'login' def errors(env): return '404 error' def reg(env): return 'reg' from datetime import datetime def get_time(env): # 藉助於時間模塊 如今後端獲取到時間數據 current_time = datetime.now().strftime('%Y-%m-%d %X') with open(r'templates/02 get_time.html','r',encoding='utf-8') as f: data = f.read() # data其實就是一串字符串 僅此而已!!! data = data.replace('$$time$$',current_time) return data
頁面的渲染 from jinja2 import Template def get_user(env): user_dict = {'username':'jason','password':'123','hobby':['read','game','running']} with open(r'templates/03 get_user.html','r',encoding='utf-8') as f: data = f.read() temp = Template(data) res = temp.render(data = user_dict) # 將user_dict傳遞給前端頁面 前端頁面經過變量名data就可以獲取到該字典 return res
動態展現數據到html import pymysql def get_db(env): conn = pymysql.connect( host = '127.0.0.1', port = 3306, user = 'root', password = '123', database = 'day51', charset = 'utf8', autocommit = True ) cursor = conn.cursor(pymysql.cursors.DictCursor) sql = "select * from userinfo" affect_rows = cursor.execute(sql) data = cursor.fetchall() # print(data) with open(r'templates/04 get_db.html','r',encoding='utf-8') as f: data1 = f.read() temp = Template(data1) res = temp.render(user_list= data) return res
靜態網頁:數據是寫死的,萬年不變,不能更改
動態網頁:數據不是寫死的,是動態獲取到的
1.後端實時獲取當前時間"傳遞"給前端頁面展現 2.後端從數據庫獲取數據"傳遞"給前端頁面展現
在Django中把HTLM文件統一存放在:templates 文件夾中 也叫模板文件
jinja2模塊
安裝:pip3 install jinja2
因爲flask框架是依賴於jinja2的 因此下載flask框架也會自帶jinja2模塊
jinja2的做用:模板的渲染 包含了 模板語法
模板語法:(貼近python語法)
前端也可以使用後端的一些語法,操做後端傳入的數據
<p>{{data}}</p> <p>{{data['username']}}</p> <p>{{data.password}}</p> <p>{{data.get('hobby')}}</p>
模板的for語法:輸入for+TAB鍵 便可補全
{%for user_dict in user_list%} <tr> <td>{{user_dict.id}}</td> <td>{{user_dict.name}}</td> <td>{{user_dict.password}}</td> </tr> {%endfor%}
1.手寫web框架
1.1.手動書寫socket代碼
1.2.手動處理http數據
2.基於wsgiref 模塊幫助咱們處理socket以及HTTP數據
wsgiref模塊
1.請求來的時候 解析http數據 幫你打包成一個字典傳輸給你 便於你操做各項數據
2.響應走的時候 自動幫你把數據再打包成符合http協議格式的樣子 再返回給前端
3.封裝路由與視圖函數對應關係 以及視圖函數文件 網站用到的全部的html文件所有放在了templates文件夾下
1.urls.py 路由與視圖函數對應關係 2.views.py 視圖函數(視圖函數不僅僅指函數 也能夠是類) 3.templates 模板文件夾
4.基於jinja2實現模板的渲染
python三大主流web框架:Django、Flask、Tornado
1.Django:大而全 自帶的功能特別特別多;就相似於航空母艦 有時候過於笨重 2.Flask:短小精悍 自帶的功能特別特別少;全都是依賴於第三方組件 flask框架第三方的組件特別多;若是把flask第三方所有加起來;徹底能夠蓋過Django 比較受限於第三方的開發者 3.Tornado:天生的異步非阻塞框架;速度特別快 可以抗住高併發 能夠開發遊戲服務器
A:socket B:路由與視圖函數匹配 C:模板語法
Django A:用的別人的 wsgiref B:本身寫的 C:本身寫的 Flask A:用的別人的 wsgiref>>> werkzeug B:本身寫的 C:用的別人的 jinja2 Tornado A,B,C全都是本身寫的
Django
注意事項(容易形成bug)
1.你的計算機的名稱不能有中文 2.文件的命名儘可能也不要用中文 3.一個pycharm窗口只能有一個項目 不要把多個項目放在一個窗口下
若是出現的「encoding」,優先考慮是文件名問題
Django版本問題
目前有的版本:1.x 2.x
面試小技巧:問大家公司Django用的是什麼版本的?
答:以前用的是1.xx 慢慢過渡到可維護的2.2xx(透露年限問題)
學習過程當中以diango1.11版本爲主
django下載
命令行安裝:pip3 install diango ==1.11.12
如何確認是否安裝成功
命令行敲 django-admin
如何建立django項目
命令行式 1.命令行建立django項目
django-admin startproject 項目名
2.命令行建立django應用(一個應用對應一起獨立的功能)
django-admin startapp 應用名
python manage.py startapp 應用名
3.命令行啓動django項目
python manage.py runserver
(******)
注意 用命令行建立django項目 不會自動新建templates模板文件夾 須要你本身手動建立 而且須要你本身去settings.py文件中註冊該文件路徑
pycharm快捷方式
app概念
django項目就相似因而一所大學,app就是大學裏面不一樣的學院
每一個學院都有本身獨立的功能
老男孩在建立應用名時,習慣寫成app xxx 如app01 ...
Bug親測:千萬別安裝python3.7版本的不然啓動不了Django項目,報錯未安裝匹配到Django
如:django-admin startproject 項目名 只書寫:startproject + 項目名便可
一個窗口不能同時打開多個ip+post同樣的項目,會報錯,打開多個要修改端口號
(******) 建立的應用必定要在settings中註冊 才能生效 不然沒法識別 django主要文件介紹 項目名文件 同名的項目文件夾 settings.py django暴露給用戶可配置的文件 urls.py 路由與視圖函數對應關係 manage.py django入口文件 應用文件夾 migrations文件夾 數據庫遷移記錄 admin.py django後臺管理 apps.py 應用註冊相關 models.py orm模型類 tests.py 測試文件 views.py 視圖函數
Django基礎必備三件套:
HttpResponse:返回字符串
render:返回html頁面 而且可以給該頁面傳值
redirect:重定向
具體使用方法:
from django.shortcuts import HttpResponse, render, redirect
HttpResponse:內部傳入一個字符串參數,返回給瀏覽器。
例如: def index(request): # 業務邏輯代碼 return HttpResponse("OK")
render:相似於咱們上面用到的jinja2,渲染後返回給htlm頁面
例如: def index(request): # 業務邏輯代碼 return render(request, "index.html", {"name": "alex", "hobby": ["燙頭", "泡吧"]})
接受一個URL參數,表示跳轉到指定的URL
def index(request): # 業務邏輯代碼 return redirect("/http://www.baidu.com/")
Django版登陸
Django 啓動時報錯 「UnicodeEncodeError ...」
報這個錯誤一般是由於計算機名爲中文,改爲英文的計算機名重啓下電腦就能夠了。
Django 啓動報錯「SyntaxError: Generator expression must be parenthesized」
報這個錯很大多是由於使用了Python3.7.0,而目前(2018-06-12)Python3.7.0和Django還有點兼容性問題,換回Python3.6的環境便可。