| 123456789101112131415161718192021222324252627282930313233343536373839404142434445 |
- # -*- coding: utf-8 -*-
- r"""算法服务的**依赖兜底**:离线目标机没有网、`wheels/` 里也没有 FastAPI 的轮子 ⇒ 用随包的 `vendor/pyfastapi/`。
- 实逮(2026-09-29):开发机的 `.venv` 是 `include-system-site-packages=true`,fastapi/uvicorn 实际来自
- 系统 Python;所以"能跑"不等于"随包能跑"。本模块在 `import fastapi` 失败时把 `vendor/pyfastapi` 插进
- `sys.path`,让服务在**纯 stdlib + 随包依赖**的环境下也能起来。
- """
- from __future__ import annotations
- import pathlib
- import sys
- try:
- from app_common.app_common_guanlan.api import install_root as _install_root
- except ImportError: # 包结构异常时按位置上跳兜底
- from pathlib import Path as _P
- def _install_root(_f): # type: ignore[no-redef]
- return _P(_f).resolve().parents[4]
- def vendor_dir() -> pathlib.Path:
- return _install_root(__file__) / 'vendor' / 'pyfastapi'
- def ensure_fastapi() -> tuple[object, object]:
- """→ (fastapi, uvicorn);缺依赖时依次尝试:本地已装 → vendor/ 随包。"""
- d = vendor_dir()
- if d.is_dir() and str(d) not in sys.path:
- sys.path.append(str(d)) # 放在最后:已装的优先
- try:
- import fastapi
- import uvicorn
- return fastapi, uvicorn
- except ImportError as e: # noqa: BLE001
- raise SystemExit(
- f'[X] 算法服务缺运行期依赖: {e}\n'
- f' 随包目录: {d}(存在: {d.is_dir()})\n'
- ' 修法: 在有网机器上跑 python scripts/fetch_offline_deps.py all 把 fastapi/uvicorn 打进 '
- 'wheels/,或把 site-packages 里的 fastapi·uvicorn·pydantic·starlette·anyio·h11·sniffio·'
- 'annotated_types·typing_extensions·typing_inspection·annotated_doc·idna·click·colorama 复制到 '
- f'{d}')
- __all__ = ['ensure_fastapi', 'vendor_dir']
|