fix(eval): 修复依赖审计网络与缓存配置

This commit is contained in:
caoqianming 2026-08-04 08:39:53 +08:00
parent 137d27acdd
commit 0bc8c28a02
2 changed files with 59 additions and 7 deletions

View File

@ -31,6 +31,7 @@ class AuditCheck:
weight: float weight: float
module: str module: str
arguments: tuple[str, ...] arguments: tuple[str, ...]
direct_network: bool = False
ENGINEERING_CHECKS = ( ENGINEERING_CHECKS = (
@ -69,12 +70,21 @@ SECURITY_CHECKS = (
"pip_audit", "pip_audit",
( (
"-m", "pip_audit", "--local", "-m", "pip_audit", "--local",
"--cache-dir", "evaluation/.cache/pip-audit",
"--progress-spinner", "off", "--progress-spinner", "off",
), ),
direct_network=True,
), ),
) )
_PROXY_ENV_KEYS = (
"HTTP_PROXY",
"HTTPS_PROXY",
"ALL_PROXY",
"http_proxy",
"https_proxy",
"all_proxy",
)
def _case_result( def _case_result(
*, *,
@ -119,23 +129,32 @@ def _tail(text: str, limit: int = 1200) -> str:
return compact[-limit:] if compact else "" return compact[-limit:] if compact else ""
def _subprocess_env(*, direct_network: bool) -> dict[str, str]:
env = {
**os.environ,
"PYTHONUTF8": "1",
"PYTHONIOENCODING": "utf-8",
}
if direct_network:
for key in _PROXY_ENV_KEYS:
env.pop(key, None)
return env
def _run( def _run(
arguments: tuple[str, ...], arguments: tuple[str, ...],
*, *,
repo_root: Path, repo_root: Path,
timeout_s: float, timeout_s: float,
evidence_path: Path | None = None, evidence_path: Path | None = None,
direct_network: bool = False,
) -> tuple[bool, str, float]: ) -> tuple[bool, str, float]:
started = time.monotonic() started = time.monotonic()
try: try:
completed = subprocess.run( completed = subprocess.run(
[sys.executable, *arguments], [sys.executable, *arguments],
cwd=repo_root, cwd=repo_root,
env={ env=_subprocess_env(direct_network=direct_network),
**os.environ,
"PYTHONUTF8": "1",
"PYTHONIOENCODING": "utf-8",
},
capture_output=True, capture_output=True,
text=True, text=True,
encoding="utf-8", encoding="utf-8",
@ -305,6 +324,7 @@ def audit_security_repository(
evidence_path=( evidence_path=(
evidence_dir / f"{check.id}.txt" if write_evidence else None evidence_dir / f"{check.id}.txt" if write_evidence else None
), ),
direct_network=check.direct_network,
) )
total_duration += duration total_duration += duration
assertions.append( assertions.append(

View File

@ -6,9 +6,14 @@ import unittest
import zipfile import zipfile
from io import BytesIO from io import BytesIO
from pathlib import Path from pathlib import Path
from unittest.mock import patch
from evaluation.audit import (
_subprocess_env,
audit_repository,
audit_security_repository,
)
from evaluation.client import EvalClientError, require_safe_base_url from evaluation.client import EvalClientError, require_safe_base_url
from evaluation.audit import audit_repository, audit_security_repository
from evaluation.combine import combine_reports from evaluation.combine import combine_reports
from evaluation.inspect_bridge import export_inspect_jsonl from evaluation.inspect_bridge import export_inspect_jsonl
from evaluation.models import AssertionSpec, EvalConfigError, RunObservation from evaluation.models import AssertionSpec, EvalConfigError, RunObservation
@ -135,6 +140,33 @@ class ClientSafetyTests(unittest.TestCase):
class ReportTests(unittest.TestCase): class ReportTests(unittest.TestCase):
def test_direct_audit_environment_ignores_proxy(self):
for key in (
"HTTP_PROXY",
"HTTPS_PROXY",
"ALL_PROXY",
"http_proxy",
"https_proxy",
"all_proxy",
):
with self.subTest(key=key), patch.dict(
"evaluation.audit.os.environ",
{key: "http://proxy.example"},
clear=True,
):
direct_env = _subprocess_env(direct_network=True)
inherited_env = _subprocess_env(direct_network=False)
direct_keys = {item.casefold() for item in direct_env}
inherited_by_key = {
item.casefold(): value for item, value in inherited_env.items()
}
self.assertNotIn(key.casefold(), direct_keys)
self.assertEqual(
inherited_by_key[key.casefold()], "http://proxy.example"
)
self.assertEqual(direct_env["PYTHONUTF8"], "1")
def test_combine_existing_dimension_reports(self): def test_combine_existing_dimension_reports(self):
engineering = { engineering = {
"suite": {"name": "engineering", "version": "1"}, "suite": {"name": "engineering", "version": "1"},