refactor: fix P0/P1/P2 security and performance issues

P0 fixes:
- CORS: replace wildcard methods/headers with configurable lists
- deps.py: remove unsafe global _warned_unset variable

P1 fixes:
- http_client: read default timeout from Settings
- bzzoiro: replace sync urllib with async httpx
- bzzoiro: normalize validation failures use warning level only
- db pool: read pool config from Settings (default 5+10)
- backtest: add asyncio.Semaphore(8) for concurrent execution
- predict/context_builder: add backtest parameter for cutoff buffer

P2 improvements:
- injuries: enforce int conversion for player_id/fixture_id
- injuries: use system temp dir for cache
- utils.py: extract shared actual_1x2/is_correct_1x2
- validation: downgrade 1x2 mismatch log to debug
- docker-compose: use env vars for all credentials
- .env.example: add POSTGRES_USER/PASSWORD/PORT, API_PORT
This commit is contained in:
shangfangjian
2026-09-16 02:38:25 +08:00
parent fa69795d69
commit 983b620659
14 changed files with 154 additions and 109 deletions
+4 -2
View File
@@ -29,12 +29,14 @@ def create_app() -> FastAPI:
)
origins = [o.strip() for o in settings.CORS_ORIGINS.split(",") if o.strip()]
methods = [m.strip() for m in settings.CORS_METHODS.split(",") if m.strip()]
headers = [h.strip() for h in settings.CORS_HEADERS.split(",") if h.strip()]
app.add_middleware(
CORSMiddleware,
allow_origins=origins,
allow_credentials=True,
allow_methods=["*"],
allow_headers=["*"],
allow_methods=methods,
allow_headers=headers,
)
from src.api.routes.matches import router as matches_router
+4 -10
View File
@@ -19,24 +19,18 @@ from src.core.config import settings
logger = logging.getLogger(__name__)
_warned_unset = False
async def require_admin_key(x_api_key: str | None = Header(None, alias="X-API-Key")) -> None:
"""保护「写入型 / 高成本」接口的依赖。
用法: `@router.post("/ingest/bzzoiro", dependencies=[Depends(require_admin_key)])`
"""
global _warned_unset
expected = settings.ADMIN_API_KEY
if not expected:
if not _warned_unset:
logger.warning(
"ADMIN_API_KEY 未设置,采集/回测接口当前【无鉴权】"
"生产环境请设置该环境变量。"
)
_warned_unset = True
logger.warning(
"ADMIN_API_KEY 未设置,采集/回测接口当前【无鉴权】。"
"生产环境请设置该环境变量"
)
return
if not x_api_key or not secrets.compare_digest(x_api_key, expected):