From e6da514c2c016d2fb269c4b2bf16d105dc18df90 Mon Sep 17 00:00:00 2001 From: yrk111222 <2493404415@qq.com> Date: Sat, 28 Feb 2026 06:00:41 +0800 Subject: [PATCH] CI: use 'sglang serve' in CI tests (#18597) Co-authored-by: Mick Co-authored-by: sglang-bot --- python/sglang/cli/utils.py | 33 +++++++++++++++++++--- python/sglang/multimodal_gen/utils.py | 11 -------- python/sglang/test/test_utils.py | 40 ++++++++++++--------------- 3 files changed, 47 insertions(+), 37 deletions(-) diff --git a/python/sglang/cli/utils.py b/python/sglang/cli/utils.py index 4f67f58c0..b198809e0 100644 --- a/python/sglang/cli/utils.py +++ b/python/sglang/cli/utils.py @@ -26,6 +26,33 @@ def _get_lock(model_name_or_path: str, cache_dir: Optional[str] = None): return lock +def _hf_hub_download( + repo_id: str, + filename: str, + local_dir: Optional[str] = None, + **kwargs, +) -> str: + """Unified hf_hub_download supporting both Hugging Face Hub and ModelScope.""" + if envs.SGLANG_USE_MODELSCOPE.get(): + from modelscope import model_file_download + + return model_file_download( + model_id=repo_id, + file_path=filename, + cache_dir=local_dir, + **kwargs, + ) + else: + from huggingface_hub import hf_hub_download as _hf_hub_download_impl + + return _hf_hub_download_impl( + repo_id=repo_id, + filename=filename, + local_dir=local_dir, + **kwargs, + ) + + # Copied and adapted from hf_diffusers_utils.py def _maybe_download_model( model_name_or_path: str, local_dir: str | None = None, download: bool = True @@ -44,8 +71,6 @@ def _maybe_download_model( Local directory path that contains the downloaded config file, or the original local directory. """ - from sglang.multimodal_gen.runtime.utils.hf_diffusers_utils import hf_hub_download - if os.path.exists(model_name_or_path): logger.debug("Model already exists locally") return model_name_or_path @@ -62,7 +87,7 @@ def _maybe_download_model( source_hub, model_name_or_path, ) - file_path = hf_hub_download( + file_path = _hf_hub_download( repo_id=model_name_or_path, filename="model_index.json", local_dir=local_dir, @@ -79,7 +104,7 @@ def _maybe_download_model( source_hub, model_name_or_path, ) - file_path = hf_hub_download( + file_path = _hf_hub_download( repo_id=model_name_or_path, filename="config.json", local_dir=local_dir, diff --git a/python/sglang/multimodal_gen/utils.py b/python/sglang/multimodal_gen/utils.py index 87bdf6341..97cd59acc 100644 --- a/python/sglang/multimodal_gen/utils.py +++ b/python/sglang/multimodal_gen/utils.py @@ -11,7 +11,6 @@ import inspect import math import os import signal -import socket import sys import threading import traceback @@ -23,7 +22,6 @@ from typing import Any, TypeVar, cast import cloudpickle import torch import yaml -from remote_pdb import RemotePdb from torch.distributed.fsdp import MixedPrecisionPolicy import sglang.multimodal_gen.envs as envs @@ -546,15 +544,6 @@ class TypeBasedDispatcher: raise ValueError(f"Invalid object: {obj}") -# For non-torch.distributed debugging -def remote_breakpoint() -> None: - with socket.socket(socket.AF_INET, socket.SOCK_STREAM) as s: - s.setsockopt(socket.SOL_SOCKET, socket.SO_REUSEADDR, 1) - s.bind(("localhost", 0)) # Let the OS pick an ephemeral port. - port = s.getsockname()[1] - RemotePdb(host="localhost", port=port).set_trace() - - @dataclass class MixedPrecisionState: param_dtype: torch.dtype | None = None diff --git a/python/sglang/test/test_utils.py b/python/sglang/test/test_utils.py index ce0064710..82ad0d963 100644 --- a/python/sglang/test/test_utils.py +++ b/python/sglang/test/test_utils.py @@ -879,18 +879,22 @@ def popen_launch_server( use_mixed_pd_engine = not pd_separated and num_replicas is not None if pd_separated or use_mixed_pd_engine: - command = "sglang.launch_pd_server" + command = [ + "python3", + "-m", + "sglang.launch_pd_server", + "--model-path", + model, + *[str(x) for x in other_args], + ] else: - command = "sglang.launch_server" - - command = [ - "python3", - "-m", - command, - "--model-path", - model, - *[str(x) for x in other_args], - ] + command = [ + "sglang", + "serve", + "--model-path", + model, + *[str(x) for x in other_args], + ] if pd_separated or use_mixed_pd_engine: command.extend(["--lb-host", host, "--lb-port", port]) @@ -1308,7 +1312,7 @@ def run_score_benchmark( json=warmup_data, timeout=aiohttp.ClientTimeout(total=30), ) - except: + except Exception: pass # Ignore warmup errors test_requests = [] @@ -1376,17 +1380,9 @@ def run_embeddings_benchmark( async def _run_benchmark(): - # Load tokenizer for generating test data - from sglang.srt.utils.hf_transformers_utils import get_tokenizer - - tokenizer = get_tokenizer(model) - def generate_text_with_token_count(num_tokens): """Generate text with precise token count using special tokens.""" - # Use a token that reliably produces 1 token special_token = "<|im_start|>" - # Verify it's a single token - test_tokens = tokenizer.encode(special_token, add_special_tokens=False) text = special_token * num_tokens return text @@ -1406,7 +1402,7 @@ def run_embeddings_benchmark( json=warmup_data, timeout=aiohttp.ClientTimeout(total=30), ) - except: + except Exception: pass # Ignore warmup errors test_requests = [] @@ -1822,7 +1818,7 @@ def run_mulit_request_test( }, }, ) - ret = response.json() + response.json() with ThreadPoolExecutor(2) as executor: list(executor.map(run_one, list(range(4))))