(
method: str,
url: str,
headers: Dict[str, str],
payload: Optional[Dict[str, Any]],
timeout: int,
)
| 4364 | |
| 4365 | @staticmethod |
| 4366 | async def _sync_json_http_request( |
| 4367 | method: str, |
| 4368 | url: str, |
| 4369 | headers: Dict[str, str], |
| 4370 | payload: Optional[Dict[str, Any]], |
| 4371 | timeout: int, |
| 4372 | ) -> tuple[int, Optional[Any], str]: |
| 4373 | req_headers = dict(headers or {}) |
| 4374 | req_headers.setdefault("Accept", "application/json") |
| 4375 | request_method = (method or "GET").upper() |
| 4376 | request_kwargs: Dict[str, Any] = { |
| 4377 | "headers": req_headers, |
| 4378 | "timeout": FlowClient._build_remote_browser_http_timeout(timeout), |
| 4379 | } |
| 4380 | |
| 4381 | if payload is not None: |
| 4382 | req_headers["Content-Type"] = "application/json; charset=utf-8" |
| 4383 | if request_method != "GET": |
| 4384 | request_kwargs["json"] = payload |
| 4385 | |
| 4386 | if httpx is None: |
| 4387 | return await FlowClient._stdlib_json_http_request( |
| 4388 | method=method, |
| 4389 | url=url, |
| 4390 | headers=req_headers, |
| 4391 | payload=payload, |
| 4392 | timeout=timeout, |
| 4393 | ) |
| 4394 | |
| 4395 | try: |
| 4396 | # remote_browser 控制面只需要稳定传输 JSON,不需要浏览器指纹伪装。 |
| 4397 | # 使用 httpx 可以避免 curl_cffi 在当前环境下 POST body 被吞掉。 |
| 4398 | async with httpx.AsyncClient(follow_redirects=False, trust_env=False) as session: |
| 4399 | response = await session.request( |
| 4400 | method=request_method, |
| 4401 | url=url, |
| 4402 | **request_kwargs, |
| 4403 | ) |
| 4404 | except Exception as e: |
| 4405 | raise RuntimeError(f"remote_browser 请求失败: {e}") from e |
| 4406 | |
| 4407 | status_code = int(getattr(response, "status_code", 0) or 0) |
| 4408 | text = response.text or "" |
| 4409 | parsed = FlowClient._parse_json_response_text(text) |
| 4410 | |
| 4411 | return status_code, parsed, text |
| 4412 | |
| 4413 | async def _call_remote_browser_service( |
| 4414 | self, |
no test coverage detected