python

关注公众号 jb51net

关闭
首页 > 脚本专栏 > python > Python请求库requests 到 httpx

Python网络请求库从 requests 到 httpx的迁移

作者:曦远Code

文章介绍了Python库httpx,它是requests的现代化替代品,原生支持异步,兼容requests API,支持HTTP/2和严格的超时管理,通过同步和异步示例对比,展示了httpx的优势,并提醒使用时注意异步相关的坑

前言

如果说 Python 有哪个库改变了互联网开发的门槛,requests 绝对榜上有名。

它用极简的 API 终结了 urllib2 那个混乱的时代。

直到今天,requests.get(url) 依然是很多程序员下意识写出的第一行爬虫代码。

但随着 Python 异步生态(Asyncio)的全面爆发,以及 HTTP/2 协议的普及,这个诞生于 2011 年的老兵开始显露疲态。

PS:为什么 AI 时代还要亲自钻研新技术?

因为 AI 的底色是“过去”。

如果你不掌握先进的工具,AI 就会用它的“经验惯性”把你留在旧时代。

只有你懂新东西,才能指挥 AI 写出更现代的代码。

AI 的本质是“概率模型”,它更倾向于给出训练数据中最常见、最保守的方案(往往也就是旧方案)

HttpX

httpx 并不是要推翻 requests,而是要完成它的现代化改造。它的核心口号是:“几乎完全兼容 Requests API,但原生支持异步。”

新项目切换到 httpx 的理由:

例子

如果你熟悉 requests,迁移到 httpx 的成本几乎为零。

同步写法对比(几乎一致)

# Requests
import requests
resp = requests.get("https://api.github.com/events")
# HTTPX
import httpx
resp = httpx.get("https://api.github.com/events")

异步写法

import httpx
import asyncio
async def fetch_tech_news():
    async with httpx.AsyncClient() as client:
        # 同时发起多个请求,效率起飞
        tasks = [client.get(f"https://news.com/api/{i}") for i in range(10)]
        responses = await asyncio.gather(*tasks)
        return [r.json() for r in responses]
asyncio.run(fetch_tech_news())

对比

特性RequestsHTTPX
异步支持❌ (需借助线程池)✅ 原生支持 (Async/Await)
HTTP/2✅ 支持
API 友好度极高极高 (兼容 Requests)
类型提示一般✅ 完善 (完美契合 IDE)
适用场景简单脚本、小型爬虫Web 异步框架、高并发采集、现代化工程

小结

异步虽然好用,但有些坑:

补充知识:

从 requests 到 httpx 的迁移,不仅仅是换一个库,更是一次从同步异步、从 HTTP/1.1 到 HTTP/2 的性能与架构升级。

为了方便你快速理解和决策,这里先用一个表格直观对比两者的核心差异:

特性requestshttpx
核心定位同步HTTP库,API简洁优雅新一代HTTP客户端,同时支持同步和异步API
异步支持❌ 不支持✅ 支持 (httpx.AsyncClient)
HTTP/2❌ 不支持✅ 支持 (需安装httpx[http2])
连接池通过 requests.Session 实现内置更高效的 httpx.Client 和 httpx.AsyncClient
默认超时⚠️ 无默认超时,需手动设置✅ 默认5秒(连接、读取、写入等各阶段)
重定向自动跟随需显式设置 follow_redirects=True
API兼容性-与 requests 高度相似,代码修改成本低

🚀 为什么选择 httpx?

选择 httpx 绝不仅仅是为了“追新”,它解决了许多 requests 在实际生产中的痛点:

🔄 如何从 requests 迁移到 httpx?

好消息是,httpx 在设计上充分考虑了与 requests 的兼容性,迁移路径非常平滑。

1. 基础用法替换

绝大多数情况下,你只需要把代码中的 requests 替换为 httpx 即可。例如,一个简单的 GET 请求:

# 使用 requests
import requests
resp = requests.get('https://api.example.com/data')
print(resp.json())
# 使用 httpx (同步方式)
import httpx
resp = httpx.get('https://api.example.com/data')
print(resp.json())

POST 请求的 json 和 data 参数用法也完全一致-3

2. 使用连接池优化性能

如果你需要复用TCP连接(比如频繁请求同一个网站),requests 使用 Session,而 httpx 则使用 Client

# requests
with requests.Session() as session:
    session.get('https://api.example.com/user')
    session.post('https://api.example.com/post', json={'key': 'value'})
# httpx
with httpx.Client() as client:
    client.get('https://api.example.com/user')
    client.post('https://api.example.com/post', json={'key': 'value'})

3. 进阶:拥抱异步,释放并发潜力

这是 httpx 的核心优势。当需要同时获取100个网页时,异步的优势尽显无疑:

import httpx
import asyncio
async def fetch_data(url):
    async with httpx.AsyncClient() as client:
        resp = await client.get(url)
        return resp.json()
async def main():
    urls = ['https://api.example.com/item/1', 'https://api.example.com/item/2'] # ... 更多URL
    tasks = [fetch_data(url) for url in urls]
    results = await asyncio.gather(*tasks)
    print(f"成功获取 {len(results)} 个结果")
asyncio.run(main())

4. 开启 HTTP/2 支持

在安装时选择 http2 额外依赖,并在创建客户端时简单配置即可享受 HTTP/2 带来的性能提升:

pip install httpx[http2]
with httpx.Client(http2=True) as client:
    resp = client.get('https://cloud.google.com') # 支持HTTP/2的网站
    print(resp.http_version) # 输出: HTTP/2

⚠️ 需要注意的几个关键区别

虽然API高度相似,但有几个行为差异是迁移时容易忽略的:

💎 总结

建议:你可以在新项目中直接尝试使用 httpx。对于已有项目,可以评估一下是否有性能瓶颈,再决定是否逐步替换。

到此这篇关于Python网络请求库,从 requests 到 httpx的文章就介绍到这了,更多相关Python网络请求库内容请搜索脚本之家以前的文章或继续浏览下面的相关文章希望大家以后多多支持脚本之家!

您可能感兴趣的文章:
阅读全文