在 Python 開發(fā)中,發(fā)送 HTTP 請求是高頻需求,無論是調(diào)用第三方 API、爬取網(wǎng)頁數(shù)據(jù),還是與后端服務(wù)交互,都需通過 HTTP 請求實(shí)現(xiàn)數(shù)據(jù)傳輸。Python 提供了多個(gè)庫支持 HTTP 請求,其中urllib(標(biāo)準(zhǔn)庫)和requests(第三方庫)最為常用。小編將詳解這兩個(gè)庫的使用方法,覆蓋 GET/POST 核心請求、參數(shù)配置及異常處理,助你高效完成 HTTP 交互需求。
一、核心庫選擇:urllib vs requests
Python 發(fā)送 HTTP 請求的庫主要分為兩類,選擇需結(jié)合場景需求:
urllib:Python 標(biāo)準(zhǔn)庫(無需額外安裝),包含urllib.request(請求發(fā)送)、urllib.parse(參數(shù)解析)等模塊,兼容性強(qiáng)但語法較繁瑣,適合無第三方庫依賴的場景;
requests:第三方庫(需pip install requests安裝),API 設(shè)計(jì)簡潔直觀,支持會(huì)話保持、文件上傳等高級(jí)功能,開發(fā)效率更高,是日常開發(fā)的首選。
二、基礎(chǔ) HTTP 請求實(shí)現(xiàn):GET 與 POST
HTTP 請求中,GET 用于獲取數(shù)據(jù),POST 用于提交數(shù)據(jù)(如表單、JSON),以下分別用兩個(gè)庫實(shí)現(xiàn)核心場景。
(一)使用 requests 庫:簡潔高效
requests庫通過requests.get()、requests.post()等方法直接發(fā)送請求,返回的Response對(duì)象包含響應(yīng)數(shù)據(jù)、狀態(tài)碼等信息。
1. GET 請求:獲取數(shù)據(jù)(如查詢接口)
GET 請求的參數(shù)通常拼接在 URL 后,用params參數(shù)傳入字典即可自動(dòng)編碼,無需手動(dòng)處理 URL 拼接。
TypeScript取消自動(dòng)換行復(fù)制
import requests
# 目標(biāo)接口:查詢天氣(示例接口,需替換為有效API)
url = "https://api.example.com/weather"
# GET參數(shù):城市、日期
params = {"city": "Beijing", "date": "20250901"}
# 發(fā)送GET請求,設(shè)置超時(shí)時(shí)間(避免無限等待)
response = requests.get(url, params=params, timeout=5)
# 處理響應(yīng)
print("狀態(tài)碼:", response.status_code) # 200表示成功
print("響應(yīng)文本:", response.text) # 字符串形式響應(yīng)內(nèi)容
print("JSON響應(yīng):", response.json()) # 若響應(yīng)為JSON,直接解析為字典
2. POST 請求:提交數(shù)據(jù)(如表單 / JSON)
POST 請求數(shù)據(jù)需放在請求體中,根據(jù)接口要求選擇 “表單格式” 或 “JSON 格式”:
表單格式:用data參數(shù)傳入字典,請求頭Content-Type自動(dòng)設(shè)為application/x-www-form-urlencoded;
JSON 格式:用json參數(shù)傳入字典,請求頭自動(dòng)設(shè)為application/json(推薦接口交互使用)。
TypeScript取消自動(dòng)換行復(fù)制
# 1. 提交表單數(shù)據(jù)
form_data = {"username": "test", "password": "123456"}
response_form = requests.post(
"https://api.example.com/login",
data=form_data,
timeout=5
)
# 2. 提交JSON數(shù)據(jù)(更常用)
json_data = {"user_id": 1001, "action": "get_info"}
response_json = requests.post(
"https://api.example.com/user",
json=json_data,
timeout=5
)
print("JSON響應(yīng)結(jié)果:", response_json.json())
(二)使用 urllib 庫:標(biāo)準(zhǔn)庫實(shí)現(xiàn)
urllib需手動(dòng)處理參數(shù)編碼、請求對(duì)象構(gòu)建,步驟較繁瑣,但無需依賴第三方庫。
1. GET 請求:手動(dòng)編碼參數(shù)
TypeScript取消自動(dòng)換行復(fù)制
from urllib import request, parse
url = "https://api.example.com/weather"
params = {"city": "Shanghai", "date": "20250901"}
# 1. 編碼參數(shù)(轉(zhuǎn)換為URL字符串格式)
encoded_params = parse.urlencode(params)
# 2. 拼接URL
full_url = f"{url}?{encoded_params}"
# 3. 發(fā)送請求
with request.urlopen(full_url, timeout=5) as response:
# 讀取響應(yīng)(字節(jié)流需解碼為字符串)
response_text = response.read().decode("utf-8")
print("響應(yīng)文本:", response_text)
2. POST 請求:構(gòu)建請求對(duì)象
TypeScript取消自動(dòng)換行復(fù)制
import json
url = "https://api.example.com/user"
json_data = {"user_id": 1002, "action": "get_info"}
# 1. 轉(zhuǎn)換JSON數(shù)據(jù)為字節(jié)流
data_bytes = json.dumps(json_data).encode("utf-8")
# 2. 構(gòu)建請求對(duì)象,設(shè)置請求頭
req = request.Request(
url=url,
data=data_bytes,
headers={"Content-Type": "application/json"} # 手動(dòng)設(shè)置JSON頭
)
# 3. 發(fā)送請求
with request.urlopen(req, timeout=5) as response:
response_json = json.loads(response.read().decode("utf-8"))
print("JSON響應(yīng):", response_json)
三、進(jìn)階操作:headers、Cookie 與會(huì)話保持
實(shí)際開發(fā)中,需配置請求頭(如 User-Agent)、攜帶 Cookie 或保持會(huì)話,確保請求符合接口要求。
(一)設(shè)置請求頭:模擬瀏覽器 / 合法身份
部分接口會(huì)驗(yàn)證User-Agent(判斷是否為瀏覽器請求)或Authorization(身份令牌),需在請求中添加 headers:
TypeScript取消自動(dòng)換行復(fù)制
headers = {
"User-Agent": "Mozilla/5.0 (Windows NT 10.0; Win64; x64) Chrome/120.0.0.0",
"Authorization": "Bearer your_token_here" # 接口認(rèn)證令牌
}
response = requests.get(
"https://api.example.com/protected",
headers=headers,
timeout=5
)
(二)攜帶 Cookie:維持登錄狀態(tài)
若接口需登錄后訪問,可通過cookies參數(shù)攜帶 Cookie(字典格式):
TypeScript取消自動(dòng)換行復(fù)制
cookies = {"session_id": "abc123xyz789", "user_name": "test"}
response = requests.get(
"https://api.example.com/user/info",
cookies=cookies,
timeout=5
)
(三)會(huì)話保持:復(fù)用連接與 Cookie
使用requests.Session()創(chuàng)建會(huì)話對(duì)象,可自動(dòng)保存 Cookie、復(fù)用 TCP 連接,適合多請求交互(如登錄后多次訪問接口):
TypeScript取消自動(dòng)換行復(fù)制
# 創(chuàng)建會(huì)話
session = requests.Session()
# 1. 登錄(會(huì)話自動(dòng)保存Cookie)
login_data = {"username": "test", "password": "123456"}
session.post("https://api.example.com/login", json=login_data, timeout=5)
# 2. 后續(xù)請求(自動(dòng)攜帶登錄Cookie)
response = session.get("https://api.example.com/user/orders", timeout=5)
print("用戶訂單:", response.json())
# 關(guān)閉會(huì)話
session.close()
四、異常處理:確保請求穩(wěn)定性
網(wǎng)絡(luò)波動(dòng)、接口錯(cuò)誤可能導(dǎo)致請求失敗,需捕獲requests.exceptions或urllib.error中的異常,避免程序崩潰:
TypeScript取消自動(dòng)換行復(fù)制
import requests
from requests.exceptions import Timeout, ConnectionError, HTTPError
try:
response = requests.get("https://api.example.com/weather", timeout=5)
response.raise_for_status() # 若狀態(tài)碼≥400(如404、500),拋出HTTPError
print("請求成功:", response.json())
except Timeout:
print("請求超時(shí):請檢查網(wǎng)絡(luò)或增加超時(shí)時(shí)間")
except ConnectionError:
print("連接失?。赫垯z查URL或服務(wù)器狀態(tài)")
except HTTPError as e:
print(f"接口錯(cuò)誤:狀態(tài)碼{e.response.status_code},詳情{e.response.text}")
except Exception as e:
print(f"未知錯(cuò)誤:{str(e)}")
Python 發(fā)送 HTTP 請求的核心庫中,requests以簡潔的 API、豐富的功能成為首選,適合絕大多數(shù)開發(fā)場景;urllib作為標(biāo)準(zhǔn)庫,適合無第三方依賴的環(huán)境。實(shí)際開發(fā)中,需根據(jù)請求類型(GET/POST)選擇對(duì)應(yīng)方法,配置 headers、Cookie 或會(huì)話保持以適配接口要求,同時(shí)通過異常處理確保請求穩(wěn)定性。