Files
sglang/test/registered/unit
leaveletandClaude Fable 5 3eef989739 Harden IndexCache for first e2e: validation, fail-fast, prefetch gating
Pre-e2e audit fixes for NSA index-topk sharing (index_topk_pattern):

- Validate the pattern at init: F/S charset only, must start with F
  (layer 0 has nothing to share from), and length must equal
  num_hidden_layers — a short pattern previously crashed deep in pool
  init with an obscure per-layer ValueError, a long one silently
  ignored tail characters. Warn when a pattern shadows a configured
  index_topk_freq (pattern takes precedence silently otherwise).
- Fail fast when a shared (S) layer receives prev_topk_indices=None:
  both gated indexer call sites previously fell through to omitting
  topk_indices entirely, running sparse attention without indices and
  silently corrupting output if threading were ever dropped.
- Reject pipeline parallelism with index-topk sharing (same rationale
  as the existing TBO guard): topk indices are not threaded across
  PP-stage boundaries, and each stage's loop resets them to None.
- Gate the CP shared-KV index prefetcher on the next layer having an
  index-cache slot: prefetching an S layer's nonexistent buffer
  tripped the inactive-layer fail-fast and disabled the prefetcher
  for the entire run on the first F->S transition.
- Log the resolved active index layer plan at pool init so an e2e run
  can confirm IndexCache is actually on.

Tests: pattern validation cases incl. the GLM-5 reference 78-char
pattern, next_skip == skip-of-next invariant; existing 'C' pattern
test updated to upstream 'F' charset.

Co-Authored-By: Claude Fable 5 <noreply@anthropic.com>
2026-06-10 06:17:52 +00:00
..

Unit Tests

Component-level tests that do not launch a server or load model weights. Tests can use CPU or GPU — the key criterion is no server process.

Quick Start

  1. Find the source file under python/sglang/srt/.
  2. Create the corresponding test here, mirroring the source tree:
    srt/mem_cache/radix_cache.py       →  unit/mem_cache/test_radix_cache.py
    srt/sampling/sampling_params.py    →  unit/sampling/test_sampling_params.py
    
  3. Register for CI at the top of the file (after imports, before test classes):
    from sglang.test.ci.ci_register import register_cpu_ci
    register_cpu_ci(est_time=5, suite="stage-a-test-cpu")
    # or: register_cuda_ci(est_time=10, suite="stage-b-test-1-gpu-small")
    
  4. Run locally:
    pytest test/registered/unit/ -v            # all unit tests
    pytest test/registered/unit/mem_cache/ -v  # one module
    
  5. Run with coverage:
    # summary
    pytest test/registered/unit/ --cov --cov-config=.coveragerc -v
    
    # PR incremental check (require ≥60% on changed lines)
    pytest test/registered/unit/ --cov --cov-config=.coveragerc --cov-report=xml
    diff-cover coverage.xml --compare-branch=origin/main --fail-under=60
    

Example

"""Unit tests for <module> — no server, no model loading."""

from sglang.test.ci.ci_register import register_cpu_ci

register_cpu_ci(est_time=5, suite="stage-a-test-cpu")

import unittest

from sglang.srt.<module> import TargetClass
from sglang.test.test_utils import CustomTestCase


class TestTargetClass(CustomTestCase):
    def test_basic_behavior(self):
        obj = TargetClass(...)
        self.assertEqual(obj.method(), expected)


if __name__ == "__main__":
    unittest.main()

Rules

  • No popen_launch_server() or Engine(...).
  • No model weight loading.
  • Use CustomTestCase (from sglang.test.test_utils, adds CI retry).
  • Use unittest.mock for dependencies that are expensive to construct.