| 1234567891011121314151617181920212223242526272829303132333435363738394041424344454647484950515253545556575859606162636465666768697071727374757677787980818283848586878889909192 |
- import aiohttp
- from typing import Optional, Union, Dict, Any
- class AsyncHttpClient:
- """异步 HTTP 客户端,基于 aiohttp,支持连接池和超时配置"""
- def __init__(
- self,
- timeout: int = 10,
- max_connections: int = 100,
- default_headers: Optional[Dict[str, str]] = None,
- ):
- self.timeout = aiohttp.ClientTimeout(total=timeout)
- self.connector = aiohttp.TCPConnector(limit=max_connections)
- self.default_headers = default_headers or {}
- self.session = None
- async def __aenter__(self):
- self.session = aiohttp.ClientSession(
- connector=self.connector,
- timeout=self.timeout,
- headers=self.default_headers,
- )
- return self
- async def __aexit__(self, exc_type, exc_val, exc_tb):
- await self.session.close()
- async def request(
- self,
- method: str,
- url: str,
- params: Optional[Dict[str, Any]] = None,
- data: Optional[Union[Dict[str, Any], str, bytes]] = None,
- json: Optional[Dict[str, Any]] = None,
- headers: Optional[Dict[str, str]] = None,
- ) -> Union[Dict[str, Any], str]:
- """核心请求方法"""
- request_headers = {**self.default_headers, **(headers or {})}
- try:
- async with self.session.request(
- method,
- url,
- params=params,
- data=data,
- json=json,
- headers=request_headers,
- ) as response:
- response.raise_for_status()
- content_type = response.headers.get("Content-Type", "")
- if "application/json" in content_type:
- return await response.json()
- return await response.text()
- except aiohttp.ClientResponseError as e:
- print(f"HTTP error: {e.status} {e.message}")
- raise
- except aiohttp.ClientError as e:
- print(f"Network error: {str(e)}")
- raise
- async def get(
- self,
- url: str,
- params: Optional[Dict[str, Any]] = None,
- headers: Optional[Dict[str, str]] = None,
- ) -> Union[Dict[str, Any], str]:
- """GET 请求"""
- return await self.request("GET", url, params=params, headers=headers)
- async def post(
- self,
- url: str,
- data: Optional[Union[Dict[str, Any], str, bytes]] = None,
- json: Optional[Dict[str, Any]] = None,
- headers: Optional[Dict[str, str]] = None,
- ) -> Union[Dict[str, Any], str]:
- """POST 请求"""
- return await self.request("POST", url, data=data, json=json, headers=headers)
- async def put(
- self,
- url: str,
- data: Optional[Union[Dict[str, Any], str, bytes]] = None,
- json: Optional[Dict[str, Any]] = None,
- headers: Optional[Dict[str, str]] = None,
- ) -> Union[Dict[str, Any], str]:
- """PUT 请求"""
- return await self.request("PUT", url, data=data, json=json, headers=headers)
|