Files
agentic-kvc/tests/test_metrics.py
Gahow Wang 0701f84c00 tests: add minimal coverage for percentile + proxy routing (S1)
- tests/test_metrics.py asserts the new linear-interp _percentile against
  hand-computed expected values (single value, two-value interpolation,
  endpoints, numpy-equivalent linear default, on-integer rank).
- tests/test_proxy_pick.py exercises InstanceState LRU eviction and
  move-to-end on hit, plus session-affinity stickiness, the overload
  fallback, the active_p_offloads penalty, and lmetric scoring. The
  proxy is loaded by file path with stub fastapi/uvicorn/httpx modules
  so the suite runs without the FastAPI server deps installed.
- pyproject.toml gets a hatchling wheel target and a [tool.pytest]
  section so `uv run --extra dev pytest` works out of the box.
2026-05-23 21:07:14 +08:00

45 lines
1.6 KiB
Python

"""Tests for replayer.metrics percentile + summary helpers (B5)."""
from __future__ import annotations
import math
from replayer.metrics import _percentile
def test_percentile_single_value():
assert _percentile([42.0], 0.50) == 42.0
assert _percentile([42.0], 0.99) == 42.0
def test_percentile_two_values_interpolates():
# For [0, 10] linear interpolation gives p50=5.0, p90=9.0.
assert math.isclose(_percentile([0.0, 10.0], 0.50), 5.0)
assert math.isclose(_percentile([0.0, 10.0], 0.90), 9.0)
def test_percentile_endpoints():
vals = [1.0, 2.0, 3.0, 4.0, 5.0]
assert _percentile(vals, 0.0) == 1.0
assert _percentile(vals, 1.0) == 5.0
def test_percentile_matches_numpy_linear_default():
# Independently computed using numpy's default linear interpolation;
# we hardcode the expectations so the test does not depend on numpy.
vals = [1.0, 2.0, 4.0, 8.0, 16.0, 32.0]
# rank for p50 = 0.5 * 5 = 2.5 -> 0.5 * 4 + 0.5 * 8 = 6.0
assert math.isclose(_percentile(vals, 0.50), 6.0)
# rank for p90 = 0.9 * 5 = 4.5 -> 0.5 * 16 + 0.5 * 32 = 24.0
assert math.isclose(_percentile(vals, 0.90), 24.0)
# rank for p99 = 0.99 * 5 = 4.95 -> 0.05 * 16 + 0.95 * 32 = 31.2
assert math.isclose(_percentile(vals, 0.99), 31.2)
def test_percentile_no_off_by_one_at_boundary():
# Regression: previous round-based implementation returned the wrong
# element when rank fell exactly on an integer.
vals = [10.0, 20.0, 30.0]
# rank for p50 = 0.5 * 2 = 1.0 -> exactly element 1 -> 20.0
assert _percentile(vals, 0.50) == 20.0