diff --git a/sdk/app/services/figures.py b/sdk/app/services/figures.py index 03bce7b..c819596 100644 --- a/sdk/app/services/figures.py +++ b/sdk/app/services/figures.py @@ -160,7 +160,7 @@ def _job_pmcid(job_dir: Path, pmcid_to_paper: dict[str, str]) -> str | None: # PMC 外网解析 # --------------------------------------------------------------------------- -async def _epmc_figures(client: httpx.AsyncClient, pmcid: str) -> tuple[list[dict], str]: +async def _epmc_figures_once(client: httpx.AsyncClient, pmcid: str) -> tuple[list[dict], str]: """返回 (figures, license)。任何失败返回 ([], "")。""" try: r = await client.get(EPMC_FULLTEXT.format(pmcid=pmcid), timeout=EXTERNAL_TIMEOUT) @@ -227,6 +227,17 @@ async def _epmc_figures(client: httpx.AsyncClient, pmcid: str) -> tuple[list[dic return [], "" +async def _epmc_figures(client: httpx.AsyncClient, pmcid: str) -> tuple[list[dict], str]: + """PMC 解析重试包装:2026-09-12 部署质检发现 176 出网到 EBI 冷连接 + 首次 TLS 握手 10s+ 超时、重连即秒回(实测 1.6-2.2s),失败重试一次。""" + for attempt in (1, 2): + figs, license_ = await _epmc_figures_once(client, pmcid) + if figs or attempt == 2: + return figs, license_ + logger.info("PMC 首次解析失败(%s)——重试一次(176 冷连接实测)", pmcid) + return [], "" + + # --------------------------------------------------------------------------- # 对外 API # ---------------------------------------------------------------------------