diff --git a/tests/entrypoints/pooling/basic/test_encode.py b/tests/entrypoints/pooling/basic/test_encode.py index ca85d2758f..61222eb780 100644 --- a/tests/entrypoints/pooling/basic/test_encode.py +++ b/tests/entrypoints/pooling/basic/test_encode.py @@ -7,6 +7,7 @@ import pytest from vllm import LLM, PoolingParams from vllm.distributed import cleanup_dist_env_and_memory +from vllm.exceptions import VLLMValidationError MODEL_NAME = "intfloat/multilingual-e5-small" @@ -61,7 +62,7 @@ def test_multiple_pooling_params(llm: LLM): assert len(PROMPTS) == len(outputs) # Exception raised, if the size of params does not match the size of prompts - with pytest.raises(ValueError): + with pytest.raises(VLLMValidationError): outputs = llm.encode( PROMPTS, pooling_params=pooling_params[:3], pooling_task="embed" ) diff --git a/tests/entrypoints/pooling/test_io_processor.py b/tests/entrypoints/pooling/test_io_processor.py new file mode 100644 index 0000000000..6c64966e58 --- /dev/null +++ b/tests/entrypoints/pooling/test_io_processor.py @@ -0,0 +1,76 @@ +# SPDX-License-Identifier: Apache-2.0 +# SPDX-FileCopyrightText: Copyright contributors to the vLLM project + +from types import SimpleNamespace + +import pytest + +from vllm import PoolingParams +from vllm.entrypoints.pooling.base.io_processor import PoolingIOProcessor +from vllm.entrypoints.pooling.typing import OfflineEncodeInputsContext +from vllm.exceptions import VLLMValidationError +from vllm.renderers import TokenizeParams + + +@pytest.fixture +def processor() -> PoolingIOProcessor: + return object.__new__(PoolingIOProcessor) + + +def test_rejects_untrusted_request_chat_template(processor: PoolingIOProcessor): + with pytest.raises(VLLMValidationError) as exc_info: + processor._validate_chat_template("template", None, False) + + assert str(exc_info.value) == ( + "Chat template is passed with request, but " + "--trust-request-chat-template is not set. " + "Refused request with untrusted chat template." + ) + assert exc_info.value.parameter is None + assert exc_info.value.value is None + + +def test_rejects_mismatched_pooling_params(processor: PoolingIOProcessor): + with pytest.raises(VLLMValidationError) as exc_info: + processor._params_to_seq([PoolingParams()], num_requests=2) + + assert str(exc_info.value) == ( + "The lengths of prompts (2) and params (1) must be the same." + ) + assert exc_info.value.parameter is None + assert exc_info.value.value is None + + +def test_rejects_mismatched_lora_requests(processor: PoolingIOProcessor): + with pytest.raises(VLLMValidationError) as exc_info: + processor._lora_request_to_seq([None], num_requests=2) + + assert str(exc_info.value) == ( + "The lengths of prompts (2) and lora_request (1) must be the same." + ) + assert exc_info.value.parameter is None + assert exc_info.value.value is None + + +def test_rejects_conflicting_pooling_task(processor: PoolingIOProcessor): + processor.model_config = SimpleNamespace(is_encoder_decoder=False) + processor.renderer = SimpleNamespace( + default_cmpl_tok_params=TokenizeParams(max_total_tokens=None) + ) + ctx = OfflineEncodeInputsContext( + pooling_task="embed", + tokenization_kwargs=None, + lora_request=None, + priorities=None, + prompts=[[1]], + pooling_params=PoolingParams(task="classify"), + ) + + with pytest.raises(VLLMValidationError) as exc_info: + processor.get_request_factory_offline(ctx) + + assert str(exc_info.value) == ( + "You cannot overwrite param.task='classify' with pooling_task='embed'!" + ) + assert exc_info.value.parameter is None + assert exc_info.value.value is None diff --git a/vllm/entrypoints/pooling/base/io_processor.py b/vllm/entrypoints/pooling/base/io_processor.py index f74b740276..940987fc16 100644 --- a/vllm/entrypoints/pooling/base/io_processor.py +++ b/vllm/entrypoints/pooling/base/io_processor.py @@ -13,6 +13,7 @@ from vllm.config import VllmConfig from vllm.entrypoints.chat_utils import ( ChatTemplateConfig, ) +from vllm.exceptions import VLLMValidationError from vllm.lora.request import LoRARequest from vllm.renderers import BaseRenderer, merge_kwargs from vllm.renderers.inputs.preprocess import parse_model_prompt, prompt_to_seq @@ -217,7 +218,7 @@ class PoolingIOProcessor: pass elif param.task != pooling_task: msg = f"You cannot overwrite {param.task=!r} with {pooling_task=!r}!" - raise ValueError(msg) + raise VLLMValidationError(msg) seq_lora_requests = self._lora_request_to_seq(ctx.lora_request, num_requests) seq_priority = self._priority_to_seq(ctx.priorities, num_requests) @@ -293,7 +294,7 @@ class PoolingIOProcessor: and chat_template_kwargs.get("chat_template") is not None ) ): - raise ValueError( + raise VLLMValidationError( "Chat template is passed with request, but " "--trust-request-chat-template is not set. " "Refused request with untrusted chat template." @@ -307,7 +308,7 @@ class PoolingIOProcessor: ) -> Sequence[PoolingParams]: if isinstance(params, Sequence): if len(params) != num_requests: - raise ValueError( + raise VLLMValidationError( f"The lengths of prompts ({num_requests}) " f"and params ({len(params)}) must be the same." ) @@ -323,7 +324,7 @@ class PoolingIOProcessor: ) -> Sequence[LoRARequest | None]: if isinstance(lora_request, Sequence): if len(lora_request) != num_requests: - raise ValueError( + raise VLLMValidationError( f"The lengths of prompts ({num_requests}) " f"and lora_request ({len(lora_request)}) must be the same." )