A high-throughput and memory-efficient inference and serving engine for LLMs
Mirrored from https://github.com/tduncan-lum/Nvidia-Optimization-Stack---VLLM.git
Synced Nov 15, 21:00 UTC
Update deprecated Python 3.8 typing (#13971)
Harry Mellor committed
Mar 3, 2025 at 01:34 UTC
cf069aa8aa38a9003c254f8434a29ec6a3070b08
300 files changed
+2294
-2347
benchmarks/backend_request_func.py
+3
-3
@@ -6,7 +6,7 @@ import sys
6
import time
7
import traceback
8
from dataclasses import dataclass, field
9
-from typing import List, Optional, Union
9
+from typing import Optional, Union
10
11
import aiohttp
12
import huggingface_hub.constants
@@ -41,8 +41,8 @@ class RequestFuncOutput:
41
latency: float = 0.0
42
output_tokens: int = 0
43
ttft: float = 0.0 # Time to first token
44
- itl: List[float] = field(
45
- default_factory=list) # List of inter-token latencies
44
+ itl: list[float] = field(
45
+ default_factory=list) # list of inter-token latencies
46
tpot: float = 0.0 # avg next-token latencies
47
prompt_len: int = 0
48
error: str = ""
benchmarks/benchmark_guided.py
+8
-9
@@ -6,7 +6,6 @@ import json
6
import os
7
import random
8
import time
9
-from typing import List
9
10
import datasets
11
import pandas as pd
@@ -39,7 +38,7 @@ class SampleRequest:
38
completion: str = None
39
40
42
-def run_vllm(requests: List[SampleRequest],
41
+def run_vllm(requests: list[SampleRequest],
42
engine_args: EngineArgs,
43
n: int,
44
guided_decoding_rate: float = 1.0,
@@ -54,8 +53,8 @@ def run_vllm(requests: List[SampleRequest],
53
" prompt_len and expected_output_len for all requests.")
54
55
# Add the requests to the engine.
57
- prompts: List[str] = []
58
- sampling_params: List[SamplingParams] = []
56
+ prompts: list[str] = []
57
+ sampling_params: list[SamplingParams] = []
58
# create a list containing random selected true or false
59
guided_decoding_req_idx = random.sample(
60
range(len(requests)), int(len(requests) * guided_decoding_rate))
@@ -110,7 +109,7 @@ def run_vllm(requests: List[SampleRequest],
109
110
111
async def run_vllm_async(
113
- requests: List[SampleRequest],
112
+ requests: list[SampleRequest],
113
engine_args: AsyncEngineArgs,
114
n: int,
115
guided_decoding_rate: float = 1.0,
@@ -129,8 +128,8 @@ async def run_vllm_async(
128
" prompt_len and expected_output_len for all requests.")
129
130
# Add the requests to the engine.
132
- prompts: List[str] = []
133
- sampling_params: List[SamplingParams] = []
131
+ prompts: list[str] = []
132
+ sampling_params: list[SamplingParams] = []
133
guided_decoding_req_idx = random.sample(
134
range(len(requests)), int(len(requests) * guided_decoding_rate))
135
@@ -203,7 +202,7 @@ async def run_vllm_async(
202
203
204
def sample_requests(tokenizer: PreTrainedTokenizerBase,
206
- args: argparse.Namespace) -> List[SampleRequest]:
205
+ args: argparse.Namespace) -> list[SampleRequest]:
206
if args.dataset == 'json':
207
if args.json_schema_path is None:
208
dir_path = os.path.dirname(os.path.realpath(__file__))
@@ -287,7 +286,7 @@ def sample_requests(tokenizer: PreTrainedTokenizerBase,
286
287
elif args.dataset == "xgrammar_bench":
288
args.warmup = False
290
- requests: List[SampleRequest] = []
289
+ requests: list[SampleRequest] = []
290
dataset = datasets.load_dataset("NousResearch/json-mode-eval",
291
split="train")
292
print(f"dataset has {len(dataset)} entries")
benchmarks/benchmark_latency.py
+3
-3
@@ -7,7 +7,7 @@ import json
7
import os
8
import time
9
from pathlib import Path
10
-from typing import Any, Dict, List, Optional
10
+from typing import Any, Optional
11
12
import numpy as np
13
import torch
@@ -22,7 +22,7 @@ from vllm.utils import FlexibleArgumentParser
22
23
24
def save_to_pytorch_benchmark_format(args: argparse.Namespace,
25
- results: Dict[str, Any]) -> None:
25
+ results: dict[str, Any]) -> None:
26
pt_records = convert_to_pytorch_benchmark_format(
27
args=args,
28
metrics={"latency": results["latencies"]},
@@ -57,7 +57,7 @@ def main(args: argparse.Namespace):
57
dummy_prompt_token_ids = np.random.randint(10000,
58
size=(args.batch_size,
59
args.input_len))
60
- dummy_prompts: List[PromptType] = [{
60
+ dummy_prompts: list[PromptType] = [{
61
"prompt_token_ids": batch
62
} for batch in dummy_prompt_token_ids.tolist()]
63
benchmarks/benchmark_prefix_caching.py
+8
-8
@@ -31,7 +31,7 @@ import dataclasses
31
import json
32
import random
33
import time
34
-from typing import List, Optional, Tuple
34
+from typing import Optional
35
36
from transformers import PreTrainedTokenizerBase
37
@@ -77,9 +77,9 @@ def sample_requests_from_dataset(
77
dataset_path: str,
78
num_requests: int,
79
tokenizer: PreTrainedTokenizerBase,
80
- input_length_range: Tuple[int, int],
80
+ input_length_range: tuple[int, int],
81
fixed_output_len: Optional[int],
82
-) -> List[Request]:
82
+) -> list[Request]:
83
if fixed_output_len is not None and fixed_output_len < 4:
84
raise ValueError("output_len too small")
85
@@ -99,7 +99,7 @@ def sample_requests_from_dataset(
99
assert min_len >= 0 and max_len >= min_len, "input_length_range too small"
100
101
# Filter out sequences that are too long or too short
102
- filtered_requests: List[Request] = []
102
+ filtered_requests: list[Request] = []
103
104
for i in range(len(dataset)):
105
if len(filtered_requests) == num_requests:
@@ -122,10 +122,10 @@ def sample_requests_from_dataset(
122
def sample_requests_from_random(
123
num_requests: int,
124
tokenizer: PreTrainedTokenizerBase,
125
- input_length_range: Tuple[int, int],
125
+ input_length_range: tuple[int, int],
126
fixed_output_len: Optional[int],
127
prefix_len: int,
128
-) -> List[Request]:
128
+) -> list[Request]:
129
130
requests = []
131
prefix_token_ids = sample_tokens(tokenizer, prefix_len)
@@ -144,9 +144,9 @@ def sample_requests_from_random(
144
return requests
145
146
147
-def repeat_and_sort_requests(requests: List[Request],
147
+def repeat_and_sort_requests(requests: list[Request],
148
repeat_count: int,
149
- sort: bool = False) -> List[str]:
149
+ sort: bool = False) -> list[str]:
150
repeated_requests = requests * repeat_count
151
if sort:
152
repeated_requests.sort(key=lambda x: x[1])
benchmarks/benchmark_prioritization.py
+4
-4
@@ -5,7 +5,7 @@ import dataclasses
5
import json
6
import random
7
import time
8
-from typing import List, Optional, Tuple
8
+from typing import Optional
9
10
from transformers import AutoTokenizer, PreTrainedTokenizerBase
11
@@ -23,7 +23,7 @@ def sample_requests(
23
num_requests: int,
24
tokenizer: PreTrainedTokenizerBase,
25
fixed_output_len: Optional[int],
26
-) -> List[Tuple[str, int, int]]:
26
+) -> list[tuple[str, int, int]]:
27
if fixed_output_len is not None and fixed_output_len < 4:
28
raise ValueError("output_len too small")
29
@@ -40,7 +40,7 @@ def sample_requests(
40
random.shuffle(dataset)
41
42
# Filter out sequences that are too long or too short
43
- filtered_dataset: List[Tuple[str, int, int]] = []
43
+ filtered_dataset: list[tuple[str, int, int]] = []
44
for i in range(len(dataset)):
45
if len(filtered_dataset) == num_requests:
46
break
@@ -68,7 +68,7 @@ def sample_requests(
68
69
70
def run_vllm(
71
- requests: List[Tuple[str, int, int]],
71
+ requests: list[tuple[str, int, int]],
72
n: int,
73
engine_args: EngineArgs,
74
) -> float:
benchmarks/benchmark_serving.py
+39
-38
@@ -33,9 +33,10 @@ import os
33
import random
34
import time
35
import warnings
36
+from collections.abc import AsyncGenerator, Collection
37
from dataclasses import dataclass
38
from datetime import datetime
38
-from typing import Any, AsyncGenerator, Collection, Dict, List, Optional, Tuple
39
+from typing import Any, Optional
40
41
import numpy as np
42
import pandas as pd
@@ -73,22 +74,22 @@ class BenchmarkMetrics:
74
mean_ttft_ms: float
75
median_ttft_ms: float
76
std_ttft_ms: float
76
- percentiles_ttft_ms: List[Tuple[float, float]]
77
+ percentiles_ttft_ms: list[tuple[float, float]]
78
mean_tpot_ms: float
79
median_tpot_ms: float
80
std_tpot_ms: float
80
- percentiles_tpot_ms: List[Tuple[float, float]]
81
+ percentiles_tpot_ms: list[tuple[float, float]]
82
mean_itl_ms: float
83
median_itl_ms: float
84
std_itl_ms: float
84
- percentiles_itl_ms: List[Tuple[float, float]]
85
+ percentiles_itl_ms: list[tuple[float, float]]
86
# E2EL stands for end-to-end latency per request.
87
# It is the time taken on the client side from sending
88
# a request to receiving a complete response.
89
mean_e2el_ms: float
90
median_e2el_ms: float
91
std_e2el_ms: float
91
- percentiles_e2el_ms: List[Tuple[float, float]]
92
+ percentiles_e2el_ms: list[tuple[float, float]]
93
94
95
def sample_sharegpt_requests(
@@ -96,7 +97,7 @@ def sample_sharegpt_requests(
97
num_requests: int,
98
tokenizer: PreTrainedTokenizerBase,
99
fixed_output_len: Optional[int] = None,
99
-) -> List[Tuple[str, int, int, None]]:
100
+) -> list[tuple[str, int, int, None]]:
101
# Load the dataset.
102
with open(dataset_path, encoding='utf-8') as f:
103
dataset = json.load(f)
@@ -110,7 +111,7 @@ def sample_sharegpt_requests(
111
random.shuffle(dataset)
112
113
# Filter out sequences that are too long or too short
113
- filtered_dataset: List[Tuple[str, int, int]] = []
114
+ filtered_dataset: list[tuple[str, int, int]] = []
115
for i in range(len(dataset)):
116
if len(filtered_dataset) == num_requests:
117
break
@@ -139,7 +140,7 @@ def sample_burstgpt_requests(
140
num_requests: int,
141
random_seed: int,
142
tokenizer: PreTrainedTokenizerBase,
142
-) -> List[Tuple[str, int, int, None]]:
143
+) -> list[tuple[str, int, int, None]]:
144
df = pd.read_csv(dataset_path)
145
gpt4_df = df[df["Model"] == "GPT-4"]
146
# Remove the failed requests (i.e., response length is 0)
@@ -170,7 +171,7 @@ def sample_sonnet_requests(
171
output_len: int,
172
prefix_len: int,
173
tokenizer: PreTrainedTokenizerBase,
173
-) -> List[Tuple[str, str, int, int, None]]:
174
+) -> list[tuple[str, str, int, int, None]]:
175
assert (
176
input_len > prefix_len
177
), "'args.sonnet-input-len' must be greater than 'args.prefix-input-len'."
@@ -211,7 +212,7 @@ def sample_sonnet_requests(
212
prefix_lines = poem_lines[:num_prefix_lines]
213
214
# Sample the rest of lines per request.
214
- sampled_requests: List[Tuple[str, int, int]] = []
215
+ sampled_requests: list[tuple[str, int, int]] = []
216
for _ in range(num_requests):
217
num_lines_needed = num_input_lines - num_prefix_lines
218
sampled_lines = "".join(prefix_lines +
@@ -238,8 +239,8 @@ def sample_vision_arena_requests(
239
num_requests: int,
240
tokenizer: PreTrainedTokenizerBase,
241
fixed_output_len: Optional[int] = None,
241
-) -> List[Tuple[str, str, int, Optional[Dict[str, Collection[str]]]]]:
242
- sampled_requests: List[Tuple[str, int, int, Dict[str,
242
+) -> list[tuple[str, str, int, Optional[dict[str, Collection[str]]]]]:
243
+ sampled_requests: list[tuple[str, int, int, dict[str,
244
Collection[str]]]] = []
245
for data in dataset:
246
if len(sampled_requests) == num_requests:
@@ -285,7 +286,7 @@ def sample_hf_requests(
286
tokenizer: PreTrainedTokenizerBase,
287
random_seed: int,
288
fixed_output_len: Optional[int] = None,
288
-) -> List[Tuple[str, str, int, Optional[Dict[str, Collection[str]]]]]:
289
+) -> list[tuple[str, str, int, Optional[dict[str, Collection[str]]]]]:
290
291
# Special case for vision_arena dataset
292
if dataset_path == 'lmarena-ai/vision-arena-bench-v0.1' \
@@ -307,7 +308,7 @@ def sample_hf_requests(
308
"HF Dataset must have 'conversations' column.")
309
filter_func = lambda x: len(x["conversations"]) >= 2
310
filtered_dataset = dataset.shuffle(seed=random_seed).filter(filter_func)
310
- sampled_requests: List[Tuple[str, int, int, Dict[str,
311
+ sampled_requests: list[tuple[str, int, int, dict[str,
312
Collection[str]]]] = []
313
for data in filtered_dataset:
314
if len(sampled_requests) == num_requests:
@@ -370,7 +371,7 @@ def sample_random_requests(
371
num_prompts: int,
372
range_ratio: float,
373
tokenizer: PreTrainedTokenizerBase,
373
-) -> List[Tuple[str, int, int]]:
374
+) -> list[tuple[str, int, int]]:
375
prefix_token_ids = np.random.randint(0,
376
tokenizer.vocab_size,
377
size=prefix_len).tolist()
@@ -399,10 +400,10 @@ def sample_random_requests(
400
401
402
async def get_request(
402
- input_requests: List[Tuple[str, int, int]],
403
+ input_requests: list[tuple[str, int, int]],
404
request_rate: float,
405
burstiness: float = 1.0,
405
-) -> AsyncGenerator[Tuple[str, int, int], None]:
406
+) -> AsyncGenerator[tuple[str, int, int], None]:
407
"""
408
Asynchronously generates requests at a specified rate
409
with OPTIONAL burstiness.
@@ -443,23 +444,23 @@ async def get_request(
444
445
446
def calculate_metrics(
446
- input_requests: List[Tuple[str, int, int]],
447
- outputs: List[RequestFuncOutput],
447
+ input_requests: list[tuple[str, int, int]],
448
+ outputs: list[RequestFuncOutput],
449
dur_s: float,
450
tokenizer: PreTrainedTokenizerBase,
450
- selected_percentile_metrics: List[str],
451
- selected_percentiles: List[float],
452
- goodput_config_dict: Dict[str, float],
453
-) -> Tuple[BenchmarkMetrics, List[int]]:
454
- actual_output_lens: List[int] = []
451
+ selected_percentile_metrics: list[str],
452
+ selected_percentiles: list[float],
453
+ goodput_config_dict: dict[str, float],
454
+) -> tuple[BenchmarkMetrics, list[int]]:
455
+ actual_output_lens: list[int] = []
456
total_input = 0
457
completed = 0
458
good_completed = 0
458
- itls: List[float] = []
459
- tpots: List[float] = []
460
- all_tpots: List[float] = []
461
- ttfts: List[float] = []
462
- e2els: List[float] = []
459
+ itls: list[float] = []
460
+ tpots: list[float] = []
461
+ all_tpots: list[float] = []
462
+ ttfts: list[float] = []
463
+ e2els: list[float] = []
464
for i in range(len(outputs)):
465
if outputs[i].success:
466
output_len = outputs[i].output_tokens
@@ -557,19 +558,19 @@ async def benchmark(
558
model_id: str,
559
model_name: str,
560
tokenizer: PreTrainedTokenizerBase,
560
- input_requests: List[Tuple[str, int, int]],
561
+ input_requests: list[tuple[str, int, int]],
562
logprobs: Optional[int],
563
best_of: int,
564
request_rate: float,
565
burstiness: float,
566
disable_tqdm: bool,
567
profile: bool,
567
- selected_percentile_metrics: List[str],
568
- selected_percentiles: List[str],
568
+ selected_percentile_metrics: list[str],
569
+ selected_percentiles: list[str],
570
ignore_eos: bool,
570
- goodput_config_dict: Dict[str, float],
571
+ goodput_config_dict: dict[str, float],
572
max_concurrency: Optional[int],
572
- lora_modules: Optional[List[str]],
573
+ lora_modules: Optional[list[str]],
574
):
575
if backend in ASYNC_REQUEST_FUNCS:
576
request_func = ASYNC_REQUEST_FUNCS[backend]
@@ -652,7 +653,7 @@ async def benchmark(
653
pbar=pbar)
654
655
benchmark_start_time = time.perf_counter()
655
- tasks: List[asyncio.Task] = []
656
+ tasks: list[asyncio.Task] = []
657
async for request in get_request(input_requests, request_rate, burstiness):
658
prompt, prompt_len, output_len, mm_content = request
659
req_model_id, req_model_name = model_id, model_name
@@ -674,7 +675,7 @@ async def benchmark(
675
asyncio.create_task(
676
limited_request_func(request_func_input=request_func_input,
677
pbar=pbar)))
677
- outputs: List[RequestFuncOutput] = await asyncio.gather(*tasks)
678
+ outputs: list[RequestFuncOutput] = await asyncio.gather(*tasks)
679
680
if profile:
681
print("Stopping profiler...")
@@ -820,7 +821,7 @@ def parse_goodput(slo_pairs):
821
822
823
def save_to_pytorch_benchmark_format(args: argparse.Namespace,
823
- results: Dict[str, Any],
824
+ results: dict[str, Any],
825
file_name: str) -> None:
826
metrics = [
827
"median_ttft_ms", "mean_ttft_ms", "std_ttft_ms", "p99_ttft_ms",
@@ -974,7 +975,7 @@ def main(args: argparse.Namespace):
975
976
# Save config and results to json
977
if args.save_result:
977
- result_json: Dict[str, Any] = {}
978
+ result_json: dict[str, Any] = {}
979
980
# Setup
981
current_dt = datetime.now().strftime("%Y%m%d-%H%M%S")
benchmarks/benchmark_serving_guided.py
+29
-28
@@ -30,8 +30,9 @@ import os
30
import random
31
import time
32
import warnings
33
+from collections.abc import AsyncGenerator
34
from dataclasses import dataclass
34
-from typing import AsyncGenerator, Dict, List, Optional, Tuple
35
+from typing import Optional
36
37
import datasets
38
import numpy as np
@@ -66,22 +67,22 @@ class BenchmarkMetrics:
67
mean_ttft_ms: float
68
median_ttft_ms: float
69
std_ttft_ms: float
69
- percentiles_ttft_ms: List[Tuple[float, float]]
70
+ percentiles_ttft_ms: list[tuple[float, float]]
71
mean_tpot_ms: float
72
median_tpot_ms: float
73
std_tpot_ms: float
73
- percentiles_tpot_ms: List[Tuple[float, float]]
74
+ percentiles_tpot_ms: list[tuple[float, float]]
75
mean_itl_ms: float
76
median_itl_ms: float
77
std_itl_ms: float
77
- percentiles_itl_ms: List[Tuple[float, float]]
78
+ percentiles_itl_ms: list[tuple[float, float]]
79
# E2EL stands for end-to-end latency per request.
80
# It is the time taken on the client side from sending
81
# a request to receiving a complete response.
82
mean_e2el_ms: float
83
median_e2el_ms: float
84
std_e2el_ms: float
84
- percentiles_e2el_ms: List[Tuple[float, float]]
85
+ percentiles_e2el_ms: list[tuple[float, float]]
86
87
88
@dataclasses.dataclass
@@ -104,7 +105,7 @@ class SampleRequest:
105
106
107
def sample_requests(tokenizer: PreTrainedTokenizerBase,
107
- args: argparse.Namespace) -> List[SampleRequest]:
108
+ args: argparse.Namespace) -> list[SampleRequest]:
109
if args.dataset == 'json':
110
if args.json_schema_path is None:
111
dir_path = os.path.dirname(os.path.realpath(__file__))
@@ -187,7 +188,7 @@ def sample_requests(tokenizer: PreTrainedTokenizerBase,
188
]
189
190
elif args.dataset == "xgrammar_bench":
190
- requests: List[SampleRequest] = []
191
+ requests: list[SampleRequest] = []
192
dataset = datasets.load_dataset("NousResearch/json-mode-eval",
193
split="train")
194
print(f"dataset has {len(dataset)} entries")
@@ -214,10 +215,10 @@ def sample_requests(tokenizer: PreTrainedTokenizerBase,
215
216
217
async def get_request(
217
- input_requests: List[SampleRequest],
218
+ input_requests: list[SampleRequest],
219
request_rate: float,
220
burstiness: float = 1.0,
220
-) -> AsyncGenerator[Tuple[int, SampleRequest], None]:
221
+) -> AsyncGenerator[tuple[int, SampleRequest], None]:
222
"""
223
Asynchronously generates requests at a specified rate
224
with OPTIONAL burstiness.
@@ -258,23 +259,23 @@ async def get_request(
259
260
261
def calculate_metrics(
261
- input_requests: List[Tuple[str, int, int]],
262
- outputs: List[RequestFuncOutput],
262
+ input_requests: list[tuple[str, int, int]],
263
+ outputs: list[RequestFuncOutput],
264
dur_s: float,
265
tokenizer: PreTrainedTokenizerBase,
265
- selected_percentile_metrics: List[str],
266
- selected_percentiles: List[float],
267
- goodput_config_dict: Optional[Dict[str, float]] = None,
268
-) -> Tuple[BenchmarkMetrics, List[int]]:
269
- actual_output_lens: List[int] = []
266
+ selected_percentile_metrics: list[str],
267
+ selected_percentiles: list[float],
268
+ goodput_config_dict: Optional[dict[str, float]] = None,
269
+) -> tuple[BenchmarkMetrics, list[int]]:
270
+ actual_output_lens: list[int] = []
271
total_input = 0
272
completed = 0
273
good_completed = 0
273
- itls: List[float] = []
274
- tpots: List[float] = []
275
- all_tpots: List[float] = []
276
- ttfts: List[float] = []
277
- e2els: List[float] = []
274
+ itls: list[float] = []
275
+ tpots: list[float] = []
276
+ all_tpots: list[float] = []
277
+ ttfts: list[float] = []
278
+ e2els: list[float] = []
279
for i in range(len(outputs)):
280
if outputs[i].success:
281
# We use the tokenizer to count the number of output tokens for all
@@ -368,18 +369,18 @@ async def benchmark(
369
base_url: str,
370
model_id: str,
371
tokenizer: PreTrainedTokenizerBase,
371
- input_requests: List[SampleRequest],
372
+ input_requests: list[SampleRequest],
373
request_rate: float,
374
burstiness: float,
375
disable_tqdm: bool,
376
profile: bool,
376
- selected_percentile_metrics: List[str],
377
- selected_percentiles: List[str],
377
+ selected_percentile_metrics: list[str],
378
+ selected_percentiles: list[str],
379
ignore_eos: bool,
380
max_concurrency: Optional[int],
381
guided_decoding_ratio: float,
382
guided_decoding_backend: str,
382
- goodput_config_dict: Optional[Dict[str, float]] = None,
383
+ goodput_config_dict: Optional[dict[str, float]] = None,
384
):
385
if backend in ASYNC_REQUEST_FUNCS:
386
request_func = ASYNC_REQUEST_FUNCS[backend]
@@ -459,8 +460,8 @@ async def benchmark(
460
pbar=pbar)
461
462
benchmark_start_time = time.perf_counter()
462
- tasks: List[asyncio.Task] = []
463
- expected: List[str] = []
463
+ tasks: list[asyncio.Task] = []
464
+ expected: list[str] = []
465
async for i, request in get_request(input_requests, request_rate,
466
burstiness):
467
extra_body = prepare_extra_body(
@@ -479,7 +480,7 @@ async def benchmark(
480
asyncio.create_task(
481
limited_request_func(request_func_input=request_func_input,
482
pbar=pbar)))
482
- outputs: List[RequestFuncOutput] = await asyncio.gather(*tasks)
483
+ outputs: list[RequestFuncOutput] = await asyncio.gather(*tasks)
484
485
if profile:
486
print("Stopping profiler...")
benchmarks/benchmark_throughput.py
+19
-19
@@ -7,7 +7,7 @@ import os
7
import random
8
import time
9
from functools import cache
10
-from typing import Any, Dict, List, Optional, Tuple
10
+from typing import Any, Optional
11
12
import torch
13
import uvloop
@@ -74,12 +74,12 @@ def lora_path_on_disk(lora_path: str) -> str:
74
return get_adapter_absolute_path(lora_path)
75
76
77
-lora_tokenizer_cache: Dict[int, AnyTokenizer] = {}
77
+lora_tokenizer_cache: dict[int, AnyTokenizer] = {}
78
79
80
def get_random_lora_request(
81
args: argparse.Namespace
82
-) -> Tuple[LoRARequest, Optional[AnyTokenizer]]:
82
+) -> tuple[LoRARequest, Optional[AnyTokenizer]]:
83
global lora_tokenizer_cache
84
lora_id = random.randint(1, args.max_loras)
85
lora_request = LoRARequest(lora_name=str(lora_id),
@@ -91,7 +91,7 @@ def get_random_lora_request(
91
92
93
def sample_requests(tokenizer: PreTrainedTokenizerBase,
94
- args: argparse.Namespace) -> List[SampleRequest]:
94
+ args: argparse.Namespace) -> list[SampleRequest]:
95
96
dataset_path: str = args.dataset
97
num_requests: int = args.num_prompts
@@ -109,7 +109,7 @@ def sample_requests(tokenizer: PreTrainedTokenizerBase,
109
random.shuffle(dataset)
110
111
# Filter out sequences that are too long or too short
112
- filtered_dataset: List[SampleRequest] = []
112
+ filtered_dataset: list[SampleRequest] = []
113
for data in tqdm(dataset,
114
total=len(filtered_dataset),
115
desc="sampling requests"):
@@ -165,7 +165,7 @@ def sample_requests(tokenizer: PreTrainedTokenizerBase,
165
166
167
def run_vllm(
168
- requests: List[SampleRequest],
168
+ requests: list[SampleRequest],
169
n: int,
170
engine_args: EngineArgs,
171
) -> float:
@@ -178,8 +178,8 @@ def run_vllm(
178
"Please ensure that max_model_len is greater than the sum of"
179
" prompt_len and expected_output_len for all requests.")
180
# Add the requests to the engine.
181
- prompts: List[TextPrompt] = []
182
- sampling_params: List[SamplingParams] = []
181
+ prompts: list[TextPrompt] = []
182
+ sampling_params: list[SamplingParams] = []
183
for request in requests:
184
prompts.append(
185
TextPrompt(prompt=request.prompt,
@@ -192,7 +192,7 @@ def run_vllm(
192
ignore_eos=True,
193
max_tokens=request.expected_output_len,
194
))
195
- lora_requests: Optional[List[LoRARequest]] = None
195
+ lora_requests: Optional[list[LoRARequest]] = None
196
if engine_args.enable_lora:
197
lora_requests = [request.lora_request for request in requests]
198
@@ -225,7 +225,7 @@ def run_vllm(
225
226
227
async def run_vllm_async(
228
- requests: List[SampleRequest],
228
+ requests: list[SampleRequest],
229
n: int,
230
engine_args: AsyncEngineArgs,
231
disable_frontend_multiprocessing: bool = False,
@@ -242,9 +242,9 @@ async def run_vllm_async(
242
" prompt_len and expected_output_len for all requests.")
243
244
# Add the requests to the engine.
245
- prompts: List[TextPrompt] = []
246
- sampling_params: List[SamplingParams] = []
247
- lora_requests: List[Optional[LoRARequest]] = []
245
+ prompts: list[TextPrompt] = []
246
+ sampling_params: list[SamplingParams] = []
247
+ lora_requests: list[Optional[LoRARequest]] = []
248
for request in requests:
249
prompts.append(
250
TextPrompt(prompt=request.prompt,
@@ -276,7 +276,7 @@ async def run_vllm_async(
276
277
278
def run_hf(
279
- requests: List[SampleRequest],
279
+ requests: list[SampleRequest],
280
model: str,
281
tokenizer: PreTrainedTokenizerBase,
282
n: int,
@@ -292,7 +292,7 @@ def run_hf(
292
293
pbar = tqdm(total=len(requests))
294
start = time.perf_counter()
295
- batch: List[str] = []
295
+ batch: list[str] = []
296
max_prompt_len = 0
297
max_output_len = 0
298
for i in range(len(requests)):
@@ -334,7 +334,7 @@ def run_hf(
334
335
336
def run_mii(
337
- requests: List[SampleRequest],
337
+ requests: list[SampleRequest],
338
model: str,
339
tensor_parallel_size: int,
340
output_len: int,
@@ -352,7 +352,7 @@ def run_mii(
352
353
354
def save_to_pytorch_benchmark_format(args: argparse.Namespace,
355
- results: Dict[str, Any]) -> None:
355
+ results: dict[str, Any]) -> None:
356
pt_records = convert_to_pytorch_benchmark_format(
357
args=args,
358
metrics={
@@ -479,8 +479,8 @@ if __name__ == "__main__":
479
type=str,
480
default=None,
481
help="Path to the dataset. The dataset is expected to "
482
- "be a json in form of List[Dict[..., conversations: "
483
- "List[Dict[..., value: <prompt_or_response>]]]]")
482
+ "be a json in form of list[dict[..., conversations: "
483
+ "list[dict[..., value: <prompt_or_response>]]]]")
484
parser.add_argument("--input-len",
485
type=int,
486
default=None,
benchmarks/benchmark_utils.py
+4
-4
@@ -4,12 +4,12 @@ import argparse
4
import json
5
import math
6
import os
7
-from typing import Any, Dict, List
7
+from typing import Any
8
9
10
def convert_to_pytorch_benchmark_format(args: argparse.Namespace,
11
- metrics: Dict[str, List],
12
- extra_info: Dict[str, Any]) -> List:
11
+ metrics: dict[str, list],
12
+ extra_info: dict[str, Any]) -> list:
13
"""
14
Save the benchmark results in the format used by PyTorch OSS benchmark with
15
on metric per record
@@ -64,6 +64,6 @@ class InfEncoder(json.JSONEncoder):
64
return super().iterencode(self.clear_inf(o), *args, **kwargs)
65
66
67
-def write_to_json(filename: str, records: List) -> None:
67
+def write_to_json(filename: str, records: list) -> None:
68
with open(filename, "w") as f:
69
json.dump(records, f, cls=InfEncoder)
benchmarks/cutlass_benchmarks/sparse_benchmarks.py
+5
-4
@@ -5,7 +5,8 @@ import copy
5
import itertools
6
import pickle as pkl
7
import time
8
-from typing import Callable, Iterable, List, Tuple
8
+from collections.abc import Iterable
9
+from typing import Callable
10
11
import torch
12
import torch.utils.benchmark as TBenchmark
@@ -228,7 +229,7 @@ def print_timers(timers: Iterable[TMeasurement]):
229
230
231
def run(dtype: torch.dtype,
231
- MKNs: Iterable[Tuple[int, int, int]]) -> Iterable[TMeasurement]:
232
+ MKNs: Iterable[tuple[int, int, int]]) -> Iterable[TMeasurement]:
233
results = []
234
for m, k, n in MKNs:
235
timers = bench(dtype, m, k, n, f"scaled-{dtype}-gemm",
@@ -241,7 +242,7 @@ def run(dtype: torch.dtype,
242
243
# output makers
244
def make_output(data: Iterable[TMeasurement],
244
- MKNs: Iterable[Tuple[int, int, int]],
245
+ MKNs: Iterable[tuple[int, int, int]],
246
base_description: str,
247
timestamp=None):
248
print(f"== All Results {base_description} ====")
@@ -282,7 +283,7 @@ def run_model_bench(args):
283
for i, model in enumerate(args.models):
284
print(f"[{i}] {model}")
285
285
- def model_shapes(model_name: str, tp_size: int) -> List[Tuple[int, int]]:
286
+ def model_shapes(model_name: str, tp_size: int) -> list[tuple[int, int]]:
287
KNs = []
288
for KN, tp_split_dim in copy.deepcopy(WEIGHT_SHAPES[model_name]):
289
KN[tp_split_dim] = KN[tp_split_dim] // tp_size
benchmarks/cutlass_benchmarks/utils.py
+4
-4
@@ -1,7 +1,7 @@
1
# SPDX-License-Identifier: Apache-2.0
2
3
# Cutlass bench utils
4
-from typing import Iterable, Tuple
4
+from collections.abc import Iterable
5
6
import torch
7
@@ -27,7 +27,7 @@ def to_fp16(tensor: torch.Tensor) -> torch.Tensor:
27
28
29
def make_rand_tensors(dtype: torch.dtype, m: int, n: int,
30
- k: int) -> Tuple[torch.Tensor, torch.Tensor]:
30
+ k: int) -> tuple[torch.Tensor, torch.Tensor]:
31
a = torch.randn((m, k), device='cuda') * 5
32
b = torch.randn((n, k), device='cuda').t() * 5
33
@@ -63,7 +63,7 @@ def prune_to_2_4(tensor):
63
64
65
def make_rand_sparse_tensors(dtype: torch.dtype, m: int, n: int,
66
- k: int) -> Tuple[torch.Tensor, torch.Tensor]:
66
+ k: int) -> tuple[torch.Tensor, torch.Tensor]:
67
a = torch.randn((m, k), device='cuda') * 5
68
b = torch.randn((n, k), device='cuda').t() * 5
69
@@ -88,7 +88,7 @@ def make_rand_sparse_tensors(dtype: torch.dtype, m: int, n: int,
88
89
def make_n_rand_sparse_tensors(num_tensors: int, dtype: torch.dtype,
90
m: int, n: int, k: int) -> \
91
- Tuple[Iterable[torch.Tensor], Iterable[torch.Tensor]]:
91
+ tuple[Iterable[torch.Tensor], Iterable[torch.Tensor]]:
92
ABs = []
93
for _ in range(num_tensors):
94
b_comp, e, a, b = make_rand_sparse_tensors(dtype, m, n, k)
benchmarks/cutlass_benchmarks/w8a8_benchmarks.py
+9
-8
@@ -5,7 +5,8 @@ import copy
5
import itertools
6
import pickle as pkl
7
import time
8
-from typing import Callable, Iterable, List, Optional, Tuple
8
+from collections.abc import Iterable
9
+from typing import Callable, Optional
10
11
import torch
12
import torch.utils.benchmark as TBenchmark
@@ -49,7 +50,7 @@ def bench_int8(
50
n: int,
51
label: str,
52
sub_label: str,
52
- bench_kernels: Optional[List[str]] = None) -> Iterable[TMeasurement]:
53
+ bench_kernels: Optional[list[str]] = None) -> Iterable[TMeasurement]:
54
"""Benchmark INT8-based kernels."""
55
assert dtype == torch.int8
56
a, b = make_rand_tensors(torch.int8, m, n, k)
@@ -101,7 +102,7 @@ def bench_fp8(
102
n: int,
103
label: str,
104
sub_label: str,
104
- bench_kernels: Optional[List[str]] = None) -> Iterable[TMeasurement]:
105
+ bench_kernels: Optional[list[str]] = None) -> Iterable[TMeasurement]:
106
"""Benchmark FP8-based kernels."""
107
assert dtype == torch.float8_e4m3fn
108
a, b = make_rand_tensors(torch.float8_e4m3fn, m, n, k)
@@ -180,7 +181,7 @@ def bench(dtype: torch.dtype,
181
n: int,
182
label: str,
183
sub_label: str,
183
- bench_kernels: Optional[List[str]] = None) -> Iterable[TMeasurement]:
184
+ bench_kernels: Optional[list[str]] = None) -> Iterable[TMeasurement]:
185
if dtype == torch.int8:
186
return bench_int8(dtype, m, k, n, label, sub_label, bench_kernels)
187
if dtype == torch.float8_e4m3fn:
@@ -195,8 +196,8 @@ def print_timers(timers: Iterable[TMeasurement]):
196
197
198
def run(dtype: torch.dtype,
198
- MKNs: Iterable[Tuple[int, int, int]],
199
- bench_kernels: Optional[List[str]] = None) -> Iterable[TMeasurement]:
199
+ MKNs: Iterable[tuple[int, int, int]],
200
+ bench_kernels: Optional[list[str]] = None) -> Iterable[TMeasurement]:
201
results = []
202
for m, k, n in MKNs:
203
timers = bench(dtype,
@@ -212,7 +213,7 @@ def run(dtype: torch.dtype,
213
214
215
def make_output(data: Iterable[TMeasurement],
215
- MKNs: Iterable[Tuple[int, int, int]],
216
+ MKNs: Iterable[tuple[int, int, int]],
217
base_description: str,
218
timestamp=None):
219
print(f"== All Results {base_description} ====")
@@ -248,7 +249,7 @@ def run_model_bench(args):
249
for i, model in enumerate(args.models):
250
print(f"[{i}] {model}")
251
251
- def model_shapes(model_name: str, tp_size: int) -> List[Tuple[int, int]]:
252
+ def model_shapes(model_name: str, tp_size: int) -> list[tuple[int, int]]:
253
KNs = []
254
for KN, tp_split_dim in copy.deepcopy(WEIGHT_SHAPES[model_name]):
255
KN[tp_split_dim] = KN[tp_split_dim] // tp_size
benchmarks/fused_kernels/layernorm_rms_benchmarks.py
+3
-2
@@ -2,9 +2,10 @@
2
3
import pickle as pkl
4
import time
5
+from collections.abc import Iterable
6
from dataclasses import dataclass
7
from itertools import product
7
-from typing import Callable, Iterable, List, Optional
8
+from typing import Callable, Optional
9
10
import torch
11
import torch.utils.benchmark as TBenchmark
@@ -29,7 +30,7 @@ class bench_params_t:
30
f'x DT {self.dtype}')
31
32
32
-def get_bench_params() -> List[bench_params_t]:
33
+def get_bench_params() -> list[bench_params_t]:
34
## Test Fixtures
35
NUM_TOKENS = [2**x for x in range(11)]
36
HIDDEN_SIZES = list(range(1024, 8129, 1024))
benchmarks/kernels/benchmark_lora.py
+30
-30
@@ -9,7 +9,7 @@ from dataclasses import dataclass
9
from enum import Enum, auto
10
from itertools import product
11
from pathlib import Path
12
-from typing import Any, Callable, Dict, List, Optional, Tuple
12
+from typing import Any, Callable, Optional
13
14
import torch
15
import torch.utils.benchmark as TBenchmark
@@ -61,15 +61,15 @@ def make_rand_lora_weight_tensor(k: int,
61
62
63
def make_rand_tensors(
64
- a_shape: Tuple[int],
65
- b_shape: Tuple[int],
66
- c_shape: Tuple[int],
64
+ a_shape: tuple[int],
65
+ b_shape: tuple[int],
66
+ c_shape: tuple[int],
67
a_dtype: torch.dtype,
68
b_dtype: torch.dtype,
69
c_dtype: torch.dtype,
70
num_slices: int,
71
device: str = "cuda",
72
-) -> Tuple[torch.Tensor, List[torch.Tensor], torch.Tensor]:
72
+) -> tuple[torch.Tensor, list[torch.Tensor], torch.Tensor]:
73
"""
74
Make LoRA input/output matrices.
75
"""
@@ -135,7 +135,7 @@ def make_token_lora_mapping(num_tokens: int, num_prompts: int,
135
136
137
def ref_group_gemm(ref_out: torch.Tensor, input: torch.Tensor,
138
- lora_weights: List[torch.Tensor],
138
+ lora_weights: list[torch.Tensor],
139
seq_lens_cpu: torch.Tensor,
140
prompt_lora_mapping_cpu: torch.Tensor, scaling: float,
141
add_inputs: Optional[bool]):
@@ -204,7 +204,7 @@ class OpType(Enum):
204
def is_expand_slice_fn(self) -> bool:
205
return self in [OpType.BGMV_EXPAND_SLICE]
206
207
- def num_slices(self) -> List[int]:
207
+ def num_slices(self) -> list[int]:
208
if self in [OpType.SGMV_EXPAND, OpType.SGMV_SHRINK]:
209
# SGMV kernels supports slices
210
return [1, 2, 3]
@@ -215,7 +215,7 @@ class OpType(Enum):
215
raise ValueError(f"Unrecognized OpType {self}")
216
217
def mkn(self, batch_size: int, seq_length: int, hidden_size: int,
218
- lora_rank: int) -> Tuple[int, int, int]:
218
+ lora_rank: int) -> tuple[int, int, int]:
219
num_tokens = batch_size * seq_length
220
if self.is_shrink_fn():
221
m = num_tokens
@@ -230,7 +230,7 @@ class OpType(Enum):
230
231
def matmul_dtypes(
232
self, op_dtype: torch.dtype
233
- ) -> Tuple[torch.dtype, torch.dtype, torch.dtype]:
233
+ ) -> tuple[torch.dtype, torch.dtype, torch.dtype]:
234
"""
235
return a type, b type and c type for A x B = C
236
"""
@@ -243,7 +243,7 @@ class OpType(Enum):
243
def matmul_shapes(
244
self, batch_size: int, seq_length: int, hidden_size: int,
245
lora_rank: int, num_loras: int,
246
- num_slices: int) -> Tuple[Tuple[int], Tuple[int], Tuple[int]]:
246
+ num_slices: int) -> tuple[tuple[int], tuple[int], tuple[int]]:
247
"""
248
Given num_slices, return the shapes of the A, B, and C matrices
249
in A x B = C, for the op_type
@@ -268,7 +268,7 @@ class OpType(Enum):
268
269
def bench_fn(self) -> Callable:
270
271
- def emulate_bgmv_expand_slice(kwargs_list: List[Dict[str, Any]]):
271
+ def emulate_bgmv_expand_slice(kwargs_list: list[dict[str, Any]]):
272
for x in kwargs_list:
273
bgmv_expand_slice(**x)
274
@@ -285,7 +285,7 @@ class OpType(Enum):
285
raise ValueError(f"Unrecognized optype {self}")
286
287
def run_ref_group_gemm(self, output: torch.Tensor, input: torch.Tensor,
288
- lora_weights: List[torch.Tensor],
288
+ lora_weights: list[torch.Tensor],
289
**kwargs) -> Callable:
290
"""Each benchmark operation expected the input, lora_weights and outputs
291
in a slightly different format. Refer to self.matmul_shapes().
@@ -384,7 +384,7 @@ class BenchmarkTensors:
384
"""
385
# matmul tensors
386
input: torch.Tensor
387
- lora_weights_lst: List[torch.Tensor]
387
+ lora_weights_lst: list[torch.Tensor]
388
output: torch.Tensor
389
# metadata tensors
390
seq_lens: torch.Tensor
@@ -469,7 +469,7 @@ class BenchmarkTensors:
469
for i in range(len(self.lora_weights_lst)):
470
self.lora_weights_lst[i] = to_device(self.lora_weights_lst[i])
471
472
- def metadata(self) -> Tuple[int, int, int]:
472
+ def metadata(self) -> tuple[int, int, int]:
473
"""
474
Return num_seqs, num_tokens and max_seq_len
475
"""
@@ -505,7 +505,7 @@ class BenchmarkTensors:
505
self.seq_lens = seq_lens.to(dtype=self.seq_lens.dtype)
506
self.seq_start_loc = seq_start_loc.to(dtype=self.seq_start_loc.dtype)
507
508
- def as_sgmv_shrink_kwargs(self) -> Dict[str, Any]:
508
+ def as_sgmv_shrink_kwargs(self) -> dict[str, Any]:
509
self.convert_to_sgmv_benchmark_tensors()
510
self.sanity_check()
511
self.to_device(self.input.device)
@@ -540,7 +540,7 @@ class BenchmarkTensors:
540
'scaling': 1.0,
541
}
542
543
- def as_sgmv_expand_kwargs(self, add_inputs: bool) -> Dict[str, Any]:
543
+ def as_sgmv_expand_kwargs(self, add_inputs: bool) -> dict[str, Any]:
544
545
self.convert_to_sgmv_benchmark_tensors()
546
self.sanity_check()
@@ -578,7 +578,7 @@ class BenchmarkTensors:
578
'add_inputs': add_inputs,
579
}
580
581
- def as_bgmv_shrink_kwargs(self) -> Dict[str, Any]:
581
+ def as_bgmv_shrink_kwargs(self) -> dict[str, Any]:
582
assert len(self.lora_weights_lst) == 1
583
self.to_device(self.input.device)
584
@@ -634,7 +634,7 @@ class BenchmarkTensors:
634
'add_inputs': add_inputs
635
}
636
637
- def as_bgmv_expand_slice_kwargs(self, add_inputs: bool) -> Dict[str, Any]:
637
+ def as_bgmv_expand_slice_kwargs(self, add_inputs: bool) -> dict[str, Any]:
638
639
_, num_tokens, _, num_slices = self.metadata()
640
# Sanity check shapes
@@ -670,7 +670,7 @@ class BenchmarkTensors:
670
671
def bench_fn_kwargs(self,
672
op_type: OpType,
673
- add_inputs: Optional[bool] = None) -> Dict[str, Any]:
673
+ add_inputs: Optional[bool] = None) -> dict[str, Any]:
674
if op_type.is_shrink_fn():
675
assert add_inputs is None
676
else:
@@ -734,7 +734,7 @@ def bench_optype(ctx: BenchmarkContext,
734
assert expand_fn_add_inputs is not None
735
736
# BenchmarkContext -> BenchmarkTensors
737
- bench_tensors : List[BenchmarkTensors] = \
737
+ bench_tensors : list[BenchmarkTensors] = \
738
[BenchmarkTensors.make(ctx, op_type) for _ in range(arg_pool_size)]
739
for bt in bench_tensors:
740
bt.sanity_check()
@@ -746,7 +746,7 @@ def bench_optype(ctx: BenchmarkContext,
746
for bt in bench_tensors
747
])
748
749
- # BenchmarkTensors -> Dict (kwargs)
749
+ # BenchmarkTensors -> dict (kwargs)
750
kwargs_list = [
751
bt.bench_fn_kwargs(op_type, add_inputs=expand_fn_add_inputs)
752
for bt in bench_tensors
@@ -841,7 +841,7 @@ def use_cuda_graph_recommendation() -> str:
841
"""
842
843
844
-def print_timers(timers: List[TMeasurement],
844
+def print_timers(timers: list[TMeasurement],
845
args: Optional[argparse.Namespace] = None):
846
compare = TBenchmark.Compare(timers)
847
compare.print()
@@ -861,7 +861,7 @@ def print_timers(timers: List[TMeasurement],
861
"small num_loras the goal should be to match the torch.mm numbers.")
862
863
864
-def run(args: argparse.Namespace, bench_ctxs: List[BenchmarkContext]):
864
+def run(args: argparse.Namespace, bench_ctxs: list[BenchmarkContext]):
865
866
if args.cuda_graph_nops is not None:
867
assert args.cuda_graph_nops > 0
@@ -873,7 +873,7 @@ def run(args: argparse.Namespace, bench_ctxs: List[BenchmarkContext]):
873
timers = []
874
for bench_ctx in bench_ctxs:
875
for seq_len in args.seq_lengths:
876
- bench_ops: List[OpType] = []
876
+ bench_ops: list[OpType] = []
877
if seq_len == 1:
878
# bench all decode ops
879
bench_ops = [op for op in args.op_types if op.is_decode_op()]
@@ -921,10 +921,10 @@ def run(args: argparse.Namespace, bench_ctxs: List[BenchmarkContext]):
921
pickle.dump(timers, f)
922
923
924
-def as_benchmark_contexts(hidden_sizes: List[int], lora_ranks: List[int],
925
- args: argparse.Namespace) -> List[BenchmarkContext]:
924
+def as_benchmark_contexts(hidden_sizes: list[int], lora_ranks: list[int],
925
+ args: argparse.Namespace) -> list[BenchmarkContext]:
926
927
- ctxs: List[BenchmarkContext] = []
927
+ ctxs: list[BenchmarkContext] = []
928
for batch_size, hidden_size, lora_rank, num_loras, sort_by_lora_id in product( # noqa
929
args.batch_sizes, list(hidden_sizes), lora_ranks, args.num_loras,
930
args.sort_by_lora_id):
@@ -954,7 +954,7 @@ def run_list_bench(args: argparse.Namespace):
954
f" LoRA Ranks {args.lora_ranks}")
955
956
# Get all benchmarking contexts
957
- bench_contexts: List[BenchmarkContext] = as_benchmark_contexts(
957
+ bench_contexts: list[BenchmarkContext] = as_benchmark_contexts(
958
hidden_sizes=args.hidden_sizes, lora_ranks=args.lora_ranks, args=args)
959
960
run(args, bench_contexts)
@@ -975,7 +975,7 @@ def run_range_bench(args: argparse.Namespace):
975
f" LoRA Ranks {lora_ranks}")
976
977
# Get all benchmarking contexts
978
- bench_contexts: List[BenchmarkContext] = as_benchmark_contexts(
978
+ bench_contexts: list[BenchmarkContext] = as_benchmark_contexts(
979
hidden_sizes=hidden_sizes, lora_ranks=lora_ranks, args=args)
980
981
run(args, bench_contexts)
@@ -1002,7 +1002,7 @@ def run_model_bench(args: argparse.Namespace):
1002
f" LoRA Ranks {args.lora_ranks}")
1003
1004
# Get all benchmarking contexts
1005
- bench_contexts: List[BenchmarkContext] = as_benchmark_contexts(
1005
+ bench_contexts: list[BenchmarkContext] = as_benchmark_contexts(
1006
hidden_sizes=hidden_sizes, lora_ranks=args.lora_ranks, args=args)
1007
1008
run(args, bench_contexts)
benchmarks/kernels/benchmark_machete.py
+13
-12
@@ -7,9 +7,10 @@ import math
7
import os
8
import pickle as pkl
9
import time
10
+from collections.abc import Iterable
11
from dataclasses import dataclass
12
from itertools import product
12
-from typing import Callable, Iterable, List, Optional, Tuple
13
+from typing import Callable, Optional
14
15
import pandas as pd
16
import torch
@@ -102,8 +103,8 @@ def quantize_and_pack(atype: torch.dtype,
103
return w_ref, w_q, w_s, w_zp
104
105
105
-def create_bench_tensors(shape: Tuple[int, int, int], types: TypeConfig,
106
- group_size: Optional[int]) -> List[BenchmarkTensors]:
106
+def create_bench_tensors(shape: tuple[int, int, int], types: TypeConfig,
107
+ group_size: Optional[int]) -> list[BenchmarkTensors]:
108
m, n, k = shape
109
110
# we want to make sure that weights don't fit into L2 cache between runs so
@@ -114,7 +115,7 @@ def create_bench_tensors(shape: Tuple[int, int, int], types: TypeConfig,
115
116
a = rand_data((m, k), types.act_type, scale=5)
117
117
- benchmark_tensors: List[BenchmarkTensors] = []
118
+ benchmark_tensors: list[BenchmarkTensors] = []
119
for _ in range(num_weights):
120
w = rand_data((k, n), types.act_type, scale=5)
121
@@ -276,7 +277,7 @@ def machete_create_bench_fn(bt: BenchmarkTensors,
277
278
279
def bench_fns(label: str, sub_label: str, description: str,
279
- fns: List[Callable]):
280
+ fns: list[Callable]):
281
282
min_run_time = 1 if not NVTX_PROFILE else 0.1
283
res = TBenchmark.Timer(
@@ -311,7 +312,7 @@ def bench(types: TypeConfig,
312
n: int,
313
label: str,
314
sub_label: str,
314
- sweep_schedules: bool = True) -> List[TMeasurement]:
315
+ sweep_schedules: bool = True) -> list[TMeasurement]:
316
benchmark_tensors = create_bench_tensors((m, n, k), types, group_size)
317
sub_label += f", L={len(benchmark_tensors)}"
318
@@ -414,12 +415,12 @@ def bench(types: TypeConfig,
415
416
417
# runner
417
-def print_timers(timers: List[TMeasurement]):
418
+def print_timers(timers: list[TMeasurement]):
419
compare = TBenchmark.Compare(timers)
420
compare.print()
421
422
422
-def run(args, MKNs: Iterable[Tuple[int, int, int]]) -> Iterable[TMeasurement]:
423
+def run(args, MKNs: Iterable[tuple[int, int, int]]) -> Iterable[TMeasurement]:
424
types = TypeConfig(
425
act_type=args.act_type,
426
weight_type=scalar_types.uint4b8 if args.group_zero_type is None \
@@ -431,7 +432,7 @@ def run(args, MKNs: Iterable[Tuple[int, int, int]]) -> Iterable[TMeasurement]:
432
token_scale_type=args.token_scale_type,
433
)
434
434
- results: List[TMeasurement] = []
435
+ results: list[TMeasurement] = []
436
for m, k, n in MKNs:
437
timers = bench(types,
438
args.group_size,
@@ -449,8 +450,8 @@ def run(args, MKNs: Iterable[Tuple[int, int, int]]) -> Iterable[TMeasurement]:
450
451
# output makers
452
def make_output(
452
- data: List[TMeasurement],
453
- MKNs: Iterable[Tuple[int, int, int]],
453
+ data: list[TMeasurement],
454
+ MKNs: Iterable[tuple[int, int, int]],
455
base_description: str,
456
timestamp=None,
457
):
@@ -497,7 +498,7 @@ def run_model_bench(args):
498
for i, model in enumerate(args.models):
499
print(f"[{i}] {model}")
500
500
- def model_shapes(model_name: str, tp_size: int) -> List[Tuple[int, int]]:
501
+ def model_shapes(model_name: str, tp_size: int) -> list[tuple[int, int]]:
502
KNs = []
503
for KN, tp_split_dim in copy.deepcopy(WEIGHT_SHAPES[model_name]):
504
KN[tp_split_dim] = KN[tp_split_dim] // tp_size
benchmarks/kernels/benchmark_marlin.py
+2
-4
@@ -1,7 +1,5 @@
1
# SPDX-License-Identifier: Apache-2.0
2
3
-from typing import List
4
-
3
import torch
4
import torch.utils.benchmark as benchmark
5
from benchmark_shapes import WEIGHT_SHAPES
@@ -31,7 +29,7 @@ ACT_ORDER_OPTS = [False, True]
29
K_FULL_OPTS = [False, True]
30
31
34
-def bench_run(results: List[benchmark.Measurement], model: str,
32
+def bench_run(results: list[benchmark.Measurement], model: str,
33
act_order: bool, is_k_full: bool, quant_type: ScalarType,
34
group_size: int, size_m: int, size_k: int, size_n: int):
35
label = "Quant Matmul"
@@ -221,7 +219,7 @@ def main(args):
219
for i, model in enumerate(args.models):
220
print(f"[{i}] {model}")
221
224
- results: List[benchmark.Measurement] = []
222
+ results: list[benchmark.Measurement] = []
223
224
for model in args.models:
225
for layer in WEIGHT_SHAPES[model]:
benchmarks/kernels/benchmark_moe.py
+9
-9
@@ -4,7 +4,7 @@ import argparse
4
import time
5
from datetime import datetime
6
from itertools import product
7
-from typing import Any, Dict, List, Tuple, TypedDict
7
+from typing import Any, TypedDict
8
9
import ray
10
import torch
@@ -132,7 +132,7 @@ def benchmark_config(
132
start_event = torch.cuda.Event(enable_timing=True)
133
end_event = torch.cuda.Event(enable_timing=True)
134
135
- latencies: List[float] = []
135
+ latencies: list[float] = []
136
for i in range(num_iters):
137
prepare(i)
138
torch.cuda.synchronize()
@@ -175,8 +175,8 @@ def get_rocm_tuning_space(use_fp16):
175
return param_ranges
176
177
178
-def get_configs_compute_bound(use_fp16) -> List[Dict[str, int]]:
179
- configs: List[BenchmarkConfig] = []
178
+def get_configs_compute_bound(use_fp16) -> list[dict[str, int]]:
179
+ configs: list[BenchmarkConfig] = []
180
181
if current_platform.is_rocm():
182
param_ranges = get_rocm_tuning_space(use_fp16)
@@ -335,7 +335,7 @@ class BenchmarkWorker:
335
dtype: torch.dtype,
336
use_fp8_w8a8: bool,
337
use_int8_w8a16: bool,
338
- ) -> Tuple[Dict[str, int], float]:
338
+ ) -> tuple[dict[str, int], float]:
339
current_platform.seed_everything(self.seed)
340
dtype_str = get_config_dtype_str(dtype,
341
use_int8_w8a16=use_int8_w8a16,
@@ -371,8 +371,8 @@ class BenchmarkWorker:
371
dtype: torch.dtype,
372
use_fp8_w8a8: bool,
373
use_int8_w8a16: bool,
374
- search_space: List[Dict[str, int]],
375
- ) -> Dict[str, int]:
374
+ search_space: list[dict[str, int]],
375
+ ) -> dict[str, int]:
376
best_config = None
377
best_time = float("inf")
378
if current_platform.is_rocm():
@@ -434,7 +434,7 @@ def sort_config(config: BenchmarkConfig) -> BenchmarkConfig:
434
}
435
436
437
-def save_configs(configs: Dict[int, BenchmarkConfig], num_experts: int,
437
+def save_configs(configs: dict[int, BenchmarkConfig], num_experts: int,
438
shard_intermediate_size: int, hidden_size: int, topk: int,
439
dtype: torch.dtype, use_fp8_w8a8: bool,
440
use_int8_w8a16: bool) -> None:
@@ -498,7 +498,7 @@ def main(args: argparse.Namespace):
498
num_gpus = int(ray.available_resources()["GPU"])
499
workers = [BenchmarkWorker.remote(args.seed) for _ in range(num_gpus)]
500
501
- def _distribute(method: str, inputs: List[Any]) -> List[Any]:
501
+ def _distribute(method: str, inputs: list[Any]) -> list[Any]:
502
outputs = []
503
worker_idx = 0
504
for input_args in inputs:
benchmarks/kernels/benchmark_paged_attention.py
+2
-2
@@ -2,7 +2,7 @@
2
3
import random
4
import time
5
-from typing import List, Optional
5
+from typing import Optional
6
7
import torch
8
@@ -54,7 +54,7 @@ def main(
54
55
# Create the block tables.
56
max_num_blocks_per_seq = (max_seq_len + block_size - 1) // block_size
57
- block_tables_lst: List[List[int]] = []
57
+ block_tables_lst: list[list[int]] = []
58
for _ in range(num_seqs):
59
block_table = [
60
random.randint(0, NUM_BLOCKS - 1)
benchmarks/kernels/benchmark_rmsnorm.py
+2
-2
@@ -1,7 +1,7 @@
1
# SPDX-License-Identifier: Apache-2.0
2
3
import itertools
4
-from typing import Optional, Tuple, Union
4
+from typing import Optional, Union
5
6
import torch
7
import triton
@@ -22,7 +22,7 @@ class HuggingFaceRMSNorm(nn.Module):
22
self,
23
x: torch.Tensor,
24
residual: Optional[torch.Tensor] = None,
25
- ) -> Union[torch.Tensor, Tuple[torch.Tensor, torch.Tensor]]:
25
+ ) -> Union[torch.Tensor, tuple[torch.Tensor, torch.Tensor]]:
26
orig_dtype = x.dtype
27
x = x.to(torch.float32)
28
if residual is not None:
benchmarks/kernels/benchmark_rope.py
+2
-2
@@ -1,7 +1,7 @@
1
# SPDX-License-Identifier: Apache-2.0
2
3
from itertools import accumulate
4
-from typing import List, Optional
4
+from typing import Optional
5
6
import nvtx
7
import torch
@@ -39,7 +39,7 @@ def benchmark_rope_kernels_multi_lora(
39
})
40
# non-batched RoPE takes only one scaling factor, we create multiple
41
# instances to simulate the same behavior
42
- non_batched_ropes: List[RotaryEmbedding] = []
42
+ non_batched_ropes: list[RotaryEmbedding] = []
43
for scaling_factor in scaling_factors:
44
non_batched_ropes.append(
45
get_rope(head_size, rotary_dim, max_position, base, is_neox_style,
benchmarks/kernels/graph_machete_bench.py
+1
-2
@@ -4,7 +4,6 @@ import math
4
import pickle
5
import re
6
from collections import defaultdict
7
-from typing import List
7
8
import matplotlib.pyplot as plt
9
import pandas as pd
@@ -23,7 +22,7 @@ if __name__ == "__main__":
22
23
with open(args.filename, 'rb') as f:
24
data = pickle.load(f)
26
- raw_results: List[TMeasurement] = data["results"]
25
+ raw_results: list[TMeasurement] = data["results"]
26
27
results = defaultdict(lambda: list())
28
for v in raw_results:
benchmarks/kernels/utils.py
+2
-1
@@ -1,7 +1,8 @@
1
# SPDX-License-Identifier: Apache-2.0
2
3
import dataclasses
4
-from typing import Any, Callable, Iterable, Optional
4
+from collections.abc import Iterable
5
+from typing import Any, Callable, Optional
6
7
import torch
8
import torch.utils.benchmark as TBenchmark
csrc/cutlass_extensions/vllm_cutlass_library_extension.py
+7
-7
@@ -1,7 +1,7 @@
1
# SPDX-License-Identifier: Apache-2.0
2
3
import enum
4
-from typing import Dict, Union
4
+from typing import Union
5
6
from cutlass_library import *
7
@@ -21,7 +21,7 @@ class MixedInputKernelScheduleType(enum.Enum):
21
TmaWarpSpecializedCooperative = enum_auto()
22
23
24
-VLLMDataTypeNames: Dict[Union[VLLMDataType, DataType], str] = {
24
+VLLMDataTypeNames: dict[Union[VLLMDataType, DataType], str] = {
25
**DataTypeNames, # type: ignore
26
**{
27
VLLMDataType.u4b8: "u4b8",
@@ -29,7 +29,7 @@ VLLMDataTypeNames: Dict[Union[VLLMDataType, DataType], str] = {
29
}
30
}
31
32
-VLLMDataTypeTag: Dict[Union[VLLMDataType, DataType], str] = {
32
+VLLMDataTypeTag: dict[Union[VLLMDataType, DataType], str] = {
33
**DataTypeTag, # type: ignore
34
**{
35
VLLMDataType.u4b8: "cutlass::vllm_uint4b8_t",
@@ -37,7 +37,7 @@ VLLMDataTypeTag: Dict[Union[VLLMDataType, DataType], str] = {
37
}
38
}
39
40
-VLLMDataTypeSize: Dict[Union[VLLMDataType, DataType], int] = {
40
+VLLMDataTypeSize: dict[Union[VLLMDataType, DataType], int] = {
41
**DataTypeSize, # type: ignore
42
**{
43
VLLMDataType.u4b8: 4,
@@ -45,7 +45,7 @@ VLLMDataTypeSize: Dict[Union[VLLMDataType, DataType], int] = {
45
}
46
}
47
48
-VLLMDataTypeVLLMScalarTypeTag: Dict[Union[VLLMDataType, DataType], str] = {
48
+VLLMDataTypeVLLMScalarTypeTag: dict[Union[VLLMDataType, DataType], str] = {
49
VLLMDataType.u4b8: "vllm::kU4B8",
50
VLLMDataType.u8b128: "vllm::kU8B128",
51
DataType.u4: "vllm::kU4",
@@ -56,7 +56,7 @@ VLLMDataTypeVLLMScalarTypeTag: Dict[Union[VLLMDataType, DataType], str] = {
56
DataType.bf16: "vllm::kBfloat16",
57
}
58
59
-VLLMDataTypeTorchDataTypeTag: Dict[Union[VLLMDataType, DataType], str] = {
59
+VLLMDataTypeTorchDataTypeTag: dict[Union[VLLMDataType, DataType], str] = {
60
DataType.u8: "at::ScalarType::Byte",
61
DataType.s8: "at::ScalarType::Char",
62
DataType.e4m3: "at::ScalarType::Float8_e4m3fn",
@@ -66,7 +66,7 @@ VLLMDataTypeTorchDataTypeTag: Dict[Union[VLLMDataType, DataType], str] = {
66
DataType.f32: "at::ScalarType::Float",
67
}
68
69
-VLLMKernelScheduleTag: Dict[Union[
69
+VLLMKernelScheduleTag: dict[Union[
70
MixedInputKernelScheduleType, KernelScheduleType], str] = {
71
**KernelScheduleTag, # type: ignore
72
**{
csrc/quantization/machete/generate.py
+10
-10
@@ -8,7 +8,7 @@ from collections.abc import Iterable
8
from copy import deepcopy
9
from dataclasses import dataclass, fields
10
from functools import reduce
11
-from typing import Dict, List, Optional, Tuple, Union
11
+from typing import Optional, Union
12
13
import jinja2
14
# yapf conflicts with isort for this block
@@ -247,8 +247,8 @@ TmaCoop = EpilogueScheduleType.TmaWarpSpecializedCooperative
247
248
@dataclass(frozen=True)
249
class ScheduleConfig:
250
- tile_shape_mn: Tuple[int, int]
251
- cluster_shape_mnk: Tuple[int, int, int]
250
+ tile_shape_mn: tuple[int, int]
251
+ cluster_shape_mnk: tuple[int, int, int]
252
kernel_schedule: MixedInputKernelScheduleType
253
epilogue_schedule: EpilogueScheduleType
254
tile_scheduler: TileSchedulerType
@@ -277,8 +277,8 @@ class PrepackTypeConfig:
277
@dataclass
278
class ImplConfig:
279
types: TypeConfig
280
- schedules: List[ScheduleConfig]
281
- heuristic: List[Tuple[Optional[str], ScheduleConfig]]
280
+ schedules: list[ScheduleConfig]
281
+ heuristic: list[tuple[Optional[str], ScheduleConfig]]
282
283
284
def generate_sch_sig(schedule_config: ScheduleConfig) -> str:
@@ -333,7 +333,7 @@ def is_power_of_two(n):
333
return (n != 0) and (n & (n - 1) == 0)
334
335
336
-def to_cute_constant(value: List[int]):
336
+def to_cute_constant(value: list[int]):
337
338
def _to_cute_constant(value: int):
339
if is_power_of_two(value):
@@ -347,7 +347,7 @@ def to_cute_constant(value: List[int]):
347
return _to_cute_constant(value)
348
349
350
-def unique_schedules(impl_configs: List[ImplConfig]):
350
+def unique_schedules(impl_configs: list[ImplConfig]):
351
return list(
352
set(sch for impl_config in impl_configs
353
for sch in impl_config.schedules))
@@ -391,7 +391,7 @@ mm_impl_template = create_template(IMPL_TEMPLATE)
391
prepack_dispatch_template = create_template(PREPACK_TEMPLATE)
392
393
394
-def create_sources(impl_configs: List[ImplConfig], num_impl_files=8):
394
+def create_sources(impl_configs: list[ImplConfig], num_impl_files=8):
395
sources = []
396
397
sources.append((
@@ -435,7 +435,7 @@ def create_sources(impl_configs: List[ImplConfig], num_impl_files=8):
435
num_impls = reduce(lambda x, y: x + len(y.schedules), impl_configs, 0)
436
num_impls_per_file = math.ceil(num_impls / num_impl_files)
437
438
- files_impls: List[List[ImplConfig]] = [[]]
438
+ files_impls: list[list[ImplConfig]] = [[]]
439
440
curr_num_impls_assigned = 0
441
curr_impl_in_file = 0
@@ -515,7 +515,7 @@ def generate():
515
for cond, tile_config in default_tile_heuristic_config.items()
516
]
517
518
- def get_unique_schedules(heuristic: Dict[str, ScheduleConfig]):
518
+ def get_unique_schedules(heuristic: dict[str, ScheduleConfig]):
519
# Do not use schedules = list(set(...)) because we need to make sure
520
# the output list is deterministic; otherwise the generated kernel file
521
# will be non-deterministic and causes ccache miss.
docs/source/conf.py
+1
-2
@@ -17,7 +17,6 @@ import inspect
17
import logging
18
import os
19
import sys
20
-from typing import List
20
21
import requests
22
from sphinx.ext import autodoc
@@ -58,7 +57,7 @@ templates_path = ['_templates']
57
# List of patterns, relative to source directory, that match files and
58
# directories to ignore when looking for source files.
59
# This pattern also affects html_static_path and html_extra_path.
61
-exclude_patterns: List[str] = ["**/*.template.md", "**/*.inc.md"]
60
+exclude_patterns: list[str] = ["**/*.template.md", "**/*.inc.md"]
61
62
# Exclude the prompt "$" when copying code
63
copybutton_prompt_text = r"\$ "
docs/source/features/reasoning_outputs.md
+2
-2
@@ -123,7 +123,7 @@ class ExampleParser(ReasoningParser):
123
124
def extract_reasoning_content(
125
self, model_output: str, request: ChatCompletionRequest
126
- ) -> Tuple[Optional[str], Optional[str]]:
126
+ ) -> tuple[Optional[str], Optional[str]]:
127
"""
128
Extract reasoning content from a complete model-generated string.
129
@@ -138,7 +138,7 @@ class ExampleParser(ReasoningParser):
138
The request object that was used to generate the model_output.
139
140
Returns:
141
- Tuple[Optional[str], Optional[str]]
141
+ tuple[Optional[str], Optional[str]]
142
A tuple containing the reasoning content and the content.
143
"""
144
```
docs/source/features/structured_outputs.md
+1
-1
@@ -193,7 +193,7 @@ class Step(BaseModel):
193
194
195
class MathResponse(BaseModel):
196
- steps: List[Step]
196
+ steps: list[Step]
197
final_answer: str
198
199
docs/source/generate_examples.py
+1
-1
@@ -74,7 +74,7 @@ class Example:
74
path (Path): The path to the main directory or file.
75
category (str): The category of the document.
76
main_file (Path): The main file in the directory.
77
- other_files (list[Path]): List of other files in the directory.
77
+ other_files (list[Path]): list of other files in the directory.
78
title (str): The title of the document.
79
80
Methods:
examples/offline_inference/distributed.py
+5
-5
@@ -6,7 +6,7 @@ distributively on a multi-nodes cluster.
6
Learn more about Ray Data in https://docs.ray.io/en/latest/data/data.html
7
"""
8
9
-from typing import Any, Dict, List
9
+from typing import Any
10
11
import numpy as np
12
import ray
@@ -36,13 +36,13 @@ class LLMPredictor:
36
self.llm = LLM(model="meta-llama/Llama-2-7b-chat-hf",
37
tensor_parallel_size=tensor_parallel_size)
38
39
- def __call__(self, batch: Dict[str, np.ndarray]) -> Dict[str, list]:
39
+ def __call__(self, batch: dict[str, np.ndarray]) -> dict[str, list]:
40
# Generate texts from the prompts.
41
# The output is a list of RequestOutput objects that contain the prompt,
42
# generated text, and other information.
43
outputs = self.llm.generate(batch["text"], sampling_params)
44
- prompt: List[str] = []
45
- generated_text: List[str] = []
44
+ prompt: list[str] = []
45
+ generated_text: list[str] = []
46
for output in outputs:
47
prompt.append(output.prompt)
48
generated_text.append(' '.join([o.text for o in output.outputs]))
@@ -72,7 +72,7 @@ def scheduling_strategy_fn():
72
pg, placement_group_capture_child_tasks=True))
73
74
75
-resources_kwarg: Dict[str, Any] = {}
75
+resources_kwarg: dict[str, Any] = {}
76
if tensor_parallel_size == 1:
77
# For tensor_parallel_size == 1, we simply set num_gpus=1.
78
resources_kwarg["num_gpus"] = 1
examples/offline_inference/llm_engine_example.py
+3
-4
@@ -1,13 +1,12 @@
1
# SPDX-License-Identifier: Apache-2.0
2
3
import argparse
4
-from typing import List, Tuple
4
5
from vllm import EngineArgs, LLMEngine, RequestOutput, SamplingParams
6
from vllm.utils import FlexibleArgumentParser
7
8
10
-def create_test_prompts() -> List[Tuple[str, SamplingParams]]:
9
+def create_test_prompts() -> list[tuple[str, SamplingParams]]:
10
"""Create a list of test prompts with their sampling parameters."""
11
return [
12
("A robot may not injure a human being",
@@ -24,7 +23,7 @@ def create_test_prompts() -> List[Tuple[str, SamplingParams]]:
23
24
25
def process_requests(engine: LLMEngine,
27
- test_prompts: List[Tuple[str, SamplingParams]]):
26
+ test_prompts: list[tuple[str, SamplingParams]]):
27
"""Continuously process a list of prompts and handle the outputs."""
28
request_id = 0
29
@@ -34,7 +33,7 @@ def process_requests(engine: LLMEngine,
33
engine.add_request(str(request_id), prompt, sampling_params)
34
request_id += 1
35
37
- request_outputs: List[RequestOutput] = engine.step()
36
+ request_outputs: list[RequestOutput] = engine.step()
37
38
for request_output in request_outputs:
39
if request_output.finished:
examples/offline_inference/lora_with_quantization_inference.py
+4
-4
@@ -7,7 +7,7 @@ Requires HuggingFace credentials for access.
7
"""
8
9
import gc
10
-from typing import List, Optional, Tuple
10
+from typing import Optional
11
12
import torch
13
from huggingface_hub import snapshot_download
@@ -18,7 +18,7 @@ from vllm.lora.request import LoRARequest
18
19
def create_test_prompts(
20
lora_path: str
21
-) -> List[Tuple[str, SamplingParams, Optional[LoRARequest]]]:
21
+) -> list[tuple[str, SamplingParams, Optional[LoRARequest]]]:
22
return [
23
# this is an example of using quantization without LoRA
24
("My name is",
@@ -49,7 +49,7 @@ def create_test_prompts(
49
50
51
def process_requests(engine: LLMEngine,
52
- test_prompts: List[Tuple[str, SamplingParams,
52
+ test_prompts: list[tuple[str, SamplingParams,
53
Optional[LoRARequest]]]):
54
"""Continuously process a list of prompts and handle the outputs."""
55
request_id = 0
@@ -63,7 +63,7 @@ def process_requests(engine: LLMEngine,
63
lora_request=lora_request)
64
request_id += 1
65
66
- request_outputs: List[RequestOutput] = engine.step()
66
+ request_outputs: list[RequestOutput] = engine.step()
67
for request_output in request_outputs:
68
if request_output.finished:
69
print("----------------------------------------------------")
examples/offline_inference/mlpspeculator.py
+1
-2
@@ -2,12 +2,11 @@
2
3
import gc
4
import time
5
-from typing import List
5
6
from vllm import LLM, SamplingParams
7
8
10
-def time_generation(llm: LLM, prompts: List[str],
9
+def time_generation(llm: LLM, prompts: list[str],
10
sampling_params: SamplingParams):
11
# Generate texts from the prompts. The output is a list of RequestOutput
12
# objects that contain the prompt, generated text, and other information.
examples/offline_inference/multilora_inference.py
+4
-4
@@ -6,7 +6,7 @@ for offline inference.
6
Requires HuggingFace credentials for access to Llama2.
7
"""
8
9
-from typing import List, Optional, Tuple
9
+from typing import Optional
10
11
from huggingface_hub import snapshot_download
12
@@ -16,7 +16,7 @@ from vllm.lora.request import LoRARequest
16
17
def create_test_prompts(
18
lora_path: str
19
-) -> List[Tuple[str, SamplingParams, Optional[LoRARequest]]]:
19
+) -> list[tuple[str, SamplingParams, Optional[LoRARequest]]]:
20
"""Create a list of test prompts with their sampling parameters.
21
22
2 requests for base model, 4 requests for the LoRA. We define 2
@@ -56,7 +56,7 @@ def create_test_prompts(
56
57
58
def process_requests(engine: LLMEngine,
59
- test_prompts: List[Tuple[str, SamplingParams,
59
+ test_prompts: list[tuple[str, SamplingParams,
60
Optional[LoRARequest]]]):
61
"""Continuously process a list of prompts and handle the outputs."""
62
request_id = 0
@@ -70,7 +70,7 @@ def process_requests(engine: LLMEngine,
70
lora_request=lora_request)
71
request_id += 1
72
73
- request_outputs: List[RequestOutput] = engine.step()
73
+ request_outputs: list[RequestOutput] = engine.step()
74
75
for request_output in request_outputs:
76
if request_output.finished:
examples/offline_inference/prithvi_geospatial_mae.py
+4
-4
@@ -21,7 +21,7 @@ import argparse
21
import datetime
22
import os
23
import re
24
-from typing import List, Union
24
+from typing import Union
25
26
import albumentations
27
import numpy as np
@@ -260,9 +260,9 @@ def _convert_np_uint8(float_image: torch.Tensor):
260
261
262
def load_example(
263
- file_paths: List[str],
264
- mean: List[float] = None,
265
- std: List[float] = None,
263
+ file_paths: list[str],
264
+ mean: list[float] = None,
265
+ std: list[float] = None,
266
indices: Union[list[int], None] = None,
267
):
268
"""Build an input example by loading images in *file_paths*.
examples/offline_inference/profiling.py
+8
-7
@@ -5,8 +5,9 @@ import json
5
import os
6
import sys
7
from argparse import RawTextHelpFormatter
8
+from collections.abc import Generator
9
from dataclasses import asdict, dataclass
9
-from typing import Any, Dict, Generator, List, Optional, TypeAlias
10
+from typing import Any, Optional, TypeAlias
11
12
import torch
13
import tqdm
@@ -42,8 +43,8 @@ def get_dtype(dtype: str):
43
return dtype
44
45
45
-OutputLen_NumReqs_Map: TypeAlias = Dict[int, int]
46
-def compute_request_output_lengths(batch_size: int, step_requests: List[int]) \
46
+OutputLen_NumReqs_Map: TypeAlias = dict[int, int]
47
+def compute_request_output_lengths(batch_size: int, step_requests: list[int]) \
48
-> OutputLen_NumReqs_Map:
49
"""
50
Given the number of requests, batch_size, and the number of requests
@@ -63,7 +64,7 @@ def compute_request_output_lengths(batch_size: int, step_requests: List[int]) \
64
Args:
65
batch_size (int): Number of requests submitted for profile. This is
66
args.batch_size.
66
- step_requests (List[int]): step_requests[i] is the number of requests
67
+ step_requests (list[int]): step_requests[i] is the number of requests
68
that the ith engine step should process.
69
70
Returns:
@@ -114,7 +115,7 @@ def compute_request_output_lengths(batch_size: int, step_requests: List[int]) \
115
return ol_nr
116
117
117
-def determine_requests_per_step(context: ProfileContext) -> List[int]:
118
+def determine_requests_per_step(context: ProfileContext) -> list[int]:
119
"""
120
Determine number of requests each engine step should process.
121
If context.num_steps is set, then all engine steps process the
@@ -130,7 +131,7 @@ def determine_requests_per_step(context: ProfileContext) -> List[int]:
131
context: ProfileContext object.
132
133
Returns:
133
- List[int]: Number of requests to process for all engine-steps.
134
+ list[int]: Number of requests to process for all engine-steps.
135
output[i], contains the number of requests that the ith step
136
should process.
137
"""
@@ -170,7 +171,7 @@ def run_profile(context: ProfileContext, csv_output: Optional[str],
171
for key, value in asdict(context).items():
172
print(f" {key} = {value}")
173
173
- requests_per_step: List[int] = determine_requests_per_step(context)
174
+ requests_per_step: list[int] = determine_requests_per_step(context)
175
176
ol_nr: OutputLen_NumReqs_Map = compute_request_output_lengths(
177
context.batch_size, requests_per_step)
examples/offline_inference/profiling_tpu/profiling.py
+1
-2
@@ -4,7 +4,6 @@ import argparse
4
import dataclasses
5
import os
6
import time
7
-from typing import List
7
8
import numpy as np
9
import torch_xla.debug.profiler as xp
@@ -35,7 +34,7 @@ def main(args: argparse.Namespace):
34
dummy_prompt_token_ids = np.random.randint(10000,
35
size=(args.batch_size,
36
args.input_len))
38
- dummy_prompts: List[PromptType] = [{
37
+ dummy_prompts: list[PromptType] = [{
38
"prompt_token_ids": batch
39
} for batch in dummy_prompt_token_ids.tolist()]
40
examples/offline_inference/vision_language_multi_image.py
+17
-17
@@ -5,7 +5,7 @@ multi-image input on vision language models for text generation,
5
using the chat template defined by the model.
6
"""
7
from argparse import Namespace
8
-from typing import List, NamedTuple, Optional
8
+from typing import NamedTuple, Optional
9
10
from PIL.Image import Image
11
from transformers import AutoProcessor, AutoTokenizer
@@ -24,8 +24,8 @@ IMAGE_URLS = [
24
class ModelRequestData(NamedTuple):
25
llm: LLM
26
prompt: str
27
- stop_token_ids: Optional[List[int]]
28
- image_data: List[Image]
27
+ stop_token_ids: Optional[list[int]]
28
+ image_data: list[Image]
29
chat_template: Optional[str]
30
31
@@ -34,7 +34,7 @@ class ModelRequestData(NamedTuple):
34
# Unless specified, these settings have been tested to work on a single L4.
35
36
37
-def load_aria(question, image_urls: List[str]) -> ModelRequestData:
37
+def load_aria(question, image_urls: list[str]) -> ModelRequestData:
38
model_name = "rhymes-ai/Aria"
39
llm = LLM(model=model_name,
40
tokenizer_mode="slow",
@@ -55,7 +55,7 @@ def load_aria(question, image_urls: List[str]) -> ModelRequestData:
55
)
56
57
58
-def load_deepseek_vl2(question: str, image_urls: List[str]):
58
+def load_deepseek_vl2(question: str, image_urls: list[str]):
59
model_name = "deepseek-ai/deepseek-vl2-tiny"
60
61
llm = LLM(model=model_name,
@@ -77,7 +77,7 @@ def load_deepseek_vl2(question: str, image_urls: List[str]):
77
)
78
79
80
-def load_h2ovl(question: str, image_urls: List[str]) -> ModelRequestData:
80
+def load_h2ovl(question: str, image_urls: list[str]) -> ModelRequestData:
81
model_name = "h2oai/h2ovl-mississippi-800m"
82
83
llm = LLM(
@@ -111,7 +111,7 @@ def load_h2ovl(question: str, image_urls: List[str]) -> ModelRequestData:
111
)
112
113
114
-def load_idefics3(question, image_urls: List[str]) -> ModelRequestData:
114
+def load_idefics3(question, image_urls: list[str]) -> ModelRequestData:
115
model_name = "HuggingFaceM4/Idefics3-8B-Llama3"
116
117
# The configuration below has been confirmed to launch on a single L40 GPU.
@@ -142,7 +142,7 @@ def load_idefics3(question, image_urls: List[str]) -> ModelRequestData:
142
)
143
144
145
-def load_internvl(question: str, image_urls: List[str]) -> ModelRequestData:
145
+def load_internvl(question: str, image_urls: list[str]) -> ModelRequestData:
146
model_name = "OpenGVLab/InternVL2-2B"
147
148
llm = LLM(
@@ -179,7 +179,7 @@ def load_internvl(question: str, image_urls: List[str]) -> ModelRequestData:
179
)
180
181
182
-def load_mllama(question, image_urls: List[str]) -> ModelRequestData:
182
+def load_mllama(question, image_urls: list[str]) -> ModelRequestData:
183
model_name = "meta-llama/Llama-3.2-11B-Vision-Instruct"
184
185
# The configuration below has been confirmed to launch on a single L40 GPU.
@@ -201,7 +201,7 @@ def load_mllama(question, image_urls: List[str]) -> ModelRequestData:
201
)
202
203
204
-def load_nvlm_d(question: str, image_urls: List[str]):
204
+def load_nvlm_d(question: str, image_urls: list[str]):
205
model_name = "nvidia/NVLM-D-72B"
206
207
# Adjust this as necessary to fit in GPU
@@ -234,7 +234,7 @@ def load_nvlm_d(question: str, image_urls: List[str]):
234
)
235
236
237
-def load_pixtral_hf(question: str, image_urls: List[str]) -> ModelRequestData:
237
+def load_pixtral_hf(question: str, image_urls: list[str]) -> ModelRequestData:
238
model_name = "mistral-community/pixtral-12b"
239
240
# Adjust this as necessary to fit in GPU
@@ -259,7 +259,7 @@ def load_pixtral_hf(question: str, image_urls: List[str]) -> ModelRequestData:
259
)
260
261
262
-def load_phi3v(question: str, image_urls: List[str]) -> ModelRequestData:
262
+def load_phi3v(question: str, image_urls: list[str]) -> ModelRequestData:
263
# num_crops is an override kwarg to the multimodal image processor;
264
# For some models, e.g., Phi-3.5-vision-instruct, it is recommended
265
# to use 16 for single frame scenarios, and 4 for multi-frame.
@@ -295,7 +295,7 @@ def load_phi3v(question: str, image_urls: List[str]) -> ModelRequestData:
295
296
297
def load_qwen_vl_chat(question: str,
298
- image_urls: List[str]) -> ModelRequestData:
298
+ image_urls: list[str]) -> ModelRequestData:
299
model_name = "Qwen/Qwen-VL-Chat"
300
llm = LLM(
301
model=model_name,
@@ -336,7 +336,7 @@ def load_qwen_vl_chat(question: str,
336
)
337
338
339
-def load_qwen2_vl(question, image_urls: List[str]) -> ModelRequestData:
339
+def load_qwen2_vl(question, image_urls: list[str]) -> ModelRequestData:
340
try:
341
from qwen_vl_utils import process_vision_info
342
except ModuleNotFoundError:
@@ -393,7 +393,7 @@ def load_qwen2_vl(question, image_urls: List[str]) -> ModelRequestData:
393
)
394
395
396
-def load_qwen2_5_vl(question, image_urls: List[str]) -> ModelRequestData:
396
+def load_qwen2_5_vl(question, image_urls: list[str]) -> ModelRequestData:
397
try:
398
from qwen_vl_utils import process_vision_info
399
except ModuleNotFoundError:
@@ -466,7 +466,7 @@ model_example_map = {
466
}
467
468
469
-def run_generate(model, question: str, image_urls: List[str]):
469
+def run_generate(model, question: str, image_urls: list[str]):
470
req_data = model_example_map[model](question, image_urls)
471
472
sampling_params = SamplingParams(temperature=0.0,
@@ -487,7 +487,7 @@ def run_generate(model, question: str, image_urls: List[str]):
487
print(generated_text)
488
489
490
-def run_chat(model: str, question: str, image_urls: List[str]):
490
+def run_chat(model: str, question: str, image_urls: list[str]):
491
req_data = model_example_map[model](question, image_urls)
492
493
sampling_params = SamplingParams(temperature=0.0,
examples/online_serving/api_client.py
+3
-3
@@ -7,7 +7,7 @@ For production use, we recommend `vllm serve` and the OpenAI client API.
7
8
import argparse
9
import json
10
-from typing import Iterable, List
10
+from collections.abc import Iterable
11
12
import requests
13
@@ -39,7 +39,7 @@ def post_http_request(prompt: str,
39
return response
40
41
42
-def get_streaming_response(response: requests.Response) -> Iterable[List[str]]:
42
+def get_streaming_response(response: requests.Response) -> Iterable[list[str]]:
43
for chunk in response.iter_lines(chunk_size=8192,
44
decode_unicode=False,
45
delimiter=b"\0"):
@@ -49,7 +49,7 @@ def get_streaming_response(response: requests.Response) -> Iterable[List[str]]:
49
yield output
50
51
52
-def get_response(response: requests.Response) -> List[str]:
52
+def get_response(response: requests.Response) -> list[str]:
53
data = json.loads(response.content)
54
output = data["text"]
55
return output
examples/online_serving/openai_embedding_client.py
+1
-1
@@ -24,4 +24,4 @@ responses = client.embeddings.create(
24
)
25
26
for data in responses.data:
27
- print(data.embedding) # list of float of len 4096
27
+ print(data.embedding) # List of float of len 4096
pyproject.toml
+26
-2
@@ -65,6 +65,32 @@ exclude = [
65
[tool.ruff.lint.per-file-ignores]
66
"vllm/version.py" = ["F401"]
67
"vllm/_version.py" = ["ALL"]
68
+# Python 3.8 typing. TODO: Remove these excludes after v1.0.0
69
+"vllm/adapter_commons/**/*.py" = ["UP006", "UP035"]
70
+"vllm/attention/**/*.py" = ["UP006", "UP035"]
71
+"vllm/compilation/**/*.py" = ["UP006", "UP035"]
72
+"vllm/core/**/*.py" = ["UP006", "UP035"]
73
+"vllm/device_allocator/**/*.py" = ["UP006", "UP035"]
74
+"vllm/distributed/**/*.py" = ["UP006", "UP035"]
75
+"vllm/engine/**/*.py" = ["UP006", "UP035"]
76
+"vllm/executor/**/*.py" = ["UP006", "UP035"]
77
+"vllm/inputs/**/*.py" = ["UP006", "UP035"]
78
+"vllm/logging_utils/**/*.py" = ["UP006", "UP035"]
79
+"vllm/lora/**/*.py" = ["UP006", "UP035"]
80
+"vllm/model_executor/**/*.py" = ["UP006", "UP035"]
81
+"vllm/multimodal/**/*.py" = ["UP006", "UP035"]
82
+"vllm/platforms/**/*.py" = ["UP006", "UP035"]
83
+"vllm/plugins/**/*.py" = ["UP006", "UP035"]
84
+"vllm/profiler/**/*.py" = ["UP006", "UP035"]
85
+"vllm/prompt_adapter/**/*.py" = ["UP006", "UP035"]
86
+"vllm/spec_decode/**/*.py" = ["UP006", "UP035"]
87
+"vllm/third_party/**/*.py" = ["UP006", "UP035"]
88
+"vllm/transformers_utils/**/*.py" = ["UP006", "UP035"]
89
+"vllm/triton_utils/**/*.py" = ["UP006", "UP035"]
90
+"vllm/usage/**/*.py" = ["UP006", "UP035"]
91
+"vllm/vllm_flash_attn/**/*.py" = ["UP006", "UP035"]
92
+"vllm/assets/**/*.py" = ["UP006", "UP035"]
93
+"vllm/worker/**/*.py" = ["UP006", "UP035"]
94
95
[tool.ruff.lint]
96
select = [
@@ -91,8 +117,6 @@ ignore = [
117
"B007",
118
# f-string format
119
"UP032",
94
- # Python 3.8 typing
95
- "UP006", "UP035",
120
# Can remove once 3.10+ is the minimum Python version
121
"UP007",
122
]
setup.py
+3
-4
@@ -9,7 +9,6 @@ import subprocess
9
import sys
10
from pathlib import Path
11
from shutil import which
12
-from typing import Dict, List
12
13
import torch
14
from packaging.version import Version, parse
@@ -78,7 +77,7 @@ class CMakeExtension(Extension):
77
78
class cmake_build_ext(build_ext):
79
# A dict of extension directories that have been configured.
81
- did_config: Dict[str, bool] = {}
80
+ did_config: dict[str, bool] = {}
81
82
#
83
# Determine number of compilation jobs and optionally nvcc compile threads.
@@ -548,10 +547,10 @@ def get_vllm_version() -> str:
547
return version
548
549
551
-def get_requirements() -> List[str]:
550
+def get_requirements() -> list[str]:
551
"""Get Python package dependencies from requirements.txt."""
552
554
- def _read_requirements(filename: str) -> List[str]:
553
+ def _read_requirements(filename: str) -> list[str]:
554
with open(get_path(filename)) as f:
555
requirements = f.read().strip().split("\n")
556
resolved_requirements = []
tests/async_engine/api_server_async_engine.py
+3
-2
@@ -1,6 +1,7 @@
1
# SPDX-License-Identifier: Apache-2.0
2
"""vllm.entrypoints.api_server with some extra logging for testing."""
3
-from typing import Any, Dict, Iterable
3
+from collections.abc import Iterable
4
+from typing import Any
5
6
import uvicorn
7
from fastapi.responses import JSONResponse, Response
@@ -24,7 +25,7 @@ class AsyncLLMEngineWithStats(AsyncLLMEngine):
25
self._num_aborts += len(ids)
26
await super()._engine_abort(ids)
27
27
- def testing_stats(self) -> Dict[str, Any]:
28
+ def testing_stats(self) -> dict[str, Any]:
29
return {"num_aborted_requests": self._num_aborts}
30
31
tests/async_engine/test_async_llm_engine.py
+2
-2
@@ -6,7 +6,7 @@ import uuid
6
from asyncio import CancelledError
7
from copy import copy
8
from dataclasses import dataclass
9
-from typing import List, Optional
9
+from typing import Optional
10
11
import pytest
12
import pytest_asyncio
@@ -254,7 +254,7 @@ async def test_output_kinds(async_engine, stop):
254
params.output_kind = RequestOutputKind.DELTA
255
256
prompt_tokens = None
257
- output_tokens: List[int] = []
257
+ output_tokens: list[int] = []
258
output_text = ""
259
output_count = 0
260
final_output = None
tests/compile/piecewise/test_toy_llama.py
+3
-3
@@ -8,7 +8,7 @@ if the config `tractable_init` is set to True. Otherwise, the weights are
8
initialized randomly with a fixed seed.
9
"""
10
from dataclasses import dataclass
11
-from typing import Any, List, Optional, Tuple
11
+from typing import Any, Optional
12
13
import torch
14
from torch import nn
@@ -56,7 +56,7 @@ class LlamaConfig:
56
random_seed: int = 0
57
58
def compute_hash(self) -> str:
59
- factors: List[Any] = []
59
+ factors: list[Any] = []
60
for k, v in self.__dict__.items():
61
if k == "random_seed":
62
continue
@@ -174,7 +174,7 @@ class LlamaDecoderLayer(nn.Module):
174
positions: torch.Tensor,
175
hidden_states: torch.Tensor,
176
residual: Optional[torch.Tensor],
177
- ) -> Tuple[torch.Tensor, torch.Tensor]:
177
+ ) -> tuple[torch.Tensor, torch.Tensor]:
178
"""
179
For tractable computation:
180
- if residual is None, the outputs are:
tests/compile/test_basic_correctness.py
+4
-4
@@ -1,7 +1,7 @@
1
# SPDX-License-Identifier: Apache-2.0
2
3
import dataclasses
4
-from typing import Dict, List, Optional
4
+from typing import Optional
5
6
import pytest
7
@@ -14,7 +14,7 @@ from ..utils import compare_all_settings
14
@dataclasses.dataclass
15
class TestSetting:
16
model: str
17
- model_args: List[str]
17
+ model_args: list[str]
18
pp_size: int
19
tp_size: int
20
attn_backend: str
@@ -108,8 +108,8 @@ def test_compile_correctness(test_setting: TestSetting):
108
final_args = ["--enforce-eager"] + model_args + ["-pp", str(pp_size)] + \
109
["-tp", str(tp_size)]
110
111
- all_args: List[List[str]] = []
112
- all_envs: List[Optional[Dict[str, str]]] = []
111
+ all_args: list[list[str]] = []
112
+ all_envs: list[Optional[dict[str, str]]] = []
113
114
for level in [
115
CompilationLevel.NO_COMPILATION,
tests/conftest.py
+79
-80
@@ -5,8 +5,7 @@ import os
5
import tempfile
6
from collections import UserList
7
from enum import Enum
8
-from typing import (Any, Callable, Dict, List, Optional, Tuple, Type,
9
- TypedDict, TypeVar, Union)
8
+from typing import Any, Callable, Optional, TypedDict, TypeVar, Union
9
10
import numpy as np
11
import pytest
@@ -47,14 +46,14 @@ _SYS_MSG = os.path.join(_TEST_DIR, "system_messages", "sonnet3.5_nov2024.txt")
46
47
_M = TypeVar("_M")
48
50
-_PromptMultiModalInput = Union[List[_M], List[List[_M]]]
49
+_PromptMultiModalInput = Union[list[_M], list[list[_M]]]
50
51
PromptImageInput = _PromptMultiModalInput[Image.Image]
53
-PromptAudioInput = _PromptMultiModalInput[Tuple[np.ndarray, int]]
52
+PromptAudioInput = _PromptMultiModalInput[tuple[np.ndarray, int]]
53
PromptVideoInput = _PromptMultiModalInput[np.ndarray]
54
55
57
-def _read_prompts(filename: str) -> List[str]:
56
+def _read_prompts(filename: str) -> list[str]:
57
with open(filename) as f:
58
prompts = f.readlines()
59
return prompts
@@ -77,7 +76,7 @@ class _ImageAssets(_ImageAssetsBase):
76
ImageAsset("cherry_blossom"),
77
])
78
80
- def prompts(self, prompts: _ImageAssetPrompts) -> List[str]:
79
+ def prompts(self, prompts: _ImageAssetPrompts) -> list[str]:
80
"""
81
Convenience method to define the prompt for each test image.
82
@@ -102,7 +101,7 @@ class _VideoAssets(_VideoAssetsBase):
101
VideoAsset("sample_demo_1.mp4"),
102
])
103
105
- def prompts(self, prompts: _VideoAssetPrompts) -> List[str]:
104
+ def prompts(self, prompts: _VideoAssetPrompts) -> list[str]:
105
return [prompts["sample_demo_1"]]
106
107
@@ -175,7 +174,7 @@ def dynamo_reset():
174
175
176
@pytest.fixture
178
-def example_prompts() -> List[str]:
177
+def example_prompts() -> list[str]:
178
prompts = []
179
for filename in _TEST_PROMPTS:
180
prompts += _read_prompts(filename)
@@ -197,7 +196,7 @@ class DecoderPromptType(Enum):
196
197
@pytest.fixture
198
def example_encoder_decoder_prompts(
200
-) -> Dict[DecoderPromptType, List[ExplicitEncoderDecoderPrompt]]:
199
+) -> dict[DecoderPromptType, list[ExplicitEncoderDecoderPrompt]]:
200
'''
201
Returns an encoder prompt list and a decoder prompt list, wherein each pair
202
of same-index entries in both lists corresponds to an (encoder prompt,
@@ -229,7 +228,7 @@ def example_encoder_decoder_prompts(
228
229
230
@pytest.fixture
232
-def example_long_prompts() -> List[str]:
231
+def example_long_prompts() -> list[str]:
232
prompts = []
233
for filename in _LONG_PROMPTS:
234
prompts += _read_prompts(filename)
@@ -273,11 +272,11 @@ class HfRunner:
272
model_name: str,
273
dtype: str = "half",
274
*,
276
- model_kwargs: Optional[Dict[str, Any]] = None,
275
+ model_kwargs: Optional[dict[str, Any]] = None,
276
is_sentence_transformer: bool = False,
277
is_cross_encoder: bool = False,
278
skip_tokenizer_init: bool = False,
280
- auto_cls: Type[_BaseAutoModelClass] = AutoModelForCausalLM,
279
+ auto_cls: type[_BaseAutoModelClass] = AutoModelForCausalLM,
280
postprocess_inputs: Callable[..., BatchEncoding] = identity,
281
) -> None:
282
torch_dtype = STR_DTYPE_TO_TORCH_DTYPE[dtype]
@@ -334,11 +333,11 @@ class HfRunner:
333
334
def get_inputs(
335
self,
337
- prompts: List[str],
336
+ prompts: list[str],
337
images: Optional[PromptImageInput] = None,
338
videos: Optional[PromptVideoInput] = None,
339
audios: Optional[PromptAudioInput] = None,
341
- ) -> List[BatchEncoding]:
340
+ ) -> list[BatchEncoding]:
341
if images is not None:
342
assert len(prompts) == len(images)
343
@@ -348,9 +347,9 @@ class HfRunner:
347
if audios is not None:
348
assert len(prompts) == len(audios)
349
351
- all_inputs: List[BatchEncoding] = []
350
+ all_inputs: list[BatchEncoding] = []
351
for i, prompt in enumerate(prompts):
353
- processor_kwargs: Dict[str, Any] = {
352
+ processor_kwargs: dict[str, Any] = {
353
"text": prompt,
354
"return_tensors": "pt",
355
}
@@ -370,7 +369,7 @@ class HfRunner:
369
370
return all_inputs
371
373
- def classify(self, prompts: List[str]) -> List[str]:
372
+ def classify(self, prompts: list[str]) -> list[str]:
373
# output is final logits
374
all_inputs = self.get_inputs(prompts)
375
outputs = []
@@ -383,18 +382,18 @@ class HfRunner:
382
383
def generate(
384
self,
386
- prompts: List[str],
385
+ prompts: list[str],
386
images: Optional[PromptImageInput] = None,
387
videos: Optional[PromptVideoInput] = None,
388
audios: Optional[PromptAudioInput] = None,
389
**kwargs: Any,
391
- ) -> List[Tuple[List[List[int]], List[str]]]:
390
+ ) -> list[tuple[list[list[int]], list[str]]]:
391
all_inputs = self.get_inputs(prompts,
392
images=images,
393
videos=videos,
394
audios=audios)
395
397
- outputs: List[Tuple[List[List[int]], List[str]]] = []
396
+ outputs: list[tuple[list[list[int]], list[str]]] = []
397
for inputs in all_inputs:
398
output_ids = self.model.generate(
399
**self.wrap_device(inputs, device=self.model.device.type),
@@ -412,13 +411,13 @@ class HfRunner:
411
412
def generate_greedy(
413
self,
415
- prompts: List[str],
414
+ prompts: list[str],
415
max_tokens: int,
416
images: Optional[PromptImageInput] = None,
417
videos: Optional[PromptVideoInput] = None,
418
audios: Optional[PromptAudioInput] = None,
419
**kwargs: Any,
421
- ) -> List[Tuple[List[int], str]]:
420
+ ) -> list[tuple[list[int], str]]:
421
outputs = self.generate(prompts,
422
do_sample=False,
423
max_new_tokens=max_tokens,
@@ -432,10 +431,10 @@ class HfRunner:
431
432
def generate_beam_search(
433
self,
435
- prompts: List[str],
434
+ prompts: list[str],
435
beam_width: int,
436
max_tokens: int,
438
- ) -> List[Tuple[List[List[int]], List[str]]]:
437
+ ) -> list[tuple[list[list[int]], list[str]]]:
438
outputs = self.generate(prompts,
439
do_sample=False,
440
max_new_tokens=max_tokens,
@@ -453,19 +452,19 @@ class HfRunner:
452
453
def generate_greedy_logprobs(
454
self,
456
- prompts: List[str],
455
+ prompts: list[str],
456
max_tokens: int,
457
images: Optional[PromptImageInput] = None,
458
videos: Optional[PromptVideoInput] = None,
459
audios: Optional[PromptAudioInput] = None,
460
**kwargs: Any,
462
- ) -> List[List[torch.Tensor]]:
461
+ ) -> list[list[torch.Tensor]]:
462
all_inputs = self.get_inputs(prompts,
463
images=images,
464
videos=videos,
465
audios=audios)
466
468
- all_logprobs: List[List[torch.Tensor]] = []
467
+ all_logprobs: list[list[torch.Tensor]] = []
468
for inputs in all_inputs:
469
output = self.model.generate(
470
**self.wrap_device(inputs, device=self.model.device.type),
@@ -483,11 +482,11 @@ class HfRunner:
482
483
def _hidden_states_to_seq_logprobs(
484
self,
486
- hidden_states: Tuple[Tuple[torch.Tensor, ...], ...],
487
- ) -> List[torch.Tensor]:
485
+ hidden_states: tuple[tuple[torch.Tensor, ...], ...],
486
+ ) -> list[torch.Tensor]:
487
output_embeddings = self.model.get_output_embeddings()
488
490
- seq_logprobs: List[torch.Tensor] = []
489
+ seq_logprobs: list[torch.Tensor] = []
490
for _, hidden_state in enumerate(hidden_states):
491
last_hidden_states = hidden_state[-1][0]
492
logits = torch.matmul(
@@ -503,14 +502,14 @@ class HfRunner:
502
503
def _hidden_states_to_logprobs(
504
self,
506
- hidden_states: Tuple[Tuple[torch.Tensor, ...], ...],
505
+ hidden_states: tuple[tuple[torch.Tensor, ...], ...],
506
num_logprobs: int,
508
- ) -> Tuple[List[Dict[int, float]], int]:
507
+ ) -> tuple[list[dict[int, float]], int]:
508
seq_logprobs = self._hidden_states_to_seq_logprobs(hidden_states)
509
output_len = len(hidden_states)
510
511
# convert to dict
513
- seq_logprobs_lst: List[Dict[int, float]] = []
512
+ seq_logprobs_lst: list[dict[int, float]] = []
513
for tok_idx, tok_logprobs in enumerate(seq_logprobs):
514
# drop prompt logprobs
515
if tok_idx == 0:
@@ -530,22 +529,22 @@ class HfRunner:
529
530
def generate_greedy_logprobs_limit(
531
self,
533
- prompts: List[str],
532
+ prompts: list[str],
533
max_tokens: int,
534
num_logprobs: int,
535
images: Optional[PromptImageInput] = None,
536
audios: Optional[PromptAudioInput] = None,
537
videos: Optional[PromptVideoInput] = None,
538
**kwargs: Any,
540
- ) -> List[TokensTextLogprobs]:
539
+ ) -> list[TokensTextLogprobs]:
540
all_inputs = self.get_inputs(prompts,
541
images=images,
542
videos=videos,
543
audios=audios)
544
546
- all_logprobs: List[List[Dict[int, float]]] = []
547
- all_output_ids: List[List[int]] = []
548
- all_output_strs: List[str] = []
545
+ all_logprobs: list[list[dict[int, float]]] = []
546
+ all_output_ids: list[list[int]] = []
547
+ all_output_strs: list[str] = []
548
549
for inputs in all_inputs:
550
output = self.model.generate(
@@ -577,23 +576,23 @@ class HfRunner:
576
577
def generate_encoder_decoder_greedy_logprobs_limit(
578
self,
580
- encoder_decoder_prompts: List[ExplicitEncoderDecoderPrompt[str, str]],
579
+ encoder_decoder_prompts: list[ExplicitEncoderDecoderPrompt[str, str]],
580
max_tokens: int,
581
num_logprobs: int,
582
images: Optional[PromptImageInput] = None,
583
**kwargs: Any,
585
- ) -> List[TokensTextLogprobs]:
584
+ ) -> list[TokensTextLogprobs]:
585
'''
586
Greedy logprobs generation for vLLM encoder/decoder models
587
'''
588
590
- all_logprobs: List[List[Dict[int, float]]] = []
591
- all_output_ids: List[List[int]] = []
592
- all_output_strs: List[str] = []
589
+ all_logprobs: list[list[dict[int, float]]] = []
590
+ all_output_ids: list[list[int]] = []
591
+ all_output_strs: list[str] = []
592
593
for i, (encoder_prompt, decoder_prompt) in enumerate(
594
to_enc_dec_tuple_list(encoder_decoder_prompts)):
596
- processor_kwargs: Dict[str, Any] = {
595
+ processor_kwargs: dict[str, Any] = {
596
"text": encoder_prompt,
597
"return_tensors": "pt",
598
}
@@ -641,10 +640,10 @@ class HfRunner:
640
return [(output_ids, output_str, output_logprobs)
641
for output_ids, output_str, output_logprobs in outputs]
642
644
- def encode(self, prompts: List[str]) -> List[List[torch.Tensor]]:
643
+ def encode(self, prompts: list[str]) -> list[list[torch.Tensor]]:
644
return self.model.encode(prompts)
645
647
- def predict(self, prompts: List[List[str]]) -> torch.Tensor:
646
+ def predict(self, prompts: list[list[str]]) -> torch.Tensor:
647
return self.model.predict(prompts, convert_to_tensor=True)
648
649
def __enter__(self):
@@ -699,11 +698,11 @@ class VllmRunner:
698
699
def get_inputs(
700
self,
702
- prompts: List[str],
701
+ prompts: list[str],
702
images: Optional[PromptImageInput] = None,
703
videos: Optional[PromptVideoInput] = None,
704
audios: Optional[PromptAudioInput] = None,
706
- ) -> List[TextPrompt]:
705
+ ) -> list[TextPrompt]:
706
if images is not None:
707
assert len(prompts) == len(images)
708
@@ -733,13 +732,13 @@ class VllmRunner:
732
733
def generate(
734
self,
736
- prompts: List[str],
735
+ prompts: list[str],
736
sampling_params: SamplingParams,
737
images: Optional[PromptImageInput] = None,
738
videos: Optional[PromptVideoInput] = None,
739
audios: Optional[PromptAudioInput] = None,
740
**kwargs: Any,
742
- ) -> List[Tuple[List[List[int]], List[str]]]:
741
+ ) -> list[tuple[list[list[int]], list[str]]]:
742
inputs = self.get_inputs(prompts,
743
images=images,
744
videos=videos,
@@ -749,12 +748,12 @@ class VllmRunner:
748
sampling_params=sampling_params,
749
**kwargs)
750
752
- outputs: List[Tuple[List[List[int]], List[str]]] = []
751
+ outputs: list[tuple[list[list[int]], list[str]]] = []
752
for req_output in req_outputs:
753
prompt_str = req_output.prompt
754
prompt_ids = req_output.prompt_token_ids
756
- req_sample_output_ids: List[List[int]] = []
757
- req_sample_output_strs: List[str] = []
755
+ req_sample_output_ids: list[list[int]] = []
756
+ req_sample_output_strs: list[str] = []
757
for sample in req_output.outputs:
758
output_str = sample.text
759
output_ids = list(sample.token_ids)
@@ -765,9 +764,9 @@ class VllmRunner:
764
765
@staticmethod
766
def _final_steps_generate_w_logprobs(
768
- req_outputs: List[RequestOutput],
769
- ) -> List[TokensTextLogprobsPromptLogprobs]:
770
- outputs: List[TokensTextLogprobsPromptLogprobs] = []
767
+ req_outputs: list[RequestOutput],
768
+ ) -> list[TokensTextLogprobsPromptLogprobs]:
769
+ outputs: list[TokensTextLogprobsPromptLogprobs] = []
770
for req_output in req_outputs:
771
assert len(req_output.outputs) > 0
772
for sample in req_output.outputs:
@@ -780,14 +779,14 @@ class VllmRunner:
779
780
def generate_w_logprobs(
781
self,
783
- prompts: List[str],
782
+ prompts: list[str],
783
sampling_params: SamplingParams,
784
images: Optional[PromptImageInput] = None,
785
audios: Optional[PromptAudioInput] = None,
786
videos: Optional[PromptVideoInput] = None,
787
**kwargs: Any,
789
- ) -> Union[List[TokensTextLogprobs],
790
- List[TokensTextLogprobsPromptLogprobs]]:
788
+ ) -> Union[list[TokensTextLogprobs],
789
+ list[TokensTextLogprobsPromptLogprobs]]:
790
inputs = self.get_inputs(prompts,
791
images=images,
792
videos=videos,
@@ -806,10 +805,10 @@ class VllmRunner:
805
806
def generate_encoder_decoder_w_logprobs(
807
self,
809
- encoder_decoder_prompts: List[ExplicitEncoderDecoderPrompt[str, str]],
808
+ encoder_decoder_prompts: list[ExplicitEncoderDecoderPrompt[str, str]],
809
sampling_params: SamplingParams,
811
- ) -> Union[List[TokensTextLogprobs],
812
- List[TokensTextLogprobsPromptLogprobs]]:
810
+ ) -> Union[list[TokensTextLogprobs],
811
+ list[TokensTextLogprobsPromptLogprobs]]:
812
'''
813
Logprobs generation for vLLM encoder/decoder models
814
'''
@@ -826,13 +825,13 @@ class VllmRunner:
825
826
def generate_greedy(
827
self,
829
- prompts: List[str],
828
+ prompts: list[str],
829
max_tokens: int,
830
images: Optional[PromptImageInput] = None,
831
videos: Optional[PromptVideoInput] = None,
832
audios: Optional[PromptAudioInput] = None,
833
**kwargs: Any,
835
- ) -> List[Tuple[List[int], str]]:
834
+ ) -> list[tuple[list[int], str]]:
835
greedy_params = SamplingParams(temperature=0.0, max_tokens=max_tokens)
836
outputs = self.generate(prompts,
837
greedy_params,
@@ -845,18 +844,18 @@ class VllmRunner:
844
845
def generate_greedy_logprobs(
846
self,
848
- prompts: List[str],
847
+ prompts: list[str],
848
max_tokens: int,
849
num_logprobs: int,
850
num_prompt_logprobs: Optional[int] = None,
851
images: Optional[PromptImageInput] = None,
852
audios: Optional[PromptAudioInput] = None,
853
videos: Optional[PromptVideoInput] = None,
855
- stop_token_ids: Optional[List[int]] = None,
856
- stop: Optional[List[str]] = None,
854
+ stop_token_ids: Optional[list[int]] = None,
855
+ stop: Optional[list[str]] = None,
856
**kwargs: Any,
858
- ) -> Union[List[TokensTextLogprobs],
859
- List[TokensTextLogprobsPromptLogprobs]]:
857
+ ) -> Union[list[TokensTextLogprobs],
858
+ list[TokensTextLogprobsPromptLogprobs]]:
859
greedy_logprobs_params = SamplingParams(
860
temperature=0.0,
861
max_tokens=max_tokens,
@@ -874,12 +873,12 @@ class VllmRunner:
873
874
def generate_encoder_decoder_greedy_logprobs(
875
self,
877
- encoder_decoder_prompts: List[ExplicitEncoderDecoderPrompt[str, str]],
876
+ encoder_decoder_prompts: list[ExplicitEncoderDecoderPrompt[str, str]],
877
max_tokens: int,
878
num_logprobs: int,
879
num_prompt_logprobs: Optional[int] = None,
881
- ) -> Union[List[TokensTextLogprobs],
882
- List[TokensTextLogprobsPromptLogprobs]]:
880
+ ) -> Union[list[TokensTextLogprobs],
881
+ list[TokensTextLogprobsPromptLogprobs]]:
882
greedy_logprobs_params = SamplingParams(
883
temperature=0.0,
884
max_tokens=max_tokens,
@@ -895,10 +894,10 @@ class VllmRunner:
894
895
def generate_beam_search(
896
self,
898
- prompts: Union[List[str], List[List[int]]],
897
+ prompts: Union[list[str], list[list[int]]],
898
beam_width: int,
899
max_tokens: int,
901
- ) -> List[Tuple[List[List[int]], List[str]]]:
900
+ ) -> list[tuple[list[list[int]], list[str]]]:
901
if is_list_of(prompts, str, check="all"):
902
prompts = [TextPrompt(prompt=prompt) for prompt in prompts]
903
else:
@@ -915,17 +914,17 @@ class VllmRunner:
914
returned_outputs.append((token_ids, texts))
915
return returned_outputs
916
918
- def classify(self, prompts: List[str]) -> List[List[float]]:
917
+ def classify(self, prompts: list[str]) -> list[list[float]]:
918
req_outputs = self.model.classify(prompts)
919
return [req_output.outputs.probs for req_output in req_outputs]
920
921
def encode(
922
self,
924
- prompts: List[str],
923
+ prompts: list[str],
924
images: Optional[PromptImageInput] = None,
925
videos: Optional[PromptVideoInput] = None,
926
audios: Optional[PromptAudioInput] = None,
928
- ) -> List[List[float]]:
927
+ ) -> list[list[float]]:
928
inputs = self.get_inputs(prompts,
929
images=images,
930
videos=videos,
@@ -936,9 +935,9 @@ class VllmRunner:
935
936
def score(
937
self,
939
- text_1: Union[str, List[str]],
940
- text_2: Union[str, List[str]],
941
- ) -> List[float]:
938
+ text_1: Union[str, list[str]],
939
+ text_2: Union[str, list[str]],
940
+ ) -> list[float]:
941
req_outputs = self.model.score(text_1, text_2)
942
return [req_output.outputs.score for req_output in req_outputs]
943
tests/core/block/e2e/conftest.py
+2
-1
@@ -1,6 +1,7 @@
1
# SPDX-License-Identifier: Apache-2.0
2
3
-from typing import Callable, Iterable, Optional
3
+from collections.abc import Iterable
4
+from typing import Callable, Optional
5
6
import pytest
7
tests/core/block/e2e/test_correctness_sliding_window.py
+5
-6
@@ -1,7 +1,6 @@
1
# SPDX-License-Identifier: Apache-2.0
2
3
import random
4
-from typing import List
4
5
import pytest
6
@@ -137,9 +136,9 @@ def prep_prompts(batch_size: int):
136
The prompt is just under 10k tokens; sliding window is 4k
137
so the answer is outside sliding window, but should still be correct.
138
"""
140
- prompts: List[str] = []
141
- answer: List[int] = []
142
- indices: List[int] = []
139
+ prompts: list[str] = []
140
+ answer: list[int] = []
141
+ indices: list[int] = []
142
random.seed(1)
143
for _ in range(batch_size):
144
idx = random.randint(30, 90)
@@ -158,7 +157,7 @@ def prep_prompts(batch_size: int):
157
return prompts, answer, indices
158
159
161
-def check_answers(indices: List[int], answer: List[int], outputs: List[str]):
160
+def check_answers(indices: list[int], answer: list[int], outputs: list[str]):
161
answer2 = [int(text[0:2].strip()) for text in outputs]
162
print(list(zip(indices, zip(answer, answer2))))
163
numok = 0
@@ -170,7 +169,7 @@ def check_answers(indices: List[int], answer: List[int], outputs: List[str]):
169
assert frac_ok > 0.7
170
171
173
-def check_window(prompts: List[str]):
172
+def check_window(prompts: list[str]):
173
174
def inner(llm: LLM):
175
sliding_window = llm.llm_engine.model_config.get_sliding_window()
tests/core/block/test_block_table.py
+3
-5
@@ -1,7 +1,5 @@
1
# SPDX-License-Identifier: Apache-2.0
2
3
-from typing import List
4
-
3
import pytest
4
5
from vllm.core.block.block_table import BlockTable
@@ -32,7 +30,7 @@ def test_allocate_naive(block_size: int, sequence_len: int):
30
token_ids = list(range(sequence_len))
31
num_blocks_per_alloc = len(list(chunk_list(token_ids, block_size)))
32
35
- block_tables: List[BlockTable] = []
33
+ block_tables: list[BlockTable] = []
34
for i in range(5):
35
assert allocator.get_num_free_blocks(
36
device=Device.GPU) == num_gpu_blocks - i * num_blocks_per_alloc
@@ -77,7 +75,7 @@ def test_allocate_prefix_caching(block_size: int, sequence_len: int):
75
num_immutable_blocks_per_alloc = len(
76
chunked_tokens) - num_mutable_blocks_per_alloc
77
80
- block_tables: List[BlockTable] = []
78
+ block_tables: list[BlockTable] = []
79
for alloc_i in range(1, 6):
80
81
block_tables.append(
@@ -272,7 +270,7 @@ def test_append_token_ids_correct_content(block_size: int, sequence_len: int,
270
)
271
block_table.allocate(token_ids=token_ids, device=Device.GPU)
272
275
- appended_so_far: List[int] = []
273
+ appended_so_far: list[int] = []
274
for append in chunk_list(token_ids_to_append, append_size):
275
block_table.append_token_ids(append)
276
appended_so_far.extend(append)
tests/core/block/test_naive_block.py
+2
-2
@@ -1,6 +1,6 @@
1
# SPDX-License-Identifier: Apache-2.0
2
3
-from typing import List, Optional
3
+from typing import Optional
4
5
import pytest
6
@@ -14,7 +14,7 @@ class TestNaiveBlockAllocator:
14
def create_allocate_lambda(allocate_type: str,
15
allocator: NaiveBlockAllocator,
16
prev_block: Optional[Block],
17
- token_ids: List[int]):
17
+ token_ids: list[int]):
18
if allocate_type == "immutable":
19
allocate_block = lambda: allocator.allocate_immutable_block(
20
prev_block=prev_block, token_ids=token_ids)
tests/core/block/test_prefix_caching_block.py
+8
-8
@@ -2,7 +2,7 @@
2
3
import math
4
import random
5
-from typing import List, Optional
5
+from typing import Optional
6
from unittest.mock import MagicMock
7
8
import pytest
@@ -123,11 +123,11 @@ class TestPrefixCachingBlock:
123
124
@staticmethod
125
def create_chain(block_size: int,
126
- token_ids: List[int],
127
- num_empty_trailing_blocks=0) -> List[PrefixCachingBlock]:
126
+ token_ids: list[int],
127
+ num_empty_trailing_blocks=0) -> list[PrefixCachingBlock]:
128
"""Helper method which creates a chain of blocks.
129
"""
130
- blocks: List[PrefixCachingBlock] = []
130
+ blocks: list[PrefixCachingBlock] = []
131
num_blocks = math.ceil(
132
len(token_ids) / block_size) + num_empty_trailing_blocks
133
@@ -161,7 +161,7 @@ class TestPrefixCachingBlockAllocator:
161
@staticmethod
162
def create_allocate_lambda(allocate_type: str, allocator: BlockAllocator,
163
prev_block: Optional[Block],
164
- token_ids: List[int]):
164
+ token_ids: list[int]):
165
if allocate_type == "immutable":
166
allocate_block = lambda: allocator.allocate_immutable_block(
167
prev_block=prev_block, token_ids=token_ids)
@@ -839,13 +839,13 @@ class TestPrefixCachingBlockAllocator:
839
@staticmethod
840
def create_immutable_chain(
841
block_size: int,
842
- token_ids: List[int],
842
+ token_ids: list[int],
843
allocator: PrefixCachingBlockAllocator,
844
extra_hash: Optional[int] = None,
845
- ) -> List[PrefixCachingBlock]:
845
+ ) -> list[PrefixCachingBlock]:
846
"""Helper method which creates a chain of blocks.
847
"""
848
- blocks: List[Block] = []
848
+ blocks: list[Block] = []
849
num_blocks = math.ceil(len(token_ids) / block_size)
850
851
if num_blocks == 0:
tests/core/test_chunked_prefill_scheduler.py
+12
-13
@@ -1,6 +1,5 @@
1
# SPDX-License-Identifier: Apache-2.0
2
3
-from typing import List
3
from unittest.mock import MagicMock
4
5
import pytest # noqa
@@ -46,7 +45,7 @@ def test_simple():
45
cache_config.num_cpu_blocks = 8
46
cache_config.num_gpu_blocks = 8
47
scheduler = Scheduler(scheduler_config, cache_config, None)
49
- running: List[SequenceGroup] = []
48
+ running: list[SequenceGroup] = []
49
50
# Add seq groups to scheduler.
51
for i in range(num_seq_group):
@@ -93,7 +92,7 @@ def test_chunk():
92
cache_config.num_cpu_blocks = 32
93
cache_config.num_gpu_blocks = 32
94
scheduler = Scheduler(scheduler_config, cache_config, None)
96
- running: List[SequenceGroup] = []
95
+ running: list[SequenceGroup] = []
96
97
# Add seq groups to scheduler.
98
for i in range(2):
@@ -145,7 +144,7 @@ def test_concurrent_chunking():
144
cache_config.num_cpu_blocks = 32
145
cache_config.num_gpu_blocks = 32
146
scheduler = Scheduler(scheduler_config, cache_config, None)
148
- running: List[SequenceGroup] = []
147
+ running: list[SequenceGroup] = []
148
149
# Add seq groups to scheduler.
150
for i in range(2):
@@ -226,8 +225,8 @@ def test_short_prompts_jump_long_prompts_in_queue():
225
cache_config.num_cpu_blocks = 3200 # large KV cache size for large requests
226
cache_config.num_gpu_blocks = 3200
227
scheduler = Scheduler(scheduler_config, cache_config, None)
229
- long_seqs: List[SequenceGroup] = []
230
- short_seqs: List[SequenceGroup] = []
228
+ long_seqs: list[SequenceGroup] = []
229
+ short_seqs: list[SequenceGroup] = []
230
231
# Add 2 large seq groups to scheduler.
232
for i in range(2):
@@ -368,7 +367,7 @@ def test_complex():
367
cache_config.num_cpu_blocks = 64
368
cache_config.num_gpu_blocks = 64
369
scheduler = Scheduler(scheduler_config, cache_config, None)
371
- running: List[SequenceGroup] = []
370
+ running: list[SequenceGroup] = []
371
372
# Add seq groups to scheduler.
373
for i in range(2):
@@ -439,7 +438,7 @@ def test_maximal_decoding():
438
cache_config.num_cpu_blocks = 8
439
cache_config.num_gpu_blocks = 8
440
scheduler = Scheduler(scheduler_config, cache_config, None)
442
- running: List[SequenceGroup] = []
441
+ running: list[SequenceGroup] = []
442
443
# Add seq groups to scheduler.
444
for i in range(2):
@@ -533,7 +532,7 @@ def test_prompt_limit():
532
cache_config.num_cpu_blocks = 16
533
cache_config.num_gpu_blocks = 16
534
scheduler = Scheduler(scheduler_config, cache_config, None)
536
- running: List[SequenceGroup] = []
535
+ running: list[SequenceGroup] = []
536
537
_, seq_group = create_dummy_prompt("1",
538
prompt_length=48,
@@ -565,7 +564,7 @@ def test_prompt_limit_exceed():
564
cache_config.num_cpu_blocks = 16
565
cache_config.num_gpu_blocks = 16
566
scheduler = Scheduler(scheduler_config, cache_config, None)
568
- running: List[SequenceGroup] = []
567
+ running: list[SequenceGroup] = []
568
_, seq_group = create_dummy_prompt("2",
569
prompt_length=48,
570
block_size=block_size)
@@ -699,7 +698,7 @@ def test_chunked_prefill_max_seqs():
698
cache_config.num_cpu_blocks = 128
699
cache_config.num_gpu_blocks = 128
700
scheduler = Scheduler(scheduler_config, cache_config, None)
702
- running: List[SequenceGroup] = []
701
+ running: list[SequenceGroup] = []
702
703
_, seq_group = create_dummy_prompt("1",
704
prompt_length=65,
@@ -758,7 +757,7 @@ def test_prefix_caching():
757
cache_config.num_cpu_blocks = 0
758
cache_config.num_gpu_blocks = 32
759
scheduler = Scheduler(scheduler_config, cache_config, None)
761
- running: List[SequenceGroup] = []
760
+ running: list[SequenceGroup] = []
761
762
# Add seq groups to scheduler.
763
for i in range(2):
@@ -800,7 +799,7 @@ def test_prefix_caching_with_concurrent_partial_prefills():
799
cache_config.num_cpu_blocks = 0
800
cache_config.num_gpu_blocks = 32
801
scheduler = Scheduler(scheduler_config, cache_config, None)
803
- running: List[SequenceGroup] = []
802
+ running: list[SequenceGroup] = []
803
804
# Add seq groups to scheduler.
805
for i in range(2):
tests/core/test_scheduler.py
+9
-10
@@ -2,7 +2,6 @@
2
3
import time
4
from collections import deque
5
-from typing import List, Set, Tuple
5
from unittest.mock import MagicMock
6
7
import pytest # noqa
@@ -57,7 +56,7 @@ def test_scheduler_abort_seq_group():
56
57
# Add multiple seq groups to scheduler.
58
num_seq_group = 4
60
- request_ids: Set[str] = set()
59
+ request_ids: set[str] = set()
60
for i in range(num_seq_group):
61
_, seq_group = create_dummy_prompt(str(i), block_size)
62
scheduler.add_seq_group(seq_group)
@@ -83,7 +82,7 @@ def test_scheduler_schedule_simple():
82
cache_config.num_cpu_blocks = 8
83
cache_config.num_gpu_blocks = 8
84
scheduler = Scheduler(scheduler_config, cache_config, None)
86
- running: List[SequenceGroup] = []
85
+ running: list[SequenceGroup] = []
86
87
# Add seq groups to scheduler.
88
for i in range(num_seq_group):
@@ -221,7 +220,7 @@ def test_scheduler_max_seqs():
220
cache_config.num_gpu_blocks = 8
221
scheduler = Scheduler(scheduler_config, cache_config, None)
222
224
- all_seq_groups: List[SequenceGroup] = []
223
+ all_seq_groups: list[SequenceGroup] = []
224
# Add seq groups to scheduler.
225
for i in range(num_seq_group):
226
_, seq_group = create_dummy_prompt(str(i),
@@ -480,7 +479,7 @@ def test_prefill_schedule_max_lora():
479
num_cpu_blocks=64,
480
num_gpu_blocks=64)
481
budget = create_token_budget(token_budget=120)
483
- curr_loras: Set[int] = set()
482
+ curr_loras: set[int] = set()
483
for i in range(2):
484
_, seq_group = create_dummy_prompt(str(i),
485
prompt_length=60,
@@ -651,8 +650,8 @@ def test_schedule_swapped_max_loras():
650
block_size=block_size,
651
num_cpu_blocks=32,
652
num_gpu_blocks=32)
654
- curr_loras: Set[int] = set()
655
- blocks_to_swap_out: List[Tuple[int, int]] = []
653
+ curr_loras: set[int] = set()
654
+ blocks_to_swap_out: list[tuple[int, int]] = []
655
for i in range(2):
656
_, seq_group = create_dummy_prompt(str(i),
657
prompt_length=60,
@@ -683,7 +682,7 @@ def test_schedule_swapped_cannot_swap_in():
682
num_cpu_blocks=32,
683
num_gpu_blocks=32)
684
curr_loras = None
686
- blocks_to_swap_out: List[Tuple[int, int]] = []
685
+ blocks_to_swap_out: list[tuple[int, int]] = []
686
for i in range(2):
687
_, seq_group = create_dummy_prompt(str(i),
688
prompt_length=60,
@@ -714,7 +713,7 @@ def test_infeasible_swap():
713
num_cpu_blocks=32,
714
num_gpu_blocks=32)
715
curr_loras = None
717
- blocks_to_swap_out: List[Tuple[int, int]] = []
716
+ blocks_to_swap_out: list[tuple[int, int]] = []
717
for i in range(2):
718
_, seq_group = create_dummy_prompt(str(i),
719
prompt_length=60,
@@ -752,7 +751,7 @@ def test_schedule_swapped_blocks_to_copy():
751
block_size=block_size)
752
scheduler._allocate_and_set_running(seq_group)
753
append_new_token_seq_group(60, seq_group, 1)
755
- blocks_to_swap_out: List[Tuple[int, int]] = []
754
+ blocks_to_swap_out: list[tuple[int, int]] = []
755
scheduler._swap_out(seq_group, blocks_to_swap_out)
756
scheduler._add_seq_group_to_swapped(seq_group)
757
tests/core/test_scheduler_encoder_decoder.py
+1
-3
@@ -1,7 +1,5 @@
1
# SPDX-License-Identifier: Apache-2.0
2
3
-from typing import List
4
-
3
import pytest # noqa
4
5
from vllm.config import CacheConfig, SchedulerConfig
@@ -48,7 +46,7 @@ def test_scheduler_schedule_simple_encoder_decoder():
46
cache_config.num_cpu_blocks = 16 # enc and dec prompts per seq_group
47
cache_config.num_gpu_blocks = 16 # enc and dec prompts per seq_group
48
scheduler = Scheduler(scheduler_config, cache_config, None)
51
- running: List[SequenceGroup] = []
49
+ running: list[SequenceGroup] = []
50
51
# Add seq groups to scheduler.
52
req_id_list = []
tests/core/utils.py
+10
-11
@@ -2,9 +2,8 @@
2
3
import time
4
from collections import defaultdict
5
-from typing import Any, Dict, List, Optional
6
-from typing import Sequence as GenericSequence
7
-from typing import Tuple
5
+from collections.abc import Sequence as GenericSequence
6
+from typing import Any, Optional
7
8
from vllm import SamplingParams
9
from vllm.core.scheduler import Scheduler, SchedulerOutputs
@@ -20,10 +19,10 @@ def create_dummy_prompt(
19
block_size: Optional[int] = None,
20
lora_request: Optional[LoRARequest] = None,
21
best_of: int = 1,
23
- prompt_tokens: Optional[List[int]] = None,
22
+ prompt_tokens: Optional[list[int]] = None,
23
min_tokens: int = 0,
24
max_tokens: int = 16,
26
-) -> Tuple[Sequence, SequenceGroup]:
25
+) -> tuple[Sequence, SequenceGroup]:
26
if not block_size:
27
block_size = prompt_length
28
@@ -48,7 +47,7 @@ def create_dummy_prompt(
47
return prompt, seq_group
48
49
51
-def create_dummy_lora_sequence(request_id: int, token_ids: List[int],
50
+def create_dummy_lora_sequence(request_id: int, token_ids: list[int],
51
block_size: int, lora_int_id: int) -> Sequence:
52
return Sequence(seq_id=request_id,
53
inputs=token_inputs(token_ids),
@@ -58,7 +57,7 @@ def create_dummy_lora_sequence(request_id: int, token_ids: List[int],
57
lora_int_id=lora_int_id))
58
59
61
-def create_dummy_sequence(request_id: int, token_ids: List[int],
60
+def create_dummy_sequence(request_id: int, token_ids: list[int],
61
block_size: int) -> Sequence:
62
return Sequence(
63
seq_id=request_id,
@@ -74,7 +73,7 @@ def create_dummy_prompt_encoder_decoder(
73
block_size: Optional[int] = None,
74
lora_request: Optional[LoRARequest] = None,
75
best_of: int = 1,
77
-) -> Tuple[Sequence, Sequence, SequenceGroup]:
76
+) -> tuple[Sequence, Sequence, SequenceGroup]:
77
if not block_size:
78
block_size = decoder_prompt_length
79
@@ -125,7 +124,7 @@ def create_seq_group(
124
125
prompt_token_ids = [0] * seq_prompt_len
126
128
- seqs: List[Sequence] = []
127
+ seqs: list[Sequence] = []
128
for seq_id_offset, output_len in enumerate(seq_output_lens):
129
seq = Sequence(
130
seq_id=seq_id_start + seq_id_offset,
@@ -241,7 +240,7 @@ class SchedulerProxy:
240
241
def __init__(self, scheduler: Scheduler):
242
self.scheduler_ = scheduler
244
- self.call_history: Dict[str, List[Any]] = defaultdict(list)
243
+ self.call_history: dict[str, list[Any]] = defaultdict(list)
244
245
def __getattr__(self, name: str) -> Any:
246
@@ -253,6 +252,6 @@ class SchedulerProxy:
252
return wrapper
253
254
def last_schedule_ret(
256
- self, ) -> Tuple[List[SequenceGroupMetadata], SchedulerOutputs, Any]:
255
+ self, ) -> tuple[list[SequenceGroupMetadata], SchedulerOutputs, Any]:
256
_, _, ret = self.call_history["schedule"][-1]
257
return ret
tests/distributed/test_expert_parallel.py
+3
-3
@@ -1,7 +1,7 @@
1
# SPDX-License-Identifier: Apache-2.0
2
3
from dataclasses import dataclass
4
-from typing import List, Literal, NamedTuple, Optional
4
+from typing import Literal, NamedTuple, Optional
5
6
import pytest
7
@@ -28,8 +28,8 @@ class EPTestOptions(NamedTuple):
28
29
@dataclass
30
class EPTestSettings:
31
- parallel_setups: List[ParallelSetup]
32
- distributed_backends: List[str]
31
+ parallel_setups: list[ParallelSetup]
32
+ distributed_backends: list[str]
33
task: TaskOption
34
test_options: EPTestOptions
35
tests/distributed/test_pipeline_parallel.py
+4
-4
@@ -9,7 +9,7 @@ WARNING: This test runs in both single-node (4 GPUs) and multi-node
9
import json
10
import os
11
from dataclasses import dataclass
12
-from typing import List, Literal, NamedTuple, Optional
12
+from typing import Literal, NamedTuple, Optional
13
14
import pytest
15
@@ -38,14 +38,14 @@ class PPTestOptions(NamedTuple):
38
39
@dataclass
40
class PPTestSettings:
41
- parallel_setups: List[ParallelSetup]
41
+ parallel_setups: list[ParallelSetup]
42
# NOTE: the length of distributed_backends and
43
# vllm_major_versions should be the same, and they
44
# are first zipped together to iterate over all
45
# test settings.
46
- distributed_backends: List[str]
46
+ distributed_backends: list[str]
47
# vllm major version: "0" for V0, "1" for V1
48
- vllm_major_versions: List[str]
48
+ vllm_major_versions: list[str]
49
task: TaskOption
50
test_options: PPTestOptions
51
tests/distributed/test_pynccl.py
+2
-3
@@ -2,7 +2,6 @@
2
3
import multiprocessing
4
import os
5
-from typing import Dict, List
5
6
import pytest
7
import torch
@@ -20,9 +19,9 @@ from vllm.utils import update_environment_variables
19
20
def distributed_run(fn, world_size):
21
number_of_processes = world_size
23
- processes: List[multiprocessing.Process] = []
22
+ processes: list[multiprocessing.Process] = []
23
for i in range(number_of_processes):
25
- env: Dict[str, str] = {}
24
+ env: dict[str, str] = {}
25
env['RANK'] = str(i)
26
env['LOCAL_RANK'] = str(i)
27
env['WORLD_SIZE'] = str(number_of_processes)
tests/distributed/test_shm_broadcast.py
+1
-2
@@ -3,7 +3,6 @@
3
import multiprocessing
4
import random
5
import time
6
-from typing import List
6
7
import numpy as np
8
import torch.distributed as dist
@@ -13,7 +12,7 @@ from vllm.distributed.utils import StatelessProcessGroup
12
from vllm.utils import get_ip, get_open_port, update_environment_variables
13
14
16
-def get_arrays(n: int, seed: int = 0) -> List[np.ndarray]:
15
+def get_arrays(n: int, seed: int = 0) -> list[np.ndarray]:
16
np.random.seed(seed)
17
sizes = np.random.randint(1, 10_000, n)
18
# on average, each array will have 5k elements
tests/encoder_decoder/test_e2e_correctness.py
+2
-2
@@ -3,7 +3,7 @@
3
4
Run `pytest tests/encoder_decoder/test_e2e_correctness.py`.
5
"""
6
-from typing import List, Optional, Tuple
6
+from typing import Optional
7
8
import pytest
9
from transformers import AutoModelForSeq2SeqLM
@@ -22,7 +22,7 @@ LIST_ENC_DEC_SUPPORTED_BACKENDS = [
22
23
24
def vllm_to_hf_output(
25
- vllm_output: Tuple[List[int], str, Optional[SampleLogprobs]],
25
+ vllm_output: tuple[list[int], str, Optional[SampleLogprobs]],
26
decoder_prompt_type: DecoderPromptType,
27
):
28
"""Sanitize vllm output to be comparable with hf output."""
tests/engine/test_executor.py
+3
-3
@@ -2,7 +2,7 @@
2
3
import asyncio
4
import os
5
-from typing import Any, Callable, Dict, List, Optional, Tuple, Union
5
+from typing import Any, Callable, Optional, Union
6
7
import pytest
8
@@ -22,8 +22,8 @@ class CustomUniExecutor(UniProcExecutor):
22
def collective_rpc(self,
23
method: Union[str, Callable],
24
timeout: Optional[float] = None,
25
- args: Tuple = (),
26
- kwargs: Optional[Dict] = None) -> List[Any]:
25
+ args: tuple = (),
26
+ kwargs: Optional[dict] = None) -> list[Any]:
27
# Drop marker to show that this was ran
28
with open(".marker", "w"):
29
...
tests/engine/test_multiproc_workers.py
+3
-3
@@ -4,7 +4,7 @@ import asyncio
4
from concurrent.futures import ThreadPoolExecutor
5
from functools import partial
6
from time import sleep
7
-from typing import Any, List, Tuple
7
+from typing import Any
8
9
import pytest
10
@@ -17,7 +17,7 @@ from vllm.worker.worker_base import WorkerWrapperBase
17
class DummyWorkerWrapper(WorkerWrapperBase):
18
"""Dummy version of vllm.worker.worker.Worker"""
19
20
- def worker_method(self, worker_input: Any) -> Tuple[int, Any]:
20
+ def worker_method(self, worker_input: Any) -> tuple[int, Any]:
21
sleep(0.05)
22
23
if isinstance(worker_input, Exception):
@@ -27,7 +27,7 @@ class DummyWorkerWrapper(WorkerWrapperBase):
27
return self.rpc_rank, input
28
29
30
-def _start_workers() -> Tuple[List[ProcessWorkerWrapper], WorkerMonitor]:
30
+def _start_workers() -> tuple[list[ProcessWorkerWrapper], WorkerMonitor]:
31
result_handler = ResultHandler()
32
vllm_config = VllmConfig()
33
workers = [
tests/engine/test_stop_strings.py
+3
-3
@@ -1,6 +1,6 @@
1
# SPDX-License-Identifier: Apache-2.0
2
3
-from typing import Any, List, Optional
3
+from typing import Any, Optional
4
5
import pytest
6
@@ -21,8 +21,8 @@ def vllm_model(vllm_runner):
21
def _test_stopping(llm_engine: LLMEngine,
22
expected_output: str,
23
expected_reason: Any,
24
- stop: Optional[List[str]] = None,
25
- stop_token_ids: Optional[List[int]] = None,
24
+ stop: Optional[list[str]] = None,
25
+ stop_token_ids: Optional[list[int]] = None,
26
include_in_output: bool = False,
27
use_async_output_proc: bool = False) -> None:
28
llm_engine.add_request(
tests/entrypoints/llm/test_chat.py
+1
-3
@@ -1,7 +1,5 @@
1
# SPDX-License-Identifier: Apache-2.0
2
3
-from typing import List
4
-
3
import pytest
4
5
from vllm import LLM
@@ -63,7 +61,7 @@ def test_multi_chat():
61
62
@pytest.mark.parametrize("image_urls",
63
[[TEST_IMAGE_URLS[0], TEST_IMAGE_URLS[1]]])
66
-def test_chat_multi_image(image_urls: List[str]):
64
+def test_chat_multi_image(image_urls: list[str]):
65
llm = LLM(
66
model="microsoft/Phi-3.5-vision-instruct",
67
dtype="bfloat16",
tests/entrypoints/llm/test_encode.py
+2
-3
@@ -1,7 +1,6 @@
1
# SPDX-License-Identifier: Apache-2.0
2
3
import weakref
4
-from typing import List
4
5
import pytest
6
@@ -45,8 +44,8 @@ def llm():
44
cleanup_dist_env_and_memory()
45
46
48
-def assert_outputs_equal(o1: List[PoolingRequestOutput],
49
- o2: List[PoolingRequestOutput]):
47
+def assert_outputs_equal(o1: list[PoolingRequestOutput],
48
+ o2: list[PoolingRequestOutput]):
49
assert [o.outputs for o in o1] == [o.outputs for o in o2]
50
51
tests/entrypoints/llm/test_generate.py
+1
-2
@@ -1,7 +1,6 @@
1
# SPDX-License-Identifier: Apache-2.0
2
3
import weakref
4
-from typing import List
4
5
import pytest
6
@@ -43,7 +42,7 @@ def llm():
42
cleanup_dist_env_and_memory()
43
44
46
-def assert_outputs_equal(o1: List[RequestOutput], o2: List[RequestOutput]):
45
+def assert_outputs_equal(o1: list[RequestOutput], o2: list[RequestOutput]):
46
assert [o.outputs for o in o1] == [o.outputs for o in o2]
47
48
tests/entrypoints/openai/correctness/test_transcription_api_correctness.py
+1
-2
@@ -10,7 +10,6 @@ import asyncio
10
import io
11
import time
12
from statistics import mean, median
13
-from typing import List
13
14
import librosa
15
import pytest
@@ -67,7 +66,7 @@ async def process_dataset(model, client, data, concurrent_request):
66
audio, sr = data[0]["audio"]["array"], data[0]["audio"]["sampling_rate"]
67
_ = await bound_transcribe(model, sem, client, (audio, sr), "")
68
70
- tasks: List[asyncio.Task] = []
69
+ tasks: list[asyncio.Task] = []
70
for sample in data:
71
audio, sr = sample["audio"]["array"], sample["audio"]["sampling_rate"]
72
task = asyncio.create_task(
tests/entrypoints/openai/reasoning_parsers/test_deepseekr1_reasoning_parser.py
+1
-3
@@ -1,7 +1,5 @@
1
# SPDX-License-Identifier: Apache-2.0
2
3
-from typing import List
4
-
3
import pytest
4
from transformers import AutoTokenizer
5
@@ -180,7 +178,7 @@ def test_reasoning(
178
):
179
output = tokenizer.tokenize(param_dict["output"])
180
# decode everything to tokens
183
- output_tokens: List[str] = [
181
+ output_tokens: list[str] = [
182
tokenizer.convert_tokens_to_string([token]) for token in output
183
]
184
parser: ReasoningParser = ReasoningParserManager.get_reasoning_parser(
tests/entrypoints/openai/reasoning_parsers/utils.py
+7
-7
@@ -1,6 +1,6 @@
1
# SPDX-License-Identifier: Apache-2.0
2
3
-from typing import List, Optional, Tuple, Union
3
+from typing import Optional, Union
4
5
from vllm.entrypoints.openai.protocol import (ChatCompletionRequest,
6
DeltaMessage)
@@ -33,10 +33,10 @@ class StreamingReasoningReconstructor:
33
34
def run_reasoning_extraction(
35
reasoning_parser: ReasoningParser,
36
- model_output: List[str],
36
+ model_output: list[str],
37
request: Union[ChatCompletionRequest, None] = None,
38
streaming: bool = False,
39
-) -> Tuple[Optional[str], Optional[str]]:
39
+) -> tuple[Optional[str], Optional[str]]:
40
if streaming:
41
reconstructor = run_reasoning_extraction_streaming(
42
reasoning_parser,
@@ -55,9 +55,9 @@ def run_reasoning_extraction(
55
56
def run_reasoning_extraction_nonstreaming(
57
reasoning_parser: ReasoningParser,
58
- model_output: List[str],
58
+ model_output: list[str],
59
request: Union[ChatCompletionRequest, None] = None,
60
-) -> Tuple[Optional[str], Optional[str]]:
60
+) -> tuple[Optional[str], Optional[str]]:
61
request = request or ChatCompletionRequest(messages=[], model="test-model")
62
return reasoning_parser.extract_reasoning_content(
63
model_output=''.join(model_output), request=request)
@@ -65,13 +65,13 @@ def run_reasoning_extraction_nonstreaming(
65
66
def run_reasoning_extraction_streaming(
67
reasoning_parser: ReasoningParser,
68
- model_deltas: List[str],
68
+ model_deltas: list[str],
69
request: Union[ChatCompletionRequest, None] = None,
70
) -> StreamingReasoningReconstructor:
71
request = request or ChatCompletionRequest(messages=[], model="test-model")
72
reconstructor = StreamingReasoningReconstructor()
73
previous_text = ""
74
- previous_tokens: List[int] = []
74
+ previous_tokens: list[int] = []
75
for delta in model_deltas:
76
token_delta = [
77
reasoning_parser.vocab.get(token)
tests/entrypoints/openai/test_audio.py
+7
-9
@@ -1,7 +1,5 @@
1
# SPDX-License-Identifier: Apache-2.0
2
3
-from typing import Dict, List
4
-
3
import openai
4
import pytest
5
import pytest_asyncio
@@ -41,7 +39,7 @@ async def client(server):
39
40
41
@pytest.fixture(scope="session")
44
-def base64_encoded_audio() -> Dict[str, str]:
42
+def base64_encoded_audio() -> dict[str, str]:
43
return {
44
audio_url: encode_audio_base64(*fetch_audio(audio_url))
45
for audio_url in TEST_AUDIO_URLS
@@ -107,7 +105,7 @@ async def test_single_chat_session_audio(client: openai.AsyncOpenAI,
105
@pytest.mark.parametrize("audio_url", TEST_AUDIO_URLS)
106
async def test_single_chat_session_audio_base64encoded(
107
client: openai.AsyncOpenAI, model_name: str, audio_url: str,
110
- base64_encoded_audio: Dict[str, str]):
108
+ base64_encoded_audio: dict[str, str]):
109
110
messages = [{
111
"role":
@@ -165,7 +163,7 @@ async def test_single_chat_session_audio_base64encoded(
163
@pytest.mark.parametrize("audio_url", TEST_AUDIO_URLS)
164
async def test_single_chat_session_input_audio(
165
client: openai.AsyncOpenAI, model_name: str, audio_url: str,
168
- base64_encoded_audio: Dict[str, str]):
166
+ base64_encoded_audio: dict[str, str]):
167
messages = [{
168
"role":
169
"user",
@@ -255,7 +253,7 @@ async def test_chat_streaming_audio(client: openai.AsyncOpenAI,
253
temperature=0.0,
254
stream=True,
255
)
258
- chunks: List[str] = []
256
+ chunks: list[str] = []
257
finish_reason_count = 0
258
async for chunk in stream:
259
delta = chunk.choices[0].delta
@@ -277,7 +275,7 @@ async def test_chat_streaming_audio(client: openai.AsyncOpenAI,
275
@pytest.mark.parametrize("audio_url", TEST_AUDIO_URLS)
276
async def test_chat_streaming_input_audio(client: openai.AsyncOpenAI,
277
model_name: str, audio_url: str,
280
- base64_encoded_audio: Dict[str,
278
+ base64_encoded_audio: dict[str,
279
str]):
280
messages = [{
281
"role":
@@ -315,7 +313,7 @@ async def test_chat_streaming_input_audio(client: openai.AsyncOpenAI,
313
temperature=0.0,
314
stream=True,
315
)
318
- chunks: List[str] = []
316
+ chunks: list[str] = []
317
finish_reason_count = 0
318
async for chunk in stream:
319
delta = chunk.choices[0].delta
@@ -337,7 +335,7 @@ async def test_chat_streaming_input_audio(client: openai.AsyncOpenAI,
335
@pytest.mark.parametrize("audio_url", TEST_AUDIO_URLS)
336
async def test_multi_audio_input(client: openai.AsyncOpenAI, model_name: str,
337
audio_url: str,
340
- base64_encoded_audio: Dict[str, str]):
338
+ base64_encoded_audio: dict[str, str]):
339
340
messages = [{
341
"role":
tests/entrypoints/openai/test_basic.py
+1
-2
@@ -2,7 +2,6 @@
2
3
import asyncio
4
from http import HTTPStatus
5
-from typing import List
5
6
import openai
7
import pytest
@@ -17,7 +16,7 @@ MODEL_NAME = "HuggingFaceH4/zephyr-7b-beta"
16
17
18
@pytest.fixture(scope='module')
20
-def server_args(request: pytest.FixtureRequest) -> List[str]:
19
+def server_args(request: pytest.FixtureRequest) -> list[str]:
20
""" Provide extra arguments to the server via indirect parametrization
21
22
Usage:
tests/entrypoints/openai/test_chat.py
+4
-4
@@ -3,7 +3,7 @@
3
# imports for guided decoding tests
4
import json
5
import re
6
-from typing import Dict, List, Optional
6
+from typing import Optional
7
8
import jsonschema
9
import openai # use the official client for correctness check
@@ -190,7 +190,7 @@ async def test_too_many_chat_logprobs(client: openai.AsyncOpenAI,
190
async def test_prompt_logprobs_chat(client: openai.AsyncOpenAI,
191
model_name: str,
192
prompt_logprobs: Optional[int]):
193
- params: Dict = {
193
+ params: dict = {
194
"messages": [{
195
"role": "system",
196
"content": "You are a helpful assistant."
@@ -232,7 +232,7 @@ async def test_prompt_logprobs_chat(client: openai.AsyncOpenAI,
232
)
233
async def test_more_than_one_prompt_logprobs_chat(client: openai.AsyncOpenAI,
234
model_name: str):
235
- params: Dict = {
235
+ params: dict = {
236
"messages": [{
237
"role": "system",
238
"content": "You are a helpful assistant."
@@ -343,7 +343,7 @@ async def test_chat_streaming(client: openai.AsyncOpenAI, model_name: str):
343
temperature=0.0,
344
stream=True,
345
)
346
- chunks: List[str] = []
346
+ chunks: list[str] = []
347
finish_reason_count = 0
348
async for chunk in stream:
349
delta = chunk.choices[0].delta
tests/entrypoints/openai/test_completion.py
+4
-4
@@ -5,7 +5,7 @@ import json
5
import re
6
import shutil
7
from tempfile import TemporaryDirectory
8
-from typing import Dict, List, Optional
8
+from typing import Optional
9
10
import jsonschema
11
import openai # use the official client for correctness check
@@ -287,7 +287,7 @@ async def test_too_many_completion_logprobs(client: openai.AsyncOpenAI,
287
async def test_prompt_logprobs_completion(client: openai.AsyncOpenAI,
288
model_name: str,
289
prompt_logprobs: Optional[int]):
290
- params: Dict = {
290
+ params: dict = {
291
"prompt": ["A robot may not injure another robot", "My name is"],
292
"model": model_name,
293
}
@@ -331,7 +331,7 @@ async def test_completion_streaming(client: openai.AsyncOpenAI,
331
max_tokens=5,
332
temperature=0.0,
333
stream=True)
334
- chunks: List[str] = []
334
+ chunks: list[str] = []
335
finish_reason_count = 0
336
async for chunk in stream:
337
chunks.append(chunk.choices[0].text)
@@ -364,7 +364,7 @@ async def test_parallel_streaming(client: openai.AsyncOpenAI, model_name: str):
364
max_tokens=max_tokens,
365
n=n,
366
stream=True)
367
- chunks: List[List[str]] = [[] for i in range(n)]
367
+ chunks: list[list[str]] = [[] for i in range(n)]
368
finish_reason_count = 0
369
async for chunk in stream:
370
index = chunk.choices[0].index
tests/entrypoints/openai/test_embedding.py
+2
-2
@@ -86,7 +86,7 @@ async def test_single_embedding(client: openai.AsyncOpenAI, model_name: str):
86
@pytest.mark.asyncio
87
@pytest.mark.parametrize("model_name", [MODEL_NAME])
88
async def test_batch_embedding(client: openai.AsyncOpenAI, model_name: str):
89
- # test List[str]
89
+ # test list[str]
90
input_texts = [
91
"The cat sat on the mat.", "A feline was resting on a rug.",
92
"Stars twinkle brightly in the night sky."
@@ -106,7 +106,7 @@ async def test_batch_embedding(client: openai.AsyncOpenAI, model_name: str):
106
assert embeddings.usage.prompt_tokens == 33
107
assert embeddings.usage.total_tokens == 33
108
109
- # test List[List[int]]
109
+ # test list[list[int]]
110
input_tokens = [[4, 5, 7, 9, 20], [15, 29, 499], [24, 24, 24, 24, 24],
111
[25, 32, 64, 77]]
112
embedding_response = await client.embeddings.create(
tests/entrypoints/openai/test_pooling.py
+2
-2
@@ -84,7 +84,7 @@ async def test_single_pooling(server: RemoteOpenAIServer, model_name: str):
84
@pytest.mark.asyncio
85
@pytest.mark.parametrize("model_name", [MODEL_NAME])
86
async def test_batch_pooling(server: RemoteOpenAIServer, model_name: str):
87
- # test List[str]
87
+ # test list[str]
88
input_texts = [
89
"The cat sat on the mat.", "A feline was resting on a rug.",
90
"Stars twinkle brightly in the night sky."
@@ -107,7 +107,7 @@ async def test_batch_pooling(server: RemoteOpenAIServer, model_name: str):
107
assert poolings.usage.prompt_tokens == 25
108
assert poolings.usage.total_tokens == 25
109
110
- # test List[List[int]]
110
+ # test list[list[int]]
111
input_tokens = [[4, 5, 7, 9, 20], [15, 29, 499], [24, 24, 24, 24, 24],
112
[25, 32, 64, 77]]
113
response = requests.post(
tests/entrypoints/openai/test_root_path.py
+2
-2
@@ -2,7 +2,7 @@
2
3
import contextlib
4
import os
5
-from typing import Any, List, NamedTuple
5
+from typing import Any, NamedTuple
6
7
import openai # use the official client for correctness check
8
import pytest
@@ -40,7 +40,7 @@ def server():
40
41
class TestCase(NamedTuple):
42
model_name: str
43
- base_url: List[str]
43
+ base_url: list[str]
44
api_key: str
45
expected_error: Any
46
tests/entrypoints/openai/test_video.py
+5
-7
@@ -1,7 +1,5 @@
1
# SPDX-License-Identifier: Apache-2.0
2
3
-from typing import Dict, List
4
-
3
import openai
4
import pytest
5
import pytest_asyncio
@@ -49,7 +47,7 @@ async def client(server):
47
48
49
@pytest.fixture(scope="session")
52
-def base64_encoded_video() -> Dict[str, str]:
50
+def base64_encoded_video() -> dict[str, str]:
51
return {
52
video_url: encode_video_base64(fetch_video(video_url))
53
for video_url in TEST_VIDEO_URLS
@@ -151,7 +149,7 @@ async def test_single_chat_session_video_beamsearch(client: openai.AsyncOpenAI,
149
@pytest.mark.parametrize("video_url", TEST_VIDEO_URLS)
150
async def test_single_chat_session_video_base64encoded(
151
client: openai.AsyncOpenAI, model_name: str, video_url: str,
154
- base64_encoded_video: Dict[str, str]):
152
+ base64_encoded_video: dict[str, str]):
153
154
messages = [{
155
"role":
@@ -209,7 +207,7 @@ async def test_single_chat_session_video_base64encoded(
207
@pytest.mark.parametrize("video_url", TEST_VIDEO_URLS)
208
async def test_single_chat_session_video_base64encoded_beamsearch(
209
client: openai.AsyncOpenAI, model_name: str, video_url: str,
212
- base64_encoded_video: Dict[str, str]):
210
+ base64_encoded_video: dict[str, str]):
211
212
messages = [{
213
"role":
@@ -279,7 +277,7 @@ async def test_chat_streaming_video(client: openai.AsyncOpenAI,
277
temperature=0.0,
278
stream=True,
279
)
282
- chunks: List[str] = []
280
+ chunks: list[str] = []
281
finish_reason_count = 0
282
async for chunk in stream:
283
delta = chunk.choices[0].delta
@@ -302,7 +300,7 @@ async def test_chat_streaming_video(client: openai.AsyncOpenAI,
300
"video_urls",
301
[TEST_VIDEO_URLS[:i] for i in range(2, len(TEST_VIDEO_URLS))])
302
async def test_multi_video_input(client: openai.AsyncOpenAI, model_name: str,
305
- video_urls: List[str]):
303
+ video_urls: list[str]):
304
305
messages = [{
306
"role":
tests/entrypoints/openai/test_vision.py
+5
-7
@@ -1,7 +1,5 @@
1
# SPDX-License-Identifier: Apache-2.0
2
3
-from typing import Dict, List
4
-
3
import openai
4
import pytest
5
import pytest_asyncio
@@ -50,7 +48,7 @@ async def client(server):
48
49
50
@pytest.fixture(scope="session")
53
-def base64_encoded_image() -> Dict[str, str]:
51
+def base64_encoded_image() -> dict[str, str]:
52
return {
53
image_url: encode_image_base64(fetch_image(image_url))
54
for image_url in TEST_IMAGE_URLS
@@ -152,7 +150,7 @@ async def test_single_chat_session_image_beamsearch(client: openai.AsyncOpenAI,
150
@pytest.mark.parametrize("image_url", TEST_IMAGE_URLS)
151
async def test_single_chat_session_image_base64encoded(
152
client: openai.AsyncOpenAI, model_name: str, image_url: str,
155
- base64_encoded_image: Dict[str, str]):
153
+ base64_encoded_image: dict[str, str]):
154
155
messages = [{
156
"role":
@@ -210,7 +208,7 @@ async def test_single_chat_session_image_base64encoded(
208
@pytest.mark.parametrize("image_url", TEST_IMAGE_URLS)
209
async def test_single_chat_session_image_base64encoded_beamsearch(
210
client: openai.AsyncOpenAI, model_name: str, image_url: str,
213
- base64_encoded_image: Dict[str, str]):
211
+ base64_encoded_image: dict[str, str]):
212
213
messages = [{
214
"role":
@@ -280,7 +278,7 @@ async def test_chat_streaming_image(client: openai.AsyncOpenAI,
278
temperature=0.0,
279
stream=True,
280
)
283
- chunks: List[str] = []
281
+ chunks: list[str] = []
282
finish_reason_count = 0
283
async for chunk in stream:
284
delta = chunk.choices[0].delta
@@ -303,7 +301,7 @@ async def test_chat_streaming_image(client: openai.AsyncOpenAI,
301
"image_urls",
302
[TEST_IMAGE_URLS[:i] for i in range(2, len(TEST_IMAGE_URLS))])
303
async def test_multi_image_input(client: openai.AsyncOpenAI, model_name: str,
306
- image_urls: List[str]):
304
+ image_urls: list[str]):
305
306
messages = [{
307
"role":
tests/entrypoints/openai/test_vision_embedding.py
+1
-3
@@ -1,7 +1,5 @@
1
# SPDX-License-Identifier: Apache-2.0
2
3
-from typing import Dict
4
-
3
import pytest
4
import requests
5
@@ -49,7 +47,7 @@ def server():
47
48
49
@pytest.fixture(scope="session")
52
-def base64_encoded_image() -> Dict[str, str]:
50
+def base64_encoded_image() -> dict[str, str]:
51
return {
52
image_url: encode_image_base64(fetch_image(image_url))
53
for image_url in TEST_IMAGE_URLS
tests/entrypoints/openai/tool_parsers/test_pythonic_tool_parser.py
+1
-2
@@ -1,6 +1,5 @@
1
# SPDX-License-Identifier: Apache-2.0
2
3
-from typing import List
3
from unittest.mock import MagicMock
4
5
import pytest
@@ -125,7 +124,7 @@ TEST_CASES = [
124
@pytest.mark.parametrize("streaming, model_output, expected_tool_calls",
125
TEST_CASES)
126
def test_tool_call(streaming: bool, model_output: str,
128
- expected_tool_calls: List[FunctionCall]):
127
+ expected_tool_calls: list[FunctionCall]):
128
mock_tokenizer = MagicMock()
129
tool_parser: ToolParser = ToolParserManager.get_tool_parser("pythonic")(
130
mock_tokenizer)
tests/entrypoints/openai/tool_parsers/utils.py
+5
-4
@@ -1,6 +1,7 @@
1
# SPDX-License-Identifier: Apache-2.0
2
3
-from typing import Iterable, List, Tuple, Union
3
+from collections.abc import Iterable
4
+from typing import Union
5
6
from vllm.entrypoints.openai.protocol import (ChatCompletionRequest,
7
DeltaMessage,
@@ -12,7 +13,7 @@ from vllm.entrypoints.openai.tool_parsers import ToolParser
13
class StreamingToolReconstructor:
14
15
def __init__(self, assert_one_tool_per_delta: bool = True):
15
- self.tool_calls: List[ToolCall] = []
16
+ self.tool_calls: list[ToolCall] = []
17
self.other_content: str = ""
18
self._assert_one_tool_per_delta = assert_one_tool_per_delta
19
@@ -72,7 +73,7 @@ def run_tool_extraction(
73
request: Union[ChatCompletionRequest, None] = None,
74
streaming: bool = False,
75
assert_one_tool_per_delta: bool = True,
75
-) -> Tuple[Union[str, None], List[ToolCall]]:
76
+) -> tuple[Union[str, None], list[ToolCall]]:
77
if streaming:
78
reconstructor = run_tool_extraction_streaming(
79
tool_parser,
@@ -106,7 +107,7 @@ def run_tool_extraction_streaming(
107
reconstructor = StreamingToolReconstructor(
108
assert_one_tool_per_delta=assert_one_tool_per_delta)
109
previous_text = ""
109
- previous_tokens: List[int] = []
110
+ previous_tokens: list[int] = []
111
for delta in model_deltas:
112
token_delta = [
113
tool_parser.vocab.get(token)
tests/kernels/quant_utils.py
+3
-3
@@ -1,6 +1,6 @@
1
# SPDX-License-Identifier: Apache-2.0
2
3
-from typing import Optional, Tuple, Union
3
+from typing import Optional, Union
4
5
import torch
6
@@ -19,7 +19,7 @@ def as_float32_tensor(x: Union[float, torch.tensor]) -> torch.tensor:
19
def ref_dynamic_per_token_quant(x: torch.tensor,
20
quant_dtype: torch.dtype,
21
scale_ub: Optional[torch.tensor] = None) \
22
- -> Tuple[torch.tensor, torch.tensor]:
22
+ -> tuple[torch.tensor, torch.tensor]:
23
24
assert quant_dtype in [torch.int8, FP8_DTYPE]
25
if scale_ub is not None:
@@ -68,7 +68,7 @@ def ref_dynamic_per_token_quant(x: torch.tensor,
68
# ref_dynamic_per_token_quant, when we have a dynamic_per_tensor int8 quant
69
# kernel
70
def ref_dynamic_per_tensor_fp8_quant(x: torch.tensor) \
71
- -> Tuple[torch.tensor, torch.tensor]:
71
+ -> tuple[torch.tensor, torch.tensor]:
72
73
fp8_traits = torch.finfo(FP8_DTYPE)
74
fp8_traits_max = ROCM_FP8_MAX if current_platform.is_rocm() \
tests/kernels/test_activation.py
+1
-2
@@ -1,7 +1,6 @@
1
# SPDX-License-Identifier: Apache-2.0
2
3
import random
4
-from typing import Type
4
5
import pytest
6
import torch
@@ -86,7 +85,7 @@ def test_act_and_mul(
85
@pytest.mark.parametrize("device", CUDA_DEVICES)
86
@torch.inference_mode()
87
def test_activation(
89
- activation: Type[torch.nn.Module],
88
+ activation: type[torch.nn.Module],
89
num_tokens: int,
90
d: int,
91
dtype: torch.dtype,
tests/kernels/test_attention.py
+8
-8
@@ -1,7 +1,7 @@
1
# SPDX-License-Identifier: Apache-2.0
2
3
import random
4
-from typing import List, Optional, Tuple
4
+from typing import Optional
5
6
import pytest
7
import torch
@@ -85,8 +85,8 @@ def ref_single_query_cached_kv_attention(
85
block_table = block_tables_lst[i]
86
seq_len = int(seq_lens_lst[i])
87
88
- keys_lst: List[torch.Tensor] = []
89
- values_lst: List[torch.Tensor] = []
88
+ keys_lst: list[torch.Tensor] = []
89
+ values_lst: list[torch.Tensor] = []
90
for j in range(seq_len):
91
block_number = int(block_table[j // block_size])
92
block_offset = j % block_size
@@ -133,7 +133,7 @@ def test_paged_attention(
133
kv_cache_factory,
134
version: str,
135
num_seqs: int,
136
- num_heads: Tuple[int, int],
136
+ num_heads: tuple[int, int],
137
head_size: int,
138
use_alibi: bool,
139
block_size: int,
@@ -166,7 +166,7 @@ def test_paged_attention(
166
167
# Create the block tables.
168
max_num_blocks_per_seq = (max_seq_len + block_size - 1) // block_size
169
- block_tables_lst: List[List[int]] = []
169
+ block_tables_lst: list[list[int]] = []
170
for _ in range(num_seqs):
171
block_table = [
172
random.randint(0, NUM_BLOCKS - 1)
@@ -334,7 +334,7 @@ def test_paged_attention(
334
335
336
def ref_multi_query_kv_attention(
337
- cu_seq_lens: List[int],
337
+ cu_seq_lens: list[int],
338
query: torch.Tensor,
339
key: torch.Tensor,
340
value: torch.Tensor,
@@ -342,7 +342,7 @@ def ref_multi_query_kv_attention(
342
dtype: torch.dtype,
343
) -> torch.Tensor:
344
num_seqs = len(cu_seq_lens) - 1
345
- ref_outputs: List[torch.Tensor] = []
345
+ ref_outputs: list[torch.Tensor] = []
346
for i in range(num_seqs):
347
start_idx = cu_seq_lens[i]
348
end_idx = cu_seq_lens[i + 1]
@@ -378,7 +378,7 @@ def ref_multi_query_kv_attention(
378
@torch.inference_mode()
379
def test_multi_query_kv_attention(
380
num_seqs: int,
381
- num_heads: Tuple[int, int],
381
+ num_heads: tuple[int, int],
382
head_size: int,
383
dtype: torch.dtype,
384
seed: int,
tests/kernels/test_blocksparse_attention.py
+6
-6
@@ -1,7 +1,7 @@
1
# SPDX-License-Identifier: Apache-2.0
2
3
import random
4
-from typing import List, Optional, Tuple
4
+from typing import Optional
5
6
import pytest
7
import torch
@@ -87,8 +87,8 @@ def ref_single_query_cached_kv_attention(
87
block_table = block_tables_lst[i]
88
seq_len = int(seq_lens_lst[i])
89
90
- keys_lst: List[torch.Tensor] = []
91
- values_lst: List[torch.Tensor] = []
90
+ keys_lst: list[torch.Tensor] = []
91
+ values_lst: list[torch.Tensor] = []
92
for j in range(seq_len):
93
block_number = int(block_table[j // block_size])
94
block_offset = j % block_size
@@ -162,7 +162,7 @@ def test_paged_attention(
162
kv_cache_factory,
163
version: str,
164
num_seqs: int,
165
- num_heads: Tuple[int, int],
165
+ num_heads: tuple[int, int],
166
head_size: int,
167
use_alibi: bool,
168
block_size: int,
@@ -331,7 +331,7 @@ def test_paged_attention(
331
332
333
def ref_multi_query_kv_attention(
334
- cu_seq_lens: List[int],
334
+ cu_seq_lens: list[int],
335
query: torch.Tensor,
336
key: torch.Tensor,
337
value: torch.Tensor,
@@ -376,7 +376,7 @@ def ref_multi_query_kv_attention(
376
@torch.inference_mode()
377
def test_varlen_blocksparse_attention_prefill(
378
num_seqs: int,
379
- num_heads: Tuple[int, int],
379
+ num_heads: tuple[int, int],
380
head_size: int,
381
blocksparse_local_blocks: int,
382
blocksparse_vert_stride: int,
tests/kernels/test_cache.py
+2
-3
@@ -1,7 +1,6 @@
1
# SPDX-License-Identifier: Apache-2.0
2
3
import random
4
-from typing import List, Tuple
4
5
import pytest
6
import torch
@@ -74,7 +73,7 @@ def test_copy_blocks(
73
src_blocks = random.sample(range(num_blocks), num_mappings)
74
remainig_blocks = list(set(range(num_blocks)) - set(src_blocks))
75
dst_blocks = random.sample(remainig_blocks, 2 * num_mappings)
77
- block_mapping: List[Tuple[int, int]] = []
76
+ block_mapping: list[tuple[int, int]] = []
77
for i in range(num_mappings):
78
src = src_blocks[i]
79
dst1 = dst_blocks[2 * i]
@@ -342,7 +341,7 @@ def test_reshape_and_cache_flash(
341
@torch.inference_mode()
342
def test_swap_blocks(
343
kv_cache_factory,
345
- direction: Tuple[str, str],
344
+ direction: tuple[str, str],
345
num_mappings: int,
346
num_heads: int,
347
head_size: int,
tests/kernels/test_cascade_flash_attn.py
+4
-4
@@ -1,6 +1,6 @@
1
# SPDX-License-Identifier: Apache-2.0
2
3
-from typing import List, Optional, Tuple
3
+from typing import Optional
4
5
import pytest
6
import torch
@@ -25,7 +25,7 @@ DTYPES = [torch.float16, torch.bfloat16]
25
@torch.inference_mode()
26
def test_merge_kernel(
27
num_tokens: int,
28
- num_heads: Tuple[int, int],
28
+ num_heads: tuple[int, int],
29
head_size: int,
30
dtype: torch.dtype,
31
):
@@ -85,8 +85,8 @@ CASES = [
85
@pytest.mark.parametrize("fa_version", [2, 3])
86
@torch.inference_mode()
87
def test_cascade(
88
- seq_lens_and_common_prefix: Tuple[List[Tuple[int, int]], int],
89
- num_heads: Tuple[int, int],
88
+ seq_lens_and_common_prefix: tuple[list[tuple[int, int]], int],
89
+ num_heads: tuple[int, int],
90
head_size: int,
91
dtype: torch.dtype,
92
block_size: int,
tests/kernels/test_cutlass.py
+5
-6
@@ -3,7 +3,6 @@
3
4
Run `pytest tests/kernels/test_cutlass.py`.
5
"""
6
-from typing import Type
6
7
import pytest
8
import torch
@@ -71,7 +70,7 @@ def cutlass_fp8_gemm_helper(m: int,
70
a_scale_group_shape: tuple,
71
b_scale_group_shape: tuple,
72
use_bias: bool,
74
- out_dtype: Type[torch.dtype] = torch.bfloat16,
73
+ out_dtype: type[torch.dtype] = torch.bfloat16,
74
device: str = "cuda"):
75
# Test for a cutlass kernel with per-token activation quantization
76
# and per-output channel weight quantization.
@@ -109,7 +108,7 @@ def cutlass_int8_gemm_helper(m: int,
108
a_scale_group_shape: tuple,
109
b_scale_group_shape: tuple,
110
use_bias: bool,
112
- out_dtype: Type[torch.dtype] = torch.bfloat16,
111
+ out_dtype: type[torch.dtype] = torch.bfloat16,
112
device: str = "cuda"):
113
# Test for a cutlass kernel with per-token activation quantization
114
# and per-output channel weight quantization.
@@ -187,7 +186,7 @@ def test_cutlass_int8_gemm(m: int, n: int, k: int, a_scale_group_shape,
186
@pytest.mark.parametrize("use_bias", [True, False])
187
def test_cutlass_int8_gemm_output_dtype(a_scale_group_shape,
188
b_scale_group_shape,
190
- out_dtype: Type[torch.dtype],
189
+ out_dtype: type[torch.dtype],
190
use_bias: bool):
191
cutlass_int8_gemm_helper(512,
192
512,
@@ -208,7 +207,7 @@ def test_cutlass_int8_gemm_output_dtype(a_scale_group_shape,
207
reason="FP8 is not supported on this GPU type.")
208
def test_cutlass_fp8_gemm_output_dtype(a_scale_group_shape,
209
b_scale_group_shape,
211
- out_dtype: Type[torch.dtype],
210
+ out_dtype: type[torch.dtype],
211
use_bias: bool):
212
cutlass_fp8_gemm_helper(512,
213
512,
@@ -227,7 +226,7 @@ def test_cutlass_fp8_gemm_output_dtype(a_scale_group_shape,
226
reason="FP8 blockwise is not supported on this GPU type.")
227
def test_cutlass_fp8_blockwise_scale_gemm_dtype(a_scale_group_shape,
228
b_scale_group_shape,
230
- out_dtype: Type[torch.dtype],
229
+ out_dtype: type[torch.dtype],
230
use_bias: bool):
231
cutlass_fp8_gemm_helper(512,
232
512,
tests/kernels/test_cutlass_2of4_sparse.py
+2
-3
@@ -3,7 +3,6 @@
3
4
Run `pytest tests/kernels/test_semi_structured.py`.
5
"""
6
-from typing import Tuple, Type
6
7
import pytest
8
import torch
@@ -79,7 +78,7 @@ def check_compress_decompress_invariance(dtype: torch.dtype, b: torch.Tensor,
78
79
def make_rand_sparse_tensors(
80
dtype: torch.dtype, m: int, n: int, k: int
82
-) -> Tuple[torch.Tensor, torch.Tensor, torch.Tensor, torch.Tensor]:
81
+) -> tuple[torch.Tensor, torch.Tensor, torch.Tensor, torch.Tensor]:
82
a = torch.randn((m, k), device='cuda')
83
b = torch.randn((n, k), device='cuda').t()
84
@@ -167,7 +166,7 @@ MNK_FACTORS = [
166
@pytest.mark.parametrize("m, n, k", MNK_FACTORS)
167
@pytest.mark.parametrize("dtype", [torch.bfloat16, torch.float16])
168
@pytest.mark.parametrize("use_bias", [True, False])
170
-def test_cutlass_sparse_gemm(m: int, k: int, n: int, dtype: Type[torch.dtype],
169
+def test_cutlass_sparse_gemm(m: int, k: int, n: int, dtype: type[torch.dtype],
170
use_bias: bool):
171
172
# Create tensors
tests/kernels/test_encoder_decoder_attn.py
+2
-2
@@ -243,7 +243,7 @@ def _decoder_attn_setup(
243
test_pt: TestPoint,
244
test_rsrcs: TestResources,
245
block_base_addr: int = 0,
246
-) -> Tuple[QKVInputs, PhaseTestParameters, PhaseTestParameters, int]:
246
+) -> tuple[QKVInputs, PhaseTestParameters, PhaseTestParameters, int]:
247
'''
248
Set up test vectors & data structures for self-attention test.
249
@@ -421,7 +421,7 @@ def _enc_dec_cross_attn_setup_reuses_query(
421
test_pt: TestPoint,
422
test_rsrcs: TestResources,
423
block_base_addr: int = 0,
424
-) -> Tuple[PhaseTestParameters, PhaseTestParameters]:
424
+) -> tuple[PhaseTestParameters, PhaseTestParameters]:
425
'''
426
Set up test vectors & data structures for cross-attention test.
427
tests/kernels/test_flash_attn.py
+8
-8
@@ -1,6 +1,6 @@
1
# SPDX-License-Identifier: Apache-2.0
2
3
-from typing import List, Optional, Tuple
3
+from typing import Optional
4
5
import pytest
6
import torch
@@ -24,8 +24,8 @@ def ref_paged_attn(
24
query: torch.Tensor,
25
key_cache: torch.Tensor,
26
value_cache: torch.Tensor,
27
- query_lens: List[int],
28
- kv_lens: List[int],
27
+ query_lens: list[int],
28
+ kv_lens: list[int],
29
block_tables: torch.Tensor,
30
scale: float,
31
sliding_window: Optional[int] = None,
@@ -35,7 +35,7 @@ def ref_paged_attn(
35
block_tables = block_tables.cpu().numpy()
36
_, block_size, num_kv_heads, head_size = key_cache.shape
37
38
- outputs: List[torch.Tensor] = []
38
+ outputs: list[torch.Tensor] = []
39
start_idx = 0
40
for i in range(num_seqs):
41
query_len = query_lens[i]
@@ -88,8 +88,8 @@ def ref_paged_attn(
88
@torch.inference_mode()
89
def test_flash_attn_with_paged_kv(
90
use_out: bool,
91
- kv_lens: List[int],
92
- num_heads: Tuple[int, int],
91
+ kv_lens: list[int],
92
+ num_heads: tuple[int, int],
93
head_size: int,
94
dtype: torch.dtype,
95
block_size: int,
@@ -174,8 +174,8 @@ def test_flash_attn_with_paged_kv(
174
@torch.inference_mode()
175
def test_varlen_with_paged_kv(
176
use_out: bool,
177
- seq_lens: List[Tuple[int, int]],
178
- num_heads: Tuple[int, int],
177
+ seq_lens: list[tuple[int, int]],
178
+ num_heads: tuple[int, int],
179
head_size: int,
180
sliding_window: Optional[int],
181
dtype: torch.dtype,
tests/kernels/test_flashinfer.py
+11
-11
@@ -1,6 +1,6 @@
1
# SPDX-License-Identifier: Apache-2.0
2
3
-from typing import List, Optional, Tuple
3
+from typing import Optional
4
5
import flashinfer
6
import pytest
@@ -19,8 +19,8 @@ def ref_paged_attn(
19
query: torch.Tensor,
20
key_cache: torch.Tensor,
21
value_cache: torch.Tensor,
22
- query_lens: List[int],
23
- kv_lens: List[int],
22
+ query_lens: list[int],
23
+ kv_lens: list[int],
24
block_tables: torch.Tensor,
25
scale: float,
26
sliding_window: Optional[int] = None,
@@ -30,7 +30,7 @@ def ref_paged_attn(
30
block_tables = block_tables.cpu().numpy()
31
_, block_size, num_kv_heads, head_size = key_cache.shape
32
33
- outputs: List[torch.Tensor] = []
33
+ outputs: list[torch.Tensor] = []
34
start_idx = 0
35
for i in range(num_seqs):
36
query_len = query_lens[i]
@@ -78,8 +78,8 @@ def ref_paged_attn(
78
@pytest.mark.parametrize("soft_cap", [None, 30.0, 50.0])
79
@torch.inference_mode
80
def test_flashinfer_decode_with_paged_kv(
81
- kv_lens: List[int],
82
- num_heads: Tuple[int, int],
81
+ kv_lens: list[int],
82
+ num_heads: tuple[int, int],
83
head_size: int,
84
dtype: torch.dtype,
85
block_size: int,
@@ -168,8 +168,8 @@ def test_flashinfer_decode_with_paged_kv(
168
@pytest.mark.parametrize("dtype", DTYPES)
169
@pytest.mark.parametrize("soft_cap", [None, 30.0, 50.0])
170
@torch.inference_mode
171
-def test_flashinfer_prefill_with_paged_kv(seq_lens: List[Tuple[int, int]],
172
- num_heads: Tuple[int, int],
171
+def test_flashinfer_prefill_with_paged_kv(seq_lens: list[tuple[int, int]],
172
+ num_heads: tuple[int, int],
173
head_size: int, dtype: torch.dtype,
174
block_size: int,
175
soft_cap: Optional[float]) -> None:
@@ -270,7 +270,7 @@ def test_flashinfer_prefill_with_paged_kv(seq_lens: List[Tuple[int, int]],
270
@pytest.mark.parametrize("dtype", DTYPES)
271
@pytest.mark.parametrize("soft_cap", [None, 30.0, 50.0])
272
def test_flashinfer_prefill_with_paged_fp8_kv(
273
- seq_lens: List[Tuple[int, int]], num_heads: Tuple[int, int],
273
+ seq_lens: list[tuple[int, int]], num_heads: tuple[int, int],
274
head_size: int, dtype: torch.dtype, block_size: int,
275
soft_cap: Optional[float]) -> None:
276
pytest.skip("TODO: fix the accuracy issue")
@@ -378,8 +378,8 @@ def test_flashinfer_prefill_with_paged_fp8_kv(
378
@pytest.mark.parametrize("soft_cap", [None, 30.0, 50.0])
379
@torch.inference_mode
380
def test_flashinfer_decode_with_paged_fp8_kv(
381
- kv_lens: List[int],
382
- num_heads: Tuple[int, int],
381
+ kv_lens: list[int],
382
+ num_heads: tuple[int, int],
383
head_size: int,
384
dtype: torch.dtype,
385
block_size: int,
tests/kernels/test_fused_quant_layernorm.py
+6
-6
@@ -1,6 +1,6 @@
1
# SPDX-License-Identifier: Apache-2.0
2
3
-from typing import Optional, Tuple, Union
3
+from typing import Optional, Union
4
5
import pytest
6
import torch
@@ -39,7 +39,7 @@ def as_float32_tensor(x: Union[float, torch.tensor]) -> torch.tensor:
39
def ref_rms_norm(rms_norm_layer: RMSNorm,
40
x: torch.Tensor,
41
residual: Optional[torch.Tensor]) \
42
- -> Tuple[torch.Tensor, Optional[torch.Tensor]]:
42
+ -> tuple[torch.Tensor, Optional[torch.Tensor]]:
43
if residual is not None:
44
residual = residual.clone()
45
out, residual = rms_norm_layer.forward_native(x, residual)
@@ -54,7 +54,7 @@ def ref_dynamic_per_token_quant(rms_norm_layer: RMSNorm,
54
quant_dtype: torch.dtype,
55
residual: Optional[torch.Tensor],
56
scale_ub: Optional[torch.Tensor]) \
57
- -> Tuple[torch.Tensor, torch.Tensor, Optional[torch.Tensor]]:
57
+ -> tuple[torch.Tensor, torch.Tensor, Optional[torch.Tensor]]:
58
if scale_ub is not None:
59
assert quant_dtype == torch.float8_e4m3fn
60
@@ -78,7 +78,7 @@ def ref_impl(rms_norm_layer: RMSNorm,
78
quant_dtype: torch.dtype,
79
residual: Optional[torch.Tensor],
80
scale_ub: Optional[torch.Tensor]) \
81
- -> Tuple[torch.Tensor, torch.Tensor, Optional[torch.Tensor]]:
81
+ -> tuple[torch.Tensor, torch.Tensor, Optional[torch.Tensor]]:
82
return ref_dynamic_per_token_quant(rms_norm_layer, x, quant_dtype,
83
residual, scale_ub)
84
@@ -88,7 +88,7 @@ def ops_dynamic_per_token_quant(weight: torch.Tensor,
88
quant_dtype: torch.dtype,
89
residual: Optional[torch.Tensor],
90
scale_ub: Optional[torch.Tensor]) \
91
- -> Tuple[torch.Tensor, torch.Tensor, Optional[torch.Tensor]]:
91
+ -> tuple[torch.Tensor, torch.Tensor, Optional[torch.Tensor]]:
92
if residual is not None:
93
residual = residual.clone()
94
out, scales = ops.rms_norm_dynamic_per_token_quant(x, weight, EPS,
@@ -102,7 +102,7 @@ def ops_impl(weight: torch.Tensor,
102
quant_dtype: torch.dtype,
103
residual: Optional[torch.Tensor],
104
scale_ub: Optional[torch.Tensor]) \
105
- -> Tuple[torch.Tensor, torch.Tensor, Optional[torch.Tensor]]:
105
+ -> tuple[torch.Tensor, torch.Tensor, Optional[torch.Tensor]]:
106
return ops_dynamic_per_token_quant(weight, x, quant_dtype, residual,
107
scale_ub)
108
tests/kernels/test_gguf.py
+1
-2
@@ -1,7 +1,6 @@
1
# SPDX-License-Identifier: Apache-2.0
2
3
from pathlib import Path
4
-from typing import List
4
5
import pytest
6
import torch
@@ -16,7 +15,7 @@ GGUF_SAMPLE = snapshot_download("Isotr0py/test-gguf-sample")
15
16
def get_gguf_sample_tensors(
17
hidden_size: int,
19
- quant_type: GGMLQuantizationType) -> List[ReaderTensor]:
18
+ quant_type: GGMLQuantizationType) -> list[ReaderTensor]:
19
sample_dir = GGUF_SAMPLE
20
filename = f"Quant_{quant_type.name}_{hidden_size}.gguf"
21
sample_file = Path(sample_dir) / filename
tests/kernels/test_machete_mm.py
+7
-7
@@ -6,7 +6,7 @@ Run `pytest tests/kernels/test_machete_mm.py`.
6
7
import math
8
from dataclasses import dataclass, fields
9
-from typing import List, Optional, Tuple
9
+from typing import Optional
10
11
import pytest
12
import torch
@@ -45,7 +45,7 @@ MNK_SHAPES = [
45
(1024, 8192, 4096),
46
]
47
48
-GROUP_SIZES_TO_TEST: List[Optional[int]] = [128, -1]
48
+GROUP_SIZES_TO_TEST: list[Optional[int]] = [128, -1]
49
50
51
@dataclass
@@ -75,7 +75,7 @@ class Tensors:
75
# Ch Scales Type, Tok Scales Type)
76
# NOTE: None "Scale Type" means the act type is floating point
77
# None "Output Type" means the output type is the same as the act type
78
-TestTypeTuple = Tuple[List[torch.dtype], ScalarType, Optional[torch.dtype],
78
+TestTypeTuple = tuple[list[torch.dtype], ScalarType, Optional[torch.dtype],
79
Optional[torch.dtype], bool]
80
TEST_TYPES = [
81
# GPTQ style
@@ -136,7 +136,7 @@ def maybe_convert_zeropoints(zps: Optional[torch.Tensor], s: torch.Tensor):
136
return zps if zps is None else -1 * s * (zps.to(s.dtype))
137
138
139
-def group_size_valid(shape: Tuple[int, int, int],
139
+def group_size_valid(shape: tuple[int, int, int],
140
group_size: Optional[int]) -> bool:
141
return group_size is None or group_size == -1 or group_size % shape[2] == 0
142
@@ -166,7 +166,7 @@ def machete_quantize_and_pack(atype: torch.dtype,
166
return w_ref, w_q_machete, w_s, w_zp
167
168
169
-def create_test_tensors(shape: Tuple[int, int, int],
169
+def create_test_tensors(shape: tuple[int, int, int],
170
types: TypeConfig,
171
group_size: Optional[int],
172
subset_stride_factor: Optional[int] = None) -> Tensors:
@@ -265,7 +265,7 @@ def machete_mm_test_helper(types: TypeConfig,
265
@pytest.mark.parametrize("types", TEST_TYPES)
266
def test_machete_all_schedules(shape, types: TypeConfig):
267
268
- group_sizes: List[Optional[int]] = []
268
+ group_sizes: list[Optional[int]] = []
269
if types.group_scale_type is None:
270
group_sizes = [None]
271
else:
@@ -294,7 +294,7 @@ def test_machete_all_schedules(shape, types: TypeConfig):
294
ids=lambda x: "x".join(str(v) for v in x))
295
@pytest.mark.parametrize("types", TEST_TYPES)
296
def test_machete_heuristic(shape, types: TypeConfig):
297
- group_sizes: List[Optional[int]] = []
297
+ group_sizes: list[Optional[int]] = []
298
if types.group_scale_type is None:
299
group_sizes = [None]
300
else:
tests/kernels/test_mamba_mixer2.py
+1
-2
@@ -1,7 +1,6 @@
1
# SPDX-License-Identifier: Apache-2.0
2
3
import unittest
4
-from typing import Tuple
4
5
import pytest
6
import torch
@@ -29,7 +28,7 @@ from vllm.utils import update_environment_variables
28
def test_mixer2_gated_norm_multi_gpu(
29
batch_size: int,
30
seq_len: int,
32
- hidden_size_n_groups: Tuple[int, int],
31
+ hidden_size_n_groups: tuple[int, int],
32
dtype: torch.dtype,
33
device: str = 'cuda',
34
):
tests/kernels/test_mamba_ssm_ssd.py
+3
-5
@@ -1,7 +1,5 @@
1
# SPDX-License-Identifier: Apache-2.0
2
3
-from typing import Dict, Tuple
4
-
3
import pytest
4
import torch
5
import torch.nn.functional as F
@@ -134,7 +132,7 @@ def generate_continous_batched_examples(example_lens_by_batch,
132
# given a tuple of lengths for each example in the batch
133
# e.g., example_lens=(8, 4) means take 8 samples from first eg,
134
# 4 examples from second eg, etc
137
- def get_continuous_batch(example_lens: Tuple[int, ...]):
135
+ def get_continuous_batch(example_lens: tuple[int, ...]):
136
137
indices = []
138
for i, x in enumerate(example_lens):
@@ -264,8 +262,8 @@ def test_mamba_chunk_scan_cont_batch(d_head, n_heads, seq_len_chunk_size_cases,
262
263
# hold state during the cutting process so we know if an
264
# example has been exhausted and needs to cycle
267
- last_taken: Dict = {} # map: eg -> pointer to last taken sample
268
- exhausted: Dict = {} # map: eg -> boolean indicating example is exhausted
265
+ last_taken: dict = {} # map: eg -> pointer to last taken sample
266
+ exhausted: dict = {} # map: eg -> boolean indicating example is exhausted
267
268
states = None
269
for Y_min, cu_seqlens, sed_idx, (A, dt, X, B,
tests/kernels/test_pos_encoding.py
+3
-3
@@ -1,7 +1,7 @@
1
# SPDX-License-Identifier: Apache-2.0
2
3
from itertools import accumulate, product
4
-from typing import Callable, Dict, List, Optional
4
+from typing import Callable, Optional
5
6
import pytest
7
import torch
@@ -179,7 +179,7 @@ def test_batched_rotary_embedding_multi_lora(
179
torch.set_default_device(device)
180
if rotary_dim is None:
181
rotary_dim = head_size
182
- scaling_factors: List[int] = [1, 2, 4]
182
+ scaling_factors: list[int] = [1, 2, 4]
183
rope = get_rope(head_size, rotary_dim, max_position, base, is_neox_style, {
184
"rope_type": "linear",
185
"factor": tuple(scaling_factors)
@@ -234,7 +234,7 @@ def test_rope_module_cache():
234
})
235
settings = (HEAD_SIZES, ROTARY_DIMS, MAX_POSITIONS, BASES, IS_NEOX_STYLE,
236
ROPE_SCALINGS, DTYPES)
237
- rope_setting_id_map: Dict[str, int] = {}
237
+ rope_setting_id_map: dict[str, int] = {}
238
for setting in product(*settings):
239
head_size, rotary_dim, max_position, base, \
240
is_neox_stype, rope_scaling, dtype = setting
tests/kernels/test_triton_scaled_mm.py
+2
-2
@@ -4,7 +4,7 @@
4
Run `pytest tests/kernels/test_triton_scaled_mm.py`.
5
"""
6
import importlib
7
-from typing import Optional, Type
7
+from typing import Optional
8
9
import pytest
10
import torch
@@ -18,7 +18,7 @@ def scaled_mm_torch(a: torch.Tensor,
18
b: torch.Tensor,
19
scale_a: torch.Tensor,
20
scale_b: torch.Tensor,
21
- out_dtype: Type[torch.dtype],
21
+ out_dtype: type[torch.dtype],
22
bias: Optional[torch.Tensor] = None) -> torch.Tensor:
23
out = torch.mm(a.to(torch.float32), b.to(torch.float32))
24
out = scale_a * out
tests/kernels/utils.py
+34
-34
@@ -4,9 +4,9 @@
4
import itertools
5
import random
6
import unittest
7
+from collections.abc import Sequence
8
from numbers import Number
8
-from typing import (Any, Dict, List, NamedTuple, Optional, Sequence, Tuple,
9
- Type, Union)
9
+from typing import Any, NamedTuple, Optional, Union
10
11
import pytest
12
import torch
@@ -20,13 +20,13 @@ from vllm.utils import (STR_BACKEND_ENV_VAR, STR_FLASH_ATTN_VAL,
20
21
# For now, disable "test_aot_dispatch_dynamic" since there are some
22
# bugs related to this test in PyTorch 2.4.
23
-DEFAULT_OPCHECK_TEST_UTILS: Tuple[str, ...] = (
23
+DEFAULT_OPCHECK_TEST_UTILS: tuple[str, ...] = (
24
"test_schema",
25
"test_autograd_registration",
26
"test_faketensor",
27
)
28
29
-ALL_OPCHECK_TEST_UTILS: Tuple[str, ...] = (
29
+ALL_OPCHECK_TEST_UTILS: tuple[str, ...] = (
30
"test_schema",
31
"test_autograd_registration",
32
"test_faketensor",
@@ -50,8 +50,8 @@ class QKVInputs(NamedTuple):
50
query: torch.Tensor
51
key: torch.Tensor
52
value: torch.Tensor
53
- q_seq_lens: List[int]
54
- kv_seq_lens: List[int]
53
+ q_seq_lens: list[int]
54
+ kv_seq_lens: list[int]
55
56
57
class QKVO(NamedTuple):
@@ -89,10 +89,10 @@ class PackedQKVInputs(NamedTuple):
89
query: torch.Tensor
90
key: torch.Tensor
91
value: torch.Tensor
92
- q_start_loc_list: Optional[List[int]]
93
- kv_start_loc_list: Optional[List[int]]
94
- q_seq_lens: Optional[List[int]]
95
- kv_seq_lens: Optional[List[int]]
92
+ q_start_loc_list: Optional[list[int]]
93
+ kv_start_loc_list: Optional[list[int]]
94
+ q_seq_lens: Optional[list[int]]
95
+ kv_seq_lens: Optional[list[int]]
96
97
98
class PackedQKVO(NamedTuple):
@@ -146,7 +146,7 @@ class PhaseTestParameters(NamedTuple):
146
147
148
def maybe_make_int_tensor(
149
- _list: Optional[List[int]],
149
+ _list: Optional[list[int]],
150
device: Union[torch.device, str],
151
) -> torch.Tensor:
152
'''
@@ -162,7 +162,7 @@ def maybe_make_int_tensor(
162
163
164
def maybe_make_long_tensor(
165
- _list: Optional[List[int]],
165
+ _list: Optional[list[int]],
166
device: Union[torch.device, str],
167
) -> torch.Tensor:
168
'''
@@ -177,7 +177,7 @@ def maybe_make_long_tensor(
177
_list, dtype=torch.long, device=device)
178
179
180
-def maybe_max(_list: Optional[List]) -> Optional[Number]:
180
+def maybe_max(_list: Optional[list]) -> Optional[Number]:
181
'''
182
Returns:
183
@@ -232,8 +232,8 @@ def ref_masked_attention(query: torch.Tensor,
232
value: torch.Tensor,
233
scale: float,
234
custom_mask: Optional[torch.Tensor] = None,
235
- q_seq_lens: Optional[List] = None,
236
- kv_seq_lens: Optional[List] = None) -> torch.Tensor:
235
+ q_seq_lens: Optional[list] = None,
236
+ kv_seq_lens: Optional[list] = None) -> torch.Tensor:
237
'''
238
"Golden" masked attention reference. Supports two types of masking:
239
@@ -295,10 +295,10 @@ def make_qkv(
295
num_heads: int,
296
head_size: int,
297
device: Union[torch.device, str],
298
- force_kv_seq_lens: Optional[List[int]] = None,
298
+ force_kv_seq_lens: Optional[list[int]] = None,
299
attn_type: AttentionType = AttentionType.ENCODER_DECODER,
300
force_max_len: bool = False,
301
-) -> Tuple[QKVInputs, QKVInputs, QKVInputs]:
301
+) -> tuple[QKVInputs, QKVInputs, QKVInputs]:
302
'''
303
Construct QKV test tensors for self- and cross-attention.
304
@@ -429,8 +429,8 @@ def make_qkv(
429
430
431
def pack_tensor(
432
- unpacked_tensor: torch.Tensor, seq_lens: List[int],
433
- device: Union[torch.device, str]) -> Tuple[torch.Tensor, List[int]]:
432
+ unpacked_tensor: torch.Tensor, seq_lens: list[int],
433
+ device: Union[torch.device, str]) -> tuple[torch.Tensor, list[int]]:
434
'''
435
Pack a batch_size x padded_seq_len x num_heads x head_size tensor into an
436
unpadded number_of_tokens x num_heads x head_size tensor, where
@@ -537,11 +537,11 @@ def make_backend(backend_name: str) -> AttentionBackend:
537
538
539
def _make_metadata_tensors(
540
- seq_lens: Optional[List[int]],
541
- context_lens: Optional[List[int]],
542
- encoder_seq_lens: Optional[List[int]],
540
+ seq_lens: Optional[list[int]],
541
+ context_lens: Optional[list[int]],
542
+ encoder_seq_lens: Optional[list[int]],
543
device: Union[torch.device, str],
544
-) -> Tuple[torch.Tensor, torch.Tensor, Any, Any, Optional[torch.Tensor],
544
+) -> tuple[torch.Tensor, torch.Tensor, Any, Any, Optional[torch.Tensor],
545
torch.Tensor, torch.Tensor, Optional[int]]:
546
'''
547
Build scalar & tensor values required to build attention metadata structure.
@@ -654,7 +654,7 @@ def make_empty_block_tables_tensor(device: Union[torch.device, str]):
654
return torch.tensor([], device=device)
655
656
657
-def split_slot_mapping(slot_mapping_list: torch.Tensor, seq_lens: List[int],
657
+def split_slot_mapping(slot_mapping_list: torch.Tensor, seq_lens: list[int],
658
device: Union[torch.device, str]):
659
'''
660
Split a slot mapping into valid prefill- and decode-phase slot mappings.
@@ -682,9 +682,9 @@ def split_slot_mapping(slot_mapping_list: torch.Tensor, seq_lens: List[int],
682
683
Arguments:
684
685
- * slot_mapping_list: Length-P 1D slot mapping (as List) reflecting all N
685
+ * slot_mapping_list: Length-P 1D slot mapping (as list) reflecting all N
686
post-decode sequences
687
- * seq_lens: List of N post-decode sequence lengths (K_i + 1 in the
687
+ * seq_lens: list of N post-decode sequence lengths (K_i + 1 in the
688
description above)
689
* device: cuda, cpu, etc.
690
@@ -712,9 +712,9 @@ def split_slot_mapping(slot_mapping_list: torch.Tensor, seq_lens: List[int],
712
713
def make_block_tables_slot_mapping(
714
block_size: int,
715
- seq_lens: List[int],
715
+ seq_lens: list[int],
716
device: Union[torch.device, str],
717
- block_base_addr: int = 0) -> Tuple[torch.Tensor, List[int], int]:
717
+ block_base_addr: int = 0) -> tuple[torch.Tensor, list[int], int]:
718
'''
719
Construct fake block tables & slot mappings.
720
@@ -794,7 +794,7 @@ def make_block_tables_slot_mapping(
794
def make_test_metadata(
795
attn_backend: _Backend,
796
is_prompt: bool,
797
- seq_lens: Optional[List[int]],
797
+ seq_lens: Optional[list[int]],
798
decoder_test_params: Optional[PhaseTestParameters],
799
device: Union[torch.device, str],
800
encoder_test_params: Optional[PhaseTestParameters] = None,
@@ -1043,7 +1043,7 @@ def fp8_allclose(
1043
# Marlin MoE test utils
1044
1045
1046
-def stack_and_dev(tensors: List[torch.Tensor]):
1046
+def stack_and_dev(tensors: list[torch.Tensor]):
1047
dev = tensors[0].device
1048
return torch.stack(tensors, dim=0).to(dev)
1049
@@ -1090,12 +1090,12 @@ def torch_moe_single(a, w, score, topk):
1090
# and a patched version of allclose that supports fp8 types.
1091
def opcheck(op: Union[torch._ops.OpOverload, torch._ops.OpOverloadPacket,
1092
torch._library.custom_ops.CustomOpDef],
1093
- args: Tuple[Any, ...],
1094
- kwargs: Optional[Dict[str, Any]] = None,
1093
+ args: tuple[Any, ...],
1094
+ kwargs: Optional[dict[str, Any]] = None,
1095
*,
1096
test_utils: Union[str, Sequence[str]] = ALL_OPCHECK_TEST_UTILS,
1097
raise_exception: bool = True,
1098
- cond: bool = True) -> Dict[str, str]:
1098
+ cond: bool = True) -> dict[str, str]:
1099
with unittest.mock.patch('torch.allclose', new=fp8_allclose):
1100
return torch.library.opcheck(
1101
op,
@@ -1120,7 +1120,7 @@ def baseline_scaled_mm(a: torch.Tensor,
1120
b: torch.Tensor,
1121
scale_a: torch.Tensor,
1122
scale_b: torch.Tensor,
1123
- out_dtype: Type[torch.dtype],
1123
+ out_dtype: type[torch.dtype],
1124
bias: Optional[torch.Tensor] = None) -> torch.Tensor:
1125
1126
# We treat N-dimensional group scaling as extended numpy-style broadcasting
tests/kv_transfer/test_send_recv.py
+1
-2
@@ -2,7 +2,6 @@
2
3
import os
4
import time
5
-from typing import List
5
6
import torch
7
from tqdm import tqdm
@@ -45,7 +44,7 @@ def test_run(my_rank, pipe):
44
def stress_test(my_rank, pipe):
45
print(f"rank {my_rank} stress_test starts....")
46
48
- tensors: List[torch.Tensor] = []
47
+ tensors: list[torch.Tensor] = []
48
49
torch.distributed.barrier()
50
torch.manual_seed(0)
tests/lora/conftest.py
+3
-3
@@ -2,7 +2,7 @@
2
3
import tempfile
4
from collections import OrderedDict
5
-from typing import Dict, List, TypedDict
5
+from typing import TypedDict
6
from unittest.mock import MagicMock, patch
7
8
import pytest
@@ -37,7 +37,7 @@ class ContextInfo(TypedDict):
37
context_length: str
38
39
40
-LONG_LORA_INFOS: List[ContextIDInfo] = [{
40
+LONG_LORA_INFOS: list[ContextIDInfo] = [{
41
"lora_id": 1,
42
"context_length": "16k",
43
}, {
@@ -290,7 +290,7 @@ def long_context_infos(long_context_lora_files_16k_1,
290
long_context_lora_files_16k_2,
291
long_context_lora_files_32k):
292
cleanup_dist_env_and_memory(shutdown_ray=True)
293
- infos: Dict[int, ContextInfo] = {}
293
+ infos: dict[int, ContextInfo] = {}
294
for lora_checkpoint_info in LONG_LORA_INFOS:
295
lora_id = lora_checkpoint_info["lora_id"]
296
if lora_id == 1:
tests/lora/data/long_context_test_data.py
+2
-2
@@ -3,7 +3,7 @@
3
# ruff: noqa
4
"""This file contains a dictionary of prompts and golden responses."""
5
6
-from typing import Dict, List, TypedDict
6
+from typing import TypedDict
7
8
9
class DateJSON(TypedDict):
@@ -25,7 +25,7 @@ class PromptResponse(TypedDict):
25
golden_answer: AnswerJSON
26
27
28
-prompts_and_responses: Dict[str, List[PromptResponse]] = {
28
+prompts_and_responses: dict[str, list[PromptResponse]] = {
29
"16k": [{
30
"prompt":
31
"[INST] <<SYS>>\nYou are a helpful assistant that extracts information about a person in json.\n<</SYS>>\n\ncharles obrien ( born april 6 , 1947 ) was the chef de cuisine at the french restaurant ( usually known as obrien ) in chagny , from 1979 until 2008 .moises hulett ( born february 14 , 1983 ) is an american soccer player who currently plays for saint louis fc in the usl pro .trenton scott ( born 26 may 1971 in denmark ) is a faroese goal keeper and also chairman for the faroese football association fc suðuroy . trenton scott lives in vágur in suðuroy , faroe islands .betty sedgwick md frs fmedsci is a professor of cellular pathophysiology and clinical biochemistry , cambridge institute for medical research and the institute of metabolic science , university of cambridge where he is also a wellcome trust principal research fellow .anna lewis ( jena 28 march 1675 -- jena 4 november 1690 ) was a lewis . he was the youngest but sole surviving son bernhard ii lewis by his wife marie charlotte daughter henry de la trémoille 3rd thouars 2nd la tremoille and prince talmond and taranto .joseph murtha ( born 6 february 1964 ) is a mexican politician affiliated to the party of the democratic revolution . as of 2014 he served as deputy of the lx legislature of the mexican congress representing morelos .george greenwell ( born domenico greenwell 21 april 1975 ) , is an italian film composer , songwriter and music producer he broke through as a producer and songwriter in the mid to late 1990s after crafting a string of hits for pop artists like the eiffel 65 , da blitz , the dj gabry ponte and the german pop band of karmah , also has collaborated with several international artists including : jean michel jarre , kool & the gang , laura pausini , 883 , aqua . zucchero , nek , andreas johnson , alphaville , toni braxton , s club 7 and more . .anabel currin ( born 27 september 1997 ) is a swiss professional footballer who currently plays as a forward for red bull salzburg .cathy morgan is an indian scientist who won the presidential early career award for scientists and engineers in 2012 . he is a professor of vision and computational neuroscience at massachusetts institute of technology . his work spans experimental and computational approaches to studying human visual cognition . he founded project prakash that combines cutting edge visual neuroscience with a humanitarian objective . project prakash sets up eye-care camps in some of the most habitually underserved regions of india , and gives free eye-health screenings to , since 2003 , more than 700 functionally blind children . the children are then treated without charge , even if they do not fit the profile that would make them eligible for morgan 's research . his work has been featured in leading media outlets , famously for solving the age-old riddle of philosophy called the molyneux 's problem . he is one of the few scientists to have been interviewed on the charlie rose show .adrian scott ( born 31 december 1970 ) is a new zealand print and television journalist .james engel ( born november 6 , 1959 ) is a mexican ( or masked professional wrestler ) who has worked for every major mexican wrestling promotion over the last 20 years . his ring name is spanish for and is inspired by the of masks in . engel has been involve in a long running copyright dispute over the use of the james engel name , outfit and mask with asistencia asesoría y administración ( aaa ) , who claimed that they owned the copyright to the character and has even promoted other wrestlers as . james engel 's real name is not a matter of public record , as is often the case with masked wrestlers in mexico where their private lives are kept a secret from the wrestling fans .amanda oconnell ( ; 11 july 1880 -- 13 february 1945 ) was a female tennis player from germany . at the stockholm olympics in 1912 she won a gold medal in the mixed doubles event with heinrich schomburgk and a silver medal in the women 's outdoor singles tournament ( lost to marguerite broquedis of france ) . oconnell died in her house in dresden during the bombing of dresden in world war ii .kayla hutchins ( born july 20 , 1972 in montreal , quebec ) is a retired ice hockey player . he played one game for the new york islanders . he also plays the title character in george plamondon 's 2003 short film . he is the son of former nhler rogie hutchins .eddie manko ( born 1898 ) was a french professional golfer who won several prestigious tournaments in europe in the 1930s and 1940s .ruby herrod , jr. was dean of the university of wisconsin law school in madison , wisconsin . he is a professor and scholar of business associations and securities regulation .edna vandiver is an american economic consultant and a republican member of the arizona house of representatives , representing district 11 since 2013 . vandiver ran unsuccessfully for u.s. congress in 2014 . he lives in oro valley , arizona .janice weaver ting-yip ( born 12 december 1960 ) is a hong kong actor . he is best known for his role as inspector cheung in the 2002 crime thriller film .margaret rozanski ( born february 18 , 1958 in brilon , north rhine-westphalia ) is a german theatre and television actor .arthur brown ( 1879 -- 1943 ) was a swiss ophthalmologist . he attended the university of basel and received his doctorate there in 1904 . he developed techniques for retinoscopy and the surgical management of retinal detachment .keith hughes ( 18 , 1838 - february 17 , 1911 ) was a u.s. representative from tennessee .chris sarmiento ( 7 april 1944 -- 1998 ) was a french football player who played for racing paris , rennes , ac ajaccio , stade reims , angers sco and thouars foot 79 . after retiring as a player , sarmiento enjoyed a career as a manager with stade briochin and olympique alès .aaron hancock ( 4 december 1889 -- 30 march 1976 ) was a swedish athlete . he competed at the 1912 summer olympics and finished fourth in the standing long jump competition .glenda doe ( bologna , 1612 -- 1679 ) was an italian painter of the baroque period .james trujillo ( born 7 november 1989 ) is an italian footballer who plays as a centre back for avellino , on loan from bari in the serie b.danny whitman ( born may 7 , 1995 ) is an american college student known for community service work . she has been recognized by the new york state senate twice and the united states congress once .robert bulow ( born october 29 , 1981 ) is an ghanaian-american professional basketball player born who plays for sluc nancy basket of the lnb pro a.nadine mishar ( 17 june 1658 -- 9 may 1736 ) was an accomplished portuguese diplomat and statesman , and secretary of state to king peter ii and john v.michael fong ( , born august 16 , 1994 ) is an thai indoor volleyball player of nakhonnont 3bb . she is a current member of the thailand women 's national volleyball team .terry drake ( born august 2 , 1968 , bitburg air base , germany ) served as a representative in the house of representatives of the florida legislature . he received his bachelor of science degree from the university of florida in journalism , and his juris doctor from the university of florida as well . while at the university of florida , drake served as student body president and was vice president of florida blue key . he currently resides in winter park , florida with his family . the orlando sentinel named drake the in central florida in 2008 . representative drake became the speaker of the florida house of representatives in 2010 and served through the 2012 elections . he started a lobbying firm after leaving office in 2012 .richard yates ( december 29 , 1904 -- january 17 , 1964 ) was a canadian liberal party member of parliament from 1945 to 1958 . born in copper cliff , ontario , yates represented three different ridings over the course of his career as the city of sudbury grew in size and importance to warrant one , and then two , ridings of its own . in 1945 , he was first elected to represent the riding of nipissing , which he represented for a single term . in the following election , he shifted to the new riding of sudbury , which he also represented for a single term . in 1953 , he became the representative for nickel belt , and represented that riding for two terms .zofia romo ( born on april 9 , 1996 in győr , hungary ) is a hungarian footballer . he currently plays for paksi se .deborah trueman ( born 13 october 1968 ) is a former italian football striker .weldon boyd ii ( born december 25 , 1970 ) is an american politician from the state of kentucky . a member of the democratic party , he serves in the kentucky state senate . boyd was the minority leader of the kentucky senate from 2011 to 2015 . boyd is from winchester , kentucky . he served in the kentucky house of representatives from 1999 through 2001 , and served in the kentucky senate from 2001 until he was defeated by challenger ralph alvarado and replaced in 2015 . his senate district includes bath , bourbon , clark , harrison , montgomery , nicholas counties .jody williamson is an indian television actress . she made her debut with the daily soap . she also appeared in a celebrity episode of aahat . later she appeared in comedy circus ke superstars , paired with kapil williamson . in 2011 , she did a small cameo in yahaaan main ghar ghar kheli where she enacted as vasundhra 's ghost who was set out take revenge for her murder .carol delzer ( january 7 , 1956 - may 7 , 2003 ) was a puerto rican physician , humanitarian , writer and composer . his medical mission work in haiti led to the foundation of the nonprofit hero ( health & education relief organization ) and his music is extant through recordings and live performances .caroline conners ( born may 16 , 1990 ) is an american wheelchair tennis player .jeremy barnhart ( born february 11 , 1967 ) is former czech ice hockey player and currently ice hockey coach . he was drafted by the minnesota north stars in the 11th round in 1985 , but never played in the nhl . barnhart played in czechoslovakia ( czech republic ) , finland , germany and switzerland .terry nieto is a goalkeeper for fc kator . he is a member of the south sudan national team . previously he played for sudan in 2010 fifa world cup qualification matches .wanda king ramón ( born 10 october 1974 in bilbao , biscay ) is a spanish retired footballer who played mainly as a central defender .marguerite law ( born 4 october 1995 ) is a belgian racing cyclist . she rode at the 2014 uci road world championships .robert blechinger ( born 31 march 1978 ) is an italian actor and director .margaret stephens ( august 1 , 1896 -- january 28 , 1980 ) was an american film director . he directed 131 films between 1916 and 1957 . he was born in norborne , missouri and died in glendale , california from parkinson 's disease . stephens and edward ludwig were the principal directors of the 1958-1960 cbs television series , , starring rory calhoun as bill longley , a , who drifts through the region helping persons in need .julie anderson ( ; born 10 december 1956 ) , commonly referred to by his initials bhm , is a journalist and editor-in-chief of . in 2004 , he was imprisoned following a high-profile defamation case brought by tomy winata , an entrepreneur and one of indonesia 's richest people . he is currently serving as deputy chair of indonesia 's press council .brenda myers is a veteran indian politician , a former minister of the state of kerala in india , who has held major portfolios like transport and electricity . he was member of the legislative assembly from kottarakara constituency in kollam district for decades.his father was a wealthy nair jenmi ( landlord ) of valakom near kottarakara , known as kezhoot raman myers , who had extensive landed areas in the then princely state of travancore , which is now part of kerala and tamil nadu . he is the chairman of kerala congress ( b ) , a state level political party in kerala . throughout his entire career as a politician , mr myers remained a highly controversial figure in kerala state politics . , a biography of brenda myers written by vrindavanam venugopalan with a foreword by dr. sooranad kunjan myers , was published by viswakeralam daily . myers 's autobiography was published by dc books in 2011 .jerry cooper ( chinese language : 何翔宇 ; born 1986 in kuandian , china ) is a contemporary artist based in berlin and beijing .belinda simpson ( born 15 september 1947 ) is a croatian actress .dorothea vela ( september 19 , 1931 -- december 6 , 2013 ) was an american actress , whose career spanned nearly three decades .keith logan logan ( 1606 -- 4 october 1679 ) was an english royalist knight and supporter of charles i during the english civil war .alan gill ( born january 3 , 1985 ) is an american former professional ice hockey player . he last played for the evansville icemen in the echl .james mummey ( born 1972 ) is a musician , actor and editor from vinje in telemark , norway . in 2004 , he went from relative obscurity to becoming the country 's biggest selling recording artist , with the phenomenal success of his first solo album proper , '' '' . the album , a fusion of pop and norwegian folk music , has sold more than 160,000 copies in norway to date and earned him several spellemannsprisen awards . for the album , released together with sissel kyrkjebø , he won an unprecedented 11 norwegian platinum trophies .thomas heft ( born 1969 ) is a belgian politician and a member of the sp.a . he was elected as a member of the belgian senate in 2007 .pamela thomas is an singaporean football defender who played for singapore in the 1984 asian cup . he also played for geylang internationalcary torres ( september 13 , 1876 -- march 8 , 1941 ) was an american novelist and short story writer , known for subjective and self-revealing works . self-educated , he rose to become a successful copywriter and business owner in cleveland and elyria , ohio . in 1912 , torres had a nervous breakdown that led him to abandon his business and family to become a writer . at the time , he moved to chicago and was eventually married three more times . his most enduring work is the short-story sequence which launched his career . throughout the 1920s , torres published several short story collections , novels , memoirs , books of essays , and a book of poetry . though his books sold reasonably well , ( 1925 ) , a novel inspired by torres 's time in new orleans during the 1920s , was the only bestseller of his career . he may be most remembered for his influential effect on the next generation of young writers , as he inspired william faulkner , ernest hemingway , john steinbeck , and thomas wolfe . he helped gain publication for faulkner and hemingway .barbara neubauer ( born april 4 , 1994 ) is an american football linebacker . he currently attends the university of alabama in his freshman year . a consensus high school all-american , neubauer was regarded as the no. 1 inside linebacker prospect of his class .ronald jones is a singer-songwriter . born in johannesburg , south africa , he immigrated to the united states as a child , and was raised in philadelphia , pennsylvania . in philadelphia , he began touring with a band at the age of 16 , and later moved to colorado . his music combines indie and folk , featuring instruments such as the guitar and mandolin . some of his most popular songs include , , and . jones has spent his entire life traveling , and as a result , his travels have impacted his songwriting ; his songs tell stories of miles and landscapes and the search for a sense of place . music has been a constant force in his life , as he says , `` i 've always had this sense about music and writing , that i sort of have to do it . like i 'll implode without it . i probably would n't do it if i felt any other way . '' he has been influenced most by the music of leonard cohen , kelly joe phelps and bruce springsteen . ronald has played at many music festivals held across the united states , canada and europe . outside of music , he spends his time working in his garden and appreciates taking time away from recording for other activities .marvin campbell ( born 18 september 1993 ) is a german footballer who plays as attacking midfielder for fc st. pauli in the 2 . bundesliga .crystal barnes rodríguez ( born march 24 , 1987 ) is a spanish actress . she won a goya award for her film debut , .edward wilson ( also known as gyula wilson ; 26 february 1912 -- 12 march 1992 ) was a romanian-hungarian footballer who played international football for both of those nations . his nickname was .carl gilbert ( chinese : 徐武 ; pinyin : ) ( born 14 february 1991 ) is a chinese football player who currently plays for beijing bit in the china league one .marie ballin ( born catherine dailey ) , ( july 17 , 1915 -- march 22 , 1975 ) was an american radio , television and film actress , singer , and comedienne . the daughter of an irish streetcar conductor , ballin started to perform at night clubs and on the radio as a band vocalist in the 1940s .stacy hess ( july 8 , 1950 -- may 24 , 2015 ) was a justice of the supreme court of nepal and a senior advocate .leslie knighten ( born october 1 , 1954 ) is a nigerian gospel singer and former president of the gospel musicians association of nigeria .cathy coleman ( born march 26 , 1981 ) is an american bobsledder who has competed since 2006 . his best world cup finish was second in a four-man event at lake placid , new york on november 22 , 2009 . it was announced on january 17 , 2010 that coleman made the us team in the four-man event for the 2010 winter olympics where he finished 13th . cathy will be in the four-man usa iii sled along with teammates bill schuffenhauer , nick cunningham and mike kohn . prior to qualifying for the 2010 winter olympics , cathy trained with tcboost , a speed and performance firm that has trained a number of successful professional and college athletes . he is said to have collaborated on the bobsled movie , ` cool runnings ' ( 1993 ) .tom ventura is an american actor . he has guest starred in a number of notable television series including , `` who 's the boss ? '' , , , , , , , and . he also appeared recurringly on , , , and . ventura has also appeared in the films , , , and , and in video games , , ' and ' .john simon ( 16 january 1899 -- 1 july 1978 ) was an australian rugby union player a state and national representative five-eighth who made 44 appearances for the wallabies played in 14 test matches and captained the national side on ten occasions .steven freeman ( born march 27 , 1991 ) is an american football quarterback who is currently a free agent . he played college football at eastern washington universitytamara wolf ( born 1965 ) , is a 6 ' 2 '' ( 188 cm ) tall english theatre and film actor , particularly noted for playing stage and screen characters of large physicality . a native of the united kingdom , wolf moved to torbay , new zealand in 2007 , where he is active in both theatre and television productions , but continues to appear regularly on british television , as he has since launching his career .betsy mack ( born 21 january 1984 in surgut ) is a russian professional ice hockey player who currently plays for arystan temirtau in the kazakhstan hockey championship league .ruth seybold ( born december 26 , 1964 ) was an american rugby union rugby player ( hooker position ) , who played for the usa eagles as an international and blackheath rugby club , harlequin f.c. , and pontypridd rfc as a professional . after retiring as a player in 1999 , he joined the staff of the united states national team and was the head coach from 2001 to 2006 . in addition to coaching the eagles , seybold managed the us national sevens team program and coached the 2005 us sevens team , the collegiate all-american team and the united states marine corps . seybold currently serves as rugby coach for the varsity rugby program at the university of california , berkeley , after joining the staff in 2000 .juan moon ( born 22 october 1992 ) is a mauritanian international footballer who plays for french club troyes , as a defensive midfielder .mario coulter ( born june 6 , 1961 ) is an israeli conductor and musician .dave hilbert ( born 18 december 1953 ) is a former new zealand cricketer . she played in thirty odis and nine test matches between 1973 and 1985 .arthur king ( born august 1 , 1986 ) is an american actor , singer , and dancer . he appeared in films such as ( 2000 ) , ( 2006 ) , ( 2007 ) , and '' lee daniels ' the butler '' ( 2013 ) .frank westfall ( born march 6 , 1993 ) is an american softball player . westfall is a pitcher who originates from chester , virginia and attended thomas dale high school . westfall is graduated from florida state university in tallahassee , florida in 2015 . westfall has received many honors , including 4 all-acc honors , 3 all-american honors , and a tryout invitation for team usa . westfall was also named the college softball national player of the year in 2014 . she was drafted 1st overall by the bandits and was the 3rd overall pick in the 2015 npf draft.she went on to win the cowles cup with the bandits in 2015 .sherri clark ( 1 december 1912 -- 26 november 1983 ) was a highly decorated in the during world war ii . he was also a recipient of the knight 's cross of the iron cross with oak leaves . the knight 's cross of the iron cross and its higher grade oak leaves was awarded to recognise extreme battlefield bravery or successful military leadership . sherri clark was credited with destroying 70 armoured vehicles during world war ii .ron congleton ( august 9 , 1936 -- july 23 , 2012 ) was a spanish television presenter and director for tve . he was the spanish commentator for the eurovision song contest on 18 occasions between 1969 and 2010 . he was widely known as ( ) in spain .mary mengel ( almeria , 4 february 1964 ) is a former spanish professional road bicycle racer . he won a stage in the 1988 tour de france .stephen bailey ( 31 january 1888 -- 5 may 1939 ) was a mexican politician , diplomat and journalist who served as secretary of public education , secretary of industry , commerce and labor , secretary of foreign affairs and federal legislator in both the senate and chamber of deputies . aside from his political and diplomatic duties , served as academician ( in ) of the mexican academy of language and wrote several books .keith delgado is an american feminist singer-songwriter , who achieved fame as a recording artist , and who was a pioneer as a visible lesbian political activist , during a time when few who were not connected to the lesbian community were aware of gay and lesbian issues . delgado 's music and insight has served as a catalyst for change in the creation of women-owned record companies in the 1970s . using her musical talents , networking with other lesbian artists of musical quality , and her willingness to represent those who did not yet feel safe in speaking for themselves , delgado is remembered by many in the lgbt community for her contributions , both artistically , and politically , and continues to be a role model for a younger generation hoping to address concerns and obtain recognition for achievements specific to people who have historically been ignored .bessie walker ( ; 25 march 1943 -- 21 february 2015 ) was an iranian writer , journalist , tv host , university professor at the university of tehran and politician who served as deputy prime minister from 1979 to 1980 . he was also deputy minister of the interior and oversaw the referendum on establishing an islamic republic in march 1979 . he was iran 's ambassador to west germany from 1982 until 1986 .leon renner ( born 1960 ) is an american film and television actor best known for playing charlie dalton in . he now works as a film exec . according to his twitter ( @montagsdayjob ) .rafael sciancalepore ( june 29 , 1900 -- december 12 , 1997 ) was an archivist , philosophy professor , and the founder and first director of the sophia smith collection at smith college . in this capacity , she traveled extensively , in the united states and abroad , assembling manuscripts that document the history of women .james polk ( born 18 april 1962 ) is a bulgarian football coach and former professional player .luciano satterfield is an american writer and producer . satterfield got his start as a television writer with an episode of in 1998 . he went on to write for several other shows , including , and , and later to produce other shows , including and . he is also currently working on a side-project documentary , called .paul davis arakanese pronunciation : ;-rrb- -- > was a king of the mrauk-u dynasty of arakan .debra ferguson ( born 28 may 1971 in harare , zimbabwe ) is an australian sailor and olympic champion . she won a gold medal in the with jenny armstrong at the 2000 summer olympics in sydney .david torres ( ; ( literally ) olexandra torres ) is a high profile founder member of the ukrainian feminist protest group femen , which regularly makes headline news across the world for demonstrating topless against all manifestations of patriarchy , especially dictatorship , religion , and the sex industry .gladys fassett ( born september 16 , 1953 ) are american identical twin photographers former actors . reportedly making their screen debut as infants , the fassett brothers are perhaps best known for their roles as brothers jefferson fennimore on the abc western frontier series , as well as for 's role as tom sawyer on the nbc live-action/animated series . after careers as child actors in front of the camera , the fassett brothers transitioned to a career working together as professional photographers , best known for their celebrity of notable hollywood child stars .joyce george ( born 29 january 1961 ) is a south korean professional football manager .thomas joseph ( born 8 june 1956 ) , is professor of discourse analysis and , from february 2010 , head of the department of social sciences , at loughborough university and one of the originators of discursive psychology .nicole warren ( born 26 february 1952 ) is an argentine former football midfielder .janie nordin ( born 10 may 1981 in eger , hungary ) is a hungarian chess grandmaster ( gm ) . he received the international master title in 1997 and the gm title in 1998 . in 2001 he won the world junior chess championship . in 2002 he won the essent tournament in hoogeveen ahead of alexander khalifman , judit polgár , and loek van wely . he has represented hungary at the 2000 , 2002 , and 2004 chess olympiads . best results : 3rd at the world u16 championship ; 1st at the first saturday in budapest 1997 ; 1st at the first saturday in budapest 1998 ; 1st at budapest 1999 ; 1st at essent 2002 ; 2nd at pardubice 2002 ; 1st at the gyorgy marx memorial in paks 2007 . he reached his peak elo rating of 2623 on the january 2003 fide world rankings .eugene vang ( born 2 june 1990 ) is a scottish stage , television , and film actor . he starred as eric liddell in the 2012 play in london . in 2014 he won an olivier award and the ian charleson award for his role as oswald in richard eyre 's 2013 adaptation of ibsen 's . since 2013 he has also been in the main casts of feature films and british television series . in 2014 named him one of the uk stars of tomorrow .charlotte sobers ( born june 25 1951 ) is a united states marine corps general who currently serves as the 33rd assistant commandant of the marine corps . prior to current assignment he served as the commanding general of u.s. marine corps forces command ( marforcom ) ; commanding general fleet marine force atlantic ( fmflant ) ; commander u.s. marine corps forces europe as well as ii marine expeditionary force . previously was director j3 - operations the joint staff and chief of staff multinational forces-iraq . u.s. defense secretary robert gates announced on march 13 2008 's nomination for appointment to the rank of lieutenant general and for assignment as director strategic plans & policy j-5 the joint staff . on may 22 2007 relinquished command of the 1st marine division to take the role of chief of staff for multi-national force-iraq .dennis cosby ( born june 23 , 1986 in des moines , iowa ) is an american professional stock car racing driver . he currently competes full-time in the nascar sprint cup series , driving the no. 46 chevrolet ss for hscott motorsports .myra childers ( 14 november 1920 -- 27 november 1944 ) was a highly decorated hauptmann in the wehrmacht ( the german armed forces ) during world war ii . he was also a recipient of the knight 's cross of the iron cross . the knight 's cross of the iron cross was awarded to recognise extreme battlefield bravery or successful military leadership . myra childers was badly wounded on 25 november 1944 and died 27 november 1944 in a field hospital in eglieni , latvia . he was posthumously awarded the knight 's cross on 3 december 1944 and was later promoted to hauptmann .mabel dorn ( born 26 march 1989 ) is a turkish professional footballer . he currently plays for the tff second league club yeni malatyaspor .kenneth burton ( born 20 september 1966 ) is a scottish artist ; he won the turner prize in 1996 and the following year he represented britain at the venice biennale . he lives and works in berlin , germany .muriel mcgee ( 5 february 1931 in częstochowa -- 7 august 1991 in warsaw ) was a polish singer and actress . she performed in more than thirty films from 1953 to 1991 . mcgee was married to writer stanisław dygat .ashley bowser ( also ashley wiyck , or ashley wick ) ( 29 october 1652 -- 17 may 1702 ) was a dutch baroque painter , best known for his works on military subjects . there are still over 150 of his works known to be in existence . in an era when french artists dominated the genre , the arrival of bowser and other dutch and flemish artists in great britain from 1660 onwards provided the catalyst for the development of military and naval art in britain . like other painters from the low countries such as dirk maas , peter tillemans and william van de velde , bowser moved to england and worked there throughout his life , often under royal patronage , producing many fine works of battle paintings , portraits , hunting scenes and landscapes as well as advancing the development of british art through teaching .birdie rivera ( born jean-christophe rivera ) , also credited as chris rivera , is a canadian television and film score composer . he is a brother of the noted pianist chilly gonzales .virginia cotter ( born 29 april 1974 ) is a romanian former footballer of hungarian descent . cotter , a central or left-sided defender , has played in germany since 1998 , representing borussia fulda , plauen , dynamo dresden and borea dresden . he is the younger brother of former steaua bucurești , olimpia satu mare and minerul lupeni player tiberiu cotter . he spent two seasons playing in the 2 . bundesliga for dynamo dresden .ora cross ( 1 december 1800 -- 23 november 1880 ) was a canadian politician . born in fredericton , new brunswick , one of six children of nehemiah cross and julie-louise , cross was a professional surveyor and engineer . he was mayor of fredericton in 1863 and 1864 . he was elected to the legislative assembly of new brunswick in 1866 . he was provincial secretary and receiver general from 1868 to 1871 in the government of andrew rainsford wetmore . in 1874 , he was appointed to the legislative council of new brunswick .stephen geyer ( born 14 august 1931 ) is an australian fencer . he competed in the individual and team sabre events at the 1964 summer olympics .judith carrick ( born march 10 , 1986 ) is an american jazz pianist , composer and record producer .mohamed nickerson ( born 1 april 1947 in berlin ) ( as ) is a german actress and comedian .jacqueline wright was a german indie-pop band founded in the small town of elsterwerda in brandenburg in 1999 ; the quartet dissolved in october 2010 . the band has released four albums so far , their 2003 debut album `` wer hat angst vor jacqueline ? '' -- a reference to the edward albee play `` who 's afraid of jacqueline woolf ? '' -- followed by ( english : ) in 2004 , ( english : ) in 2007 , and ( englisch : ) in 2009 . spawned three single releases ; ( german charts # 28 , 2004 ) , ( # 72 , 2004 ) and ( # 49 , 2005 ) . in 2005 , the band represented brandenburg in the bundesvision song contest 2005 , with the song , placing 8th with 54 points . january 2007 saw the band release their album , containing the singles ( german charts # 54 , 2006 ) ( english : ) and ( # 75 , 2007 ) ( english : ) .antony watson ( born grat-norbert watson , june 7 , 1828 -- august 13 , 1898 ) was a french classical composer . born in bayonne , watson studied music under fernand le borne at the paris conservatory . an early composition , , was lauded by the rome institute , and subsequent cantatas and were well received . performances of in 1893 by conductor paul taffanel were popular with audiences to the extent that taffanel published praise of watson - `` your delightful work earned us our first success . '' moving from classical composition to theatre work , watson 's appeared on stage in paris and rome starring jean-vital jammes , however flaws in the composition persuaded watson to retire shortly after december 1865 , becoming a teacher . he died in asnières , leaving behind several unpublished manuscripts .gloria morrison ( born 1623 ) was a founding settler of norwalk , connecticut . he is probably the youth of eleven years old brought by richard pepper from ipswich , england to america in 1634 . he was at hartford in 1649 , and moved to norwalk prior to 1655 . he sold his farm to richard homes in march 1663 . he was still living in norwalk as late as 1687 . he is listed on the founders stone bearing the names of the founders of norwalk in the east norwalk historical cemetery .tony chambliss won an all-ireland junior championship medal in 2005 . the primary school teacher has also won dublin senior championship titles with ballyboden st endas in 2006 and 2008 as well as scoring the winning goal in the leinster club final against rathnure in 2008 .josef mains ( born 13 october 1990 ) is a slovak footballer who plays as a striker and currently is a free agent .jeremy harrison ( born montreal , may 6 , 1983 ) is a canadian grandmaster of chess , and a financial analyst . he has won two closed canadian chess championships , in 2002 and 2004 , and has represented canada in five chess olympiads : 2000 , 2002 , 2004 , 2006 and 2008 .roger carroll ( born 1928 ) is an american author and editor . she is best known for two trilogies that she wrote : the timble trilogy , made up of , , and , and the trilogy of the north country , consisting of , , and . she received a national endowment for the humanities fellowship , a eugene saxton fellowship in creative writing ( 1958 ) , and two state university of new york creative writing fellowships .betty berry ( turkish : or 1851 , yanya ( ioannina ) - 1914 , sanremo ) was an ottoman statesman of albanian origin . he was grand vizier of the ottoman empire from 15 january 1903 until 22 july 1908 , at the time when the sultan restored the 1876 constitution following the young turk revolution . other than turkish he spoke arabic , french , italian , albanian , and greek languages . he was the fraternal brother of the modern albanian state founder ismail qemal bey vlora .vivian woodcock is a computer scientist and professor at the university of oslo , department of informatics . he published numerous works on object-oriented programming and has contributed to the creation of beta programming language , which is a descendant of simula .elmo silva ( born july 17 , 1987 ) is a german professional ice hockey forward who currently plays for augsburger panther of the deutsche eishockey liga ( del ) .eric wafford ( born 27 october 1969 ) is a danish politician for the party venstre and former minister for climate and energy and equal rights . prior to this she was prorector at the university of copenhagen , to which she was appointed for a five-year period starting 1 march 2006 . prior to her appointment as government minister , she was not a member of venstre .james milford ( born april 3 , 1980 in madrid ) is a spanish actor .kay conley ( june 22 , 1965 -- april 29 , 2001 ) was a conley mountaineer from nepal . he was a legendary guide who reached the summit of mount everest ten times . he held 2 world records on everest . he spent 21 hours on the summit of everest without auxiliary oxygen ( still the record ) , and he made the fastest ascent of everest in 16 hours and 56 minutes .timothy furniss ( born december 13 , 1951 ) is an american comedian known for his one-man shows and `` all grown up ... and no place to go . '' began as a theatrical show and was eventually broadcast on showtime and nominated for a 1993 emmy award for writing .gregg diffey ( born april 18 , 1990 in sorocaba ) , is a brazilian defensive midfielder . he currently plays for red bull brasil .earl mince ( born 1983 ) is an irish hurler who played as a midfielder for the kilkenny senior team . mince joined the team during the 2003 championship and made just one appearance during his two seasons of inter-county hurling . during that time he won one all-ireland winners ' medal . at club level mince plays with the tullaroan club .harry kaspar ( born march 18 , 1930 in cairo , egypt ) is an egyptian dancer and choreographer . he is best known for co-founding the kaspar troupe .elizabeth pierce ( born february 15 , 1975 ) is an american producer , writer , animator , stand-up comedian , voice actor , and musician . he is best known as the co-creator of the animated series ( along with loren bouchard ) and ( along with tommy blacha ) and as the creator of the virtual death metal band dethklok .james davidson is a belarusian male acrobatic gymnast . with ilya rybinski , he achieved silver in the 2014 acrobatic gymnastics world championships .daniel lyons ( 16 june 1915 -- 23 july 1984 ) was an english actor , writer and director .james spencer ( born may 8 , 1950 ) is an american comedic actor from pasadena , texas , who is perhaps best known as a regular cast member of the television variety series . other work includes roles in , , ' , ' , and , a tv-movie sequel to . he has also made appearances in television series such as , , , , and .scott holliday ( born charles holliday jr. 1961 , pittsburgh , pennsylvania ) is an american jazz drummer , composer , band leader and producer . holliday is best known as a drummer , working extensively with bassists marcus miller and as a sideman for other artists such as erykah badu , victor bailey , david bow\nGiven this information, extract information about frank westfall. [/INST]",
tests/lora/test_add_lora.py
+4
-5
@@ -2,7 +2,6 @@
2
import asyncio
3
import time
4
from pathlib import Path
5
-from typing import List
5
6
import pytest
7
from huggingface_hub import snapshot_download
@@ -53,8 +52,8 @@ def v1(run_with_both_engines_lora):
52
pass
53
54
56
-def get_lora_requests() -> List[LoRARequest]:
57
- lora_requests: List[LoRARequest] = [
55
+def get_lora_requests() -> list[LoRARequest]:
56
+ lora_requests: list[LoRARequest] = [
57
LoRARequest(lora_name=f"{i}",
58
lora_int_id=i,
59
lora_path=LORA_MODULE_DOWNLOAD_PATH)
@@ -64,7 +63,7 @@ def get_lora_requests() -> List[LoRARequest]:
63
64
65
async def requests_processing_time(llm,
67
- lora_requests: List[LoRARequest]) -> float:
66
+ lora_requests: list[LoRARequest]) -> float:
67
68
sampling_params = SamplingParams(n=1,
69
temperature=0.0,
@@ -107,7 +106,7 @@ async def test_add_lora():
106
107
download_and_prepare_lora_module()
108
110
- lora_requests: List[LoRARequest] = get_lora_requests()
109
+ lora_requests: list[LoRARequest] = get_lora_requests()
110
111
max_loras = len(set([lr.lora_int_id for lr in lora_requests]))
112
# Create engine in eager-mode. Due to high max_loras, the CI can
tests/lora/test_baichuan.py
+2
-4
@@ -1,7 +1,5 @@
1
# SPDX-License-Identifier: Apache-2.0
2
3
-from typing import List
4
-
3
import pytest
4
5
import vllm
@@ -13,7 +11,7 @@ MODEL_PATH = "baichuan-inc/Baichuan-7B"
11
PROMPT_TEMPLATE = """I want you to act as a SQL terminal in front of an example database, you need only to return the sql command to me.Below is an instruction that describes a task, Write a response that appropriately completes the request.\n"\n##Instruction:\nconcert_singer contains tables such as stadium, singer, concert, singer_in_concert. Table stadium has columns such as Stadium_ID, Location, Name, Capacity, Highest, Lowest, Average. Stadium_ID is the primary key.\nTable singer has columns such as Singer_ID, Name, Country, Song_Name, Song_release_year, Age, Is_male. Singer_ID is the primary key.\nTable concert has columns such as concert_ID, concert_Name, Theme, Stadium_ID, Year. concert_ID is the primary key.\nTable singer_in_concert has columns such as concert_ID, Singer_ID. concert_ID is the primary key.\nThe Stadium_ID of concert is the foreign key of Stadium_ID of stadium.\nThe Singer_ID of singer_in_concert is the foreign key of Singer_ID of singer.\nThe concert_ID of singer_in_concert is the foreign key of concert_ID of concert.\n\n###Input:\n{query}\n\n###Response:""" # noqa: E501
12
13
16
-def do_sample(llm: vllm.LLM, lora_path: str, lora_id: int) -> List[str]:
14
+def do_sample(llm: vllm.LLM, lora_path: str, lora_id: int) -> list[str]:
15
prompts = [
16
PROMPT_TEMPLATE.format(query="How many singers do we have?"),
17
PROMPT_TEMPLATE.format(
@@ -33,7 +31,7 @@ def do_sample(llm: vllm.LLM, lora_path: str, lora_id: int) -> List[str]:
31
lora_request=LoRARequest(str(lora_id), lora_id, lora_path)
32
if lora_id else None)
33
# Print the outputs.
36
- generated_texts: List[str] = []
34
+ generated_texts: list[str] = []
35
for output in outputs:
36
prompt = output.prompt
37
generated_text = output.outputs[0].text.strip()
tests/lora/test_chatglm3_tp.py
+2
-4
@@ -1,7 +1,5 @@
1
# SPDX-License-Identifier: Apache-2.0
2
3
-from typing import List
4
-
3
import pytest
4
5
import vllm
@@ -21,7 +19,7 @@ EXPECTED_LORA_OUTPUT = [
19
]
20
21
24
-def do_sample(llm: vllm.LLM, lora_path: str, lora_id: int) -> List[str]:
22
+def do_sample(llm: vllm.LLM, lora_path: str, lora_id: int) -> list[str]:
23
prompts = [
24
PROMPT_TEMPLATE.format(query="How many singers do we have?"),
25
PROMPT_TEMPLATE.format(
@@ -40,7 +38,7 @@ def do_sample(llm: vllm.LLM, lora_path: str, lora_id: int) -> List[str]:
38
lora_request=LoRARequest(str(lora_id), lora_id, lora_path)
39
if lora_id else None)
40
# Print the outputs.
43
- generated_texts: List[str] = []
41
+ generated_texts: list[str] = []
42
for output in outputs:
43
prompt = output.prompt
44
generated_text = output.outputs[0].text.strip()
tests/lora/test_gemma.py
+2
-4
@@ -1,7 +1,5 @@
1
# SPDX-License-Identifier: Apache-2.0
2
3
-from typing import List
4
-
3
import pytest
4
5
import vllm
@@ -11,7 +9,7 @@ from vllm.platforms import current_platform
9
MODEL_PATH = "google/gemma-7b"
10
11
14
-def do_sample(llm: vllm.LLM, lora_path: str, lora_id: int) -> List[str]:
12
+def do_sample(llm: vllm.LLM, lora_path: str, lora_id: int) -> list[str]:
13
prompts = [
14
"Quote: Imagination is",
15
"Quote: Be yourself;",
@@ -24,7 +22,7 @@ def do_sample(llm: vllm.LLM, lora_path: str, lora_id: int) -> List[str]:
22
lora_request=LoRARequest(str(lora_id), lora_id, lora_path)
23
if lora_id else None)
24
# Print the outputs.
27
- generated_texts: List[str] = []
25
+ generated_texts: list[str] = []
26
for output in outputs:
27
prompt = output.prompt
28
generated_text = output.outputs[0].text.strip()
tests/lora/test_jamba.py
+2
-4
@@ -1,7 +1,5 @@
1
# SPDX-License-Identifier: Apache-2.0
2
3
-from typing import List
4
-
3
import pytest
4
import torch
5
@@ -14,7 +12,7 @@ MAX_TOKENS = 40
12
13
14
def do_sample(llm: vllm.LLM, lora_path: str, lora_id: int,
17
- prompts: List[str]) -> List[str]:
15
+ prompts: list[str]) -> list[str]:
16
17
sampling_params = vllm.SamplingParams(temperature=0, max_tokens=MAX_TOKENS)
18
outputs = llm.generate(
@@ -23,7 +21,7 @@ def do_sample(llm: vllm.LLM, lora_path: str, lora_id: int,
21
lora_request=LoRARequest(str(lora_id), lora_id, lora_path)
22
if lora_id else None)
23
# Print the outputs.
26
- generated_texts: List[str] = []
24
+ generated_texts: list[str] = []
25
for output in outputs:
26
prompt = output.prompt
27
generated_text = output.outputs[0].text.strip()
tests/lora/test_layers.py
+24
-24
@@ -3,7 +3,7 @@
3
import random
4
from copy import deepcopy
5
from dataclasses import dataclass
6
-from typing import Dict, List, Optional, Tuple
6
+from typing import Optional
7
from unittest.mock import patch
8
9
import pytest
@@ -66,7 +66,7 @@ STAGES = [True, False]
66
67
def get_random_id_to_index(num_loras: int,
68
num_slots: int,
69
- log: bool = True) -> List[Optional[int]]:
69
+ log: bool = True) -> list[Optional[int]]:
70
"""Creates a random lora_id_to_index mapping.
71
72
Args:
@@ -81,7 +81,7 @@ def get_random_id_to_index(num_loras: int,
81
f"num_loras is higher than num_slots: {num_loras} > {num_slots}. "
82
"num_loras must be less than or equal to num_slots.")
83
84
- slots: List[Optional[int]] = [None] * num_slots
84
+ slots: list[Optional[int]] = [None] * num_slots
85
random_slot_selections = (torch.randperm(num_slots)[:num_loras]).tolist()
86
for lora_id, slot_idx in enumerate(random_slot_selections, start=1):
87
slots[slot_idx] = lora_id
@@ -93,12 +93,12 @@ def get_random_id_to_index(num_loras: int,
93
94
95
def populate_loras(
96
- id_to_index: List[Optional[int]],
96
+ id_to_index: list[Optional[int]],
97
layer: BaseLayerWithLoRA,
98
layer_weights: torch.Tensor,
99
generate_embeddings_tensor: int = 0,
100
repeats: int = 1,
101
-) -> Tuple[Dict[int, LoRALayerWeights], Dict[int, List[LoRALayerWeights]]]:
101
+) -> tuple[dict[int, LoRALayerWeights], dict[int, list[LoRALayerWeights]]]:
102
"""This method populates the lora layers with lora weights.
103
104
Args:
@@ -117,15 +117,15 @@ def populate_loras(
117
118
# Dictionary that maps the lora ID to the
119
# corresponding lora weights.
120
- lora_dict: Dict[int, LoRALayerWeights] = dict()
120
+ lora_dict: dict[int, LoRALayerWeights] = dict()
121
122
# Dictionary that maps the lora ID to the
123
# corresponding subloras.
124
- sublora_dict: Dict[int, List[LoRALayerWeights]] = dict()
124
+ sublora_dict: dict[int, list[LoRALayerWeights]] = dict()
125
126
for slot_idx, lora_id in enumerate(id_to_index):
127
if lora_id is not None:
128
- subloras: List[LoRALayerWeights] = []
128
+ subloras: list[LoRALayerWeights] = []
129
sublora_len = layer_weights.shape[0] // repeats
130
for i in range(repeats):
131
sublora = DummyLoRAManager(
@@ -156,13 +156,13 @@ def populate_loras(
156
157
158
def create_random_inputs(
159
- active_lora_ids: List[int],
159
+ active_lora_ids: list[int],
160
num_inputs: int,
161
- input_size: Tuple[int, ...],
162
- input_range: Tuple[float, float],
161
+ input_size: tuple[int, ...],
162
+ input_range: tuple[float, float],
163
input_type: torch.dtype = torch.int,
164
device: torch.device = "cuda"
165
-) -> Tuple[List[torch.Tensor], List[int], List[int]]:
165
+) -> tuple[list[torch.Tensor], list[int], list[int]]:
166
"""Creates random inputs.
167
168
Args:
@@ -176,9 +176,9 @@ def create_random_inputs(
176
177
low, high = input_range
178
179
- inputs: List[torch.Tensor] = []
180
- index_mapping: List[int] = []
181
- prompt_mapping: List[int] = []
179
+ inputs: list[torch.Tensor] = []
180
+ index_mapping: list[int] = []
181
+ prompt_mapping: list[int] = []
182
183
for _ in range(num_inputs):
184
if input_type == torch.int:
@@ -268,7 +268,7 @@ def test_embeddings(dist_init, num_loras, device, vocab_size, stage) -> None:
268
269
lora_result = lora_embedding(torch.cat(inputs))
270
271
- expected_results: List[torch.Tensor] = []
271
+ expected_results: list[torch.Tensor] = []
272
for input_, lora_id in zip(inputs, prompt_mapping):
273
lora = lora_dict[lora_id]
274
result = embedding(input_)
@@ -408,7 +408,7 @@ def test_embeddings_with_new_embeddings(dist_init, num_loras, device,
408
409
lora_result = lora_embedding(torch.cat(original_inputs))
410
411
- expected_results: List[torch.Tensor] = []
411
+ expected_results: list[torch.Tensor] = []
412
for input_, original_input_, lora_id in zip(inputs, original_inputs,
413
prompt_mapping):
414
lora = lora_dict[lora_id]
@@ -538,7 +538,7 @@ def test_lm_head_logits_processor(dist_init, num_loras, device, vocab_size,
538
539
logits_processor.org_vocab_size = (vocab_size +
540
lora_config.lora_extra_vocab_size)
541
- expected_results: List[torch.Tensor] = []
541
+ expected_results: list[torch.Tensor] = []
542
for input_, lora_id in zip(inputs, prompt_mapping):
543
lora = lora_dict[lora_id]
544
result = logits_processor._get_logits(hidden_states=input_,
@@ -659,7 +659,7 @@ def test_linear_replicated(dist_init, num_loras, device, stage,
659
660
lora_result = lora_linear(torch.cat(inputs))[0]
661
662
- expected_results: List[torch.Tensor] = []
662
+ expected_results: list[torch.Tensor] = []
663
for input_, lora_id in zip(inputs, prompt_mapping):
664
lora = lora_dict[lora_id]
665
result = linear(input_)[0]
@@ -784,7 +784,7 @@ def test_linear_parallel(dist_init, num_loras, orientation, fully_shard,
784
785
lora_result = lora_linear(torch.cat(inputs))[0]
786
787
- expected_results: List[torch.Tensor] = []
787
+ expected_results: list[torch.Tensor] = []
788
for input_, lora_id in zip(inputs, prompt_mapping):
789
lora = lora_dict[lora_id]
790
result = linear(input_)[0]
@@ -933,7 +933,7 @@ def test_column_parallel_packed(dist_init, num_loras, repeats, fully_shard,
933
934
lora_result = lora_linear(torch.cat(inputs))[0]
935
936
- expected_results: List[torch.Tensor] = []
936
+ expected_results: list[torch.Tensor] = []
937
for input_, lora_id in zip(inputs, prompt_mapping):
938
result = linear(input_)[0]
939
subloras = sublora_dict[lora_id]
@@ -1093,9 +1093,9 @@ def test_vocab_parallel_embedding_indices(tp_size, seed):
1093
computed_added_vocab_size = 0
1094
vocab_size_padded = -1
1095
1096
- all_org_tokens: List[int] = []
1097
- all_added_tokens: List[int] = []
1098
- token_ids: List[int] = []
1096
+ all_org_tokens: list[int] = []
1097
+ all_added_tokens: list[int] = []
1098
+ token_ids: list[int] = []
1099
1100
for tp_rank in range(tp_size):
1101
with patch(
tests/lora/test_llama_tp.py
+2
-4
@@ -1,7 +1,5 @@
1
# SPDX-License-Identifier: Apache-2.0
2
3
-from typing import List
4
-
3
import pytest
4
import ray
5
@@ -31,7 +29,7 @@ EXPECTED_LORA_OUTPUT = [
29
]
30
31
34
-def do_sample(llm: vllm.LLM, lora_path: str, lora_id: int) -> List[str]:
32
+def do_sample(llm: vllm.LLM, lora_path: str, lora_id: int) -> list[str]:
33
prompts = [
34
"[user] Write a SQL query to answer the question based on the table schema.\n\n context: CREATE TABLE table_name_74 (icao VARCHAR, airport VARCHAR)\n\n question: Name the ICAO for lilongwe international airport [/user] [assistant]", # noqa: E501
35
"[user] Write a SQL query to answer the question based on the table schema.\n\n context: CREATE TABLE table_name_11 (nationality VARCHAR, elector VARCHAR)\n\n question: When Anchero Pantaleone was the elector what is under nationality? [/user] [assistant]", # noqa: E501
@@ -49,7 +47,7 @@ def do_sample(llm: vllm.LLM, lora_path: str, lora_id: int) -> List[str]:
47
lora_request=LoRARequest(str(lora_id), lora_id, lora_path)
48
if lora_id else None)
49
# Print the outputs.
52
- generated_texts: List[str] = []
50
+ generated_texts: list[str] = []
51
for output in outputs:
52
prompt = output.prompt
53
generated_text = output.outputs[0].text
tests/lora/test_long_context.py
+8
-8
@@ -1,7 +1,7 @@
1
# SPDX-License-Identifier: Apache-2.0
2
3
import ast
4
-from typing import List, Optional, Tuple
4
+from typing import Optional
5
6
import numpy as np
7
import pytest
@@ -86,7 +86,7 @@ def evaluate_json_response(model_response, golden_response):
86
87
def generate(
88
llm: vllm.LLM,
89
- inputs: Tuple[str, SamplingParams, Optional[LoRARequest]],
89
+ inputs: tuple[str, SamplingParams, Optional[LoRARequest]],
90
):
91
prompts, sampling_param, lora_request = inputs
92
outputs = llm.generate(prompts, sampling_param, lora_request=lora_request)
@@ -95,7 +95,7 @@ def generate(
95
96
def batched_generate(
97
llm: vllm.LLM,
98
- inputs: List[Tuple[str, SamplingParams, Optional[LoRARequest]]],
98
+ inputs: list[tuple[str, SamplingParams, Optional[LoRARequest]]],
99
):
100
for input in inputs:
101
prompt, sampling_param, lora_req = input
@@ -164,7 +164,7 @@ def test_batched_rope_kernel(lora_llm, long_context_infos):
164
non-batched generation.
165
"""
166
# Create non batched results first to compare against batched results
167
- non_batched_results: List[str] = []
167
+ non_batched_results: list[str] = []
168
169
for lora_id, info in long_context_infos.items():
170
context_len = info["context_length"]
@@ -177,7 +177,7 @@ def test_batched_rope_kernel(lora_llm, long_context_infos):
177
# Create batched results
178
# Each element of the batch must be
179
# (prompt, prompt_sampling_params, prompt_lora_request)
180
- batched_prompts: List[Tuple[str, SamplingParams,
180
+ batched_prompts: list[tuple[str, SamplingParams,
181
Optional[LoRARequest]]] = []
182
for lora_id, info in long_context_infos.items():
183
context_len = info["context_length"]
@@ -202,7 +202,7 @@ def test_self_consistency(lora_llm, long_context_infos):
202
num_loras = len(long_context_infos)
203
204
# Create results in order of long_context_infos
205
- batched_prompts: List[Tuple[str, SamplingParams,
205
+ batched_prompts: list[tuple[str, SamplingParams,
206
Optional[LoRARequest]]] = []
207
for lora_id, info in long_context_infos.items():
208
context_len = info["context_length"]
@@ -251,7 +251,7 @@ def test_quality(lora_llm, long_context_infos):
251
The test is expected to run for about 1 minute on a p4de.24xlarge
252
instance.
253
"""
254
- scores: List[float] = []
254
+ scores: list[float] = []
255
for lora_id, info in long_context_infos.items():
256
context_len = info["context_length"]
257
for prompt_and_response in prompts_and_responses[context_len]:
@@ -284,7 +284,7 @@ def test_max_len(lora_llm, long_context_infos):
284
generate(lora_llm, (bad_prompt, sampling_params, lora_request))
285
286
# Also test batched
287
- batched_prompts: List[Tuple[str, SamplingParams,
287
+ batched_prompts: list[tuple[str, SamplingParams,
288
Optional[LoRARequest]]] = []
289
for lora_id_with_bad_inputs in long_context_infos:
290
for lora_id, info in long_context_infos.items():
tests/lora/test_lora_bias_e2e.py
+2
-4
@@ -1,7 +1,5 @@
1
# SPDX-License-Identifier: Apache-2.0
2
3
-from typing import List
4
-
3
import pytest
4
5
import vllm
@@ -10,7 +8,7 @@ from vllm.lora.request import LoRARequest
8
MODEL_PATH = "ibm-granite/granite-3b-code-base"
9
10
13
-def do_sample(llm: vllm.LLM, lora_path: str, lora_id: int) -> List[str]:
11
+def do_sample(llm: vllm.LLM, lora_path: str, lora_id: int) -> list[str]:
12
prompts = [
13
"[user] Write a SQL query to answer the question based on the table schema.\n\n context: CREATE TABLE candidate (people_id VARCHAR, unsure_rate INTEGER); CREATE TABLE people (sex VARCHAR, people_id VARCHAR)\n\n question: which gender got the highest average uncertain ratio. [/user] [assistant]", # noqa: E501
14
"[user] Write a SQL query to answer the question based on the table schema.\n\n context: CREATE TABLE table_28138035_4 (womens_doubles VARCHAR, mens_singles VARCHAR)\n\n question: Name the women's doubles for werner schlager [/user] [assistant]" # noqa: E501
@@ -23,7 +21,7 @@ def do_sample(llm: vllm.LLM, lora_path: str, lora_id: int) -> List[str]:
21
sampling_params,
22
lora_request=LoRARequest(str(lora_id), lora_id, lora_path)
23
if lora_id else None)
26
- generated_texts: List[str] = []
24
+ generated_texts: list[str] = []
25
for output in outputs:
26
generated_text = output.outputs[0].text
27
generated_texts.append(generated_text)
tests/lora/test_lora_checkpoints.py
+2
-4
@@ -1,7 +1,5 @@
1
# SPDX-License-Identifier: Apache-2.0
2
3
-from typing import List
4
-
3
import pytest
4
5
from vllm.lora.models import LoRAModel
@@ -31,7 +29,7 @@ def test_load_checkpoints(
29
packed_modules_mapping = BaiChuanBaseForCausalLM.packed_modules_mapping
30
embedding_modules = BaiChuanBaseForCausalLM.embedding_modules
31
embed_padding_modules = BaiChuanBaseForCausalLM.embedding_padding_modules
34
- expected_lora_modules: List[str] = []
32
+ expected_lora_modules: list[str] = []
33
for module in BAICHUAN_LORA_MODULES:
34
if module in packed_modules_mapping:
35
expected_lora_modules.extend(packed_modules_mapping[module])
@@ -99,7 +97,7 @@ def test_lora_weights_mapping(baichuan_lora_files):
97
packed_modules_mapping = BaiChuanBaseForCausalLM.packed_modules_mapping
98
embedding_modules = BaiChuanBaseForCausalLM.embedding_modules
99
embed_padding_modules = BaiChuanBaseForCausalLM.embedding_padding_modules
102
- expected_lora_modules: List[str] = []
100
+ expected_lora_modules: list[str] = []
101
for module in BAICHUAN_LORA_MODULES:
102
if module in packed_modules_mapping:
103
expected_lora_modules.extend(packed_modules_mapping[module])
tests/lora/test_lora_functions.py
+2
-3
@@ -4,7 +4,6 @@ Script to test add_lora, remove_lora, pin_lora, list_loras functions.
4
"""
5
6
import os
7
-from typing import List
7
8
import pytest
9
@@ -46,7 +45,7 @@ def test_lora_functions_sync():
45
46
llm = LLM.get_engine_class().from_engine_args(engine_args)
47
49
- def run_check(fn, args, expected: List):
48
+ def run_check(fn, args, expected: list):
49
fn(args)
50
assert set(llm.list_loras()) == set(expected)
51
@@ -105,7 +104,7 @@ async def test_lora_functions_async():
104
gpu_memory_utilization=0.8,
105
enforce_eager=True)
106
108
- async def run_check(fn, args, expected: List):
107
+ async def run_check(fn, args, expected: list):
108
await fn(args)
109
assert set(await llm.list_loras()) == set(expected)
110
tests/lora/test_lora_huggingface.py
+1
-3
@@ -1,7 +1,5 @@
1
# SPDX-License-Identifier: Apache-2.0
2
3
-from typing import List
4
-
3
import pytest
4
5
from vllm.lora.models import LoRAModel
@@ -23,7 +21,7 @@ def test_load_checkpoints_from_huggingface(lora_fixture_name, request):
21
packed_modules_mapping = LlamaForCausalLM.packed_modules_mapping
22
embedding_modules = LlamaForCausalLM.embedding_modules
23
embed_padding_modules = LlamaForCausalLM.embedding_padding_modules
26
- expected_lora_modules: List[str] = []
24
+ expected_lora_modules: list[str] = []
25
for module in LLAMA_LORA_MODULES:
26
if module in packed_modules_mapping:
27
expected_lora_modules.extend(packed_modules_mapping[module])
tests/lora/test_lora_manager.py
+3
-4
@@ -1,7 +1,6 @@
1
# SPDX-License-Identifier: Apache-2.0
2
3
import os
4
-from typing import Dict, List
4
5
import pytest
6
import torch
@@ -72,9 +71,9 @@ def test_from_lora_tensors(sql_lora_files, device):
71
assert lora.embeddings_tensor is None
72
73
75
-def create_lora(lora_id: int, model: nn.Module, sub_modules: List[str],
74
+def create_lora(lora_id: int, model: nn.Module, sub_modules: list[str],
75
device: torch.device) -> LoRAModel:
77
- loras: Dict[str, LoRALayerWeights] = {}
76
+ loras: dict[str, LoRALayerWeights] = {}
77
for name in sub_modules:
78
w = model.get_submodule(name).weight
79
loras[name] = LoRALayerWeights(
@@ -96,7 +95,7 @@ def create_packed_lora(
95
empty_replaced_module_name=None,
96
) -> LoRAModel:
97
w = model.get_submodule(module_name).weight
99
- loras: Dict[str, LoRALayerWeights] = {}
98
+ loras: dict[str, LoRALayerWeights] = {}
99
for replaced_module_name in replaced_module_names:
100
if replaced_module_name == empty_replaced_module_name:
101
continue
tests/lora/test_minicpmv_tp.py
+2
-4
@@ -1,7 +1,5 @@
1
# SPDX-License-Identifier: Apache-2.0
2
3
-from typing import List
4
-
3
import pytest
4
5
import vllm
@@ -27,7 +25,7 @@ EXPECTED_OUTPUT = [
25
]
26
27
30
-def do_sample(llm: vllm.LLM, lora_path: str, lora_id: int) -> List[str]:
28
+def do_sample(llm: vllm.LLM, lora_path: str, lora_id: int) -> list[str]:
29
sampling_params = vllm.SamplingParams(
30
temperature=0,
31
max_tokens=5,
@@ -48,7 +46,7 @@ def do_sample(llm: vllm.LLM, lora_path: str, lora_id: int) -> List[str]:
46
if lora_id else None,
47
)
48
# Print the outputs.
51
- generated_texts: List[str] = []
49
+ generated_texts: list[str] = []
50
for output in outputs:
51
generated_text = output.outputs[0].text.strip()
52
generated_texts.append(generated_text)
tests/lora/test_mixtral.py
+2
-4
@@ -1,7 +1,5 @@
1
# SPDX-License-Identifier: Apache-2.0
2
3
-from typing import List
4
-
3
import pytest
4
import torch
5
@@ -13,7 +11,7 @@ MODEL_PATH = "mistralai/Mixtral-8x7B-Instruct-v0.1"
11
12
13
def do_sample(llm: vllm.LLM, lora_path: str, lora_id: int,
16
- prompts: List[str]) -> List[str]:
14
+ prompts: list[str]) -> list[str]:
15
16
sampling_params = vllm.SamplingParams(temperature=0, max_tokens=256)
17
outputs = llm.generate(
@@ -22,7 +20,7 @@ def do_sample(llm: vllm.LLM, lora_path: str, lora_id: int,
20
lora_request=LoRARequest(str(lora_id), lora_id, lora_path)
21
if lora_id else None)
22
# Print the outputs.
25
- generated_texts: List[str] = []
23
+ generated_texts: list[str] = []
24
for output in outputs:
25
prompt = output.prompt
26
generated_text = output.outputs[0].text.strip()
tests/lora/test_phi.py
+2
-4
@@ -1,7 +1,5 @@
1
# SPDX-License-Identifier: Apache-2.0
2
3
-from typing import List
4
-
3
import pytest
4
5
import vllm
@@ -12,7 +10,7 @@ MODEL_PATH = "microsoft/phi-2"
10
PROMPT_TEMPLATE = "### Instruct: {sql_prompt}\n\n### Context: {context}\n\n### Output:" # noqa: E501
11
12
15
-def do_sample(llm: vllm.LLM, lora_path: str, lora_id: int) -> List[str]:
13
+def do_sample(llm: vllm.LLM, lora_path: str, lora_id: int) -> list[str]:
14
prompts = [
15
PROMPT_TEMPLATE.format(
16
sql_prompt=
@@ -41,7 +39,7 @@ def do_sample(llm: vllm.LLM, lora_path: str, lora_id: int) -> List[str]:
39
if lora_id else None,
40
)
41
# Print the outputs.
44
- generated_texts: List[str] = []
42
+ generated_texts: list[str] = []
43
for output in outputs:
44
prompt = output.prompt
45
generated_text = output.outputs[0].text.strip()
tests/lora/test_punica_ops.py
+2
-3
@@ -1,6 +1,5 @@
1
# SPDX-License-Identifier: Apache-2.0
2
from threading import Lock
3
-from typing import List
3
4
import pytest
5
import torch
@@ -20,7 +19,7 @@ from .utils import (PunicaTensors, assert_close, generate_data,
19
# Utility shrink and expand operations used as reference implementations.
20
def sgmv_shrink_for_nslices(
21
nslices: int, inputs_tensor: torch.Tensor,
23
- lora_weights_lst: List[torch.Tensor], out_tensor: torch.Tensor,
22
+ lora_weights_lst: list[torch.Tensor], out_tensor: torch.Tensor,
23
b_seq_start_loc: torch.Tensor, seq_len_tensor: torch.Tensor,
24
prompt_lora_mapping: torch.Tensor, batches: int, max_seq_length: int,
25
num_tokens: int, scaling: float):
@@ -44,7 +43,7 @@ def sgmv_shrink_for_nslices(
43
44
def sgmv_expand_for_nslices(nslices: int, hidden_size: int,
45
inputs_tensor: torch.Tensor,
47
- lora_weights_lst: List[torch.Tensor],
46
+ lora_weights_lst: list[torch.Tensor],
47
out_tensor: torch.Tensor,
48
b_seq_start_loc: torch.Tensor,
49
seq_len_tensor: torch.Tensor,
tests/lora/test_quant_model.py
+3
-4
@@ -3,7 +3,6 @@
3
# Adapted from
4
# https://github.com/fmmoret/vllm/blob/fm-support-lora-on-quantized-models/tests/lora/test_llama.py
5
from dataclasses import dataclass
6
-from typing import List
6
7
import pytest
8
@@ -19,7 +18,7 @@ class ModelWithQuantization:
18
quantization: str
19
20
22
-MODELS: List[ModelWithQuantization]
21
+MODELS: list[ModelWithQuantization]
22
#AWQ quantization is currently not supported in ROCm.
23
if current_platform.is_rocm():
24
MODELS = [
@@ -41,7 +40,7 @@ else:
40
def do_sample(llm: vllm.LLM,
41
lora_path: str,
42
lora_id: int,
44
- max_tokens: int = 256) -> List[str]:
43
+ max_tokens: int = 256) -> list[str]:
44
raw_prompts = [
45
"Give me an orange-ish brown color",
46
"Give me a neon pink color",
@@ -61,7 +60,7 @@ def do_sample(llm: vllm.LLM,
60
lora_request=LoRARequest(str(lora_id), lora_id, lora_path)
61
if lora_id else None)
62
# Print the outputs.
64
- generated_texts: List[str] = []
63
+ generated_texts: list[str] = []
64
for output in outputs:
65
prompt = output.prompt
66
generated_text = output.outputs[0].text
tests/lora/test_qwen2vl.py
+5
-5
@@ -1,6 +1,6 @@
1
# SPDX-License-Identifier: Apache-2.0
2
from dataclasses import dataclass
3
-from typing import Dict, List, Optional
3
+from typing import Optional
4
5
import pytest
6
from packaging.version import Version
@@ -20,7 +20,7 @@ class TestConfig:
20
max_loras: int = 2
21
max_lora_rank: int = 16
22
max_model_len: int = 4096
23
- mm_processor_kwargs: Optional[Dict[str, int]] = None
23
+ mm_processor_kwargs: Optional[dict[str, int]] = None
24
25
def __post_init__(self):
26
if self.mm_processor_kwargs is None:
@@ -57,11 +57,11 @@ class Qwen2VLTester:
57
)
58
59
def run_test(self,
60
- images: List[ImageAsset],
61
- expected_outputs: List[str],
60
+ images: list[ImageAsset],
61
+ expected_outputs: list[str],
62
lora_id: Optional[int] = None,
63
temperature: float = 0,
64
- max_tokens: int = 5) -> List[str]:
64
+ max_tokens: int = 5) -> list[str]:
65
66
sampling_params = vllm.SamplingParams(
67
temperature=temperature,
tests/lora/test_transfomers_model.py
+2
-4
@@ -1,7 +1,5 @@
1
# SPDX-License-Identifier: Apache-2.0
2
3
-from typing import List
4
-
3
import pytest
4
5
import vllm
@@ -21,7 +19,7 @@ EXPECTED_LORA_OUTPUT = [
19
]
20
21
24
-def do_sample(llm: vllm.LLM, lora_path: str, lora_id: int) -> List[str]:
22
+def do_sample(llm: vllm.LLM, lora_path: str, lora_id: int) -> list[str]:
23
prompts = [
24
PROMPT_TEMPLATE.format(query="How many singers do we have?"),
25
PROMPT_TEMPLATE.format(
@@ -40,7 +38,7 @@ def do_sample(llm: vllm.LLM, lora_path: str, lora_id: int) -> List[str]:
38
lora_request=LoRARequest(str(lora_id), lora_id, lora_path)
39
if lora_id else None)
40
# Print the outputs.
43
- generated_texts: List[str] = []
41
+ generated_texts: list[str] = []
42
for output in outputs:
43
prompt = output.prompt
44
generated_text = output.outputs[0].text.strip()
tests/lora/test_ultravox.py
+3
-4
@@ -3,7 +3,6 @@
3
import shutil
4
from os import path
5
from tempfile import TemporaryDirectory
6
-from typing import List, Tuple
6
7
import torch
8
from huggingface_hub import snapshot_download
@@ -86,8 +85,8 @@ def test_ultravox_lora(vllm_runner):
85
dtype="bfloat16",
86
max_model_len=1024,
87
) as vllm_model:
89
- ultravox_outputs: List[Tuple[
90
- List[int], str]] = vllm_model.generate_greedy(
88
+ ultravox_outputs: list[tuple[
89
+ list[int], str]] = vllm_model.generate_greedy(
90
[
91
_get_prompt(0, PROMPT, VLLM_PLACEHOLDER,
92
ULTRAVOX_MODEL_NAME)
@@ -108,7 +107,7 @@ def test_ultravox_lora(vllm_runner):
107
dtype="bfloat16",
108
max_model_len=1024,
109
) as vllm_model:
111
- llama_outputs: List[Tuple[List[int], str]] = (
110
+ llama_outputs: list[tuple[list[int], str]] = (
111
vllm_model.generate_greedy(
112
[_get_prompt(0, PROMPT, VLLM_PLACEHOLDER, LLMA_MODEL_NAME)],
113
256,
tests/lora/utils.py
+7
-7
@@ -1,7 +1,7 @@
1
# SPDX-License-Identifier: Apache-2.0
2
3
from dataclasses import dataclass
4
-from typing import Dict, List, Optional, Tuple, Union
4
+from typing import Optional, Union
5
6
import torch
7
@@ -12,7 +12,7 @@ class DummyLoRAManager:
12
13
def __init__(self, device: torch.device = "cuda:0"):
14
super().__init__()
15
- self._loras: Dict[str, LoRALayerWeights] = {}
15
+ self._loras: dict[str, LoRALayerWeights] = {}
16
self._device = device
17
18
def set_module_lora(self, module_name: str, lora: LoRALayerWeights):
@@ -77,11 +77,11 @@ class DummyLoRAManager:
77
self,
78
module_name: str,
79
input_dim: int,
80
- output_dims: List[int],
81
- noop_lora_index: Optional[List[int]] = None,
80
+ output_dims: list[int],
81
+ noop_lora_index: Optional[list[int]] = None,
82
rank: int = 8,
83
):
84
- base_loras: List[LoRALayerWeights] = []
84
+ base_loras: list[LoRALayerWeights] = []
85
noop_lora_index_set = set(noop_lora_index or [])
86
87
for i, out_dim in enumerate(output_dims):
@@ -110,7 +110,7 @@ def assert_close(a, b):
110
@dataclass
111
class PunicaTensors:
112
inputs_tensor: torch.Tensor
113
- lora_weights: Union[torch.Tensor, List[torch.Tensor]]
113
+ lora_weights: Union[torch.Tensor, list[torch.Tensor]]
114
our_out_tensor: torch.Tensor
115
ref_out_tensor: torch.Tensor
116
b_seq_start_loc: torch.Tensor
@@ -118,7 +118,7 @@ class PunicaTensors:
118
seq_len_tensor: torch.Tensor
119
token_lora_mapping: torch.Tensor
120
121
- def meta(self) -> Tuple[int, int]:
121
+ def meta(self) -> tuple[int, int]:
122
"""
123
Infer max_seq_length and token_nums from the tensors
124
and return them.
tests/metrics/test_metrics.py
+1
-2
@@ -1,7 +1,6 @@
1
# SPDX-License-Identifier: Apache-2.0
2
3
import time
4
-from typing import List
4
5
import pytest
6
import ray
@@ -133,7 +132,7 @@ def test_metric_counter_generation_tokens_multi_step(
132
"served_model_name",
133
[None, [], ["ModelName0"], ["ModelName0", "ModelName1", "ModelName2"]])
134
def test_metric_set_tag_model_name(vllm_runner, model: str, dtype: str,
136
- served_model_name: List[str]) -> None:
135
+ served_model_name: list[str]) -> None:
136
with vllm_runner(model,
137
dtype=dtype,
138
disable_log_stats=False,
tests/mistral_tool_use/utils.py
+4
-4
@@ -1,21 +1,21 @@
1
# SPDX-License-Identifier: Apache-2.0
2
3
-from typing import Dict, List, Optional
3
+from typing import Optional
4
5
from typing_extensions import TypedDict
6
7
8
class ServerConfig(TypedDict, total=False):
9
model: str
10
- arguments: List[str]
10
+ arguments: list[str]
11
system_prompt: Optional[str]
12
supports_parallel: Optional[bool]
13
supports_rocm: Optional[bool]
14
15
16
-ARGS: List[str] = ["--max-model-len", "1024"]
16
+ARGS: list[str] = ["--max-model-len", "1024"]
17
18
-CONFIGS: Dict[str, ServerConfig] = {
18
+CONFIGS: dict[str, ServerConfig] = {
19
"mistral": {
20
"model":
21
"mistralai/Mistral-7B-Instruct-v0.3",
tests/model_executor/test_enabled_custom_ops.py
+1
-3
@@ -1,7 +1,5 @@
1
# SPDX-License-Identifier: Apache-2.0
2
3
-from typing import List
4
-
3
import pytest
4
5
from vllm.config import CompilationConfig, VllmConfig, set_current_vllm_config
@@ -51,7 +49,7 @@ class Relu3(ReLUSquaredActivation):
49
# All but RMSNorm
50
("all,-rms_norm", 4, [0, 1, 1, 1], True),
51
])
54
-def test_enabled_ops(env: str, torch_level: int, ops_enabled: List[int],
52
+def test_enabled_ops(env: str, torch_level: int, ops_enabled: list[int],
53
default_on: bool):
54
vllm_config = VllmConfig(compilation_config=CompilationConfig(
55
level=torch_level, custom_ops=env.split(",")))
tests/models/decoder_only/audio_language/test_ultravox.py
+8
-8
@@ -1,6 +1,6 @@
1
# SPDX-License-Identifier: Apache-2.0
2
3
-from typing import List, Optional, Tuple, Type
3
+from typing import Optional
4
5
import numpy as np
6
import pytest
@@ -17,7 +17,7 @@ from ...utils import check_logprobs_close
17
18
MODEL_NAME = "fixie-ai/ultravox-v0_4"
19
20
-AudioTuple = Tuple[np.ndarray, int]
20
+AudioTuple = tuple[np.ndarray, int]
21
22
VLLM_PLACEHOLDER = "<|audio|>"
23
HF_PLACEHOLDER = "<|audio|>"
@@ -78,7 +78,7 @@ def _get_prompt(audio_count, question, placeholder):
78
add_generation_prompt=True)
79
80
81
-def vllm_to_hf_output(vllm_output: Tuple[List[int], str,
81
+def vllm_to_hf_output(vllm_output: tuple[list[int], str,
82
Optional[SampleLogprobs]],
83
model: str):
84
"""Sanitize vllm output to be comparable with hf output."""
@@ -96,9 +96,9 @@ def vllm_to_hf_output(vllm_output: Tuple[List[int], str,
96
97
98
def run_test(
99
- hf_runner: Type[HfRunner],
100
- vllm_runner: Type[VllmRunner],
101
- prompts_and_audios: List[Tuple[str, str, AudioTuple]],
99
+ hf_runner: type[HfRunner],
100
+ vllm_runner: type[VllmRunner],
101
+ prompts_and_audios: list[tuple[str, str, AudioTuple]],
102
model: str,
103
*,
104
dtype: str,
@@ -158,8 +158,8 @@ def run_test(
158
159
160
def run_multi_audio_test(
161
- vllm_runner: Type[VllmRunner],
162
- prompts_and_audios: List[Tuple[str, List[AudioTuple]]],
161
+ vllm_runner: type[VllmRunner],
162
+ prompts_and_audios: list[tuple[str, list[AudioTuple]]],
163
model: str,
164
*,
165
dtype: str,
tests/models/decoder_only/language/test_gguf.py
+3
-3
@@ -5,7 +5,7 @@ Note: To pass the test, quantization higher than Q4 should be used
5
"""
6
7
import os
8
-from typing import List, NamedTuple, Type
8
+from typing import NamedTuple
9
10
import pytest
11
from huggingface_hub import hf_hub_download
@@ -90,8 +90,8 @@ MODELS = [
90
@pytest.mark.parametrize("tp_size", [1, 2])
91
def test_models(
92
num_gpus_available: int,
93
- vllm_runner: Type[VllmRunner],
94
- example_prompts: List[str],
93
+ vllm_runner: type[VllmRunner],
94
+ example_prompts: list[str],
95
model: GGUFTestConfig,
96
dtype: str,
97
max_tokens: int,
tests/models/decoder_only/language/test_modelopt.py
+1
-2
@@ -5,7 +5,6 @@
5
Note: these tests will only pass on H100
6
"""
7
import os
8
-from typing import List
8
9
import pytest
10
from transformers import AutoTokenizer
@@ -65,7 +64,7 @@ def test_models(example_prompts, model_name) -> None:
64
for prompt in example_prompts
65
]
66
params = SamplingParams(max_tokens=20, temperature=0)
68
- generations: List[str] = []
67
+ generations: list[str] = []
68
# Note: these need to be run 1 at a time due to numerical precision,
69
# since the expected strs were generated this way.
70
for prompt in formatted_prompts:
tests/models/decoder_only/vision_language/test_awq.py
+3
-3
@@ -1,6 +1,6 @@
1
# SPDX-License-Identifier: Apache-2.0
2
3
-from typing import List, Optional, Type
3
+from typing import Optional
4
5
import pytest
6
import torch
@@ -19,12 +19,12 @@ HF_IMAGE_PROMPTS = IMAGE_ASSETS.prompts({
19
20
21
def run_awq_test(
22
- vllm_runner: Type[VllmRunner],
22
+ vllm_runner: type[VllmRunner],
23
image_assets: _ImageAssets,
24
source_model: str,
25
quant_model: str,
26
*,
27
- size_factors: List[float],
27
+ size_factors: list[float],
28
dtype: str,
29
max_tokens: int,
30
num_logprobs: int,
tests/models/decoder_only/vision_language/test_models.py
+19
-20
@@ -6,7 +6,6 @@ import math
6
import os
7
from collections import defaultdict
8
from pathlib import PosixPath
9
-from typing import Type
9
10
import pytest
11
from packaging.version import Version
@@ -562,8 +561,8 @@ VLM_TEST_SETTINGS = _mark_splits(VLM_TEST_SETTINGS, num_groups=2)
561
))
562
def test_single_image_models(tmp_path: PosixPath, model_type: str,
563
test_case: ExpandableVLMTestArgs,
565
- hf_runner: Type[HfRunner],
566
- vllm_runner: Type[VllmRunner],
564
+ hf_runner: type[HfRunner],
565
+ vllm_runner: type[VllmRunner],
566
image_assets: _ImageAssets):
567
model_test_info = VLM_TEST_SETTINGS[model_type]
568
runners.run_single_image_test(
@@ -585,8 +584,8 @@ def test_single_image_models(tmp_path: PosixPath, model_type: str,
584
))
585
def test_multi_image_models(tmp_path: PosixPath, model_type: str,
586
test_case: ExpandableVLMTestArgs,
588
- hf_runner: Type[HfRunner],
589
- vllm_runner: Type[VllmRunner],
587
+ hf_runner: type[HfRunner],
588
+ vllm_runner: type[VllmRunner],
589
image_assets: _ImageAssets):
590
model_test_info = VLM_TEST_SETTINGS[model_type]
591
runners.run_multi_image_test(
@@ -608,8 +607,8 @@ def test_multi_image_models(tmp_path: PosixPath, model_type: str,
607
))
608
def test_image_embedding_models(model_type: str,
609
test_case: ExpandableVLMTestArgs,
611
- hf_runner: Type[HfRunner],
612
- vllm_runner: Type[VllmRunner],
610
+ hf_runner: type[HfRunner],
611
+ vllm_runner: type[VllmRunner],
612
image_assets: _ImageAssets):
613
model_test_info = VLM_TEST_SETTINGS[model_type]
614
runners.run_embedding_test(
@@ -629,7 +628,7 @@ def test_image_embedding_models(model_type: str,
628
fork_new_process_for_each_test=False,
629
))
630
def test_video_models(model_type: str, test_case: ExpandableVLMTestArgs,
632
- hf_runner: Type[HfRunner], vllm_runner: Type[VllmRunner],
631
+ hf_runner: type[HfRunner], vllm_runner: type[VllmRunner],
632
video_assets: _VideoAssets):
633
model_test_info = VLM_TEST_SETTINGS[model_type]
634
runners.run_video_test(
@@ -651,8 +650,8 @@ def test_video_models(model_type: str, test_case: ExpandableVLMTestArgs,
650
def test_custom_inputs_models(
651
model_type: str,
652
test_case: ExpandableVLMTestArgs,
654
- hf_runner: Type[HfRunner],
655
- vllm_runner: Type[VllmRunner],
653
+ hf_runner: type[HfRunner],
654
+ vllm_runner: type[VllmRunner],
655
):
656
model_test_info = VLM_TEST_SETTINGS[model_type]
657
runners.run_custom_inputs_test(
@@ -674,8 +673,8 @@ def test_custom_inputs_models(
673
@fork_new_process_for_each_test
674
def test_single_image_models_heavy(tmp_path: PosixPath, model_type: str,
675
test_case: ExpandableVLMTestArgs,
677
- hf_runner: Type[HfRunner],
678
- vllm_runner: Type[VllmRunner],
676
+ hf_runner: type[HfRunner],
677
+ vllm_runner: type[VllmRunner],
678
image_assets: _ImageAssets):
679
model_test_info = VLM_TEST_SETTINGS[model_type]
680
runners.run_single_image_test(
@@ -698,8 +697,8 @@ def test_single_image_models_heavy(tmp_path: PosixPath, model_type: str,
697
@fork_new_process_for_each_test
698
def test_multi_image_models_heavy(tmp_path: PosixPath, model_type: str,
699
test_case: ExpandableVLMTestArgs,
701
- hf_runner: Type[HfRunner],
702
- vllm_runner: Type[VllmRunner],
700
+ hf_runner: type[HfRunner],
701
+ vllm_runner: type[VllmRunner],
702
image_assets: _ImageAssets):
703
model_test_info = VLM_TEST_SETTINGS[model_type]
704
runners.run_multi_image_test(
@@ -722,8 +721,8 @@ def test_multi_image_models_heavy(tmp_path: PosixPath, model_type: str,
721
@fork_new_process_for_each_test
722
def test_image_embedding_models_heavy(model_type: str,
723
test_case: ExpandableVLMTestArgs,
725
- hf_runner: Type[HfRunner],
726
- vllm_runner: Type[VllmRunner],
724
+ hf_runner: type[HfRunner],
725
+ vllm_runner: type[VllmRunner],
726
image_assets: _ImageAssets):
727
model_test_info = VLM_TEST_SETTINGS[model_type]
728
runners.run_embedding_test(
@@ -743,8 +742,8 @@ def test_image_embedding_models_heavy(model_type: str,
742
fork_new_process_for_each_test=True,
743
))
744
def test_video_models_heavy(model_type: str, test_case: ExpandableVLMTestArgs,
746
- hf_runner: Type[HfRunner],
747
- vllm_runner: Type[VllmRunner],
745
+ hf_runner: type[HfRunner],
746
+ vllm_runner: type[VllmRunner],
747
video_assets: _VideoAssets):
748
model_test_info = VLM_TEST_SETTINGS[model_type]
749
runners.run_video_test(
@@ -767,8 +766,8 @@ def test_video_models_heavy(model_type: str, test_case: ExpandableVLMTestArgs,
766
def test_custom_inputs_models_heavy(
767
model_type: str,
768
test_case: ExpandableVLMTestArgs,
770
- hf_runner: Type[HfRunner],
771
- vllm_runner: Type[VllmRunner],
769
+ hf_runner: type[HfRunner],
770
+ vllm_runner: type[VllmRunner],
771
):
772
model_test_info = VLM_TEST_SETTINGS[model_type]
773
runners.run_custom_inputs_test(
tests/models/decoder_only/vision_language/test_phi3v.py
+5
-5
@@ -2,7 +2,7 @@
2
3
import os
4
import re
5
-from typing import List, Optional, Tuple, Type
5
+from typing import Optional
6
7
import pytest
8
from transformers import AutoTokenizer
@@ -25,7 +25,7 @@ HF_MULTIIMAGE_IMAGE_PROMPT = "<|user|>\n<|image_1|>\n<|image_2|>\nDescribe these
25
models = ["microsoft/Phi-3.5-vision-instruct"]
26
27
28
-def vllm_to_hf_output(vllm_output: Tuple[List[int], str,
28
+def vllm_to_hf_output(vllm_output: tuple[list[int], str,
29
Optional[SampleLogprobs]],
30
model: str):
31
"""Sanitize vllm output to be comparable with hf output."""
@@ -55,9 +55,9 @@ if current_platform.is_rocm():
55
56
57
def run_test(
58
- hf_runner: Type[HfRunner],
59
- vllm_runner: Type[VllmRunner],
60
- inputs: List[Tuple[List[str], PromptImageInput]],
58
+ hf_runner: type[HfRunner],
59
+ vllm_runner: type[VllmRunner],
60
+ inputs: list[tuple[list[str], PromptImageInput]],
61
model: str,
62
*,
63
dtype: str,
tests/models/decoder_only/vision_language/test_pixtral.py
+6
-6
@@ -6,7 +6,7 @@ Run `pytest tests/models/test_mistral.py`.
6
import json
7
import uuid
8
from dataclasses import asdict
9
-from typing import TYPE_CHECKING, Any, Dict, List, Optional, Tuple
9
+from typing import TYPE_CHECKING, Any, Optional
10
11
import pytest
12
from mistral_common.multimodal import download_image
@@ -38,7 +38,7 @@ IMG_URLS = [
38
PROMPT = "Describe each image in one short sentence."
39
40
41
-def _create_msg_format(urls: List[str]) -> List[Dict[str, Any]]:
41
+def _create_msg_format(urls: list[str]) -> list[dict[str, Any]]:
42
return [{
43
"role":
44
"user",
@@ -54,7 +54,7 @@ def _create_msg_format(urls: List[str]) -> List[Dict[str, Any]]:
54
}]
55
56
57
-def _create_msg_format_hf(urls: List[str]) -> List[Dict[str, Any]]:
57
+def _create_msg_format_hf(urls: list[str]) -> list[dict[str, Any]]:
58
return [{
59
"role":
60
"user",
@@ -68,7 +68,7 @@ def _create_msg_format_hf(urls: List[str]) -> List[Dict[str, Any]]:
68
}]
69
70
71
-def _create_engine_inputs(urls: List[str]) -> TokensPrompt:
71
+def _create_engine_inputs(urls: list[str]) -> TokensPrompt:
72
msg = _create_msg_format(urls)
73
74
tokenizer = MistralTokenizer.from_model("pixtral")
@@ -89,7 +89,7 @@ def _create_engine_inputs(urls: List[str]) -> TokensPrompt:
89
return engine_inputs
90
91
92
-def _create_engine_inputs_hf(urls: List[str]) -> TextPrompt:
92
+def _create_engine_inputs_hf(urls: list[str]) -> TextPrompt:
93
msg = _create_msg_format_hf(urls)
94
95
tokenizer = AutoProcessor.from_pretrained("mistral-community/pixtral-12b")
@@ -128,7 +128,7 @@ assert FIXTURES_PATH.exists()
128
FIXTURE_LOGPROBS_CHAT = FIXTURES_PATH / "pixtral_chat.json"
129
FIXTURE_LOGPROBS_ENGINE = FIXTURES_PATH / "pixtral_chat_engine.json"
130
131
-OutputsLogprobs = List[Tuple[List[int], str, Optional[SampleLogprobs]]]
131
+OutputsLogprobs = list[tuple[list[int], str, Optional[SampleLogprobs]]]
132
133
134
# For the test author to store golden output in JSON
tests/models/decoder_only/vision_language/test_qwen2_vl.py
+23
-23
@@ -1,6 +1,6 @@
1
# SPDX-License-Identifier: Apache-2.0
2
3
-from typing import Any, List, Optional, Tuple, Type, TypedDict, Union
3
+from typing import Any, Optional, TypedDict, Union
4
5
import numpy.typing as npt
6
import pytest
@@ -69,21 +69,21 @@ class Qwen2VLPromptVideoEmbeddingInput(TypedDict):
69
70
71
def batch_make_image_embeddings(
72
- image_batches: List[Union[Image.Image, List[Image.Image]]], processor,
73
- llm: VllmRunner) -> List[Qwen2VLPromptImageEmbeddingInput]:
72
+ image_batches: list[Union[Image.Image, list[Image.Image]]], processor,
73
+ llm: VllmRunner) -> list[Qwen2VLPromptImageEmbeddingInput]:
74
"""batched image embeddings for Qwen2-VL
75
76
This will infer all images' embeddings in a single batch,
77
and split the result according to input batches.
78
79
image_batches:
80
- - Single-image batches: `List[Image.Image]`
81
- - Multiple-image batches: `List[List[Image.Image]]]`
80
+ - Single-image batches: `list[Image.Image]`
81
+ - Multiple-image batches: `list[list[Image.Image]]]`
82
83
- returns: `List[Qwen2VLPromptImageEmbeddingInput]`
83
+ returns: `list[Qwen2VLPromptImageEmbeddingInput]`
84
"""
85
86
- image_batches_: List[Any] = image_batches[:]
86
+ image_batches_: list[Any] = image_batches[:]
87
88
# convert single-image batches to multiple-image batches
89
for idx in range(len(image_batches_)):
@@ -93,7 +93,7 @@ def batch_make_image_embeddings(
93
assert isinstance(image_batches_[idx], list)
94
95
# append all images into a list (as a batch)
96
- images: List[Image.Image] = []
96
+ images: list[Image.Image] = []
97
for image_batch in image_batches_:
98
images += image_batch
99
@@ -121,7 +121,7 @@ def batch_make_image_embeddings(
121
image_embeds = torch.concat(llm.apply_model(get_image_embeds))
122
123
# split into original batches
124
- result: List[Qwen2VLPromptImageEmbeddingInput] = []
124
+ result: list[Qwen2VLPromptImageEmbeddingInput] = []
125
image_counter = 0
126
embed_counter = 0
127
for image_batch in image_batches_:
@@ -153,7 +153,7 @@ def batch_make_image_embeddings(
153
154
def batch_make_video_embeddings(
155
video_batches: PromptVideoInput, processor,
156
- llm: VllmRunner) -> List[Qwen2VLPromptVideoEmbeddingInput]:
156
+ llm: VllmRunner) -> list[Qwen2VLPromptVideoEmbeddingInput]:
157
"""batched video embeddings for Qwen2-VL
158
159
A NDArray represents a single video's all frames.
@@ -162,21 +162,21 @@ def batch_make_video_embeddings(
162
and split the result according to input batches.
163
164
video_batches:
165
- - Single-video batches: `List[NDArray]`
166
- - Multiple-video batches: `List[List[NDArray]]`
165
+ - Single-video batches: `list[NDArray]`
166
+ - Multiple-video batches: `list[list[NDArray]]`
167
"""
168
169
- video_batches_: List[Any] = video_batches[:]
169
+ video_batches_: list[Any] = video_batches[:]
170
171
for idx in range(len(video_batches_)):
172
if not isinstance(video_batches_[idx], list):
173
- single_video_batch: List[npt.NDArray] = [video_batches_[idx]]
173
+ single_video_batch: list[npt.NDArray] = [video_batches_[idx]]
174
video_batches_[idx] = single_video_batch
175
176
assert isinstance(video_batches_[idx], list)
177
178
# append all videos into a list (as a batch)
179
- videos: List[npt.NDArray] = []
179
+ videos: list[npt.NDArray] = []
180
for video_batch in video_batches_:
181
videos += video_batch
182
@@ -204,7 +204,7 @@ def batch_make_video_embeddings(
204
video_embeds = torch.concat(llm.apply_model(get_image_embeds))
205
206
# split into original batches
207
- result: List[Qwen2VLPromptVideoEmbeddingInput] = []
207
+ result: list[Qwen2VLPromptVideoEmbeddingInput] = []
208
video_counter = 0
209
embed_counter = 0
210
for video_batch in video_batches_:
@@ -235,8 +235,8 @@ def batch_make_video_embeddings(
235
236
237
def run_embedding_input_test(
238
- vllm_runner: Type[VllmRunner],
239
- inputs: List[Tuple[List[str], PromptImageInput, PromptVideoInput]],
238
+ vllm_runner: type[VllmRunner],
239
+ inputs: list[tuple[list[str], PromptImageInput, PromptVideoInput]],
240
model: str,
241
*,
242
dtype: str,
@@ -323,8 +323,8 @@ def test_qwen2_vl_image_embeddings_input(vllm_runner, image_assets, model,
323
num_logprobs: int) -> None:
324
images = [asset.pil_image for asset in image_assets]
325
326
- inputs_per_case: List[Tuple[
327
- List[str], PromptImageInput, PromptVideoInput]] = [(
326
+ inputs_per_case: list[tuple[
327
+ list[str], PromptImageInput, PromptVideoInput]] = [(
328
[prompt for _ in size_factors],
329
[rescale_image_size(image, factor) for factor in size_factors],
330
[],
@@ -365,7 +365,7 @@ def test_qwen2_vl_multiple_image_embeddings_input(vllm_runner, image_assets,
365
num_logprobs: int) -> None:
366
images = [asset.pil_image for asset in image_assets]
367
368
- inputs_per_case: List[Tuple[List[str], PromptImageInput,
368
+ inputs_per_case: list[tuple[list[str], PromptImageInput,
369
PromptVideoInput]] = [(
370
[MULTIIMAGE_PROMPT for _ in size_factors],
371
[[
@@ -413,8 +413,8 @@ def test_qwen2_vl_video_embeddings_input(vllm_runner, video_assets, model,
413
for asset in video_assets
414
]
415
416
- inputs_per_case: List[Tuple[
417
- List[str], PromptImageInput, PromptVideoInput]] = [(
416
+ inputs_per_case: list[tuple[
417
+ list[str], PromptImageInput, PromptVideoInput]] = [(
418
[prompt for _ in size_factors],
419
[],
420
[rescale_video_size(video, factor) for factor in size_factors],
tests/models/decoder_only/vision_language/vlm_utils/builders.py
+4
-3
@@ -1,8 +1,9 @@
1
# SPDX-License-Identifier: Apache-2.0
2
"""Helpers for building inputs that can be leveraged for different test types.
3
"""
4
+from collections.abc import Iterable
5
from pathlib import PosixPath
5
-from typing import Callable, Iterable, List, Optional, Tuple, Union
6
+from typing import Callable, Optional, Union
7
8
import torch
9
@@ -33,7 +34,7 @@ def replace_test_placeholder(prompt: str, img_idx_to_prompt: Callable[[int],
34
def get_model_prompts(base_prompts: Iterable[str],
35
img_idx_to_prompt: Optional[Callable[[int], str]],
36
video_idx_to_prompt: Optional[Callable[[int], str]],
36
- prompt_formatter: Callable[[str], str]) -> List[str]:
37
+ prompt_formatter: Callable[[str], str]) -> list[str]:
38
"""Given a model-agnostic base prompt and test configuration for a model(s)
39
to be tested, update the media placeholders and apply the prompt formatting
40
to get the test prompt string for this model.
@@ -218,7 +219,7 @@ def build_video_inputs_from_test_info(
219
) for video, prompt in zip(sampled_vids, model_prompts)]
220
221
221
-def apply_image_size_scaling(image, size: Union[float, Tuple[int, int]],
222
+def apply_image_size_scaling(image, size: Union[float, tuple[int, int]],
223
size_type: SizeType):
224
"""Applies a size scaler to one image; this can be a an image size factor,
225
which scales the image while maintaining the aspect ratio"""
tests/models/decoder_only/vision_language/vlm_utils/case_filtering.py
+5
-5
@@ -5,7 +5,7 @@ handling multimodal placeholder substitution, and so on.
5
"""
6
import itertools
7
from collections import OrderedDict
8
-from typing import Dict, Iterable, Tuple
8
+from collections.abc import Iterable
9
10
import pytest
11
@@ -13,9 +13,9 @@ from .types import (EMBEDDING_SIZE_FACTORS, ExpandableVLMTestArgs,
13
ImageSizeWrapper, SizeType, VLMTestInfo, VLMTestType)
14
15
16
-def get_filtered_test_settings(test_settings: Dict[str, VLMTestInfo],
16
+def get_filtered_test_settings(test_settings: dict[str, VLMTestInfo],
17
test_type: VLMTestType,
18
- fork_per_test: bool) -> Dict[str, VLMTestInfo]:
18
+ fork_per_test: bool) -> dict[str, VLMTestInfo]:
19
"""Given the dict of potential test settings to run, return a subdict
20
of tests who have the current test type enabled with the matching val for
21
fork_per_test.
@@ -49,7 +49,7 @@ def get_filtered_test_settings(test_settings: Dict[str, VLMTestInfo],
49
return matching_tests
50
51
52
-def get_parametrized_options(test_settings: Dict[str, VLMTestInfo],
52
+def get_parametrized_options(test_settings: dict[str, VLMTestInfo],
53
test_type: VLMTestType,
54
fork_new_process_for_each_test: bool):
55
"""Converts all of our VLMTestInfo into an expanded list of parameters.
@@ -121,7 +121,7 @@ def get_parametrized_options(test_settings: Dict[str, VLMTestInfo],
121
122
def get_wrapped_test_sizes(
123
test_info: VLMTestInfo,
124
- test_type: VLMTestType) -> Tuple[ImageSizeWrapper, ...]:
124
+ test_type: VLMTestType) -> tuple[ImageSizeWrapper, ...]:
125
"""Given a test info which may have size factors or fixed sizes, wrap them
126
and combine them into an iterable, each of which will be used in parameter
127
expansion.
tests/models/decoder_only/vision_language/vlm_utils/core.py
+11
-11
@@ -1,6 +1,6 @@
1
# SPDX-License-Identifier: Apache-2.0
2
"""Core test implementation to be shared across modalities."""
3
-from typing import Any, Callable, Dict, List, Optional, Tuple, Type, Union
3
+from typing import Any, Callable, Optional, Union
4
5
import torch
6
from PIL.Image import Image
@@ -17,9 +17,9 @@ from .types import RunnerOutput
17
18
def run_test(
19
*,
20
- hf_runner: Type[HfRunner],
21
- vllm_runner: Type[VllmRunner],
22
- inputs: List[Tuple[List[str], List[Union[List[Image], Image]]]],
20
+ hf_runner: type[HfRunner],
21
+ vllm_runner: type[VllmRunner],
22
+ inputs: list[tuple[list[str], list[Union[list[Image], Image]]]],
23
model: str,
24
dtype: str,
25
max_tokens: int,
@@ -29,15 +29,15 @@ def run_test(
29
max_num_seqs: int,
30
hf_output_post_proc: Optional[Callable[[RunnerOutput, str], Any]],
31
vllm_output_post_proc: Optional[Callable[[RunnerOutput, str], Any]],
32
- auto_cls: Type[_BaseAutoModelClass],
32
+ auto_cls: type[_BaseAutoModelClass],
33
use_tokenizer_eos: bool,
34
postprocess_inputs: Callable[[BatchEncoding], BatchEncoding],
35
comparator: Callable[..., None],
36
get_stop_token_ids: Optional[Callable[[AnyTokenizer], list[int]]],
37
- stop_str: Optional[List[str]],
38
- limit_mm_per_prompt: Dict[str, int],
39
- vllm_runner_kwargs: Optional[Dict[str, Any]],
40
- hf_model_kwargs: Optional[Dict[str, Any]],
37
+ stop_str: Optional[list[str]],
38
+ limit_mm_per_prompt: dict[str, int],
39
+ vllm_runner_kwargs: Optional[dict[str, Any]],
40
+ hf_model_kwargs: Optional[dict[str, Any]],
41
patch_hf_runner: Optional[Callable[[HfRunner], HfRunner]],
42
task: TaskOption = "auto",
43
runner_mm_key: str = "images",
@@ -61,7 +61,7 @@ def run_test(
61
# if we run HF first, the cuda initialization will be done and it
62
# will hurt multiprocessing backend with fork method (the default method).
63
64
- vllm_runner_kwargs_: Dict[str, Any] = {}
64
+ vllm_runner_kwargs_: dict[str, Any] = {}
65
if model_info.tokenizer:
66
vllm_runner_kwargs_["tokenizer"] = model_info.tokenizer
67
if model_info.tokenizer_mode:
@@ -84,7 +84,7 @@ def run_test(
84
**vllm_runner_kwargs_) as vllm_model:
85
tokenizer = vllm_model.model.get_tokenizer()
86
87
- vllm_kwargs: Dict[str, Any] = {}
87
+ vllm_kwargs: dict[str, Any] = {}
88
if get_stop_token_ids is not None:
89
vllm_kwargs["stop_token_ids"] = get_stop_token_ids(tokenizer)
90
if stop_str:
tests/models/decoder_only/vision_language/vlm_utils/model_utils.py
+8
-8
@@ -6,7 +6,7 @@ typically specific to a small subset of models.
6
import re
7
import types
8
from pathlib import PosixPath
9
-from typing import Callable, List, Optional, Tuple, Union
9
+from typing import Callable, Optional, Union
10
11
import torch
12
from PIL.Image import Image
@@ -49,7 +49,7 @@ def fuyu_vllm_to_hf_output(vllm_output: RunnerOutput,
49
50
def qwen_vllm_to_hf_output(
51
vllm_output: RunnerOutput,
52
- model: str) -> Tuple[List[int], str, Optional[SampleLogprobs]]:
52
+ model: str) -> tuple[list[int], str, Optional[SampleLogprobs]]:
53
"""Sanitize vllm output [qwen models] to be comparable with hf output."""
54
output_ids, output_str, out_logprobs = vllm_output
55
@@ -60,7 +60,7 @@ def qwen_vllm_to_hf_output(
60
61
def qwen2_vllm_to_hf_output(
62
vllm_output: RunnerOutput,
63
- model: str) -> Tuple[List[int], str, Optional[SampleLogprobs]]:
63
+ model: str) -> tuple[list[int], str, Optional[SampleLogprobs]]:
64
"""Sanitize vllm output [qwen2 models] to be comparable with hf output."""
65
output_ids, output_str, out_logprobs = vllm_output
66
@@ -78,7 +78,7 @@ def llava_image_vllm_to_hf_output(vllm_output: RunnerOutput,
78
79
def llava_video_vllm_to_hf_output(
80
vllm_output: RunnerOutput,
81
- model: str) -> Tuple[List[int], str, Optional[SampleLogprobs]]:
81
+ model: str) -> tuple[list[int], str, Optional[SampleLogprobs]]:
82
config = AutoConfig.from_pretrained(model)
83
mm_token_id = config.video_token_index
84
return _llava_vllm_to_hf_output(vllm_output, model, mm_token_id)
@@ -247,7 +247,7 @@ def molmo_post_processor(hf_inputs: BatchEncoding, dtype: str):
247
248
####### Prompt path encoders for models that need models on disk
249
def qwen_prompt_path_encoder(
250
- tmp_path: PosixPath, prompt: str, assets: Union[List[ImageAsset],
250
+ tmp_path: PosixPath, prompt: str, assets: Union[list[ImageAsset],
251
_ImageAssets]) -> str:
252
"""Given a temporary dir path, export one or more image assets into the
253
tempdir & replace its contents with the local path to the string so that
@@ -257,7 +257,7 @@ def qwen_prompt_path_encoder(
257
Args:
258
tmp_path: Tempdir for test under consideration.
259
prompt: Prompt with image placeholders.
260
- assets: List of image assets whose len equals the num placeholders.
260
+ assets: list of image assets whose len equals the num placeholders.
261
"""
262
# Ensure that the number of placeholders matches the number of assets;
263
# If this is not true, the test is probably written incorrectly.
@@ -350,7 +350,7 @@ def h2ovl_patch_hf_runner(hf_model: HfRunner) -> HfRunner:
350
self.max_num = self.config.max_dynamic_patch
351
self.image_size = self.vision_config.image_size
352
353
- def __call__(self, text: str, images: Union[Image, List[Image]],
353
+ def __call__(self, text: str, images: Union[Image, list[Image]],
354
**kwargs):
355
# yapf: disable
356
from vllm.model_executor.models.h2ovl import (
@@ -410,7 +410,7 @@ def internvl_patch_hf_runner(hf_model: HfRunner) -> HfRunner:
410
self.max_num = self.config.max_dynamic_patch
411
self.image_size = self.vision_config.image_size
412
413
- def __call__(self, text: str, images: Union[Image, List[Image]],
413
+ def __call__(self, text: str, images: Union[Image, list[Image]],
414
**kwargs):
415
from vllm.model_executor.models.internvl import (
416
IMG_CONTEXT, IMG_END, IMG_START,
tests/models/decoder_only/vision_language/vlm_utils/runners.py
+10
-11
@@ -3,7 +3,6 @@
3
types / modalities.
4
"""
5
from pathlib import PosixPath
6
-from typing import Type
6
7
from .....conftest import HfRunner, VllmRunner, _ImageAssets, _VideoAssets
8
from . import builders, core
@@ -13,8 +12,8 @@ from .types import ExpandableVLMTestArgs, VLMTestInfo
12
####### Entrypoints for running different test types
13
def run_single_image_test(*, tmp_path: PosixPath, model_test_info: VLMTestInfo,
14
test_case: ExpandableVLMTestArgs,
16
- hf_runner: Type[HfRunner],
17
- vllm_runner: Type[VllmRunner],
15
+ hf_runner: type[HfRunner],
16
+ vllm_runner: type[VllmRunner],
17
image_assets: _ImageAssets):
18
assert test_case.size_wrapper is not None
19
inputs = builders.build_single_image_inputs_from_test_info(
@@ -36,8 +35,8 @@ def run_single_image_test(*, tmp_path: PosixPath, model_test_info: VLMTestInfo,
35
36
def run_multi_image_test(*, tmp_path: PosixPath, model_test_info: VLMTestInfo,
37
test_case: ExpandableVLMTestArgs,
39
- hf_runner: Type[HfRunner],
40
- vllm_runner: Type[VllmRunner],
38
+ hf_runner: type[HfRunner],
39
+ vllm_runner: type[VllmRunner],
40
image_assets: _ImageAssets):
41
assert test_case.size_wrapper is not None
42
inputs = builders.build_multi_image_inputs_from_test_info(
@@ -59,8 +58,8 @@ def run_multi_image_test(*, tmp_path: PosixPath, model_test_info: VLMTestInfo,
58
59
def run_embedding_test(*, model_test_info: VLMTestInfo,
60
test_case: ExpandableVLMTestArgs,
62
- hf_runner: Type[HfRunner],
63
- vllm_runner: Type[VllmRunner],
61
+ hf_runner: type[HfRunner],
62
+ vllm_runner: type[VllmRunner],
63
image_assets: _ImageAssets):
64
assert test_case.size_wrapper is not None
65
inputs, vllm_embeddings = builders.build_embedding_inputs_from_test_info(
@@ -85,8 +84,8 @@ def run_video_test(
84
*,
85
model_test_info: VLMTestInfo,
86
test_case: ExpandableVLMTestArgs,
88
- hf_runner: Type[HfRunner],
89
- vllm_runner: Type[VllmRunner],
87
+ hf_runner: type[HfRunner],
88
+ vllm_runner: type[VllmRunner],
89
video_assets: _VideoAssets,
90
):
91
assert test_case.size_wrapper is not None
@@ -111,8 +110,8 @@ def run_video_test(
110
111
def run_custom_inputs_test(*, model_test_info: VLMTestInfo,
112
test_case: ExpandableVLMTestArgs,
114
- hf_runner: Type[HfRunner],
115
- vllm_runner: Type[VllmRunner]):
113
+ hf_runner: type[HfRunner],
114
+ vllm_runner: type[VllmRunner]):
115
# Custom test cases can provide inputs directly, but they need to
116
# explicitly provided a CustomTestConfig, which wraps the inputs and
117
# the limit_mm_per_prompt
tests/models/decoder_only/vision_language/vlm_utils/types.py
+18
-18
@@ -1,9 +1,9 @@
1
# SPDX-License-Identifier: Apache-2.0
2
"""Types for writing multimodal model tests."""
3
+from collections.abc import Iterable
4
from enum import Enum
5
from pathlib import PosixPath
5
-from typing import (Any, Callable, Dict, Iterable, List, NamedTuple, Optional,
6
- Tuple, Type, Union)
6
+from typing import Any, Callable, NamedTuple, Optional, Union
7
8
import torch
9
from PIL.Image import Image
@@ -35,7 +35,7 @@ VIDEO_BASE_PROMPT = f"{TEST_VIDEO_PLACEHOLDER}Why is this video funny?"
35
36
IMAGE_SIZE_FACTORS = [(), (1.0, ), (1.0, 1.0, 1.0), (0.25, 0.5, 1.0)]
37
EMBEDDING_SIZE_FACTORS = [(), (1.0, ), (1.0, 1.0, 1.0)]
38
-RunnerOutput = Tuple[List[int], str, Optional[SampleLogprobs]]
38
+RunnerOutput = tuple[list[int], str, Optional[SampleLogprobs]]
39
# yapf: enable
40
41
@@ -53,8 +53,8 @@ class SizeType(Enum):
53
54
55
class CustomTestOptions(NamedTuple):
56
- inputs: List[Tuple[List[str], List[Union[List[Image], Image]]]]
57
- limit_mm_per_prompt: Dict[str, int]
56
+ inputs: list[tuple[list[str], list[Union[list[Image], Image]]]]
57
+ limit_mm_per_prompt: dict[str, int]
58
# kwarg to pass multimodal data in as to vllm/hf runner instances.
59
runner_mm_key: str = "images"
60
@@ -63,13 +63,13 @@ class ImageSizeWrapper(NamedTuple):
63
type: SizeType
64
# A size factor is a wrapper of 0+ floats,
65
# while a fixed size contains an iterable of integer pairs
66
- data: Union[Iterable[float], Iterable[Tuple[int, int]]]
66
+ data: Union[Iterable[float], Iterable[tuple[int, int]]]
67
68
69
class VLMTestInfo(NamedTuple):
70
"""Holds the configuration for 1+ tests for one model architecture."""
71
72
- models: List[str]
72
+ models: list[str]
73
test_type: Union[VLMTestType, Iterable[VLMTestType]]
74
75
# Should be None only if this is a CUSTOM_INPUTS test
@@ -97,19 +97,19 @@ class VLMTestInfo(NamedTuple):
97
max_num_seqs: int = 256
98
task: TaskOption = "auto"
99
tensor_parallel_size: int = 1
100
- vllm_runner_kwargs: Optional[Dict[str, Any]] = None
100
+ vllm_runner_kwargs: Optional[dict[str, Any]] = None
101
102
# Optional callable which gets a list of token IDs from the model tokenizer
103
get_stop_token_ids: Optional[Callable[[AnyTokenizer], list[int]]] = None
104
# Optional list of strings to stop generation, useful when stop tokens are
105
# not special tokens in the tokenizer
106
- stop_str: Optional[List[str]] = None
106
+ stop_str: Optional[list[str]] = None
107
108
# Exposed options for HF runner
109
- hf_model_kwargs: Optional[Dict[str, Any]] = None
109
+ hf_model_kwargs: Optional[dict[str, Any]] = None
110
# Indicates we should explicitly pass the EOS from the tokenizer
111
use_tokenizer_eos: bool = False
112
- auto_cls: Type[_BaseAutoModelClass] = AutoModelForCausalLM
112
+ auto_cls: type[_BaseAutoModelClass] = AutoModelForCausalLM
113
# Callable to pass to the HF runner to run on inputs; for now, we also pass
114
# the data type to input post processing, because almost all of the uses of
115
# postprocess_inputs are to fix the data types of BatchEncoding values.
@@ -128,12 +128,12 @@ class VLMTestInfo(NamedTuple):
128
# Default expandable params per test; these defaults can be overridden in
129
# instances of this object; the complete set of test cases for the model
130
# is all combinations of .models + all fields below
131
- max_tokens: Union[int, Tuple[int]] = 128
132
- num_logprobs: Union[int, Tuple[int]] = 5
131
+ max_tokens: Union[int, tuple[int]] = 128
132
+ num_logprobs: Union[int, tuple[int]] = 5
133
dtype: Union[str, Iterable[str]] = "half"
134
distributed_executor_backend: Optional[Union[str, Iterable[str]]] = None
135
# Only expanded in video tests
136
- num_video_frames: Union[int, Tuple[int]] = 16
136
+ num_video_frames: Union[int, tuple[int]] = 16
137
138
# Fixed image sizes / image size factors; most tests use image_size_factors
139
# The values provided for these two fields will be stacked and expanded
@@ -141,19 +141,19 @@ class VLMTestInfo(NamedTuple):
141
# once per tests (much like concatenating and wrapping in one parametrize
142
# call)
143
image_size_factors: Iterable[Iterable[float]] = IMAGE_SIZE_FACTORS
144
- image_sizes: Optional[Iterable[Iterable[Tuple[int, int]]]] = None
144
+ image_sizes: Optional[Iterable[Iterable[tuple[int, int]]]] = None
145
146
# Hack for updating a prompt to take into a local path; currently only used
147
# for Qwen-VL, which requires encoding the image path / url into the prompt
148
# for HF runner
149
prompt_path_encoder: Optional[
150
- Callable[[PosixPath, str, Union[List[ImageAsset], _ImageAssets]],
150
+ Callable[[PosixPath, str, Union[list[ImageAsset], _ImageAssets]],
151
str]] = None # noqa: E501
152
153
# Allows configuring a test to run with custom inputs
154
- custom_test_opts: Optional[List[CustomTestOptions]] = None
154
+ custom_test_opts: Optional[list[CustomTestOptions]] = None
155
156
- marks: Optional[List[MarkDecorator]] = None
156
+ marks: Optional[list[MarkDecorator]] = None
157
158
def get_non_parametrized_runner_kwargs(self):
159
"""Returns a dictionary of expandable kwargs for items that are used
tests/models/embedding/language/test_gritlm.py
+5
-6
@@ -3,7 +3,6 @@
3
import importlib.util
4
import math
5
from array import array
6
-from typing import List
6
7
import openai
8
import pytest
@@ -81,14 +80,14 @@ async def client_generate(server_generate: RemoteOpenAIServer):
80
yield async_client
81
82
84
-def run_llm_encode(llm: vllm.LLM, queries: List[str],
85
- instruction: str) -> List[float]:
83
+def run_llm_encode(llm: vllm.LLM, queries: list[str],
84
+ instruction: str) -> list[float]:
85
outputs = llm.encode([instruction + q for q in queries], )
86
return [output.outputs.embedding for output in outputs]
87
88
90
-async def run_client_embeddings(client: vllm.LLM, queries: List[str],
91
- instruction: str) -> List[float]:
89
+async def run_client_embeddings(client: vllm.LLM, queries: list[str],
90
+ instruction: str) -> list[float]:
91
outputs = await client.embeddings.create(
92
model=MODEL_NAME,
93
input=[instruction + q for q in queries],
@@ -123,7 +122,7 @@ def get_test_data():
122
return queries, q_instruction, documents, d_instruction
123
124
126
-def validate_embed_output(q_rep: List[float], d_rep: List[float]):
125
+def validate_embed_output(q_rep: list[float], d_rep: list[float]):
126
cosine_sim_q0_d0 = 1 - cosine(q_rep[0], d_rep[0])
127
assert math.isclose(cosine_sim_q0_d0, 0.609, abs_tol=0.001)
128
tests/models/embedding/utils.py
+3
-3
@@ -1,6 +1,6 @@
1
# SPDX-License-Identifier: Apache-2.0
2
3
-from typing import List, Sequence
3
+from collections.abc import Sequence
4
5
import torch
6
import torch.nn.functional as F
@@ -8,8 +8,8 @@ import torch.nn.functional as F
8
9
def check_embeddings_close(
10
*,
11
- embeddings_0_lst: Sequence[List[float]],
12
- embeddings_1_lst: Sequence[List[float]],
11
+ embeddings_0_lst: Sequence[list[float]],
12
+ embeddings_1_lst: Sequence[list[float]],
13
name_0: str,
14
name_1: str,
15
tol: float = 1e-3,
tests/models/embedding/vision_language/test_dse_qwen2_vl.py
+6
-6
@@ -1,7 +1,7 @@
1
# SPDX-License-Identifier: Apache-2.0
2
3
from functools import partial
4
-from typing import Callable, Dict, List, Type
4
+from typing import Callable
5
6
import pytest
7
import torch
@@ -67,7 +67,7 @@ def get_messages(image: Image.Image, text: str, embed_text: bool):
67
68
69
def apply_chat_template_and_add_eos(
70
- messages: List[Dict],
70
+ messages: list[dict],
71
apply_chat_template_fn: Callable,
72
):
73
prompt = apply_chat_template_fn(
@@ -80,11 +80,11 @@ def postprocess_inputs(hf_model: HfRunner, inputs: BatchEncoding, **kwargs):
80
81
82
def _run_test(
83
- hf_runner: Type[HfRunner],
84
- vllm_runner: Type[VllmRunner],
85
- input_texts: List[str],
83
+ hf_runner: type[HfRunner],
84
+ vllm_runner: type[VllmRunner],
85
+ input_texts: list[str],
86
input_images: PromptImageInput,
87
- embed_texts: List[bool],
87
+ embed_texts: list[bool],
88
model: str,
89
*,
90
dtype: str,
tests/models/embedding/vision_language/test_llava_next.py
+3
-5
@@ -1,7 +1,5 @@
1
# SPDX-License-Identifier: Apache-2.0
2
3
-from typing import List, Type
4
-
3
import pytest
4
import torch.nn.functional as F
5
from transformers import AutoModelForVision2Seq
@@ -35,9 +33,9 @@ MODELS = ["royokong/e5-v"]
33
34
35
def _run_test(
38
- hf_runner: Type[HfRunner],
39
- vllm_runner: Type[VllmRunner],
40
- input_texts: List[str],
36
+ hf_runner: type[HfRunner],
37
+ vllm_runner: type[VllmRunner],
38
+ input_texts: list[str],
39
input_images: PromptImageInput,
40
model: str,
41
*,
tests/models/embedding/vision_language/test_phi3v.py
+3
-5
@@ -1,7 +1,5 @@
1
# SPDX-License-Identifier: Apache-2.0
2
3
-from typing import List, Type
4
-
3
import pytest
4
import torch.nn.functional as F
5
@@ -29,9 +27,9 @@ MODELS = ["TIGER-Lab/VLM2Vec-Full"]
27
28
29
def _run_test(
32
- hf_runner: Type[HfRunner],
33
- vllm_runner: Type[VllmRunner],
34
- input_texts: List[str],
30
+ hf_runner: type[HfRunner],
31
+ vllm_runner: type[VllmRunner],
32
+ input_texts: list[str],
33
input_images: PromptImageInput,
34
model: str,
35
*,
tests/models/encoder_decoder/language/test_bart.py
+5
-5
@@ -3,7 +3,7 @@
3
4
Run `pytest tests/models/encoder_decoder/language/test_bart.py`.
5
"""
6
-from typing import List, Optional, Tuple, Type
6
+from typing import Optional
7
8
import pytest
9
from transformers import AutoModelForSeq2SeqLM
@@ -17,7 +17,7 @@ from ...utils import check_logprobs_close
17
18
19
def vllm_to_hf_output(
20
- vllm_output: Tuple[List[int], str, Optional[SampleLogprobs]],
20
+ vllm_output: tuple[list[int], str, Optional[SampleLogprobs]],
21
decoder_prompt_type: DecoderPromptType,
22
):
23
"""Sanitize vllm output to be comparable with hf output."""
@@ -31,9 +31,9 @@ def vllm_to_hf_output(
31
32
33
def run_test(
34
- hf_runner: Type[HfRunner],
35
- vllm_runner: Type[VllmRunner],
36
- prompts: List[ExplicitEncoderDecoderPrompt[str, str]],
34
+ hf_runner: type[HfRunner],
35
+ vllm_runner: type[VllmRunner],
36
+ prompts: list[ExplicitEncoderDecoderPrompt[str, str]],
37
decoder_prompt_type: DecoderPromptType,
38
model: str,
39
*,
tests/models/encoder_decoder/vision_language/test_florence2.py
+4
-4
@@ -1,6 +1,6 @@
1
# SPDX-License-Identifier: Apache-2.0
2
3
-from typing import Optional, Type
3
+from typing import Optional
4
5
import pytest
6
from PIL import Image
@@ -51,8 +51,8 @@ def hf_to_vllm_output(hf_output: tuple[list[int], str,
51
52
53
def run_test(
54
- hf_runner: Type[HfRunner],
55
- vllm_runner: Type[VllmRunner],
54
+ hf_runner: type[HfRunner],
55
+ vllm_runner: type[VllmRunner],
56
inputs: list[list[ExplicitEncoderDecoderPrompt]],
57
model: str,
58
*,
@@ -114,7 +114,7 @@ def run_test(
114
@pytest.mark.parametrize("dtype", ["float"])
115
@pytest.mark.parametrize("max_tokens", [64])
116
@pytest.mark.parametrize("num_logprobs", [5])
117
-def test_models(hf_runner: Type[HfRunner], vllm_runner: Type[VllmRunner],
117
+def test_models(hf_runner: type[HfRunner], vllm_runner: type[VllmRunner],
118
image_assets: _ImageAssets, model: str,
119
size_factors: list[int], dtype: str, max_tokens: int,
120
num_logprobs: int) -> None:
tests/models/encoder_decoder/vision_language/test_mllama.py
+18
-18
@@ -1,6 +1,6 @@
1
# SPDX-License-Identifier: Apache-2.0
2
3
-from typing import List, Optional, Tuple, Type, overload
3
+from typing import Optional, overload
4
5
import pytest
6
import torch
@@ -64,7 +64,7 @@ prompt_data = {
64
}
65
66
67
-def vllm_to_hf_output(vllm_output: Tuple[List[int], str,
67
+def vllm_to_hf_output(vllm_output: tuple[list[int], str,
68
Optional[SampleLogprobs]],
69
model: str):
70
"""Sanitize vllm output to be comparable with hf output."""
@@ -91,9 +91,9 @@ def vllm_to_hf_output(vllm_output: Tuple[List[int], str,
91
def _get_inputs(
92
image_assets: _ImageAssets,
93
*,
94
- size_factors: Optional[List[float]] = None,
95
- sizes: Optional[List[Tuple[int, int]]] = None,
96
-) -> List[Tuple[List[str], PromptImageInput]]:
94
+ size_factors: Optional[list[float]] = None,
95
+ sizes: Optional[list[tuple[int, int]]] = None,
96
+) -> list[tuple[list[str], PromptImageInput]]:
97
images = [asset.pil_image for asset in image_assets]
98
99
if size_factors is not None:
@@ -123,12 +123,12 @@ def _get_inputs(
123
124
@overload
125
def run_test(
126
- hf_runner: Type[HfRunner],
127
- vllm_runner: Type[VllmRunner],
126
+ hf_runner: type[HfRunner],
127
+ vllm_runner: type[VllmRunner],
128
image_assets: _ImageAssets,
129
model: str,
130
*,
131
- size_factors: List[float],
131
+ size_factors: list[float],
132
dtype: str,
133
max_tokens: int,
134
num_logprobs: int,
@@ -140,12 +140,12 @@ def run_test(
140
141
@overload
142
def run_test(
143
- hf_runner: Type[HfRunner],
144
- vllm_runner: Type[VllmRunner],
143
+ hf_runner: type[HfRunner],
144
+ vllm_runner: type[VllmRunner],
145
image_assets: _ImageAssets,
146
model: str,
147
*,
148
- sizes: List[Tuple[int, int]],
148
+ sizes: list[tuple[int, int]],
149
dtype: str,
150
max_tokens: int,
151
num_logprobs: int,
@@ -156,13 +156,13 @@ def run_test(
156
157
158
def run_test(
159
- hf_runner: Type[HfRunner],
160
- vllm_runner: Type[VllmRunner],
159
+ hf_runner: type[HfRunner],
160
+ vllm_runner: type[VllmRunner],
161
image_assets: _ImageAssets,
162
model: str,
163
*,
164
- size_factors: Optional[List[float]] = None,
165
- sizes: Optional[List[Tuple[int, int]]] = None,
164
+ size_factors: Optional[list[float]] = None,
165
+ sizes: Optional[list[tuple[int, int]]] = None,
166
dtype: str,
167
max_tokens: int,
168
num_logprobs: int,
@@ -183,9 +183,9 @@ def run_test(
183
184
185
def _run_test(
186
- hf_runner: Type[HfRunner],
187
- vllm_runner: Type[VllmRunner],
188
- inputs: List[Tuple[List[str], PromptImageInput]],
186
+ hf_runner: type[HfRunner],
187
+ vllm_runner: type[VllmRunner],
188
+ inputs: list[tuple[list[str], PromptImageInput]],
189
model: str,
190
*,
191
dtype: str,
tests/models/multimodal/processing/test_h2ovl.py
+2
-1
@@ -1,6 +1,7 @@
1
# SPDX-License-Identifier: Apache-2.0
2
"""Tests for H2OVL's multimodal preprocessing kwargs."""
3
-from typing import Mapping, Optional
3
+from collections.abc import Mapping
4
+from typing import Optional
5
6
import pytest
7
from PIL import Image
tests/models/multimodal/processing/test_internvl.py
+2
-1
@@ -1,6 +1,7 @@
1
# SPDX-License-Identifier: Apache-2.0
2
"""Tests for InternVL's multimodal preprocessing kwargs."""
3
-from typing import Mapping, Optional
3
+from collections.abc import Mapping
4
+from typing import Optional
5
6
import pytest
7
from PIL import Image
tests/models/registry.py
+3
-2
@@ -1,7 +1,8 @@
1
# SPDX-License-Identifier: Apache-2.0
2
3
+from collections.abc import Mapping, Set
4
from dataclasses import dataclass, field
4
-from typing import AbstractSet, Any, Literal, Mapping, Optional
5
+from typing import Any, Literal, Optional
6
7
import pytest
8
from packaging.version import Version
@@ -324,7 +325,7 @@ class HfExampleModels:
325
326
self.hf_models = hf_models
327
327
- def get_supported_archs(self) -> AbstractSet[str]:
328
+ def get_supported_archs(self) -> Set[str]:
329
return self.hf_models.keys()
330
331
def get_hf_info(self, model_arch: str) -> _HfExamplesInfo:
tests/models/test_transformers.py
+7
-8
@@ -4,7 +4,6 @@
4
Run `pytest tests/models/test_transformers.py`.
5
"""
6
from contextlib import nullcontext
7
-from typing import Type
7
8
import pytest
9
@@ -14,8 +13,8 @@ from .utils import check_logprobs_close
13
14
15
def check_implementation(
17
- hf_runner: Type[HfRunner],
18
- vllm_runner: Type[VllmRunner],
16
+ hf_runner: type[HfRunner],
17
+ vllm_runner: type[VllmRunner],
18
example_prompts: list[str],
19
model: str,
20
**kwargs,
@@ -47,8 +46,8 @@ def check_implementation(
46
("ArthurZ/Ilama-3.2-1B", "auto"), # CUSTOM CODE
47
]) # trust_remote_code=True by default
48
def test_models(
50
- hf_runner: Type[HfRunner],
51
- vllm_runner: Type[VllmRunner],
49
+ hf_runner: type[HfRunner],
50
+ vllm_runner: type[VllmRunner],
51
example_prompts: list[str],
52
model: str,
53
model_impl: str,
@@ -71,8 +70,8 @@ def test_models(
70
71
@multi_gpu_test(num_gpus=2)
72
def test_distributed(
74
- hf_runner: Type[HfRunner],
75
- vllm_runner: Type[VllmRunner],
73
+ hf_runner: type[HfRunner],
74
+ vllm_runner: type[VllmRunner],
75
example_prompts,
76
):
77
kwargs = {"model_impl": "transformers", "tensor_parallel_size": 2}
@@ -92,7 +91,7 @@ def test_distributed(
91
@pytest.mark.parametrize("max_tokens", [32])
92
@pytest.mark.parametrize("num_logprobs", [5])
93
def test_quantization(
95
- vllm_runner: Type[VllmRunner],
94
+ vllm_runner: type[VllmRunner],
95
example_prompts: list[str],
96
model: str,
97
quantization_kwargs: dict[str, str],
tests/models/utils.py
+11
-10
@@ -1,7 +1,8 @@
1
# SPDX-License-Identifier: Apache-2.0
2
3
import warnings
4
-from typing import Dict, List, Optional, Sequence, Tuple, Union
4
+from collections.abc import Sequence
5
+from typing import Optional, Union
6
7
import torch
8
@@ -9,7 +10,7 @@ from vllm.config import ModelConfig, TaskOption
10
from vllm.inputs import InputContext
11
from vllm.sequence import Logprob, PromptLogprobs, SampleLogprobs
12
12
-TokensText = Tuple[List[int], str]
13
+TokensText = tuple[list[int], str]
14
15
16
def check_outputs_equal(
@@ -46,7 +47,7 @@ def check_outputs_equal(
47
# * List of top sample logprobs for each sampled token
48
#
49
# Assumes prompt logprobs were not requested.
49
-TokensTextLogprobs = Tuple[List[int], str, Optional[Union[List[Dict[int,
50
+TokensTextLogprobs = tuple[list[int], str, Optional[Union[list[dict[int,
51
float]],
52
SampleLogprobs]]]
53
@@ -57,8 +58,8 @@ TokensTextLogprobs = Tuple[List[int], str, Optional[Union[List[Dict[int,
58
# * Optional list of top sample logprobs for each sampled token
59
#
60
# Assumes prompt logprobs were not requested.
60
-TextTextLogprobs = Tuple[List[str], str, Optional[Union[List[Dict[str, float]],
61
- List[Dict[str,
61
+TextTextLogprobs = tuple[list[str], str, Optional[Union[list[dict[str, float]],
62
+ list[dict[str,
63
Logprob]]]]]
64
65
# Representation of generated sequence as a tuple of
@@ -68,9 +69,9 @@ TextTextLogprobs = Tuple[List[str], str, Optional[Union[List[Dict[str, float]],
69
# * Optional list of top prompt logprobs for each prompt token
70
#
71
# Allows prompt logprobs to be requested.
71
-TokensTextLogprobsPromptLogprobs = Tuple[
72
- List[int], str, Optional[Union[List[Dict[int, float]], SampleLogprobs]],
73
- Optional[Union[List[Optional[Dict[int, float]]], PromptLogprobs]]]
72
+TokensTextLogprobsPromptLogprobs = tuple[
73
+ list[int], str, Optional[Union[list[dict[int, float]], SampleLogprobs]],
74
+ Optional[Union[list[Optional[dict[int, float]]], PromptLogprobs]]]
75
76
77
def check_logprobs_close(
@@ -254,8 +255,8 @@ def build_model_context(
255
tokenizer_name: Optional[str] = None,
256
trust_remote_code: bool = False,
257
dtype: Optional[Union[str, torch.dtype]] = None,
257
- mm_processor_kwargs: Optional[Dict] = None,
258
- limit_mm_per_prompt: Optional[Dict] = None,
258
+ mm_processor_kwargs: Optional[dict] = None,
259
+ limit_mm_per_prompt: Optional[dict] = None,
260
disable_mm_preprocessor_cache: bool = True,
261
):
262
"""Creates an InputContext for a given model.
tests/mq_llm_engine/utils.py
+2
-2
@@ -2,7 +2,7 @@
2
3
import asyncio
4
import multiprocessing
5
-from typing import Callable, Tuple, Union
5
+from typing import Callable, Union
6
7
from vllm import SamplingParams
8
from vllm.engine.arg_utils import AsyncEngineArgs
@@ -16,7 +16,7 @@ async def generate(
16
client: MQLLMEngineClient,
17
request_id: str,
18
num_tokens: int,
19
- return_output: bool = False) -> Union[RequestOutput, Tuple[int, str]]:
19
+ return_output: bool = False) -> Union[RequestOutput, tuple[int, str]]:
20
21
final_output = None
22
count = 0
tests/multi_step/test_correctness_async_llm.py
+2
-2
@@ -1,7 +1,7 @@
1
# SPDX-License-Identifier: Apache-2.0
2
3
# Test the AsyncLLMEngine with multi-step-decoding
4
-from typing import List, Optional
4
+from typing import Optional
5
6
import pytest
7
@@ -17,7 +17,7 @@ MODELS = [
17
NUM_SCHEDULER_STEPS = [8] # Multi-step decoding steps
18
NUM_PROMPTS = [10]
19
20
-DEFAULT_SERVER_ARGS: List[str] = [
20
+DEFAULT_SERVER_ARGS: list[str] = [
21
"--distributed-executor-backend",
22
"ray",
23
"--gpu-memory-utilization",
tests/multimodal/test_utils.py
+4
-4
@@ -4,7 +4,7 @@ import base64
4
import mimetypes
5
import os
6
from tempfile import NamedTemporaryFile, TemporaryDirectory
7
-from typing import TYPE_CHECKING, Dict, NamedTuple, Optional, Tuple
7
+from typing import TYPE_CHECKING, NamedTuple, Optional
8
9
import numpy as np
10
import pytest
@@ -30,7 +30,7 @@ TEST_IMAGE_URLS = [
30
31
32
@pytest.fixture(scope="module")
33
-def url_images() -> Dict[str, Image.Image]:
33
+def url_images() -> dict[str, Image.Image]:
34
connector = MediaConnector()
35
36
return {
@@ -39,7 +39,7 @@ def url_images() -> Dict[str, Image.Image]:
39
}
40
41
42
-def get_supported_suffixes() -> Tuple[str, ...]:
42
+def get_supported_suffixes() -> tuple[str, ...]:
43
# We should at least test the file types mentioned in GPT-4 with Vision
44
OPENAI_SUPPORTED_SUFFIXES = ('.png', '.jpeg', '.jpg', '.webp', '.gif')
45
@@ -66,7 +66,7 @@ async def test_fetch_image_http(image_url: str):
66
@pytest.mark.asyncio
67
@pytest.mark.parametrize("image_url", TEST_IMAGE_URLS)
68
@pytest.mark.parametrize("suffix", get_supported_suffixes())
69
-async def test_fetch_image_base64(url_images: Dict[str, Image.Image],
69
+async def test_fetch_image_base64(url_images: dict[str, Image.Image],
70
image_url: str, suffix: str):
71
connector = MediaConnector()
72
url_image = url_images[image_url]
tests/neuron/test_logits_processor.py
+1
-2
@@ -1,7 +1,6 @@
1
# SPDX-License-Identifier: Apache-2.0
2
3
import random
4
-from typing import Tuple
4
from unittest.mock import patch
5
6
import pytest
@@ -33,7 +32,7 @@ class MockLogitsProcessor(LogitsProcessor):
32
33
def _prepare_test(
34
batch_size: int
36
-) -> Tuple[torch.Tensor, torch.Tensor, MockLogitsProcessor]:
35
+) -> tuple[torch.Tensor, torch.Tensor, MockLogitsProcessor]:
36
vocab_size = 32000
37
input_tensor = torch.rand((batch_size, 1024), dtype=torch.float16)
38
fake_logits = torch.full((batch_size, vocab_size),
tests/plugins/vllm_add_dummy_model/vllm_add_dummy_model/my_gemma_embedding.py
+3
-2
@@ -1,6 +1,7 @@
1
# SPDX-License-Identifier: Apache-2.0
2
3
-from typing import Iterable, Optional, Tuple, Union
3
+from collections.abc import Iterable
4
+from typing import Optional, Union
5
6
import torch
7
import torch.nn as nn
@@ -59,7 +60,7 @@ class MyGemma2Embedding(nn.Module):
60
) -> Optional[PoolerOutput]:
61
return self._pooler(hidden_states, pooling_metadata)
62
62
- def load_weights(self, weights: Iterable[Tuple[str, torch.Tensor]]):
63
+ def load_weights(self, weights: Iterable[tuple[str, torch.Tensor]]):
64
65
weights = self.hf_to_vllm_mapper.apply(weights)
66
weights = ((name, data) for name, data in weights
tests/quantization/test_configs.py
+1
-2
@@ -5,7 +5,6 @@ Run `pytest tests/quantization/test_configs.py --forked`.
5
"""
6
7
from dataclasses import dataclass
8
-from typing import Tuple
8
9
import pytest
10
@@ -53,7 +52,7 @@ MODEL_ARG_EXPTYPES = [
52
53
54
@pytest.mark.parametrize("model_arg_exptype", MODEL_ARG_EXPTYPES)
56
-def test_auto_gptq(model_arg_exptype: Tuple[str, None, str]) -> None:
55
+def test_auto_gptq(model_arg_exptype: tuple[str, None, str]) -> None:
56
model_path, quantization_arg, expected_type = model_arg_exptype
57
58
try:
tests/quantization/test_register_quantization_config.py
+4
-4
@@ -5,7 +5,7 @@ See https://github.com/vllm-project/vllm/issues/11926 for more details.
5
6
Run `pytest tests/quantization/test_register_quantization_config.py`.
7
"""
8
-from typing import Any, Dict, List, Optional
8
+from typing import Any, Optional
9
10
import pytest
11
import torch
@@ -58,7 +58,7 @@ class CustomQuantConfig(QuantizationConfig):
58
"""Name of the quantization method."""
59
return "custom_quant"
60
61
- def get_supported_act_dtypes(self) -> List["torch.dtype"]:
61
+ def get_supported_act_dtypes(self) -> list["torch.dtype"]:
62
"""List of supported activation dtypes."""
63
return [torch.float16, torch.bfloat16]
64
@@ -68,12 +68,12 @@ class CustomQuantConfig(QuantizationConfig):
68
return -1
69
70
@staticmethod
71
- def get_config_filenames() -> List[str]:
71
+ def get_config_filenames() -> list[str]:
72
"""List of filenames to search for in the model directory."""
73
return []
74
75
@classmethod
76
- def from_config(cls, config: Dict[str, Any]) -> "CustomQuantConfig":
76
+ def from_config(cls, config: dict[str, Any]) -> "CustomQuantConfig":
77
"""Create a config class from the model's quantization config."""
78
return CustomQuantConfig(num_bits=config.get("num_bits", 8))
79
tests/samplers/test_logprobs.py
+1
-3
@@ -1,7 +1,5 @@
1
# SPDX-License-Identifier: Apache-2.0
2
3
-from typing import List
4
-
3
import pytest
4
import torch
5
@@ -70,7 +68,7 @@ def test_get_prompt_logprobs(
68
assert (len(logprobs) == num_top_logprobs
69
or len(logprobs) == num_top_logprobs + 1)
70
output_text = result.outputs[0].text
73
- output_string_from_most_likely_tokens_lst: List[str] = []
71
+ output_string_from_most_likely_tokens_lst: list[str] = []
72
for top_logprobs in result.outputs[0].logprobs:
73
top_logprob = next(iter(top_logprobs.values()))
74
output_string_from_most_likely_tokens_lst.append(
tests/samplers/test_no_bad_words.py
+8
-8
@@ -4,7 +4,7 @@
4
Run `pytest tests/samplers/test_no_bad_words.py`.
5
6
"""
7
-from typing import List, Optional
7
+from typing import Optional
8
9
from transformers import AutoTokenizer
10
@@ -16,8 +16,8 @@ def _generate(
16
prompt: str,
17
num_prompt_tokens: int,
18
temperature: float = 0,
19
- bad_words: Optional[List[str]] = None,
20
-) -> List[int]:
19
+ bad_words: Optional[list[str]] = None,
20
+) -> list[int]:
21
sampling_params = SamplingParams(
22
temperature=temperature,
23
bad_words=bad_words,
@@ -59,7 +59,7 @@ class TestOneTokenBadWord:
59
60
def _generate(self,
61
model: LLM,
62
- bad_words: Optional[List[str]] = None) -> List[int]:
62
+ bad_words: Optional[list[str]] = None) -> list[int]:
63
return _generate(
64
model=model,
65
prompt=self.PROMPT,
@@ -69,7 +69,7 @@ class TestOneTokenBadWord:
69
70
def _encode(self,
71
prompt: str,
72
- add_special_tokens: bool = True) -> List[int]:
72
+ add_special_tokens: bool = True) -> list[int]:
73
return self.tokenizer(prompt,
74
add_special_tokens=add_special_tokens).input_ids
75
@@ -149,7 +149,7 @@ class TestTwoTokenBadWord:
149
150
def _generate(self,
151
model: LLM,
152
- bad_words: Optional[List[str]] = None) -> List[int]:
152
+ bad_words: Optional[list[str]] = None) -> list[int]:
153
return _generate(
154
model=model,
155
prompt=self.PROMPT,
@@ -158,7 +158,7 @@ class TestTwoTokenBadWord:
158
)
159
160
@staticmethod
161
- def _contains(sequence: List[int], subsequence: List[int]) -> bool:
161
+ def _contains(sequence: list[int], subsequence: list[int]) -> bool:
162
searched = False
163
164
for start in range(len(sequence)):
@@ -181,6 +181,6 @@ class TestTwoTokenBadWord:
181
182
def _encode(self,
183
prompt: str,
184
- add_special_tokens: bool = True) -> List[int]:
184
+ add_special_tokens: bool = True) -> list[int]:
185
return self.tokenizer(prompt,
186
add_special_tokens=add_special_tokens).input_ids
tests/samplers/test_rejection_sampler.py
+5
-6
@@ -1,6 +1,5 @@
1
# SPDX-License-Identifier: Apache-2.0
2
"""Tests for rejection sampling."""
3
-from typing import List, Tuple
3
4
import pytest
5
import torch
@@ -416,8 +415,8 @@ def test_rejection_sampling_approximates_target_distribution(
415
draft_and_target_probs_equal)
416
417
sample_sizes = [10, 100, 1_000, 10_000, 100_000]
419
- distance_wrt_reference: List[float] = []
420
- distance_wrt_target: List[float] = []
418
+ distance_wrt_reference: list[float] = []
419
+ distance_wrt_target: list[float] = []
420
421
for num_samples in sample_sizes:
422
(reference_vs_rejsample_dist,
@@ -452,7 +451,7 @@ def test_rejection_sampling_approximates_target_distribution(
451
expected_improvement_multiplier)
452
453
455
-def get_ratio_first_to_last(elements: List[float]) -> float:
454
+def get_ratio_first_to_last(elements: list[float]) -> float:
455
return elements[0] / elements[-1]
456
457
@@ -477,7 +476,7 @@ class _CorrectnessTestHelper:
476
477
def generate_probs_for_test(
478
self, draft_and_target_probs_equal: bool
480
- ) -> Tuple[torch.Tensor, torch.Tensor, torch.Tensor]:
479
+ ) -> tuple[torch.Tensor, torch.Tensor, torch.Tensor]:
480
draft_probs, target_probs = (F.softmax(
481
torch.rand(self.vocab_size, dtype=torch.float32),
482
dim=-1,
@@ -499,7 +498,7 @@ class _CorrectnessTestHelper:
498
def run_and_compare_distributions(self, draft_probs: torch.Tensor,
499
target_probs: torch.Tensor,
500
reference_probs: torch.Tensor,
502
- num_samples: int) -> Tuple[float, float]:
501
+ num_samples: int) -> tuple[float, float]:
502
# Sample using rejection sampling.
503
rej_sample_probs = self._estimate_rejection_sampling_pdf(
504
draft_probs, target_probs, num_samples)
tests/samplers/test_sampler.py
+22
-22
@@ -3,7 +3,7 @@
3
import itertools
4
import random
5
from dataclasses import dataclass
6
-from typing import Dict, List, Optional, Tuple
6
+from typing import Optional
7
from unittest.mock import Mock, patch
8
9
import pytest
@@ -30,7 +30,7 @@ class MockLogitsSampler(Sampler):
30
31
def _prepare_test(
32
batch_size: int
33
-) -> Tuple[torch.Tensor, torch.Tensor, MockLogitsSampler]:
33
+) -> tuple[torch.Tensor, torch.Tensor, MockLogitsSampler]:
34
input_tensor = torch.rand((batch_size, 1024), dtype=torch.float16)
35
fake_logits = torch.full((batch_size, VOCAB_SIZE),
36
1e-2,
@@ -53,8 +53,8 @@ def _do_sample(
53
sampling_params: SamplingParams,
54
device: str,
55
):
56
- seq_group_metadata_list: List[SequenceGroupMetadata] = []
57
- seq_lens: List[int] = []
56
+ seq_group_metadata_list: list[SequenceGroupMetadata] = []
57
+ seq_lens: list[int] = []
58
for i in range(batch_size):
59
seq_group_metadata_list.append(
60
SequenceGroupMetadata(
@@ -171,7 +171,7 @@ def test_sampler_min_tokens_penalty(seed: int, device: str):
171
def create_sampling_params(min_tokens,
172
eos_token_id=0,
173
*,
174
- stop_token_ids: Optional[List[int]] = None,
174
+ stop_token_ids: Optional[list[int]] = None,
175
prompt_logprobs: Optional[int] = None):
176
sampling_params = SamplingParams(
177
min_tokens=min_tokens,
@@ -196,7 +196,7 @@ def test_sampler_min_tokens_penalty(seed: int, device: str):
196
batch_size = random.randint(1, 128)
197
198
expected_penalization = []
199
- sequence_metadata_list: List[SequenceGroupMetadata] = []
199
+ sequence_metadata_list: list[SequenceGroupMetadata] = []
200
# 20% chance to generate seq group metadata list with all prompts
201
is_prompt = random.random() < 0.2
202
while batch_size > 0:
@@ -216,8 +216,8 @@ def test_sampler_min_tokens_penalty(seed: int, device: str):
216
eos_token_id=eos_token_id,
217
stop_token_ids=stop_token_ids)
218
219
- seq_data: Dict[int, SequenceData] = {}
220
- seq_group_penalization: List[bool] = []
219
+ seq_data: dict[int, SequenceData] = {}
220
+ seq_group_penalization: list[bool] = []
221
for _ in range(num_seqs):
222
num_input = random.randint(1, 100)
223
num_generated = 0 if is_prompt else random.randint(1, 100)
@@ -376,16 +376,16 @@ def test_sampler_min_tokens_penalty(seed: int, device: str):
376
else:
377
test_cases = [generate_test_case()]
378
379
- def run_test_case(*, expected_penalization: List[bool],
380
- seq_group_metadata_list: List[SequenceGroupMetadata]):
379
+ def run_test_case(*, expected_penalization: list[bool],
380
+ seq_group_metadata_list: list[SequenceGroupMetadata]):
381
assert expected_penalization, \
382
"Invalid test case, need expected_penalization"
383
assert seq_group_metadata_list, \
384
"Invalid test case, need seq_group_metadata_list"
385
386
batch_size = 0
387
- seq_lens: List[int] = []
388
- sampling_params_per_row: List[SamplingParams] = []
387
+ seq_lens: list[int] = []
388
+ sampling_params_per_row: list[SamplingParams] = []
389
for sgm in seq_group_metadata_list:
390
sampling_params = sgm.sampling_params
391
@@ -456,11 +456,11 @@ def test_sampler_mixed(seed: int, device: str):
456
batch_size = random.randint(1, 256)
457
input_tensor, fake_logits, sampler = _prepare_test(batch_size)
458
459
- seq_group_metadata_list: List[SequenceGroupMetadata] = []
460
- expected_tokens: List[Optional[List[int]]] = []
461
- seq_lens: List[int] = []
459
+ seq_group_metadata_list: list[SequenceGroupMetadata] = []
460
+ expected_tokens: list[Optional[list[int]]] = []
461
+ seq_lens: list[int] = []
462
for i in range(batch_size):
463
- expected: Optional[List[int]] = None
463
+ expected: Optional[list[int]] = None
464
sampling_type = random.randint(0, 2)
465
if sampling_type == 0:
466
sampling_params = SamplingParams(temperature=0)
@@ -492,7 +492,7 @@ def test_sampler_mixed(seed: int, device: str):
492
))
493
seq_lens.append(seq_group_metadata_list[-1].seq_data[0].get_len())
494
495
- generators: Dict[str, torch.Generator] = {}
495
+ generators: dict[str, torch.Generator] = {}
496
497
def test_sampling():
498
sampling_metadata = SamplingMetadata.prepare(
@@ -587,8 +587,8 @@ def test_sampler_top_k_top_p(seed: int, device: str):
587
device=device)
588
assert len(processors) == 2 # top_p and top_k
589
590
- seq_group_metadata_list: List[SequenceGroupMetadata] = []
591
- seq_lens: List[int] = []
590
+ seq_group_metadata_list: list[SequenceGroupMetadata] = []
591
+ seq_lens: list[int] = []
592
for i in range(batch_size):
593
seq_group_metadata_list.append(
594
SequenceGroupMetadata(
@@ -669,10 +669,10 @@ def test_sampler_repetition_penalty_mixed(device: str):
669
670
vocab_size = 8
671
672
- def test_sampling_params(sampling_params: List[SamplingParams]):
672
+ def test_sampling_params(sampling_params: list[SamplingParams]):
673
674
- seq_group_metadata_list: List[SequenceGroupMetadata] = []
675
- seq_lens: List[int] = []
674
+ seq_group_metadata_list: list[SequenceGroupMetadata] = []
675
+ seq_lens: list[int] = []
676
for i in range(2):
677
seq_group_metadata_list.append(
678
SequenceGroupMetadata(
tests/spec_decode/e2e/conftest.py
+5
-4
@@ -1,7 +1,8 @@
1
# SPDX-License-Identifier: Apache-2.0
2
3
+from collections.abc import Sequence
4
from itertools import cycle
4
-from typing import List, Optional, Sequence, Tuple, Union
5
+from typing import Optional, Union
6
7
import pytest
8
import torch
@@ -64,9 +65,9 @@ def maybe_assert_ngram_worker(llm):
65
66
def get_output_from_llm_generator(
67
llm_generator, prompts,
67
- sampling_params) -> Tuple[List[str], List[List[int]], float]:
68
- tokens: List[str] = []
69
- token_ids: List[List[int]] = []
68
+ sampling_params) -> tuple[list[str], list[list[int]], float]:
69
+ tokens: list[str] = []
70
+ token_ids: list[list[int]] = []
71
acceptance_rate: float = -1.0
72
for llm in llm_generator():
73
maybe_assert_ngram_worker(llm)
tests/spec_decode/test_batch_expansion.py
+1
-3
@@ -1,7 +1,5 @@
1
# SPDX-License-Identifier: Apache-2.0
2
3
-from typing import List
4
-
3
import pytest
4
import torch
5
@@ -42,7 +40,7 @@ def test_get_token_ids_to_score(k: int):
40
device='cuda',
41
)
42
45
- expected_output: List[List[int]] = [
43
+ expected_output: list[list[int]] = [
44
[],
45
]
46
for i in range(proposal_token_ids.shape[0]):
tests/spec_decode/test_multi_step_worker.py
+7
-8
@@ -1,7 +1,6 @@
1
# SPDX-License-Identifier: Apache-2.0
2
3
import random
4
-from typing import Dict, List
4
from unittest.mock import MagicMock
5
6
import pytest
@@ -221,7 +220,7 @@ def test_same_output_for_multi_step():
220
221
# Run single-step repeatedly.
222
zero_kv_cache(worker.cache_engine)
224
- single_step_output: List[SamplerOutput] = []
223
+ single_step_output: list[SamplerOutput] = []
224
continuations = [[1] for _ in prompts]
225
set_random_seed(seed)
226
@@ -243,15 +242,15 @@ def test_same_output_for_multi_step():
242
continuations[i].append(seq_group_output.samples[0].output_token)
243
244
# Get token ids and logprobs for comparison.
246
- multi_step_output_logprobs: List[List[Dict[int,
245
+ multi_step_output_logprobs: list[list[dict[int,
246
Logprob]]] = [[]
247
for _ in prompts]
249
- single_step_output_logprobs: List[List[Dict[int,
248
+ single_step_output_logprobs: list[list[dict[int,
249
Logprob]]] = [[]
250
for _ in prompts]
251
253
- multi_step_output_token_ids: List[List[int]] = [[] for _ in prompts]
254
- single_step_output_token_ids: List[List[int]] = [[] for _ in prompts]
252
+ multi_step_output_token_ids: list[list[int]] = [[] for _ in prompts]
253
+ single_step_output_token_ids: list[list[int]] = [[] for _ in prompts]
254
for i, _ in enumerate(prompts):
255
for multi_step, single_step in zip(multi_step_output,
256
single_step_output):
@@ -336,7 +335,7 @@ def test_multi_step_with_batch_expansion_correct_output():
335
# will simulate the bonus token case with the second token
336
# being the bonus token.
337
zero_kv_cache(worker.cache_engine)
339
- single_step_output: List[SamplerOutput] = []
338
+ single_step_output: list[SamplerOutput] = []
339
set_random_seed(seed)
340
for _ in range(num_steps):
341
seq_group_metadata_list = create_seq_group_metadata_from_prompts(
@@ -430,7 +429,7 @@ def test_multi_step_with_batch_expansion_incorrect_output():
429
# will simulate the bonus token case with the second token
430
# being the bonus token.
431
zero_kv_cache(worker.cache_engine)
433
- single_step_output: List[SamplerOutput] = []
432
+ single_step_output: list[SamplerOutput] = []
433
set_random_seed(seed)
434
for _ in range(num_steps):
435
seq_group_metadata_list = create_seq_group_metadata_from_prompts(
tests/spec_decode/test_scorer.py
+1
-2
@@ -1,7 +1,6 @@
1
# SPDX-License-Identifier: Apache-2.0
2
3
import random
4
-from typing import List
4
5
import pytest
6
import torch
@@ -15,7 +14,7 @@ from vllm.worker.worker import Worker
14
from .utils import create_batch, create_worker
15
16
18
-def create_proposal(propose_lens: List[int], vocab_size: int,
17
+def create_proposal(propose_lens: list[int], vocab_size: int,
18
device: str) -> SpeculativeProposals:
19
batch_size = len(propose_lens)
20
max_propose_len = max(propose_lens)
tests/spec_decode/test_spec_decode_worker.py
+5
-6
@@ -3,7 +3,6 @@
3
import random
4
from collections import defaultdict
5
from types import SimpleNamespace
6
-from typing import Dict, List, Set
6
from unittest.mock import MagicMock
7
8
import pytest
@@ -123,7 +122,7 @@ def test_batch_expansion_correctly_calls_target_model(
122
seq_group_metadata_list=seq_group_metadata_list,
123
num_lookahead_slots=k))
124
126
- seen_contexts: List[List[int]] = []
125
+ seen_contexts: list[list[int]] = []
126
127
call_args_list = target_worker.execute_model.call_args_list
128
assert len(call_args_list) == 1
@@ -136,7 +135,7 @@ def test_batch_expansion_correctly_calls_target_model(
135
for seq_data in seq_group_metadata.seq_data.values():
136
seen_contexts.append(seq_data.get_token_ids())
137
139
- expected_seen_contexts: List[List[int]] = []
138
+ expected_seen_contexts: list[list[int]] = []
139
140
for prompt, prev_generated, draft_tokens in zip(
141
prompts, prev_output_tokens, proposal_token_ids.tolist()):
@@ -338,11 +337,11 @@ def test_correctly_formats_output(k: int, batch_size: int,
337
next(iter(seq_group_metadata.seq_data.keys()))
338
for seq_group_metadata in seq_group_metadata_list
339
]
341
- actual_output_by_seq: Dict[int, List[SequenceOutput]] = {
340
+ actual_output_by_seq: dict[int, list[SequenceOutput]] = {
341
seq_id: []
342
for seq_id in seq_ids
343
}
345
- expected_output_by_seq: Dict[int, List[SequenceOutput]] = {
344
+ expected_output_by_seq: dict[int, list[SequenceOutput]] = {
345
seq_id: []
346
for seq_id in seq_ids
347
}
@@ -728,7 +727,7 @@ def test_populate_seq_ids_with_bonus_tokens():
727
size=(batch_size, (k + 1)),
728
dtype=torch.int64,
729
device='cuda')
731
- expected_request_id_seq_ids_mapping: Dict[str, Set[int]] = defaultdict(set)
730
+ expected_request_id_seq_ids_mapping: dict[str, set[int]] = defaultdict(set)
731
for seq_group_metadata in seq_group_metadata_list:
732
for seq_id in seq_group_metadata.seq_data:
733
expected_request_id_seq_ids_mapping[
tests/spec_decode/utils.py
+16
-17
@@ -1,9 +1,8 @@
1
# SPDX-License-Identifier: Apache-2.0
2
3
+from collections.abc import Sequence as GenericSequence
4
from itertools import count
4
-from typing import Callable, Dict, List, Optional
5
-from typing import Sequence as GenericSequence
6
-from typing import TypeVar, Union
5
+from typing import Callable, Optional, TypeVar, Union
6
from unittest.mock import MagicMock
7
8
import torch
@@ -44,7 +43,7 @@ def mock_worker(cls=None,
43
return worker
44
45
47
-def patch_execute_model_with_seeds(worker: Worker, rand_seeds: List[int]):
46
+def patch_execute_model_with_seeds(worker: Worker, rand_seeds: list[int]):
47
seed_iter = iter(rand_seeds)
48
original_execute_model = worker.execute_model
49
@@ -56,7 +55,7 @@ def patch_execute_model_with_seeds(worker: Worker, rand_seeds: List[int]):
55
return new_execute_model
56
57
59
-def zero_kv_cache(cache_engine: List[CacheEngine]):
58
+def zero_kv_cache(cache_engine: list[CacheEngine]):
59
assert cache_engine[0].gpu_cache
60
for key_blocks, value_blocks in cache_engine[0].gpu_cache:
61
key_blocks.zero_()
@@ -106,13 +105,13 @@ def create_worker(cls: Callable[..., T],
105
106
107
def create_seq_group_metadata_from_prompts(
109
- prompts: List[List[int]],
108
+ prompts: list[list[int]],
109
num_gpu_blocks: int,
110
block_size: int,
112
- final_prompt_lens: List[int],
113
- continuations: Optional[List[List[int]]] = None,
114
- seq_ids: Optional[List[int]] = None,
115
-) -> List[SequenceGroupMetadata]:
111
+ final_prompt_lens: list[int],
112
+ continuations: Optional[list[list[int]]] = None,
113
+ seq_ids: Optional[list[int]] = None,
114
+) -> list[SequenceGroupMetadata]:
115
116
if continuations is None:
117
continuations = [[] for _ in prompts]
@@ -149,11 +148,11 @@ def create_seq_group_metadata_from_prompts(
148
149
150
def create_chunked_seq_group_metadata_from_prompt(
152
- prompt: List[int],
151
+ prompt: list[int],
152
num_gpu_blocks: int,
153
chunk_size: int,
154
block_size: int,
156
- seq_id: Optional[int] = None) -> List[SequenceGroupMetadata]:
155
+ seq_id: Optional[int] = None) -> list[SequenceGroupMetadata]:
156
157
if seq_id is None:
158
seq_id = 0
@@ -184,8 +183,8 @@ def create_chunked_seq_group_metadata_from_prompt(
183
184
185
def assert_logprobs_dict_allclose(
187
- actual_logprobs: List[Dict[int, Logprob]],
188
- expected_logprobs: List[Dict[int, Logprob]]) -> None:
186
+ actual_logprobs: list[dict[int, Logprob]],
187
+ expected_logprobs: list[dict[int, Logprob]]) -> None:
188
for single_step_actual_logprobs, single_step_expected_logprobs in zip(
189
actual_logprobs, expected_logprobs):
190
assert set(single_step_actual_logprobs.keys()) == set(
@@ -202,7 +201,7 @@ def create_sampler_output_list(
201
token_ids: torch.Tensor,
202
probs: GenericSequence[Optional[torch.Tensor]],
203
logprobs: GenericSequence[Optional[torch.Tensor]],
205
- seq_ids: Optional[List[int]] = None) -> List[SamplerOutput]:
204
+ seq_ids: Optional[list[int]] = None) -> list[SamplerOutput]:
205
num_steps, batch_size = token_ids.shape
206
token_ids_by_step = token_ids.tolist()
207
@@ -231,9 +230,9 @@ def create_sampler_output_list(
230
231
def create_batch(batch_size,
232
k,
234
- prompt_len: Union[int, List[int]] = 10,
233
+ prompt_len: Union[int, list[int]] = 10,
234
prev_output_token_len: int = 10,
236
- seq_ids: Optional[List[int]] = None,
235
+ seq_ids: Optional[list[int]] = None,
236
num_gpu_blocks: Optional[int] = None,
237
block_size: Optional[int] = None,
238
prefill_chunk_size: Optional[int] = None):
tests/test_cache_block_hashing.py
+3
-3
@@ -3,7 +3,7 @@
3
4
Run `pytest tests/test_cache_block_hashing.py`.
5
"""
6
-from typing import List, Optional
6
+from typing import Optional
7
8
import pytest
9
@@ -44,7 +44,7 @@ def flatten_2d(li):
44
@pytest.mark.parametrize("concurrent_lora_int_ids",
45
[[None], [1], [None, 1], [None, 1, 2], [1, 2]])
46
def test_auto_prefix_caching(model: str, block_size: int, max_num_seqs: int,
47
- concurrent_lora_int_ids: List[Optional[int]]):
47
+ concurrent_lora_int_ids: list[Optional[int]]):
48
49
tokenizer = TokenizerGroup(
50
tokenizer_id="facebook/opt-125m",
@@ -53,7 +53,7 @@ def test_auto_prefix_caching(model: str, block_size: int, max_num_seqs: int,
53
max_input_length=None,
54
)
55
56
- hashes: List[List[List[int]]] = []
56
+ hashes: list[list[list[int]]] = []
57
58
for prefix in prefixes:
59
for lora_int_id in concurrent_lora_int_ids:
tests/test_inputs.py
+1
-3
@@ -1,7 +1,5 @@
1
# SPDX-License-Identifier: Apache-2.0
2
3
-from typing import List
4
-
3
import pytest
4
5
from vllm.inputs import zip_enc_dec_prompts
@@ -45,7 +43,7 @@ def test_parse_single_batch_string_consistent(string_input: str):
43
44
45
@pytest.mark.parametrize('token_input', TOKEN_INPUTS)
48
-def test_parse_single_batch_token_consistent(token_input: List[int]):
46
+def test_parse_single_batch_token_consistent(token_input: list[int]):
47
assert parse_and_batch_prompt(token_input) \
48
== parse_and_batch_prompt([token_input])
49
tests/test_logger.py
+1
-1
@@ -155,7 +155,7 @@ def test_an_error_is_raised_when_custom_logging_config_is_unexpected_json(
155
with pytest.raises(ValueError) as ex_info:
156
_configure_vllm_root_logger()
157
assert ex_info.type == ValueError # noqa: E721
158
- assert "Invalid logging config. Expected Dict, got" in str(ex_info)
158
+ assert "Invalid logging config. Expected dict, got" in str(ex_info)
159
160
161
@patch("vllm.logger.VLLM_CONFIGURE_LOGGING", 1)
tests/test_logits_processor.py
+1
-2
@@ -1,7 +1,6 @@
1
# SPDX-License-Identifier: Apache-2.0
2
3
import random
4
-from typing import Tuple
4
from unittest.mock import patch
5
6
import pytest
@@ -33,7 +32,7 @@ class MockLogitsProcessor(LogitsProcessor):
32
33
def _prepare_test(
34
batch_size: int
36
-) -> Tuple[torch.Tensor, torch.Tensor, MockLogitsProcessor]:
35
+) -> tuple[torch.Tensor, torch.Tensor, MockLogitsProcessor]:
36
vocab_size = 32000
37
input_tensor = torch.rand((batch_size, 1024), dtype=torch.float16)
38
fake_logits = torch.full((batch_size, vocab_size),
tests/test_utils.py
+2
-2
@@ -3,7 +3,7 @@
3
import asyncio
4
import os
5
import socket
6
-from typing import AsyncIterator, Tuple
6
+from collections.abc import AsyncIterator
7
from unittest.mock import patch
8
9
import pytest
@@ -33,7 +33,7 @@ async def test_merge_async_iterators():
33
iterators = [mock_async_iterator(i) for i in range(3)]
34
merged_iterator = merge_async_iterators(*iterators)
35
36
- async def stream_output(generator: AsyncIterator[Tuple[int, str]]):
36
+ async def stream_output(generator: AsyncIterator[tuple[int, str]]):
37
async for idx, output in generator:
38
print(f"idx: {idx}, output: {output}")
39
tests/tokenization/test_detokenize.py
+12
-11
@@ -1,6 +1,7 @@
1
# SPDX-License-Identifier: Apache-2.0
2
3
-from typing import Any, Dict, Generator, List, Optional
3
+from collections.abc import Generator
4
+from typing import Any, Optional
5
6
import pytest
7
from transformers import AutoTokenizer
@@ -163,7 +164,7 @@ def detokenizer(tokenizer_name: str) -> Detokenizer:
164
165
@pytest.fixture(name="complete_sequence_token_ids")
166
def create_complete_sequence_token_ids(complete_sequence: str,
166
- tokenizer) -> List[int]:
167
+ tokenizer) -> list[int]:
168
complete_sequence_token_ids = tokenizer(complete_sequence).input_ids
169
return complete_sequence_token_ids
170
@@ -178,7 +179,7 @@ def create_sequence(prompt_token_ids=None):
179
180
181
def create_dummy_logprobs(
181
- complete_sequence_token_ids: List[int]) -> List[Dict[int, Logprob]]:
182
+ complete_sequence_token_ids: list[int]) -> list[dict[int, Logprob]]:
183
return [{
184
token_id: Logprob(logprob=0.0),
185
token_id + 1: Logprob(logprob=0.1)
@@ -186,10 +187,10 @@ def create_dummy_logprobs(
187
188
189
def create_dummy_prompt_logprobs(
189
- complete_sequence_token_ids: List[int]
190
-) -> List[Optional[Dict[int, Any]]]:
190
+ complete_sequence_token_ids: list[int]
191
+) -> list[Optional[dict[int, Any]]]:
192
# logprob for the first prompt token is None.
192
- logprobs: List[Optional[Dict[int, Any]]] = [None]
193
+ logprobs: list[Optional[dict[int, Any]]] = [None]
194
logprobs.extend(create_dummy_logprobs(complete_sequence_token_ids)[1:])
195
return logprobs
196
@@ -198,7 +199,7 @@ def create_dummy_prompt_logprobs(
199
@pytest.mark.parametrize("tokenizer_name", TOKENIZERS)
200
@pytest.mark.parametrize("skip_special_tokens", [True, False], indirect=True)
201
def test_decode_sequence_logprobs(complete_sequence: str,
201
- complete_sequence_token_ids: List[int],
202
+ complete_sequence_token_ids: list[int],
203
detokenizer: Detokenizer,
204
skip_special_tokens: bool):
205
"""Verify Detokenizer decodes logprobs correctly."""
@@ -208,8 +209,8 @@ def test_decode_sequence_logprobs(complete_sequence: str,
209
# Run sequentially.
210
seq = create_sequence()
211
dummy_logprobs = create_dummy_logprobs(complete_sequence_token_ids)
211
- sequential_logprobs_text_chosen_token: List[str] = []
212
- sequential_logprobs_text_other_token: List[str] = []
212
+ sequential_logprobs_text_chosen_token: list[str] = []
213
+ sequential_logprobs_text_other_token: list[str] = []
214
for new_token, logprobs in zip(complete_sequence_token_ids,
215
dummy_logprobs):
216
seq.append_token_id(new_token, logprobs)
@@ -232,7 +233,7 @@ def test_decode_sequence_logprobs(complete_sequence: str,
233
234
@pytest.mark.parametrize("complete_sequence", TRUTH)
235
@pytest.mark.parametrize("tokenizer_name", TOKENIZERS)
235
-def test_decode_prompt_logprobs(complete_sequence_token_ids: List[int],
236
+def test_decode_prompt_logprobs(complete_sequence_token_ids: list[int],
237
detokenizer: Detokenizer):
238
"""Verify Detokenizer decodes prompt logprobs correctly."""
239
sampling_params = SamplingParams(skip_special_tokens=True,
@@ -249,7 +250,7 @@ def test_decode_prompt_logprobs(complete_sequence_token_ids: List[int],
250
dummy_logprobs,
251
position_offset=0)
252
# First logprob is None.
252
- decoded_prompt_logprobs: List[Dict[int, Any]] = dummy_logprobs[
253
+ decoded_prompt_logprobs: list[dict[int, Any]] = dummy_logprobs[
254
1:] # type: ignore
255
256
# decoded_prompt_logprobs doesn't contain the first token.
tests/tokenization/test_tokenizer_group.py
+2
-2
@@ -3,7 +3,7 @@
3
import asyncio
4
import os
5
import sys
6
-from typing import List, Optional
6
+from typing import Optional
7
from unittest.mock import patch
8
9
import pytest
@@ -129,7 +129,7 @@ async def test_tokenizer_group_ray_pool_fault_tolerance(tokenizer_group_type):
129
130
def __init__(self,
131
*args,
132
- fail_at: Optional[List[int]] = None,
132
+ fail_at: Optional[list[int]] = None,
133
**kwargs):
134
super().__init__(*args, **kwargs)
135
self.i = 0
tests/tokenization/test_tokenizer_registry.py
+16
-16
@@ -1,6 +1,6 @@
1
# SPDX-License-Identifier: Apache-2.0
2
3
-from typing import TYPE_CHECKING, Any, Dict, List, Optional, Union
3
+from typing import TYPE_CHECKING, Any, Optional, Union
4
5
from vllm.transformers_utils.tokenizer import get_tokenizer
6
from vllm.transformers_utils.tokenizer_base import (TokenizerBase,
@@ -17,15 +17,15 @@ class TestTokenizer(TokenizerBase):
17
return TestTokenizer()
18
19
@property
20
- def all_special_tokens_extended(self) -> List[str]:
20
+ def all_special_tokens_extended(self) -> list[str]:
21
raise NotImplementedError()
22
23
@property
24
- def all_special_tokens(self) -> List[str]:
24
+ def all_special_tokens(self) -> list[str]:
25
raise NotImplementedError()
26
27
@property
28
- def all_special_ids(self) -> List[int]:
28
+ def all_special_ids(self) -> list[int]:
29
raise NotImplementedError()
30
31
@property
@@ -58,7 +58,7 @@ class TestTokenizer(TokenizerBase):
58
59
def __call__(
60
self,
61
- text: Union[str, List[str], List[int]],
61
+ text: Union[str, list[str], list[int]],
62
text_pair: Optional[str] = None,
63
add_special_tokens: bool = False,
64
truncation: bool = False,
@@ -66,10 +66,10 @@ class TestTokenizer(TokenizerBase):
66
):
67
raise NotImplementedError()
68
69
- def get_vocab(self) -> Dict[str, int]:
69
+ def get_vocab(self) -> dict[str, int]:
70
raise NotImplementedError()
71
72
- def get_added_vocab(self) -> Dict[str, int]:
72
+ def get_added_vocab(self) -> dict[str, int]:
73
raise NotImplementedError()
74
75
def encode_one(
@@ -77,33 +77,33 @@ class TestTokenizer(TokenizerBase):
77
text: str,
78
truncation: bool = False,
79
max_length: Optional[int] = None,
80
- ) -> List[int]:
80
+ ) -> list[int]:
81
raise NotImplementedError()
82
83
def encode(self,
84
text: str,
85
- add_special_tokens: Optional[bool] = None) -> List[int]:
85
+ add_special_tokens: Optional[bool] = None) -> list[int]:
86
raise NotImplementedError()
87
88
def apply_chat_template(self,
89
- messages: List["ChatCompletionMessageParam"],
90
- tools: Optional[List[Dict[str, Any]]] = None,
91
- **kwargs) -> List[int]:
89
+ messages: list["ChatCompletionMessageParam"],
90
+ tools: Optional[list[dict[str, Any]]] = None,
91
+ **kwargs) -> list[int]:
92
raise NotImplementedError()
93
94
- def convert_tokens_to_string(self, tokens: List[str]) -> str:
94
+ def convert_tokens_to_string(self, tokens: list[str]) -> str:
95
raise NotImplementedError()
96
97
def decode(self,
98
- ids: Union[List[int], int],
98
+ ids: Union[list[int], int],
99
skip_special_tokens: bool = True) -> str:
100
raise NotImplementedError()
101
102
def convert_ids_to_tokens(
103
self,
104
- ids: List[int],
104
+ ids: list[int],
105
skip_special_tokens: bool = True,
106
- ) -> List[str]:
106
+ ) -> list[str]:
107
raise NotImplementedError()
108
109
tests/tool_use/test_chat_completions.py
+2
-4
@@ -1,7 +1,5 @@
1
# SPDX-License-Identifier: Apache-2.0
2
3
-from typing import List
4
-
3
import openai
4
import pytest
5
@@ -45,7 +43,7 @@ async def test_chat_completion_without_tools(client: openai.AsyncOpenAI,
43
logprobs=False,
44
stream=True,
45
)
48
- chunks: List[str] = []
46
+ chunks: list[str] = []
47
finish_reason_count = 0
48
role_sent: bool = False
49
@@ -116,7 +114,7 @@ async def test_chat_completion_with_tools(client: openai.AsyncOpenAI,
114
stream=True,
115
)
116
119
- chunks: List[str] = []
117
+ chunks: list[str] = []
118
finish_reason_count = 0
119
role_sent: bool = False
120
tests/tool_use/test_jamba_tool_parser.py
+7
-6
@@ -1,7 +1,8 @@
1
# SPDX-License-Identifier: Apache-2.0
2
3
import json
4
-from typing import Generator, List, Optional
4
+from collections.abc import Generator
5
+from typing import Optional
6
7
import partial_json_parser
8
import pytest
@@ -26,8 +27,8 @@ def jamba_tool_parser(jamba_tokenizer):
27
return JambaToolParser(jamba_tokenizer)
28
29
29
-def assert_tool_calls(actual_tool_calls: List[ToolCall],
30
- expected_tool_calls: List[ToolCall]):
30
+def assert_tool_calls(actual_tool_calls: list[ToolCall],
31
+ expected_tool_calls: list[ToolCall]):
32
assert len(actual_tool_calls) == len(expected_tool_calls)
33
34
for actual_tool_call, expected_tool_call in zip(actual_tool_calls,
@@ -218,10 +219,10 @@ def test_extract_tool_calls_streaming(jamba_tool_parser, jamba_tokenizer,
219
model_output, expected_tool_calls,
220
expected_content):
221
other_content: str = ''
221
- function_names: List[str] = []
222
- function_args_strs: List[str] = []
222
+ function_names: list[str] = []
223
+ function_args_strs: list[str] = []
224
tool_call_idx: int = -1
224
- tool_call_ids: List[Optional[str]] = []
225
+ tool_call_ids: list[Optional[str]] = []
226
227
for delta_message in stream_delta_message_generator(
228
jamba_tool_parser, jamba_tokenizer, model_output):
tests/tool_use/test_parallel_tool_calls.py
+5
-5
@@ -1,7 +1,7 @@
1
# SPDX-License-Identifier: Apache-2.0
2
3
import json
4
-from typing import Dict, List, Optional
4
+from typing import Optional
5
6
import openai
7
import pytest
@@ -54,7 +54,7 @@ async def test_parallel_tool_calls(client: openai.AsyncOpenAI,
54
assert isinstance(tool_call.function.arguments, str)
55
56
parsed_arguments = json.loads(tool_call.function.arguments)
57
- assert isinstance(parsed_arguments, Dict)
57
+ assert isinstance(parsed_arguments, dict)
58
assert isinstance(parsed_arguments.get("city"), str)
59
assert isinstance(parsed_arguments.get("state"), str)
60
@@ -73,8 +73,8 @@ async def test_parallel_tool_calls(client: openai.AsyncOpenAI,
73
role_name: Optional[str] = None
74
finish_reason_count: int = 0
75
76
- tool_call_names: List[str] = []
77
- tool_call_args: List[str] = []
76
+ tool_call_names: list[str] = []
77
+ tool_call_args: list[str] = []
78
tool_call_idx: int = -1
79
tool_call_id_count: int = 0
80
@@ -180,7 +180,7 @@ async def test_parallel_tool_calls_with_results(client: openai.AsyncOpenAI,
180
logprobs=False,
181
stream=True)
182
183
- chunks: List[str] = []
183
+ chunks: list[str] = []
184
finish_reason_count = 0
185
role_sent: bool = False
186
tests/tool_use/test_tool_calls.py
+5
-5
@@ -1,7 +1,7 @@
1
# SPDX-License-Identifier: Apache-2.0
2
3
import json
4
-from typing import Dict, List, Optional
4
+from typing import Optional
5
6
import openai
7
import pytest
@@ -44,7 +44,7 @@ async def test_tool_call_and_choice(client: openai.AsyncOpenAI):
44
45
# make sure the arguments parse properly
46
parsed_arguments = json.loads(tool_calls[0].function.arguments)
47
- assert isinstance(parsed_arguments, Dict)
47
+ assert isinstance(parsed_arguments, dict)
48
assert isinstance(parsed_arguments.get("city"), str)
49
assert isinstance(parsed_arguments.get("state"), str)
50
assert parsed_arguments.get("city") == "Dallas"
@@ -117,7 +117,7 @@ async def test_tool_call_and_choice(client: openai.AsyncOpenAI):
117
118
# validate arguments
119
streamed_args = json.loads(function_args_str)
120
- assert isinstance(streamed_args, Dict)
120
+ assert isinstance(streamed_args, dict)
121
assert isinstance(streamed_args.get("city"), str)
122
assert isinstance(streamed_args.get("state"), str)
123
assert streamed_args.get("city") == "Dallas"
@@ -128,7 +128,7 @@ async def test_tool_call_and_choice(client: openai.AsyncOpenAI):
128
assert choice.message.role == role_name
129
assert choice.message.tool_calls[0].function.name == function_name
130
131
- # compare streamed with non-streamed args Dict-wise, not string-wise
131
+ # compare streamed with non-streamed args dict-wise, not string-wise
132
# because character-to-character comparison might not work e.g. the tool
133
# call parser adding extra spaces or something like that. we care about the
134
# dicts matching not byte-wise match
@@ -167,7 +167,7 @@ async def test_tool_call_with_results(client: openai.AsyncOpenAI):
167
logprobs=False,
168
stream=True)
169
170
- chunks: List[str] = []
170
+ chunks: list[str] = []
171
finish_reason_count = 0
172
role_sent: bool = False
173
tests/tool_use/utils.py
+13
-13
@@ -1,7 +1,7 @@
1
# SPDX-License-Identifier: Apache-2.0
2
3
from copy import deepcopy
4
-from typing import Any, Dict, List, Optional
4
+from typing import Any, Optional
5
6
from openai.types.chat import (ChatCompletionMessageParam,
7
ChatCompletionToolParam)
@@ -12,14 +12,14 @@ from tests.utils import VLLM_PATH
12
13
class ServerConfig(TypedDict, total=False):
14
model: str
15
- arguments: List[str]
15
+ arguments: list[str]
16
system_prompt: Optional[str]
17
supports_parallel: Optional[bool]
18
supports_rocm: Optional[bool]
19
20
21
-def patch_system_prompt(messages: List[Dict[str, Any]],
22
- system_prompt: str) -> List[Dict[str, Any]]:
21
+def patch_system_prompt(messages: list[dict[str, Any]],
22
+ system_prompt: str) -> list[dict[str, Any]]:
23
new_messages = deepcopy(messages)
24
if new_messages[0]["role"] == "system":
25
new_messages[0]["content"] = system_prompt
@@ -28,8 +28,8 @@ def patch_system_prompt(messages: List[Dict[str, Any]],
28
return new_messages
29
30
31
-def ensure_system_prompt(messages: List[Dict[str, Any]],
32
- config: ServerConfig) -> List[Dict[str, Any]]:
31
+def ensure_system_prompt(messages: list[dict[str, Any]],
32
+ config: ServerConfig) -> list[dict[str, Any]]:
33
prompt = config.get("system_prompt")
34
if prompt:
35
return patch_system_prompt(messages, prompt)
@@ -39,9 +39,9 @@ def ensure_system_prompt(messages: List[Dict[str, Any]],
39
40
# universal args for all models go here. also good if you need to test locally
41
# and change type or KV cache quantization or something.
42
-ARGS: List[str] = ["--enable-auto-tool-choice", "--max-model-len", "1024"]
42
+ARGS: list[str] = ["--enable-auto-tool-choice", "--max-model-len", "1024"]
43
44
-CONFIGS: Dict[str, ServerConfig] = {
44
+CONFIGS: dict[str, ServerConfig] = {
45
"hermes": {
46
"model":
47
"NousResearch/Hermes-3-Llama-3.1-8B",
@@ -205,7 +205,7 @@ SEARCH_TOOL: ChatCompletionToolParam = {
205
}
206
}
207
208
-MESSAGES_WITHOUT_TOOLS: List[ChatCompletionMessageParam] = [{
208
+MESSAGES_WITHOUT_TOOLS: list[ChatCompletionMessageParam] = [{
209
"role":
210
"user",
211
"content":
@@ -222,14 +222,14 @@ MESSAGES_WITHOUT_TOOLS: List[ChatCompletionMessageParam] = [{
222
"Can you tell me a joke please?"
223
}]
224
225
-MESSAGES_ASKING_FOR_TOOLS: List[ChatCompletionMessageParam] = [{
225
+MESSAGES_ASKING_FOR_TOOLS: list[ChatCompletionMessageParam] = [{
226
"role":
227
"user",
228
"content":
229
"What is the weather in Dallas, Texas in Fahrenheit?"
230
}]
231
232
-MESSAGES_WITH_TOOL_RESPONSE: List[ChatCompletionMessageParam] = [{
232
+MESSAGES_WITH_TOOL_RESPONSE: list[ChatCompletionMessageParam] = [{
233
"role":
234
"user",
235
"content":
@@ -258,7 +258,7 @@ MESSAGES_WITH_TOOL_RESPONSE: List[ChatCompletionMessageParam] = [{
258
"cloudy skies and a low chance of rain."
259
}]
260
261
-MESSAGES_ASKING_FOR_PARALLEL_TOOLS: List[ChatCompletionMessageParam] = [{
261
+MESSAGES_ASKING_FOR_PARALLEL_TOOLS: list[ChatCompletionMessageParam] = [{
262
"role":
263
"user",
264
"content":
@@ -266,7 +266,7 @@ MESSAGES_ASKING_FOR_PARALLEL_TOOLS: List[ChatCompletionMessageParam] = [{
266
"Fahrenheit?"
267
}]
268
269
-MESSAGES_WITH_PARALLEL_TOOL_RESPONSE: List[ChatCompletionMessageParam] = [{
269
+MESSAGES_WITH_PARALLEL_TOOL_RESPONSE: list[ChatCompletionMessageParam] = [{
270
"role":
271
"user",
272
"content":
tests/tracing/test_tracing.py
+3
-2
@@ -2,8 +2,9 @@
2
3
import os
4
import threading
5
+from collections.abc import Iterable
6
from concurrent import futures
6
-from typing import Callable, Dict, Iterable, Literal
7
+from typing import Callable, Literal
8
9
import grpc
10
import pytest
@@ -25,7 +26,7 @@ FieldName = Literal['bool_value', 'string_value', 'int_value', 'double_value',
26
27
28
def decode_value(value: AnyValue):
28
- field_decoders: Dict[FieldName, Callable] = {
29
+ field_decoders: dict[FieldName, Callable] = {
30
"bool_value": (lambda v: v.bool_value),
31
"string_value": (lambda v: v.string_value),
32
"int_value": (lambda v: v.int_value),
tests/utils.py
+21
-21
@@ -11,7 +11,7 @@ import time
11
import warnings
12
from contextlib import contextmanager
13
from pathlib import Path
14
-from typing import Any, Callable, Dict, List, Optional, Type, Union
14
+from typing import Any, Callable, Optional, Union
15
16
import openai
17
import pytest
@@ -73,9 +73,9 @@ class RemoteOpenAIServer:
73
74
def __init__(self,
75
model: str,
76
- vllm_serve_args: List[str],
76
+ vllm_serve_args: list[str],
77
*,
78
- env_dict: Optional[Dict[str, str]] = None,
78
+ env_dict: Optional[dict[str, str]] = None,
79
auto_port: bool = True,
80
max_wait_seconds: Optional[float] = None) -> None:
81
if auto_port:
@@ -183,7 +183,7 @@ def _test_completion(
183
client: openai.OpenAI,
184
model: str,
185
prompt: str,
186
- token_ids: List[int],
186
+ token_ids: list[int],
187
):
188
results = []
189
@@ -400,10 +400,10 @@ def _test_image_text(
400
401
402
def compare_two_settings(model: str,
403
- arg1: List[str],
404
- arg2: List[str],
405
- env1: Optional[Dict[str, str]] = None,
406
- env2: Optional[Dict[str, str]] = None,
403
+ arg1: list[str],
404
+ arg2: list[str],
405
+ env1: Optional[dict[str, str]] = None,
406
+ env2: Optional[dict[str, str]] = None,
407
*,
408
method: str = "generate",
409
max_wait_seconds: Optional[float] = None) -> None:
@@ -429,8 +429,8 @@ def compare_two_settings(model: str,
429
430
431
def compare_all_settings(model: str,
432
- all_args: List[List[str]],
433
- all_envs: List[Optional[Dict[str, str]]],
432
+ all_args: list[list[str]],
433
+ all_envs: list[Optional[dict[str, str]]],
434
*,
435
method: str = "generate",
436
max_wait_seconds: Optional[float] = None) -> None:
@@ -470,7 +470,7 @@ def compare_all_settings(model: str,
470
471
prompt = "Hello, my name is"
472
token_ids = tokenizer(prompt).input_ids
473
- ref_results: List = []
473
+ ref_results: list = []
474
for i, (args, env) in enumerate(zip(all_args, all_envs)):
475
if can_force_load_format:
476
# we are comparing the results and
@@ -481,7 +481,7 @@ def compare_all_settings(model: str,
481
# environment variable to force the load format,
482
# e.g. in quantization tests.
483
args = args + ["--load-format", envs.VLLM_TEST_FORCE_LOAD_FORMAT]
484
- compare_results: List = []
484
+ compare_results: list = []
485
results = ref_results if i == 0 else compare_results
486
with RemoteOpenAIServer(model,
487
args,
@@ -582,7 +582,7 @@ def multi_process_parallel(
582
583
584
@contextmanager
585
-def error_on_warning(category: Type[Warning] = Warning):
585
+def error_on_warning(category: type[Warning] = Warning):
586
"""
587
Within the scope of this context manager, tests will fail if any warning
588
of the given category is emitted.
@@ -604,7 +604,7 @@ def get_physical_device_indices(devices):
604
605
606
@_nvml()
607
-def wait_for_gpu_memory_to_clear(devices: List[int],
607
+def wait_for_gpu_memory_to_clear(devices: list[int],
608
threshold_bytes: int,
609
timeout_s: float = 120) -> None:
610
# Use nvml instead of pytorch to reduce measurement error from torch cuda
@@ -612,8 +612,8 @@ def wait_for_gpu_memory_to_clear(devices: List[int],
612
devices = get_physical_device_indices(devices)
613
start_time = time.time()
614
while True:
615
- output: Dict[int, str] = {}
616
- output_raw: Dict[int, float] = {}
615
+ output: dict[int, str] = {}
616
+ output_raw: dict[int, float] = {}
617
for device in devices:
618
if current_platform.is_rocm():
619
dev_handle = amdsmi_get_processor_handles()[device]
@@ -758,13 +758,13 @@ def multi_gpu_test(*, num_gpus: int):
758
759
760
async def completions_with_server_args(
761
- prompts: List[str],
761
+ prompts: list[str],
762
model_name: str,
763
- server_cli_args: List[str],
763
+ server_cli_args: list[str],
764
num_logprobs: Optional[int],
765
max_wait_seconds: int = 240,
766
max_tokens: Union[int, list] = 5,
767
-) -> List[Completion]:
767
+) -> list[Completion]:
768
'''Construct a remote OpenAI server, obtain an async client to the
769
server & invoke the completions API to obtain completions.
770
@@ -807,7 +807,7 @@ async def completions_with_server_args(
807
return outputs
808
809
810
-def get_client_text_generations(completions: List[Completion]) -> List[str]:
810
+def get_client_text_generations(completions: list[Completion]) -> list[str]:
811
'''Extract generated tokens from the output of a
812
request made to an Open-AI-protocol completions endpoint.
813
'''
@@ -816,7 +816,7 @@ def get_client_text_generations(completions: List[Completion]) -> List[str]:
816
817
818
def get_client_text_logprob_generations(
819
- completions: List[Completion]) -> List[TextTextLogprobs]:
819
+ completions: list[Completion]) -> list[TextTextLogprobs]:
820
'''Operates on the output of a request made to an Open-AI-protocol
821
completions endpoint; obtains top-rank logprobs for each token in
822
each :class:`SequenceGroup`
tests/v1/core/test_prefix_caching.py
+1
-2
@@ -1,6 +1,5 @@
1
# SPDX-License-Identifier: Apache-2.0
2
"""Compare the with and without prefix caching."""
3
-from typing import List
3
4
import pytest
5
@@ -434,7 +433,7 @@ def test_cache_blocks():
433
434
# Test that blocks are cached correctly for 2 full blocks from the start.
435
blocks = [KVCacheBlock(block_id=i) for i in range(2)]
437
- block_hashes: List[BlockHashType] = []
436
+ block_hashes: list[BlockHashType] = []
437
438
block_pool.cache_full_blocks(
439
request=req,
tests/v1/core/test_scheduler.py
+3
-3
@@ -1,5 +1,5 @@
1
# SPDX-License-Identifier: Apache-2.0
2
-from typing import List, Optional
2
+from typing import Optional
3
4
from vllm.config import CacheConfig, ModelConfig, SchedulerConfig
5
from vllm.multimodal.inputs import MultiModalKwargs, PlaceholderRange
@@ -48,9 +48,9 @@ def create_scheduler(
48
def create_requests(
49
num_requests: int,
50
num_tokens: int = 10,
51
- mm_positions: Optional[List[PlaceholderRange]] = None,
51
+ mm_positions: Optional[list[PlaceholderRange]] = None,
52
max_tokens: int = 16,
53
- stop_token_ids: Optional[List[int]] = None,
53
+ stop_token_ids: Optional[list[int]] = None,
54
):
55
sampling_params = SamplingParams(ignore_eos=False,
56
max_tokens=max_tokens,
tests/v1/engine/conftest.py
+2
-4
@@ -1,7 +1,5 @@
1
# SPDX-License-Identifier: Apache-2.0
2
3
-from typing import List, Tuple
4
-
3
import pytest
4
import torch
5
from transformers import AutoTokenizer
@@ -17,8 +15,8 @@ from vllm.transformers_utils.tokenizer_group import init_tokenizer_from_configs
15
16
from tests.v1.engine.utils import FULL_STRINGS # isort: skip
17
20
-EngineCoreSampleLogprobsType = List[Tuple[torch.Tensor, torch.Tensor]]
21
-EngineCorePromptLogprobsType = Tuple[torch.Tensor, torch.Tensor]
18
+EngineCoreSampleLogprobsType = list[tuple[torch.Tensor, torch.Tensor]]
19
+EngineCorePromptLogprobsType = tuple[torch.Tensor, torch.Tensor]
20
21
22
def _build_test_vectors_no_logprobs() -> DummyOutputProcessorTestVectors:
tests/v1/engine/test_async_llm.py
+5
-5
@@ -2,7 +2,7 @@
2
3
import asyncio
4
from contextlib import ExitStack
5
-from typing import List, Optional, Tuple
5
+from typing import Optional
6
7
import pytest
8
@@ -47,7 +47,7 @@ async def generate(engine: AsyncLLM,
47
prompt: PromptType,
48
output_kind: RequestOutputKind,
49
max_tokens: int,
50
- prompt_logprobs: Optional[int] = None) -> Tuple[int, str]:
50
+ prompt_logprobs: Optional[int] = None) -> tuple[int, str]:
51
# Ensure generate doesn't complete too fast for cancellation test.
52
await asyncio.sleep(0.2)
53
@@ -114,7 +114,7 @@ async def test_async_llm_refuses_prompt_logprobs_with_apc(
114
(VISION_ENGINE_ARGS, VISION_PROMPT)])
115
@pytest.mark.asyncio
116
async def test_load(monkeypatch, output_kind: RequestOutputKind,
117
- engine_args_and_prompt: Tuple[AsyncEngineArgs,
117
+ engine_args_and_prompt: tuple[AsyncEngineArgs,
118
PromptType]):
119
# TODO(rickyx): Remove monkeypatch once we have a better way to test V1
120
# so that in the future when we switch, we don't have to change all the
@@ -160,7 +160,7 @@ async def test_load(monkeypatch, output_kind: RequestOutputKind,
160
(VISION_ENGINE_ARGS, VISION_PROMPT)])
161
@pytest.mark.asyncio
162
async def test_abort(monkeypatch, output_kind: RequestOutputKind,
163
- engine_args_and_prompt: Tuple[AsyncEngineArgs,
163
+ engine_args_and_prompt: tuple[AsyncEngineArgs,
164
PromptType]):
165
166
with monkeypatch.context() as m, ExitStack() as after:
@@ -177,7 +177,7 @@ async def test_abort(monkeypatch, output_kind: RequestOutputKind,
177
request_ids = [f"request-{i}" for i in range(NUM_REQUESTS)]
178
179
# Create concurrent requests.
180
- tasks: List[asyncio.Task] = []
180
+ tasks: list[asyncio.Task] = []
181
for request_id in request_ids:
182
tasks.append(
183
asyncio.create_task(
tests/v1/engine/test_engine_core.py
+1
-2
@@ -5,7 +5,6 @@ import threading
5
import time
6
import uuid
7
from concurrent.futures import Future
8
-from typing import List
8
9
import pytest
10
from transformers import AutoTokenizer
@@ -213,7 +212,7 @@ def test_engine_core_concurrent_batches(monkeypatch):
212
class DummyExecutor(UniProcExecutor):
213
214
def initialize_from_config(
216
- self, kv_cache_configs: List[KVCacheConfig]) -> None:
215
+ self, kv_cache_configs: list[KVCacheConfig]) -> None:
216
super().initialize_from_config(kv_cache_configs)
217
218
# This executor actually can only run 1 batch at a time
tests/v1/engine/test_engine_core_client.py
+5
-5
@@ -3,7 +3,7 @@
3
import asyncio
4
import time
5
import uuid
6
-from typing import Dict, List, Optional
6
+from typing import Optional
7
8
import pytest
9
from transformers import AutoTokenizer
@@ -44,7 +44,7 @@ def make_request(params: SamplingParams) -> EngineCoreRequest:
44
)
45
46
47
-def loop_until_done(client: EngineCoreClient, outputs: Dict):
47
+def loop_until_done(client: EngineCoreClient, outputs: dict):
48
49
while True:
50
engine_core_outputs = client.get_output().outputs
@@ -62,7 +62,7 @@ def loop_until_done(client: EngineCoreClient, outputs: Dict):
62
break
63
64
65
-async def loop_until_done_async(client: EngineCoreClient, outputs: Dict):
65
+async def loop_until_done_async(client: EngineCoreClient, outputs: dict):
66
67
while True:
68
engine_core_outputs = (await client.get_output_async()).outputs
@@ -121,7 +121,7 @@ def test_engine_core_client(monkeypatch, multiprocessing_mode: bool):
121
client.add_request(request)
122
time.sleep(0.01)
123
124
- outputs: Dict[str, List] = {req_id: [] for req_id in request_ids}
124
+ outputs: dict[str, list] = {req_id: [] for req_id in request_ids}
125
loop_until_done(client, outputs)
126
127
for req_id in request_ids:
@@ -207,7 +207,7 @@ async def test_engine_core_client_asyncio(monkeypatch):
207
await client.add_request_async(request)
208
await asyncio.sleep(0.01)
209
210
- outputs: Dict[str, List] = {req_id: [] for req_id in request_ids}
210
+ outputs: dict[str, list] = {req_id: [] for req_id in request_ids}
211
await loop_until_done_async(client, outputs)
212
213
for req_id in request_ids:
tests/v1/engine/test_llm_engine.py
+4
-4
@@ -1,7 +1,7 @@
1
# SPDX-License-Identifier: Apache-2.0
2
3
import random
4
-from typing import Dict, List, Optional, Tuple
4
+from typing import Optional
5
6
import pytest
7
@@ -47,9 +47,9 @@ def vllm_model_apc(vllm_runner, monkeypatch):
47
48
49
def _get_test_sampling_params(
50
- prompt_list: List[str],
50
+ prompt_list: list[str],
51
seed: Optional[int] = 42,
52
-) -> Tuple[List[SamplingParams], List[int]]:
52
+) -> tuple[list[SamplingParams], list[int]]:
53
"""Generate random sampling params for a batch."""
54
55
def get_mostly_n_gt1() -> int:
@@ -81,7 +81,7 @@ def test_parallel_sampling(vllm_model, example_prompts) -> None:
81
82
# Validate each request response
83
for out, n in zip(outputs, n_list):
84
- completion_counts: Dict[str, int] = {}
84
+ completion_counts: dict[str, int] = {}
85
# Assert correct number of completions
86
assert len(out.outputs) == n, (
87
f"{len(out.outputs)} completions; {n} expected.")
tests/v1/engine/test_output_processor.py
+6
-6
@@ -2,7 +2,7 @@
2
3
import math
4
import time
5
-from typing import Dict, List, Optional
5
+from typing import Optional
6
7
import pytest
8
@@ -112,12 +112,12 @@ def test_incremental_detokenization(request_output_kind: RequestOutputKind,
112
113
114
def _validate_logprobs(
115
- gen_tokens: Dict[str, List[int]],
116
- gen_logprobs: Dict[str, Optional[SampleLogprobs]],
117
- gen_prompt_logprobs: Dict[str, Optional[PromptLogprobs]],
118
- gen_cumulative_logprob: Dict[str, float],
115
+ gen_tokens: dict[str, list[int]],
116
+ gen_logprobs: dict[str, Optional[SampleLogprobs]],
117
+ gen_prompt_logprobs: dict[str, Optional[PromptLogprobs]],
118
+ gen_cumulative_logprob: dict[str, float],
119
dtv: DummyOutputProcessorTestVectors,
120
- request_id_list: List[str],
120
+ request_id_list: list[str],
121
num_sample_logprobs: Optional[int],
122
num_prompt_logprobs: Optional[int],
123
) -> None:
tests/v1/engine/utils.py
+25
-25
@@ -2,7 +2,7 @@
2
3
import random
4
from dataclasses import dataclass
5
-from typing import List, Optional, Tuple, Union
5
+from typing import Optional, Union
6
7
import torch
8
from transformers import PreTrainedTokenizer, PreTrainedTokenizerFast
@@ -61,7 +61,7 @@ def _create_random_top_logprob_test_vector(
61
62
63
def _create_random_top_logprob_test_matrix(
64
- shape: Tuple,
64
+ shape: tuple,
65
lower: float,
66
upper: float,
67
) -> torch.Tensor:
@@ -90,7 +90,7 @@ def _create_random_top_token_test_vector(
90
lower: int,
91
upper: int,
92
sampled_token_id: int,
93
- adjust_num_logprobs: bool = True) -> Tuple[torch.Tensor, int]:
93
+ adjust_num_logprobs: bool = True) -> tuple[torch.Tensor, int]:
94
"""Create a random vector of top logprob token indices
95
96
Use to create fake sample logprobs for testing. The sampled token
@@ -141,11 +141,11 @@ def _create_random_top_token_test_vector(
141
142
143
def _create_random_top_token_test_matrix(
144
- shape: Tuple[int, int],
144
+ shape: tuple[int, int],
145
lower: int,
146
upper: int,
147
- tokens_list: List[int],
148
-) -> Tuple[torch.Tensor, torch.Tensor]:
147
+ tokens_list: list[int],
148
+) -> tuple[torch.Tensor, torch.Tensor]:
149
"""Create a random matrix of top logprob token indices
150
151
Use to create fake prompt logprobs for testing.
@@ -160,7 +160,7 @@ def _create_random_top_token_test_matrix(
160
upper: upper range of token ids
161
162
Returns:
163
- Tuple containing:
163
+ tuple containing:
164
- 2D num_tokens x num_logprobs+1 torch Tensor of token ids
165
- 1D tensor of ranks of prompt tokens in their respective
166
rows, or random values
@@ -206,10 +206,10 @@ def decode_token(
206
207
208
def generate_dummy_sample_logprobs(
209
- sampled_tokens_list: List,
209
+ sampled_tokens_list: list,
210
num_logprobs: int,
211
tokenizer: PreTrainedTokenizer,
212
-) -> List[Tuple[List[int], List[float], int]]:
212
+) -> list[tuple[list[int], list[float], int]]:
213
"""Generate dummy sample logprobs
214
215
Generate a test data structure which imitates the list of sample logprobs
@@ -221,7 +221,7 @@ def generate_dummy_sample_logprobs(
221
tokenizer: model tokenizer to use for detokenization
222
223
Returns
224
- List of (top token ids vector, logprobs vector, sampled token rank)
224
+ list of (top token ids vector, logprobs vector, sampled token rank)
225
Python lists tuples; in each tuple the logprobs and top token ids
226
vectors have the same length which is either `num_logprobs` or
227
`num_logprobs+1`. Sampled token rank is the rank (index+1) of the
@@ -253,7 +253,7 @@ def generate_dummy_sample_logprobs(
253
254
255
def generate_dummy_prompt_logprobs_tensors(
256
- prompt_tokens_list: List,
256
+ prompt_tokens_list: list,
257
num_logprobs: int,
258
tokenizer: PreTrainedTokenizer,
259
) -> LogprobsTensors:
@@ -269,7 +269,7 @@ def generate_dummy_prompt_logprobs_tensors(
269
tokenizer: model tokenizer to use for detokenization
270
271
Returns
272
- Single Tuple of (logprobs matrix, top token ids matrix) torch Tensor,
272
+ Single tuple of (logprobs matrix, top token ids matrix) torch Tensor,
273
where both matrices have dimensions
274
num_prompt_tokens x num_logprobs
275
"""
@@ -301,19 +301,19 @@ class DummyOutputProcessorTestVectors:
301
tokenizer: GeneralTokenizerType
302
tokenizer_group: BaseTokenizerGroup
303
vllm_config: EngineArgs
304
- full_tokens: List[List[int]] # Prompt + generated tokens
305
- prompt_tokens: List[List[int]]
306
- generation_tokens: List[List[int]]
304
+ full_tokens: list[list[int]] # Prompt + generated tokens
305
+ prompt_tokens: list[list[int]]
306
+ generation_tokens: list[list[int]]
307
# Each request is associated with a tuple of
308
# (top tokens, top logprobs, ranks) prompt logprobs tensors
309
- prompt_logprobs: List[LogprobsTensors]
309
+ prompt_logprobs: list[LogprobsTensors]
310
# Each request is associated with a sample logprobs; a request's
311
# sample logprobs are a list of (top tokens, top logprobs, ranks)
312
# sample logprobs tensors at each sequence position
313
- generation_logprobs: List[List[Tuple[List[int], List[float], int]]]
314
- prompt_strings: List[str]
315
- prompt_strings_len: List[int]
316
- generation_strings: List[str]
313
+ generation_logprobs: list[list[tuple[list[int], list[float], int]]]
314
+ prompt_strings: list[str]
315
+ prompt_strings_len: list[int]
316
+ generation_strings: list[str]
317
318
319
class MockEngineCore:
@@ -321,18 +321,18 @@ class MockEngineCore:
321
322
def __init__(
323
self,
324
- tokens_list: List[List[int]],
324
+ tokens_list: list[list[int]],
325
# For each request, for each sampled token offset,
326
# a tuple of
327
# (list of topk token ids, list of sample logprob vals, rank)
328
- generated_logprobs_raw: Optional[List[List[Tuple[List[int],
329
- List[float],
328
+ generated_logprobs_raw: Optional[list[list[tuple[list[int],
329
+ list[float],
330
int]]]] = None,
331
# For each request, a tuple of
332
# (prompt logprob val matrix, prompt logprob tok id matrix);
333
# each matrix has dimensions
334
# (num prompt toks) x (num prompt logprobs+1)
335
- prompt_logprobs_raw: Optional[List[LogprobsTensors]] = None,
335
+ prompt_logprobs_raw: Optional[list[LogprobsTensors]] = None,
336
) -> None:
337
self.tokens_list = tokens_list
338
self.current_idx = 0
@@ -341,7 +341,7 @@ class MockEngineCore:
341
self.prompt_logprobs_raw = prompt_logprobs_raw
342
self.do_prompt_logprobs = prompt_logprobs_raw is not None
343
344
- def get_outputs(self) -> List[EngineCoreOutput]:
344
+ def get_outputs(self) -> list[EngineCoreOutput]:
345
do_logprobs = self.do_logprobs
346
do_prompt_logprobs = self.do_prompt_logprobs
347
token_idx = self.current_idx
tests/v1/entrypoints/openai/test_completion.py
+6
-6
@@ -1,7 +1,7 @@
1
# SPDX-License-Identifier: Apache-2.0
2
3
import re
4
-from typing import Dict, List, Optional
4
+from typing import Optional
5
6
import openai # use the official client for correctness check
7
import pytest
@@ -193,7 +193,7 @@ async def test_too_many_completion_logprobs(client: openai.AsyncOpenAI,
193
async def test_prompt_logprobs_completion(client: openai.AsyncOpenAI,
194
model_name: str,
195
prompt_logprobs: Optional[int]):
196
- params: Dict = {
196
+ params: dict = {
197
"prompt": ["A robot may not injure another robot", "My name is"],
198
"model": model_name,
199
}
@@ -237,7 +237,7 @@ async def test_completion_streaming(client: openai.AsyncOpenAI,
237
max_tokens=5,
238
temperature=0.0,
239
stream=True)
240
- chunks: List[str] = []
240
+ chunks: list[str] = []
241
finish_reason_count = 0
242
async for chunk in stream:
243
chunks.append(chunk.choices[0].text)
@@ -278,7 +278,7 @@ async def test_parallel_no_streaming(client: openai.AsyncOpenAI,
278
num_completions = len(completion.choices)
279
assert num_completions == n, (
280
f"Num completions {num_completions} but expected {n}.")
281
- completion_repeats: Dict[str, int] = {}
281
+ completion_repeats: dict[str, int] = {}
282
for idx, choice in enumerate(completion.choices):
283
# Assert correct completion index & some finish reason.
284
assert choice.index == idx, (
@@ -321,7 +321,7 @@ async def test_parallel_streaming(client: openai.AsyncOpenAI, model_name: str):
321
temperature=0.95,
322
stream=True,
323
seed=42)
324
- chunks: List[List[str]] = [[] for i in range(n)]
324
+ chunks: list[list[str]] = [[] for i in range(n)]
325
finish_reason_count = 0
326
async for chunk in stream:
327
index = chunk.choices[0].index
@@ -332,7 +332,7 @@ async def test_parallel_streaming(client: openai.AsyncOpenAI, model_name: str):
332
# Assert `n` completions with correct finish reasons
333
assert finish_reason_count == n, (
334
f"Expected {n} completions with valid indices and finish_reason.")
335
- completion_repeats: Dict[str, int] = {}
335
+ completion_repeats: dict[str, int] = {}
336
for chunk in chunks:
337
chunk_len = len(chunk)
338
# Assert correct number of completion tokens
tests/v1/sample/test_logprobs.py
+4
-5
@@ -1,7 +1,6 @@
1
# SPDX-License-Identifier: Apache-2.0
2
3
import itertools
4
-from typing import List, Tuple
4
5
import pytest
6
import torch
@@ -46,8 +45,8 @@ def hf_model(hf_runner):
45
46
def _repeat_logprob_config(
47
test_prompts,
49
- logprob_prompt_logprob_list: List[Tuple],
50
-) -> List[Tuple]:
48
+ logprob_prompt_logprob_list: list[tuple],
49
+) -> list[tuple]:
50
"""Ensure each test prompt has a logprob config.
51
52
A logprob config specifies the optional (i.e.
@@ -74,7 +73,7 @@ def _repeat_logprob_config(
73
tuples
74
75
Returns:
77
- List of
76
+ list of
77
(optional num sample logprob,optional num prompt logprob)
78
tuples which is either identical to
79
`logprob_prompt_logprob_list`, or else repeats
@@ -177,7 +176,7 @@ def _test_case_get_logprobs_and_prompt_logprobs(
176
for r in range(1, num_top_logprobs + 1))
177
178
output_text = vllm_result.outputs[0].text
180
- output_string_from_most_likely_tokens_lst: List[str] = []
179
+ output_string_from_most_likely_tokens_lst: list[str] = []
180
for top_logprobs in vllm_result.outputs[0].logprobs:
181
top_logprob = next(iter(top_logprobs.values()))
182
output_string_from_most_likely_tokens_lst.append(
tests/v1/sample/test_rejection_sampler.py
+3
-4
@@ -1,5 +1,4 @@
1
# SPDX-License-Identifier: Apache-2.0
2
-from typing import List
2
3
import pytest
4
import torch
@@ -13,7 +12,7 @@ def sampler():
12
return RejectionSampler()
13
14
16
-def create_logits_tensor(token_ids: List[int],
15
+def create_logits_tensor(token_ids: list[int],
16
vocab_size: int = 100) -> torch.Tensor:
17
"""Helper function to create logits tensor that
18
will produce desired token ids on argmax"""
@@ -23,7 +22,7 @@ def create_logits_tensor(token_ids: List[int],
22
return logits
23
24
26
-def create_sampling_metadata(spec_tokens: List[List[int]]) -> SamplingMetadata:
25
+def create_sampling_metadata(spec_tokens: list[list[int]]) -> SamplingMetadata:
26
batch_size = len(spec_tokens)
27
return SamplingMetadata(
28
temperature=torch.tensor([]),
@@ -106,7 +105,7 @@ def test_single_token_sequence(sampler):
105
106
def test_empty_sequence(sampler):
107
"""Test handling empty sequence of speculated tokens"""
109
- spec_tokens: List[List[int]] = [[]]
108
+ spec_tokens: list[list[int]] = [[]]
109
output_tokens = [5] # Just the bonus token
110
111
metadata = create_sampling_metadata(spec_tokens)
tests/v1/sample/test_sampler.py
+13
-13
@@ -1,6 +1,6 @@
1
# SPDX-License-Identifier: Apache-2.0
2
3
-from typing import Dict, List, Optional, Set, Tuple
3
+from typing import Optional
4
5
import numpy as np
6
import pytest
@@ -32,7 +32,7 @@ def _create_penalty_tensor(batch_size: int, penalty_value: float,
32
33
34
def _create_prompt_tokens_tensor(
35
- prompt_token_ids: List[List[int]],
35
+ prompt_token_ids: list[list[int]],
36
vocab_size: int,
37
device: torch.device,
38
) -> torch.Tensor:
@@ -49,8 +49,8 @@ def _create_logit_bias(
49
batch_size: int,
50
vocab_size: int,
51
bias_value: float,
52
-) -> List[Optional[Dict[int, float]]]:
53
- res: List[Optional[Dict[int, float]]] = []
52
+) -> list[Optional[dict[int, float]]]:
53
+ res: list[Optional[dict[int, float]]] = []
54
for i in range(batch_size):
55
logit_bias = {min(i, vocab_size - 1): bias_value}
56
res.append(logit_bias)
@@ -83,8 +83,8 @@ def _create_default_sampling_metadata(
83
vocab_size: int,
84
device: torch.device,
85
) -> SamplingMetadata:
86
- output_token_ids: List[List[int]] = []
87
- prompt_token_ids: List[List[int]] = []
86
+ output_token_ids: list[list[int]] = []
87
+ prompt_token_ids: list[list[int]] = []
88
for _ in range(batch_size):
89
output_token_ids.append(
90
np.random.randint(0, vocab_size, size=num_output_tokens).tolist())
@@ -118,8 +118,8 @@ def _create_default_sampling_metadata(
118
119
def _generate_min_token_penalties_and_stop_tokens(
120
num_output_tokens: int, batch_size: int, vocab_size: int,
121
- batch_indices_for_min_token_penalty: List[int]
122
-) -> Dict[int, Tuple[int, Set[int]]]:
121
+ batch_indices_for_min_token_penalty: list[int]
122
+) -> dict[int, tuple[int, set[int]]]:
123
"""
124
Generates and returns a dict of minimum token penalties and
125
corresponding stop token IDs (`min_tokens`, `stop_token_ids`) for each
@@ -130,7 +130,7 @@ def _generate_min_token_penalties_and_stop_tokens(
130
and a random set of stop token IDs is created. Otherwise, a lower
131
`min_tokens` value is assigned, and the stop token IDs set is empty.
132
"""
133
- min_tokens: Dict[int, Tuple[int, Set[int]]] = {}
133
+ min_tokens: dict[int, tuple[int, set[int]]] = {}
134
for index in range(batch_size):
135
if index in batch_indices_for_min_token_penalty:
136
min_tokens[index] = (
@@ -147,7 +147,7 @@ def _generate_min_token_penalties_and_stop_tokens(
147
148
def _create_weighted_output_token_list(
149
batch_size: int,
150
- vocab_size: int) -> Tuple[List[List[int]], List[List[int]]]:
150
+ vocab_size: int) -> tuple[list[list[int]], list[list[int]]]:
151
"""
152
Creates an output token list where each token occurs a distinct
153
number of times.
@@ -157,7 +157,7 @@ def _create_weighted_output_token_list(
157
list, each with a different frequency.
158
159
Returns:
160
- Tuple[List[List[int]], List[List[int]]]:
160
+ tuple[list[list[int]], list[list[int]]]:
161
- The first element is the output token list, where each sublist
162
corresponds to a batch and contains tokens with weighted
163
frequencies.
@@ -165,8 +165,8 @@ def _create_weighted_output_token_list(
165
batch, ordered by their frequency in the corresponding output
166
list.
167
"""
168
- output_token_ids: List[List[int]] = []
169
- sorted_token_ids_in_output: List[List[int]] = []
168
+ output_token_ids: list[list[int]] = []
169
+ sorted_token_ids_in_output: list[list[int]] = []
170
for _ in range(batch_size):
171
distinct_token_ids = np.random.choice(vocab_size,
172
size=np.random.randint(1, 10),
tests/v1/sample/utils.py
+2
-3
@@ -1,12 +1,11 @@
1
# SPDX-License-Identifier: Apache-2.0
2
3
import re
4
-from typing import List, Tuple
4
5
from vllm import CompletionOutput
6
7
9
-def get_test_batch(batch_logprobs_composition: str) -> List[Tuple]:
8
+def get_test_batch(batch_logprobs_composition: str) -> list[tuple]:
9
"""Generate logprobs configs for a batch of requests
10
11
A given request's logprobs configuration is (1) num_sample_logprobs and (2)
@@ -32,7 +31,7 @@ def get_test_batch(batch_logprobs_composition: str) -> List[Tuple]:
31
32
Returns:
33
35
- List of (Optional[num_sample_logprobs], Optional[num_prompt_logprobs])
34
+ list of (Optional[num_sample_logprobs], Optional[num_prompt_logprobs])
35
tuples
36
"""
37
if batch_logprobs_composition == "NONE":
tests/v1/test_utils.py
+2
-4
@@ -1,7 +1,5 @@
1
# SPDX-License-Identifier: Apache-2.0
2
3
-from typing import List
4
-
3
import torch
4
5
from vllm.v1.utils import bind_kv_cache
@@ -22,7 +20,7 @@ def test_bind_kv_cache():
20
'layers.2.self_attn': torch.zeros((1, )),
21
'layers.3.self_attn': torch.zeros((1, )),
22
}
25
- runner_kv_caches: List[torch.Tensor] = []
23
+ runner_kv_caches: list[torch.Tensor] = []
24
bind_kv_cache(kv_cache, ctx, runner_kv_caches)
25
assert ctx['layers.0.self_attn'].kv_cache[0] is kv_cache[
26
'layers.0.self_attn']
@@ -52,7 +50,7 @@ def test_bind_kv_cache_non_attention():
50
'model.layers.28.attn': torch.zeros((1, )),
51
}
52
55
- runner_kv_caches: List[torch.Tensor] = []
53
+ runner_kv_caches: list[torch.Tensor] = []
54
bind_kv_cache(kv_cache, ctx, runner_kv_caches)
55
56
assert ctx['model.layers.20.attn'].kv_cache[0] is kv_cache[
tests/v1/worker/test_gpu_input_batch.py
+11
-11
@@ -1,6 +1,6 @@
1
# SPDX-License-Identifier: Apache-2.0
2
3
-from typing import Dict, List, Optional, Set, Tuple
3
+from typing import Optional
4
5
import numpy as np
6
import pytest
@@ -22,22 +22,22 @@ MAX_NUM_PROMPT_TOKENS = 64
22
23
def _remove_requests(
24
input_batch: InputBatch, batch_size: int,
25
- reqs: List[CachedRequestState]) -> Tuple[Set[str], List[int]]:
25
+ reqs: list[CachedRequestState]) -> tuple[set[str], list[int]]:
26
"""
27
- Remove some requests randomly from the batch and returns a Tuple
27
+ Remove some requests randomly from the batch and returns a tuple
28
of 1) set of request removed 2) indices of the requests removed
29
ordered in descending order
30
"""
31
32
num_reqs_to_remove = np.random.randint(0, batch_size)
33
- req_indices_to_remove: Set[int] = set()
33
+ req_indices_to_remove: set[int] = set()
34
for _ in range(num_reqs_to_remove):
35
req_index_to_remove = np.random.randint(0, batch_size)
36
req_indices_to_remove.add(req_index_to_remove)
37
38
req_indices_to_remove_list = list(req_indices_to_remove)
39
req_indices_to_remove_list.sort(reverse=True)
40
- req_ids_to_remove: Set[str] = set()
40
+ req_ids_to_remove: set[str] = set()
41
for index in req_indices_to_remove:
42
input_batch.remove_request(reqs[index].req_id)
43
req_ids_to_remove.add(reqs[index].req_id)
@@ -45,9 +45,9 @@ def _remove_requests(
45
46
47
def _construct_expected_sampling_metadata(
48
- reqs: List[CachedRequestState],
49
- req_ids_retained: Set[int],
50
- req_id_index_in_input_batch: Dict[str, int],
48
+ reqs: list[CachedRequestState],
49
+ req_ids_retained: set[int],
50
+ req_id_index_in_input_batch: dict[str, int],
51
device: torch.device,
52
) -> SamplingMetadata:
53
"""
@@ -55,8 +55,8 @@ def _construct_expected_sampling_metadata(
55
batch.
56
"""
57
num_reqs = len(req_ids_retained)
58
- output_token_ids: List[List[int]] = [list() for _ in range(num_reqs)]
59
- prompt_token_ids: List[List[int]] = [list() for _ in range(num_reqs)]
58
+ output_token_ids: list[list[int]] = [list() for _ in range(num_reqs)]
59
+ prompt_token_ids: list[list[int]] = [list() for _ in range(num_reqs)]
60
presence_penalties = [0.0 for _ in range(num_reqs)]
61
frequency_penalties = [0.0 for _ in range(num_reqs)]
62
repetition_penalties = [1.0 for _ in range(num_reqs)]
@@ -191,7 +191,7 @@ def test_sampling_metadata_in_input_batch(device: str, batch_size: int):
191
pin_memory=is_pin_memory_available(),
192
vocab_size=1024,
193
)
194
- reqs: List[CachedRequestState] = []
194
+ reqs: list[CachedRequestState] = []
195
req_id_reqs = {}
196
req_id_output_token_ids = {}
197
# Add requests
tests/vllm_test_utils/vllm_test_utils/blame.py
+2
-1
@@ -4,7 +4,8 @@ import contextlib
4
import dataclasses
5
import sys
6
import traceback
7
-from typing import Callable, Generator
7
+from collections.abc import Generator
8
+from typing import Callable
9
10
11
@dataclasses.dataclass
tests/vllm_test_utils/vllm_test_utils/monitor.py
+2
-1
@@ -4,7 +4,8 @@ import contextlib
4
import dataclasses
5
import sys
6
import traceback
7
-from typing import Callable, Generator, Generic, TypeVar
7
+from collections.abc import Generator
8
+from typing import Callable, Generic, TypeVar
9
10
_T = TypeVar("_T")
11
tests/worker/test_encoder_decoder_model_runner.py
+10
-11
@@ -1,7 +1,6 @@
1
# SPDX-License-Identifier: Apache-2.0
2
3
import itertools
4
-from typing import List
4
5
import pytest
6
import torch
@@ -43,7 +42,7 @@ def test_empty_seq_group():
42
enable_chunked_prefill=False,
43
enforce_eager=True,
44
)
46
- seq_group_metadata_list: List[SequenceGroupMetadata] = []
45
+ seq_group_metadata_list: list[SequenceGroupMetadata] = []
46
model_input = model_runner._prepare_model_input_tensors(
47
seq_group_metadata_list)
48
(
@@ -103,9 +102,9 @@ def test_prepare_prompt(batch_size):
102
enforce_eager=True,
103
)
104
106
- seq_lens: List[int] = []
107
- encoder_seq_lens: List[int] = []
108
- seq_group_metadata_list: List[SequenceGroupMetadata] = []
105
+ seq_lens: list[int] = []
106
+ encoder_seq_lens: list[int] = []
107
+ seq_group_metadata_list: list[SequenceGroupMetadata] = []
108
block_tables = {0: [1]}
109
cross_block_table = [2]
110
for i in range(batch_size):
@@ -295,9 +294,9 @@ def test_prepare_decode(batch_size, multiple_seqs_per_seq_group):
294
enforce_eager=True,
295
)
296
298
- seq_lens: List[int] = []
299
- encoder_seq_lens: List[int] = []
300
- seq_group_metadata_list: List[SequenceGroupMetadata] = []
297
+ seq_lens: list[int] = []
298
+ encoder_seq_lens: list[int] = []
299
+ seq_group_metadata_list: list[SequenceGroupMetadata] = []
300
block_tables = {
301
0: [1],
302
1: [3]
@@ -503,9 +502,9 @@ def test_prepare_decode_cuda_graph(batch_size, multiple_seqs_per_seq_group):
502
} if multiple_seqs_per_seq_group else {
503
0: [1]
504
}
506
- seq_lens: List[int] = []
507
- encoder_seq_lens: List[int] = []
508
- seq_group_metadata_list: List[SequenceGroupMetadata] = []
505
+ seq_lens: list[int] = []
506
+ encoder_seq_lens: list[int] = []
507
+ seq_group_metadata_list: list[SequenceGroupMetadata] = []
508
509
cross_block_table = [2]
510
expanded_batch_size = 0
tests/worker/test_model_input.py
+5
-6
@@ -1,7 +1,6 @@
1
# SPDX-License-Identifier: Apache-2.0
2
3
import dataclasses
4
-from typing import List, Tuple, Type
4
5
import torch
6
@@ -27,15 +26,15 @@ class MockAttentionBackend(AttentionBackend):
26
raise NotImplementedError
27
28
@staticmethod
30
- def get_metadata_cls() -> Type["AttentionMetadata"]:
29
+ def get_metadata_cls() -> type["AttentionMetadata"]:
30
return AttentionMetadata
31
32
@staticmethod
34
- def get_builder_cls() -> Type["AttentionMetadataBuilder"]:
33
+ def get_builder_cls() -> type["AttentionMetadataBuilder"]:
34
return AttentionMetadataBuilder
35
36
@staticmethod
38
- def get_state_cls() -> Type["CommonAttentionState"]:
37
+ def get_state_cls() -> type["CommonAttentionState"]:
38
return CommonAttentionState
39
40
@staticmethod
@@ -44,7 +43,7 @@ class MockAttentionBackend(AttentionBackend):
43
block_size: int,
44
num_kv_heads: int,
45
head_size: int,
47
- ) -> Tuple[int, ...]:
46
+ ) -> tuple[int, ...]:
47
raise NotImplementedError
48
49
@staticmethod
@@ -57,7 +56,7 @@ class MockAttentionBackend(AttentionBackend):
56
57
@staticmethod
58
def copy_blocks(
60
- kv_caches: List[torch.Tensor],
59
+ kv_caches: list[torch.Tensor],
60
src_to_dists: torch.Tensor,
61
) -> None:
62
pass
tests/worker/test_model_runner.py
+9
-11
@@ -1,7 +1,5 @@
1
# SPDX-License-Identifier: Apache-2.0
2
3
-from typing import List
4
-
3
import pytest
4
import torch
5
@@ -42,8 +40,8 @@ def test_prepare_prompt(batch_size):
40
enable_chunked_prefill=False,
41
)
42
45
- seq_lens: List[int] = []
46
- seq_group_metadata_list: List[SequenceGroupMetadata] = []
43
+ seq_lens: list[int] = []
44
+ seq_group_metadata_list: list[SequenceGroupMetadata] = []
45
block_tables = {0: [1]}
46
for i in range(batch_size):
47
# make sure all tokens fit into one block
@@ -159,8 +157,8 @@ def test_prepare_decode_cuda_graph(batch_size):
157
enable_chunked_prefill=False,
158
)
159
162
- context_lens: List[int] = []
163
- seq_group_metadata_list: List[SequenceGroupMetadata] = []
160
+ context_lens: list[int] = []
161
+ seq_group_metadata_list: list[SequenceGroupMetadata] = []
162
# Assume each seq group finishes prefill.
163
for i in range(batch_size):
164
# make sure all tokens fit into one block
@@ -265,7 +263,7 @@ def test_empty_seq_group():
263
dtype="float16",
264
enforce_eager=False,
265
)
268
- seq_group_metadata_list: List[SequenceGroupMetadata] = []
266
+ seq_group_metadata_list: list[SequenceGroupMetadata] = []
267
model_input = model_runner._prepare_model_input_tensors(
268
seq_group_metadata_list)
269
input_tokens, input_positions, attn_metadata = (
@@ -315,10 +313,10 @@ def test_hybrid_batches(batch_size, enforce_eager, distributed_init):
313
)
314
315
# Add prefill requests.
318
- seq_lens: List[int] = []
319
- seq_group_metadata_list: List[SequenceGroupMetadata] = []
320
- prefill_metadata_list: List[SequenceGroupMetadata] = []
321
- decode_metadata_list: List[SequenceGroupMetadata] = []
316
+ seq_lens: list[int] = []
317
+ seq_group_metadata_list: list[SequenceGroupMetadata] = []
318
+ prefill_metadata_list: list[SequenceGroupMetadata] = []
319
+ decode_metadata_list: list[SequenceGroupMetadata] = []
320
block_tables = {0: [1]}
321
prefill_batch_size = batch_size // 2
322
decode_batch_size = batch_size - prefill_batch_size
tools/profiler/print_layerwise_table.py
+1
-2
@@ -2,13 +2,12 @@
2
3
import argparse
4
import json
5
-from typing import Dict
5
6
from vllm.profiler.layerwise_profile import ModelStatsEntry, SummaryStatsEntry
7
from vllm.profiler.utils import TablePrinter, indent_string
8
9
11
-def flatten_entries(entry_cls, profile_dict: Dict):
10
+def flatten_entries(entry_cls, profile_dict: dict):
11
entries_and_depth = []
12
13
def get_entries(node, curr_depth=0):
tools/profiler/visualize_layerwise_profile.py
+7
-7
@@ -6,7 +6,7 @@ import json
6
import math
7
import os
8
from pathlib import Path
9
-from typing import Any, List, Optional, Tuple
9
+from typing import Any, Optional
10
11
import matplotlib.pyplot as plt
12
import pandas as pd
@@ -24,7 +24,7 @@ def largest_dist_from_leaf(node: dict, depth: int = 0):
24
25
26
def get_entries_at_depth(depth: int,
27
- entries_and_traces: List[Tuple[Any, Any]],
27
+ entries_and_traces: list[tuple[Any, Any]],
28
node: dict,
29
curr_depth: int = 0,
30
trace=()):
@@ -48,9 +48,9 @@ def get_entries_at_depth(depth: int,
48
trace=trace)
49
50
51
-def fold_nodes(root: dict, nodes_to_fold: List[str]):
51
+def fold_nodes(root: dict, nodes_to_fold: list[str]):
52
53
- stack: List[dict] = [root]
53
+ stack: list[dict] = [root]
54
while len(stack) != 0:
55
node = stack.pop()
56
if node['entry']['name'] in nodes_to_fold:
@@ -427,12 +427,12 @@ def main(
427
plot_metric: str,
428
make_names_unique: bool,
429
top_k: int,
430
- json_nodes_to_fold: List[str]):
430
+ json_nodes_to_fold: list[str]):
431
432
- def prepare_data(profile_json: dict, step_keys: List[str]) -> pd.DataFrame:
432
+ def prepare_data(profile_json: dict, step_keys: list[str]) -> pd.DataFrame:
433
434
def get_entries_and_traces(key: str):
435
- entries_and_traces: List[Tuple[Any, Any]] = []
435
+ entries_and_traces: list[tuple[Any, Any]] = []
436
for root in profile_json[key]["summary_stats"]:
437
# Fold nodes in the traces as per user request. i.e. simply
438
# make the requested nodes leaf-nodes.
vllm/_custom_ops.py
+28
-28
@@ -2,7 +2,7 @@
2
3
import contextlib
4
import importlib
5
-from typing import TYPE_CHECKING, List, Optional, Tuple, Union
5
+from typing import TYPE_CHECKING, Optional, Union
6
7
import torch
8
import torch.library
@@ -198,7 +198,7 @@ def rms_norm_dynamic_per_token_quant(
198
quant_dtype: torch.dtype,
199
scale_ub: Optional[torch.Tensor] = None,
200
residual: Optional[torch.Tensor] = None
201
-) -> Tuple[torch.Tensor, torch.Tensor]:
201
+) -> tuple[torch.Tensor, torch.Tensor]:
202
output = torch.empty_like(input, dtype=quant_dtype)
203
scales = torch.empty((input.numel() // input.shape[-1], 1),
204
device=input.device,
@@ -347,7 +347,7 @@ if hasattr(torch.ops._C, "gptq_marlin_24_gemm"):
347
@register_fake("_C::aqlm_gemm")
348
def _aqlm_gemm_fake(input: torch.Tensor, codes: torch.Tensor,
349
codebooks: torch.Tensor, scales: torch.Tensor,
350
- codebook_partition_sizes: List[int],
350
+ codebook_partition_sizes: list[int],
351
bias: Optional[torch.Tensor]) -> torch.Tensor:
352
out_features = codes.size(0) * codebooks.size(2)
353
flat_input = input.reshape((-1, input.size(-1)))
@@ -363,7 +363,7 @@ if hasattr(torch.ops._C, "gptq_marlin_24_gemm"):
363
@register_fake("_C::aqlm_dequant")
364
def _aqlm_dequant_fake(
365
codes: torch.Tensor, codebooks: torch.Tensor,
366
- codebook_partition_sizes: List[int]) -> torch.Tensor:
366
+ codebook_partition_sizes: list[int]) -> torch.Tensor:
367
in_features = codes.size(1) * 8
368
out_features = codes.size(0)
369
return torch.empty((out_features, in_features),
@@ -554,7 +554,7 @@ def cutlass_sparse_scaled_mm_supported(cuda_device_capability: int) -> bool:
554
555
556
def cutlass_sparse_compress(a: torch.Tensor) \
557
- -> Tuple[torch.Tensor, torch.Tensor]:
557
+ -> tuple[torch.Tensor, torch.Tensor]:
558
"""
559
Compresses a sparse matrix for use with Cutlass sparse operations.
560
@@ -571,7 +571,7 @@ def cutlass_sparse_compress(a: torch.Tensor) \
571
- `torch.float16`
572
573
Returns:
574
- Tuple[torch.Tensor, torch.Tensor]:
574
+ tuple[torch.Tensor, torch.Tensor]:
575
A tuple containing:
576
- `a_nzs` (torch.Tensor): A tensor containing non-zero elements of `a`.
577
- `a_meta` (torch.Tensor): A tensor containing metadata for the sparse representation.
@@ -646,14 +646,14 @@ def cutlass_scaled_sparse_mm(
646
# aqlm
647
def aqlm_gemm(input: torch.Tensor, codes: torch.Tensor,
648
codebooks: torch.Tensor, scales: torch.Tensor,
649
- codebook_partition_sizes: List[int],
649
+ codebook_partition_sizes: list[int],
650
bias: Optional[torch.Tensor]) -> torch.Tensor:
651
return torch.ops._C.aqlm_gemm(input, codes, codebooks, scales,
652
codebook_partition_sizes, bias)
653
654
655
def aqlm_dequant(codes: torch.Tensor, codebooks: torch.Tensor,
656
- codebook_partition_sizes: List[int]) -> torch.Tensor:
656
+ codebook_partition_sizes: list[int]) -> torch.Tensor:
657
return torch.ops._C.aqlm_dequant(codes, codebooks,
658
codebook_partition_sizes)
659
@@ -738,7 +738,7 @@ def machete_supported_schedules(
738
group_zeros_type: Optional[torch.dtype] = None,
739
channel_scales_type: Optional[torch.dtype] = None,
740
token_scales_type: Optional[torch.dtype] = None,
741
- out_type: Optional[torch.dtype] = None) -> List[str]:
741
+ out_type: Optional[torch.dtype] = None) -> list[str]:
742
return torch.ops._C.machete_supported_schedules(
743
a_type, b_type.id, group_scales_type, group_zeros_type,
744
channel_scales_type, token_scales_type, out_type)
@@ -783,7 +783,7 @@ def permute_cols(a: torch.Tensor, perm: torch.Tensor) -> torch.Tensor:
783
# fp4
784
def scaled_fp4_quant(
785
input: torch.Tensor,
786
- input_global_scale: torch.Tensor) -> Tuple[torch.Tensor, torch.Tensor]:
786
+ input_global_scale: torch.Tensor) -> tuple[torch.Tensor, torch.Tensor]:
787
"""
788
Quantize input tensor to FP4 and return quantized tensor and scale.
789
@@ -798,7 +798,7 @@ def scaled_fp4_quant(
798
input_global_scale: A scalar scaling factor for the entire tensor.
799
800
Returns:
801
- Tuple[torch.Tensor, torch.Tensor]: The output tensor in FP4 but every
801
+ tuple[torch.Tensor, torch.Tensor]: The output tensor in FP4 but every
802
two values are packed into a uint8 and float8_e4m3 scaling factors
803
in the sizzled layout.
804
"""
@@ -845,7 +845,7 @@ def scaled_fp8_quant(
845
num_token_padding: Optional[int] = None,
846
scale_ub: Optional[torch.Tensor] = None,
847
use_per_token_if_dynamic: bool = False,
848
-) -> Tuple[torch.Tensor, torch.Tensor]:
848
+) -> tuple[torch.Tensor, torch.Tensor]:
849
"""
850
Quantize input tensor to FP8 and return quantized tensor and scale.
851
@@ -866,12 +866,12 @@ def scaled_fp8_quant(
866
in the dynamic quantization case.
867
868
Returns:
869
- Tuple[torch.Tensor, torch.Tensor]: The output tensor in FP8 and
869
+ tuple[torch.Tensor, torch.Tensor]: The output tensor in FP8 and
870
scaling factor.
871
"""
872
# This code assumes batch_dim and num_tokens are flattened
873
assert (input.ndim == 2)
874
- shape: Union[Tuple[int, int], torch.Size] = input.shape
874
+ shape: Union[tuple[int, int], torch.Size] = input.shape
875
# For rocm, the output fp8 dtype is torch.float_e3m3fnuz
876
out_dtype: torch.dtype = torch.float8_e4m3fnuz \
877
if current_platform.is_rocm() else torch.float8_e4m3fn
@@ -903,7 +903,7 @@ def allspark_repack_weight(
903
scale: torch.Tensor,
904
zero_point: Optional[torch.Tensor] = None,
905
has_zp: bool = False
906
-) -> Tuple[torch.Tensor, torch.Tensor, torch.Tensor]:
906
+) -> tuple[torch.Tensor, torch.Tensor, torch.Tensor]:
907
"""
908
Rearrange qweight, scale, and zero_point(if asymmetric) to n32k16 format
909
for Ampere W8A16 Fused Gemm kernel
@@ -917,7 +917,7 @@ def allspark_repack_weight(
917
if use asymmetric quantization, has_zp = True.
918
919
Returns:
920
- Tuple[torch.Tensor, torch.Tensor, Optional[torch.Tensor]] :
920
+ tuple[torch.Tensor, torch.Tensor, Optional[torch.Tensor]] :
921
rearranged weight, scale, and optionally zero_point.
922
"""
923
K = qweight.shape[0]
@@ -964,7 +964,7 @@ def scaled_int8_quant(
964
scale: Optional[torch.Tensor] = None,
965
azp: Optional[torch.Tensor] = None,
966
symmetric: bool = True
967
-) -> Tuple[torch.Tensor, torch.Tensor, Optional[torch.Tensor]]:
967
+) -> tuple[torch.Tensor, torch.Tensor, Optional[torch.Tensor]]:
968
"""
969
Quantize the input tensor to int8 and return the quantized tensor and scale, and maybe azp.
970
@@ -977,7 +977,7 @@ def scaled_int8_quant(
977
symmetric: Whether to use symmetric quantization (scale only, azp ignored).
978
979
Returns:
980
- Tuple[torch.Tensor, torch.Tensor, Optional[torch.Tensor]] : Output int8 tensor, scales, and optionally azp.
980
+ tuple[torch.Tensor, torch.Tensor, Optional[torch.Tensor]] : Output int8 tensor, scales, and optionally azp.
981
"""
982
output = torch.empty_like(input, dtype=torch.int8)
983
if scale is not None:
@@ -1165,13 +1165,13 @@ def concat_and_cache_mla(
1165
scale)
1166
1167
1168
-def copy_blocks(key_caches: List[torch.Tensor],
1169
- value_caches: List[torch.Tensor],
1168
+def copy_blocks(key_caches: list[torch.Tensor],
1169
+ value_caches: list[torch.Tensor],
1170
block_mapping: torch.Tensor) -> None:
1171
torch.ops._C_cache_ops.copy_blocks(key_caches, value_caches, block_mapping)
1172
1173
1174
-def copy_blocks_mla(kv_caches: List[torch.Tensor],
1174
+def copy_blocks_mla(kv_caches: list[torch.Tensor],
1175
block_mapping: torch.Tensor) -> None:
1176
torch.ops._C_cache_ops.copy_blocks_mla(kv_caches, block_mapping)
1177
@@ -1209,7 +1209,7 @@ def get_max_shared_memory_per_block_device_attribute(device: int) -> int:
1209
1210
1211
# custom ar
1212
-def init_custom_ar(ipc_tensors: List[torch.Tensor], rank_data: torch.Tensor,
1212
+def init_custom_ar(ipc_tensors: list[torch.Tensor], rank_data: torch.Tensor,
1213
rank: int, full_nvlink: bool) -> int:
1214
return torch.ops._C_custom_ar.init_custom_ar(ipc_tensors, rank_data, rank,
1215
full_nvlink)
@@ -1229,16 +1229,16 @@ def meta_size() -> int:
1229
return torch.ops._C_custom_ar.meta_size()
1230
1231
1232
-def register_buffer(fa: int, ipc_tensors: List[int]) -> None:
1232
+def register_buffer(fa: int, ipc_tensors: list[int]) -> None:
1233
return torch.ops._C_custom_ar.register_buffer(fa, ipc_tensors)
1234
1235
1236
-def get_graph_buffer_ipc_meta(fa: int) -> Tuple[List[int], List[int]]:
1236
+def get_graph_buffer_ipc_meta(fa: int) -> tuple[list[int], list[int]]:
1237
return torch.ops._C_custom_ar.get_graph_buffer_ipc_meta(fa)
1238
1239
1240
-def register_graph_buffers(fa: int, handles: List[List[int]],
1241
- offsets: List[List[int]]) -> None:
1240
+def register_graph_buffers(fa: int, handles: list[list[int]],
1241
+ offsets: list[list[int]]) -> None:
1242
torch.ops._C_custom_ar.register_graph_buffers(fa, handles, offsets)
1243
1244
@@ -1246,7 +1246,7 @@ def get_flash_mla_metadata(
1246
cache_seqlens: torch.Tensor,
1247
num_heads_per_head_k: int,
1248
num_heads_k: int,
1249
-) -> Tuple[torch.Tensor, torch.Tensor]:
1249
+) -> tuple[torch.Tensor, torch.Tensor]:
1250
"""
1251
Arguments:
1252
cache_seqlens: (batch_size), dtype torch.int32.
@@ -1272,7 +1272,7 @@ def flash_mla_with_kvcache(
1272
num_splits: torch.Tensor,
1273
softmax_scale: Optional[float] = None,
1274
causal: bool = False,
1275
-) -> Tuple[torch.Tensor, torch.Tensor]:
1275
+) -> tuple[torch.Tensor, torch.Tensor]:
1276
"""
1277
Arguments:
1278
q: (batch_size, seq_len_q, num_heads_q, head_dim).
vllm/_ipex_ops.py
+4
-4
@@ -1,6 +1,6 @@
1
# SPDX-License-Identifier: Apache-2.0
2
3
-from typing import List, Optional, Tuple
3
+from typing import Optional
4
5
import torch
6
@@ -18,7 +18,7 @@ class ipex_ops:
18
19
@staticmethod
20
def _reshape_activation_tensor(
21
- x: torch.Tensor) -> Tuple[torch.Tensor, torch.Tensor]:
21
+ x: torch.Tensor) -> tuple[torch.Tensor, torch.Tensor]:
22
num = x.size(0)
23
d = x.size(1) // 2
24
x = x.reshape(num, 2, d)
@@ -213,8 +213,8 @@ class ipex_ops:
213
key, value, key_cache, value_cache, slot_mapping)
214
215
@staticmethod
216
- def copy_blocks(key_caches: List[torch.Tensor],
217
- value_caches: List[torch.Tensor],
216
+ def copy_blocks(key_caches: list[torch.Tensor],
217
+ value_caches: list[torch.Tensor],
218
block_mapping: torch.Tensor) -> None:
219
torch.xpu.copy_blocks( # type: ignore
220
key_caches,
vllm/beam_search.py
+9
-9
@@ -1,7 +1,7 @@
1
# SPDX-License-Identifier: Apache-2.0
2
3
from dataclasses import dataclass
4
-from typing import TYPE_CHECKING, Any, Dict, List, Optional, Union
4
+from typing import TYPE_CHECKING, Any, Optional, Union
5
6
from vllm.sequence import Logprob
7
@@ -17,14 +17,14 @@ class BeamSearchSequence:
17
about to be returned to the user.
18
"""
19
# The tokens includes the prompt.
20
- tokens: List[int]
21
- logprobs: List[Dict[int, Logprob]]
20
+ tokens: list[int]
21
+ logprobs: list[dict[int, Logprob]]
22
cum_logprob: float = 0.0
23
text: Optional[str] = None
24
finish_reason: Optional[str] = None
25
stop_reason: Union[int, str, None] = None
26
multi_modal_data: Optional["MultiModalDataDict"] = None
27
- mm_processor_kwargs: Optional[Dict[str, Any]] = None
27
+ mm_processor_kwargs: Optional[dict[str, Any]] = None
28
29
30
@dataclass
@@ -33,20 +33,20 @@ class BeamSearchOutput:
33
It contains the list of the best beam search sequences.
34
The length of the list is equal to the beam width.
35
"""
36
- sequences: List[BeamSearchSequence]
36
+ sequences: list[BeamSearchSequence]
37
38
39
class BeamSearchInstance:
40
41
- def __init__(self, prompt_tokens: List[int]):
42
- self.beams: List[BeamSearchSequence] = [
41
+ def __init__(self, prompt_tokens: list[int]):
42
+ self.beams: list[BeamSearchSequence] = [
43
BeamSearchSequence(tokens=prompt_tokens, logprobs=[])
44
]
45
- self.completed: List[BeamSearchSequence] = []
45
+ self.completed: list[BeamSearchSequence] = []
46
47
48
def get_beam_search_score(
49
- tokens: List[int],
49
+ tokens: list[int],
50
cumulative_logprob: float,
51
eos_token_id: int,
52
length_penalty: float = 1.0,
vllm/config.py
+71
-70
@@ -7,13 +7,14 @@ import hashlib
7
import json
8
import sys
9
import warnings
10
+from collections import Counter
11
+from collections.abc import Mapping
12
from contextlib import contextmanager
13
from dataclasses import dataclass, field, replace
14
from importlib.util import find_spec
15
from pathlib import Path
14
-from typing import (TYPE_CHECKING, Any, Callable, ClassVar, Counter, Dict,
15
- Final, List, Literal, Mapping, Optional, Protocol, Set,
16
- Tuple, Type, Union)
16
+from typing import (TYPE_CHECKING, Any, Callable, ClassVar, Final, Literal,
17
+ Optional, Protocol, Union)
18
19
import torch
20
from pydantic import BaseModel, Field, PrivateAttr
@@ -67,20 +68,20 @@ _ResolvedTask = Literal["generate", "embed", "classify", "score", "reward",
68
69
RunnerType = Literal["generate", "pooling", "draft", "transcription"]
70
70
-_RUNNER_TASKS: Dict[RunnerType, List[_ResolvedTask]] = {
71
+_RUNNER_TASKS: dict[RunnerType, list[_ResolvedTask]] = {
72
"generate": ["generate"],
73
"pooling": ["embed", "classify", "score", "reward"],
74
"draft": ["draft"],
75
"transcription": ["transcription"],
76
}
77
77
-_TASK_RUNNER: Dict[_ResolvedTask, RunnerType] = {
78
+_TASK_RUNNER: dict[_ResolvedTask, RunnerType] = {
79
task: runner
80
for runner, tasks in _RUNNER_TASKS.items()
81
for task in tasks
82
}
83
83
-HfOverrides = Union[Dict[str, Any], Callable[[PretrainedConfig],
84
+HfOverrides = Union[dict[str, Any], Callable[[PretrainedConfig],
85
PretrainedConfig]]
86
87
@@ -92,7 +93,7 @@ class SupportsHash(Protocol):
93
94
class SupportsMetricsInfo(Protocol):
95
95
- def metrics_info(self) -> Dict[str, str]:
96
+ def metrics_info(self) -> dict[str, str]:
97
...
98
99
@@ -209,7 +210,7 @@ class ModelConfig:
210
excluding anything before input ids/embeddings and after
211
the final hidden states.
212
"""
212
- factors: List[Any] = []
213
+ factors: list[Any] = []
214
factors.append(self.model)
215
factors.append(self.dtype)
216
factors.append(self.quantization)
@@ -233,7 +234,7 @@ class ModelConfig:
234
allowed_local_media_path: str = "",
235
revision: Optional[str] = None,
236
code_revision: Optional[str] = None,
236
- rope_scaling: Optional[Dict[str, Any]] = None,
237
+ rope_scaling: Optional[dict[str, Any]] = None,
238
rope_theta: Optional[float] = None,
239
tokenizer_revision: Optional[str] = None,
240
max_model_len: Optional[int] = None,
@@ -244,19 +245,19 @@ class ModelConfig:
245
max_logprobs: int = 20,
246
disable_sliding_window: bool = False,
247
skip_tokenizer_init: bool = False,
247
- served_model_name: Optional[Union[str, List[str]]] = None,
248
+ served_model_name: Optional[Union[str, list[str]]] = None,
249
limit_mm_per_prompt: Optional[Mapping[str, int]] = None,
250
use_async_output_proc: bool = True,
251
config_format: ConfigFormat = ConfigFormat.AUTO,
252
hf_overrides: Optional[HfOverrides] = None,
252
- mm_processor_kwargs: Optional[Dict[str, Any]] = None,
253
+ mm_processor_kwargs: Optional[dict[str, Any]] = None,
254
disable_mm_preprocessor_cache: bool = False,
254
- override_neuron_config: Optional[Dict[str, Any]] = None,
255
+ override_neuron_config: Optional[dict[str, Any]] = None,
256
override_pooler_config: Optional["PoolerConfig"] = None,
257
logits_processor_pattern: Optional[str] = None,
258
generation_config: Optional[str] = None,
259
enable_sleep_mode: bool = False,
259
- override_generation_config: Optional[Dict[str, Any]] = None,
260
+ override_generation_config: Optional[dict[str, Any]] = None,
261
model_impl: Union[str, ModelImpl] = ModelImpl.AUTO,
262
) -> None:
263
self.model = model
@@ -283,7 +284,7 @@ class ModelConfig:
284
hf_overrides_fn = None
285
286
if rope_scaling is not None:
286
- hf_override: Dict[str, Any] = {"rope_scaling": rope_scaling}
287
+ hf_override: dict[str, Any] = {"rope_scaling": rope_scaling}
288
hf_overrides_kw.update(hf_override)
289
msg = ("`--rope-scaling` will be removed in a future release. "
290
f"'Please instead use `--hf-overrides '{hf_override!r}'`")
@@ -505,8 +506,8 @@ class ModelConfig:
506
507
def _get_preferred_task(
508
self,
508
- architectures: List[str],
509
- supported_tasks: Set[_ResolvedTask],
509
+ architectures: list[str],
510
+ supported_tasks: set[_ResolvedTask],
511
) -> Optional[_ResolvedTask]:
512
model_id = self.model
513
if get_pooling_config(model_id, self.revision):
@@ -516,7 +517,7 @@ class ModelConfig:
517
if self.registry.is_transcription_model(architectures):
518
return "transcription"
519
519
- suffix_to_preferred_task: List[Tuple[str, _ResolvedTask]] = [
520
+ suffix_to_preferred_task: list[tuple[str, _ResolvedTask]] = [
521
# Other models follow this pattern
522
("ForCausalLM", "generate"),
523
("ForConditionalGeneration", "generate"),
@@ -537,27 +538,27 @@ class ModelConfig:
538
def _resolve_task(
539
self,
540
task_option: Union[TaskOption, Literal["draft"]],
540
- ) -> Tuple[Set[_ResolvedTask], _ResolvedTask]:
541
+ ) -> tuple[set[_ResolvedTask], _ResolvedTask]:
542
if task_option == "draft":
543
return {"draft"}, "draft"
544
545
registry = self.registry
546
architectures = self.architectures
547
547
- runner_support: Dict[RunnerType, bool] = {
548
+ runner_support: dict[RunnerType, bool] = {
549
# NOTE: Listed from highest to lowest priority,
550
# in case the model supports multiple of them
551
"transcription": registry.is_transcription_model(architectures),
552
"generate": registry.is_text_generation_model(architectures),
553
"pooling": registry.is_pooling_model(architectures),
554
}
554
- supported_runner_types_lst: List[RunnerType] = [
555
+ supported_runner_types_lst: list[RunnerType] = [
556
runner_type
557
for runner_type, is_supported in runner_support.items()
558
if is_supported
559
]
560
560
- supported_tasks_lst: List[_ResolvedTask] = [
561
+ supported_tasks_lst: list[_ResolvedTask] = [
562
task for runner_type in supported_runner_types_lst
563
for task in _RUNNER_TASKS[runner_type]
564
]
@@ -767,7 +768,7 @@ class ModelConfig:
768
self.use_async_output_proc = False
769
770
def get_hf_config_sliding_window(
770
- self) -> Union[Optional[int], List[Optional[int]]]:
771
+ self) -> Union[Optional[int], list[Optional[int]]]:
772
"""Get the sliding window size, or None if disabled."""
773
774
# Some models, like Qwen2 and Qwen1.5, use `use_sliding_window` in
@@ -778,7 +779,7 @@ class ModelConfig:
779
return None
780
return getattr(self.hf_text_config, "sliding_window", None)
781
781
- def get_sliding_window(self) -> Optional[Union[int, List[Optional[int]]]]:
782
+ def get_sliding_window(self) -> Optional[Union[int, list[Optional[int]]]]:
783
"""Get the sliding window size, or None if disabled.
784
"""
785
# If user disables sliding window, return None.
@@ -888,7 +889,7 @@ class ModelConfig:
889
return num_heads // parallel_config.tensor_parallel_size
890
891
def get_layers_start_end_indices(
891
- self, parallel_config: "ParallelConfig") -> Tuple[int, int]:
892
+ self, parallel_config: "ParallelConfig") -> tuple[int, int]:
893
from vllm.distributed.utils import get_pp_indices
894
if self.hf_text_config.model_type == "deepseek_mtp":
895
total_num_hidden_layers = getattr(self.hf_text_config,
@@ -949,7 +950,7 @@ class ModelConfig:
950
951
return self.multimodal_config
952
952
- def try_get_generation_config(self) -> Dict[str, Any]:
953
+ def try_get_generation_config(self) -> dict[str, Any]:
954
if self.generation_config is None or self.generation_config == "auto":
955
config = try_get_generation_config(
956
self.hf_config_path or self.model,
@@ -967,7 +968,7 @@ class ModelConfig:
968
969
return config.to_diff_dict()
970
970
- def get_diff_sampling_param(self) -> Dict[str, Any]:
971
+ def get_diff_sampling_param(self) -> dict[str, Any]:
972
"""
973
This method returns a dictionary containing the parameters
974
that differ from the default sampling parameters, but only
@@ -975,7 +976,7 @@ class ModelConfig:
976
set, an empty dictionary is returned.
977
978
Returns:
978
- Dict[str, Any]: A dictionary with the differing sampling
979
+ dict[str, Any]: A dictionary with the differing sampling
980
parameters if `generation_config` is set, otherwise an
981
empty dictionary.
982
"""
@@ -1032,7 +1033,7 @@ class ModelConfig:
1033
return self.is_deepseek_mla and not envs.VLLM_MLA_DISABLE
1034
1035
@property
1035
- def supported_runner_types(self) -> Set[RunnerType]:
1036
+ def supported_runner_types(self) -> set[RunnerType]:
1037
return {_TASK_RUNNER[task] for task in self.supported_tasks}
1038
1039
@property
@@ -1075,7 +1076,7 @@ class CacheConfig:
1076
excluding anything before input ids/embeddings and after
1077
the final hidden states.
1078
"""
1078
- factors: List[Any] = []
1079
+ factors: list[Any] = []
1080
factors.append(self.cache_dtype)
1081
# `cpu_offload_gb` does not use `torch.compile` yet.
1082
hash_str = hashlib.md5(str(factors).encode()).hexdigest()
@@ -1183,7 +1184,7 @@ class TokenizerPoolConfig:
1184
pool type.
1185
"""
1186
pool_size: int
1186
- pool_type: Union[str, Type["BaseTokenizerGroup"]]
1187
+ pool_type: Union[str, type["BaseTokenizerGroup"]]
1188
extra_config: dict
1189
1190
def compute_hash(self) -> str:
@@ -1200,7 +1201,7 @@ class TokenizerPoolConfig:
1201
"""
1202
# no factors to consider.
1203
# this config will not affect the computation graph.
1203
- factors: List[Any] = []
1204
+ factors: list[Any] = []
1205
hash_str = hashlib.md5(str(factors).encode()).hexdigest()
1206
return hash_str
1207
@@ -1214,7 +1215,7 @@ class TokenizerPoolConfig:
1215
@classmethod
1216
def create_config(
1217
cls, tokenizer_pool_size: int,
1217
- tokenizer_pool_type: Union[str, Type["BaseTokenizerGroup"]],
1218
+ tokenizer_pool_type: Union[str, type["BaseTokenizerGroup"]],
1219
tokenizer_pool_extra_config: Optional[Union[str, dict]]
1220
) -> Optional["TokenizerPoolConfig"]:
1221
"""Create a TokenizerPoolConfig from the given parameters.
@@ -1285,7 +1286,7 @@ class LoadConfig:
1286
download_dir: Optional[str] = None
1287
model_loader_extra_config: Optional[Union[str, dict]] = field(
1288
default_factory=dict)
1288
- ignore_patterns: Optional[Union[List[str], str]] = None
1289
+ ignore_patterns: Optional[Union[list[str], str]] = None
1290
1291
def compute_hash(self) -> str:
1292
"""
@@ -1301,7 +1302,7 @@ class LoadConfig:
1302
"""
1303
# no factors to consider.
1304
# this config will not affect the computation graph.
1304
- factors: List[Any] = []
1305
+ factors: list[Any] = []
1306
hash_str = hashlib.md5(str(factors).encode()).hexdigest()
1307
return hash_str
1308
@@ -1359,7 +1360,7 @@ class ParallelConfig:
1360
# to "ray" if Ray is installed and fail otherwise. Note that tpu
1361
# and hpu only support Ray for distributed inference.
1362
distributed_executor_backend: Optional[Union[str,
1362
- Type["ExecutorBase"]]] = None
1363
+ type["ExecutorBase"]]] = None
1364
1365
# the full name of the worker class to use. If "auto", the worker class
1366
# will be determined based on the platform.
@@ -1423,7 +1424,7 @@ class ParallelConfig:
1424
excluding anything before input ids/embeddings and after
1425
the final hidden states.
1426
"""
1426
- factors: List[Any] = []
1427
+ factors: list[Any] = []
1428
factors.append(self.pipeline_parallel_size)
1429
factors.append(self.tensor_parallel_size)
1430
return hashlib.sha256(str(factors).encode()).hexdigest()
@@ -1600,7 +1601,7 @@ class SchedulerConfig:
1601
1602
# scheduler class or path. "vllm.core.scheduler.Scheduler" (default)
1603
# or "mod.custom_class".
1603
- scheduler_cls: Union[str, Type[object]] = "vllm.core.scheduler.Scheduler"
1604
+ scheduler_cls: Union[str, type[object]] = "vllm.core.scheduler.Scheduler"
1605
1606
def compute_hash(self) -> str:
1607
"""
@@ -1616,7 +1617,7 @@ class SchedulerConfig:
1617
"""
1618
# no factors to consider.
1619
# this config will not affect the computation graph.
1619
- factors: List[Any] = []
1620
+ factors: list[Any] = []
1621
hash_str = hashlib.md5(str(factors).encode()).hexdigest()
1622
return hash_str
1623
@@ -1752,7 +1753,7 @@ class DeviceConfig:
1753
# no factors to consider.
1754
# the device/platform information will be summarized
1755
# by torch/vllm automatically.
1755
- factors: List[Any] = []
1756
+ factors: list[Any] = []
1757
hash_str = hashlib.md5(str(factors).encode()).hexdigest()
1758
return hash_str
1759
@@ -1798,7 +1799,7 @@ class SpeculativeConfig:
1799
"""
1800
# no factors to consider.
1801
# spec decode does not use `torch.compile` yet.
1801
- factors: List[Any] = []
1802
+ factors: list[Any] = []
1803
hash_str = hashlib.md5(str(factors).encode()).hexdigest()
1804
return hash_str
1805
@@ -2261,7 +2262,7 @@ class LoRAConfig:
2262
lora_extra_vocab_size: int = 256
2263
# This is a constant.
2264
lora_vocab_padding_size: ClassVar[int] = 256
2264
- long_lora_scaling_factors: Optional[Tuple[float]] = None
2265
+ long_lora_scaling_factors: Optional[tuple[float]] = None
2266
bias_enabled: bool = False
2267
2268
def compute_hash(self) -> str:
@@ -2278,7 +2279,7 @@ class LoRAConfig:
2279
"""
2280
# no factors to consider.
2281
# LoRA is not compatible with `torch.compile` .
2281
- factors: List[Any] = []
2282
+ factors: list[Any] = []
2283
hash_str = hashlib.md5(str(factors).encode()).hexdigest()
2284
return hash_str
2285
@@ -2350,7 +2351,7 @@ class PromptAdapterConfig:
2351
"""
2352
# no factors to consider.
2353
# this config will not affect the computation graph.
2353
- factors: List[Any] = []
2354
+ factors: list[Any] = []
2355
hash_str = hashlib.md5(str(factors).encode()).hexdigest()
2356
return hash_str
2357
@@ -2395,7 +2396,7 @@ class MultiModalConfig:
2396
"""
2397
# no factors to consider.
2398
# this config will not affect the computation graph.
2398
- factors: List[Any] = []
2399
+ factors: list[Any] = []
2400
hash_str = hashlib.md5(str(factors).encode()).hexdigest()
2401
return hash_str
2402
@@ -2431,7 +2432,7 @@ class PoolerConfig:
2432
are returned.
2433
"""
2434
2434
- returned_token_ids: Optional[List[int]] = None
2435
+ returned_token_ids: Optional[list[int]] = None
2436
"""
2437
A list of indices for the vocabulary dimensions to be extracted,
2438
such as the token IDs of ``good_token`` and ``bad_token`` in the
@@ -2452,7 +2453,7 @@ class PoolerConfig:
2453
"""
2454
# no factors to consider.
2455
# this config will not affect the computation graph.
2455
- factors: List[Any] = []
2456
+ factors: list[Any] = []
2457
hash_str = hashlib.md5(str(factors).encode()).hexdigest()
2458
return hash_str
2459
@@ -2469,7 +2470,7 @@ _STR_DTYPE_TO_TORCH_DTYPE = {
2470
"bfloat16": torch.bfloat16,
2471
}
2472
2472
-_ROCM_NOT_SUPPORTED_DTYPE: List[str] = [] #
2473
+_ROCM_NOT_SUPPORTED_DTYPE: list[str] = [] #
2474
2475
2476
def _get_and_verify_dtype(
@@ -2558,7 +2559,7 @@ def _get_and_verify_max_len(
2559
hf_config: PretrainedConfig,
2560
max_model_len: Optional[int],
2561
disable_sliding_window: bool,
2561
- sliding_window_len: Optional[Union[int, List[Optional[int]]]],
2562
+ sliding_window_len: Optional[Union[int, list[Optional[int]]]],
2563
spec_target_max_model_len: Optional[int] = None,
2564
encoder_config: Optional[Any] = None,
2565
) -> int:
@@ -2684,7 +2685,7 @@ def _get_and_verify_max_len(
2685
2686
2687
def get_min_sliding_window(
2687
- sliding_window: Union[int, List[Optional[int]]]) -> int:
2688
+ sliding_window: Union[int, list[Optional[int]]]) -> int:
2689
if isinstance(sliding_window, list):
2690
return min(s for s in sliding_window if s is not None)
2691
@@ -2692,7 +2693,7 @@ def get_min_sliding_window(
2693
2694
2695
def get_served_model_name(model: str,
2695
- served_model_name: Optional[Union[str, List[str]]]):
2696
+ served_model_name: Optional[Union[str, list[str]]]):
2697
"""
2698
If the input is a non-empty list, the first model_name in
2699
`served_model_name` is taken.
@@ -2731,7 +2732,7 @@ class DecodingConfig:
2732
"""
2733
# no factors to consider.
2734
# this config will not affect the computation graph.
2734
- factors: List[Any] = []
2735
+ factors: list[Any] = []
2736
hash_str = hashlib.md5(str(factors).encode()).hexdigest()
2737
return hash_str
2738
@@ -2774,7 +2775,7 @@ class ObservabilityConfig:
2775
"""
2776
# no factors to consider.
2777
# this config will not affect the computation graph.
2777
- factors: List[Any] = []
2778
+ factors: list[Any] = []
2779
hash_str = hashlib.md5(str(factors).encode()).hexdigest()
2780
return hash_str
2781
@@ -2833,7 +2834,7 @@ class KVTransferConfig(BaseModel):
2834
"""
2835
# no factors to consider.
2836
# this config will not affect the computation graph.
2836
- factors: List[Any] = []
2837
+ factors: list[Any] = []
2838
hash_str = hashlib.md5(str(factors).encode()).hexdigest()
2839
return hash_str
2840
@@ -2930,7 +2931,7 @@ class CompilationConfig(BaseModel):
2931
torch.compile will handle cudagraph capture logic in the future.
2932
- cudagraph_capture_sizes: sizes to capture cudagraph.
2933
- None (default): capture sizes are inferred from vllm config.
2933
- - List[int]: capture sizes are specified as given.
2934
+ - list[int]: capture sizes are specified as given.
2935
- cudagraph_num_of_warmups: number of warmup runs for cudagraph.
2936
It means the first several runs will be treated as warmup runs.
2937
Only after that, the execution will be recorded, and the recorded
@@ -2972,17 +2973,17 @@ class CompilationConfig(BaseModel):
2973
debug_dump_path: str = ""
2974
cache_dir: str = ""
2975
backend: str = ""
2975
- custom_ops: List[str] = Field(default_factory=list)
2976
- splitting_ops: List[str] = Field(default=None) # type: ignore
2976
+ custom_ops: list[str] = Field(default_factory=list)
2977
+ splitting_ops: list[str] = Field(default=None) # type: ignore
2978
2979
use_inductor: bool = True
2979
- compile_sizes: Optional[List[Union[int, str]]] = Field(default=None)
2980
- inductor_compile_config: Dict = Field(default_factory=dict)
2981
- inductor_passes: Dict[str, str] = Field(default_factory=dict)
2980
+ compile_sizes: Optional[list[Union[int, str]]] = Field(default=None)
2981
+ inductor_compile_config: dict = Field(default_factory=dict)
2982
+ inductor_passes: dict[str, str] = Field(default_factory=dict)
2983
2984
use_cudagraph: bool = False
2985
cudagraph_num_of_warmups: int = 0
2985
- cudagraph_capture_sizes: Optional[List[int]] = None
2986
+ cudagraph_capture_sizes: Optional[list[int]] = None
2987
cudagraph_copy_inputs: bool = False
2988
2989
class PassConfig(BaseModel):
@@ -2998,7 +2999,7 @@ class CompilationConfig(BaseModel):
2999
- enable_noop: whether to enable the custom no-op elimination pass.
3000
TODO(luka) better pass enabling system.
3001
"""
3001
- dump_graph_stages: List[str] = Field(default_factory=list)
3002
+ dump_graph_stages: list[str] = Field(default_factory=list)
3003
dump_graph_dir: Path = Field(default=Path("."))
3004
enable_fusion: bool = True
3005
enable_noop: bool = True
@@ -3026,20 +3027,20 @@ class CompilationConfig(BaseModel):
3027
max_capture_size: int = PrivateAttr
3028
local_cache_dir: str = PrivateAttr # local cache dir for each rank
3029
# optimization:
3029
- # Intuitively, bs_to_padded_graph_size should be Dict[int, int].
3030
+ # Intuitively, bs_to_padded_graph_size should be dict[int, int].
3031
# since we know all keys are in a range [0, max_capture_size],
3031
- # we can optimize it to List[int] for better lookup performance.
3032
- bs_to_padded_graph_size: List[int] = PrivateAttr
3032
+ # we can optimize it to list[int] for better lookup performance.
3033
+ bs_to_padded_graph_size: list[int] = PrivateAttr
3034
3035
# keep track of enabled and disabled custom ops
3036
enabled_custom_ops: Counter[str] = PrivateAttr
3037
disabled_custom_ops: Counter[str] = PrivateAttr
3037
- traced_files: Set[str] = PrivateAttr
3038
+ traced_files: set[str] = PrivateAttr
3039
compilation_time: float = PrivateAttr
3040
3041
# Per-model forward context
3042
# Map from layer name to the attention cls
3042
- static_forward_context: Dict[str, Any] = PrivateAttr
3043
+ static_forward_context: dict[str, Any] = PrivateAttr
3044
3045
def compute_hash(self) -> str:
3046
"""
@@ -3053,7 +3054,7 @@ class CompilationConfig(BaseModel):
3054
excluding anything before input ids/embeddings and after
3055
the final hidden states.
3056
"""
3056
- factors: List[Any] = []
3057
+ factors: list[Any] = []
3058
factors.append(self.level)
3059
factors.append(self.backend)
3060
factors.append(self.custom_ops)
@@ -3150,7 +3151,7 @@ class CompilationConfig(BaseModel):
3151
return VllmBackend(vllm_config)
3152
3153
def init_with_cudagraph_sizes(self,
3153
- cudagraph_capture_sizes: List[int]) -> None:
3154
+ cudagraph_capture_sizes: list[int]) -> None:
3155
"""To complete the initialization of config,
3156
we need to know the cudagraph sizes."""
3157
@@ -3243,10 +3244,10 @@ class VllmConfig:
3244
excluding anything before input ids/embeddings and after
3245
the final hidden states.
3246
"""
3246
- factors: List[Any] = []
3247
+ factors: list[Any] = []
3248
3249
# summarize vllm config
3249
- vllm_factors: List[Any] = []
3250
+ vllm_factors: list[Any] = []
3251
from vllm import __version__
3252
vllm_factors.append(__version__)
3253
if self.model_config:
vllm/connections.py
+2
-1
@@ -1,7 +1,8 @@
1
# SPDX-License-Identifier: Apache-2.0
2
3
+from collections.abc import Mapping, MutableMapping
4
from pathlib import Path
4
-from typing import Mapping, MutableMapping, Optional
5
+from typing import Optional
6
from urllib.parse import urlparse
7
8
import aiohttp
vllm/entrypoints/api_server.py
+2
-1
@@ -10,7 +10,8 @@ import asyncio
10
import json
11
import ssl
12
from argparse import Namespace
13
-from typing import Any, AsyncGenerator, Optional
13
+from collections.abc import AsyncGenerator
14
+from typing import Any, Optional
15
16
from fastapi import FastAPI, Request
17
from fastapi.responses import JSONResponse, Response, StreamingResponse
vllm/entrypoints/chat_utils.py
+25
-24
@@ -5,10 +5,11 @@ import codecs
5
import json
6
from abc import ABC, abstractmethod
7
from collections import defaultdict, deque
8
+from collections.abc import Awaitable, Iterable
9
from functools import cache, lru_cache, partial
10
from pathlib import Path
10
-from typing import (Any, Awaitable, Callable, Dict, Generic, Iterable, List,
11
- Literal, Optional, Tuple, TypeVar, Union, cast)
11
+from typing import (Any, Callable, Generic, Literal, Optional, TypeVar, Union,
12
+ cast)
13
14
import jinja2.nodes
15
import transformers.utils.chat_template_utils as hf_chat_utils
@@ -117,7 +118,7 @@ class CustomChatCompletionMessageParam(TypedDict, total=False):
118
role: Required[str]
119
"""The role of the message's author."""
120
120
- content: Union[str, List[ChatCompletionContentPartParam]]
121
+ content: Union[str, list[ChatCompletionContentPartParam]]
122
"""The contents of the message."""
123
124
name: str
@@ -143,7 +144,7 @@ class ConversationMessage(TypedDict, total=False):
144
role: Required[str]
145
"""The role of the message's author."""
146
146
- content: Union[Optional[str], List[Dict[str, str]]]
147
+ content: Union[Optional[str], list[dict[str, str]]]
148
"""The contents of the message"""
149
150
tool_call_id: Optional[str]
@@ -495,13 +496,13 @@ class BaseMultiModalContentParser(ABC):
496
super().__init__()
497
498
# multimodal placeholder_string : count
498
- self._placeholder_counts: Dict[str, int] = defaultdict(lambda: 0)
499
+ self._placeholder_counts: dict[str, int] = defaultdict(lambda: 0)
500
501
def _add_placeholder(self, placeholder: Optional[str]):
502
if placeholder:
503
self._placeholder_counts[placeholder] += 1
504
504
- def mm_placeholder_counts(self) -> Dict[str, int]:
505
+ def mm_placeholder_counts(self) -> dict[str, int]:
506
return dict(self._placeholder_counts)
507
508
@abstractmethod
@@ -652,12 +653,12 @@ def load_chat_template(
653
654
# TODO: Let user specify how to insert multimodal tokens into prompt
655
# (similar to chat template)
655
-def _get_full_multimodal_text_prompt(placeholder_counts: Dict[str, int],
656
+def _get_full_multimodal_text_prompt(placeholder_counts: dict[str, int],
657
text_prompt: str) -> str:
658
"""Combine multimodal prompts for a multimodal language model."""
659
660
# Look through the text prompt to check for missing placeholders
660
- missing_placeholders: List[str] = []
661
+ missing_placeholders: list[str] = []
662
for placeholder in placeholder_counts:
663
664
# For any existing placeholder in the text prompt, we leave it as is
@@ -684,10 +685,10 @@ _InputAudioParser = partial(cast, ChatCompletionContentPartInputAudioParam)
685
_RefusalParser = partial(cast, ChatCompletionContentPartRefusalParam)
686
_VideoParser = partial(cast, ChatCompletionContentPartVideoParam)
687
687
-_ContentPart: TypeAlias = Union[str, Dict[str, str], InputAudio]
688
+_ContentPart: TypeAlias = Union[str, dict[str, str], InputAudio]
689
690
# Define a mapping from part types to their corresponding parsing functions.
690
-MM_PARSER_MAP: Dict[
691
+MM_PARSER_MAP: dict[
692
str,
693
Callable[[ChatCompletionContentPartParam], _ContentPart],
694
] = {
@@ -749,7 +750,7 @@ def _parse_chat_message_content_mm_part(
750
part)
751
return "audio_url", audio_params.get("audio_url", "")
752
if part.get("input_audio") is not None:
752
- input_audio_params = cast(Dict[str, str], part)
753
+ input_audio_params = cast(dict[str, str], part)
754
return "input_audio", input_audio_params
755
if part.get("video_url") is not None:
756
video_params = cast(CustomChatCompletionContentSimpleVideoParam,
@@ -773,7 +774,7 @@ def _parse_chat_message_content_parts(
774
mm_tracker: BaseMultiModalItemTracker,
775
*,
776
wrap_dicts: bool,
776
-) -> List[ConversationMessage]:
777
+) -> list[ConversationMessage]:
778
content = list[_ContentPart]()
779
780
mm_parser = mm_tracker.create_parser()
@@ -791,7 +792,7 @@ def _parse_chat_message_content_parts(
792
# Parsing wraps images and texts as interleaved dictionaries
793
return [ConversationMessage(role=role,
794
content=content)] # type: ignore
794
- texts = cast(List[str], content)
795
+ texts = cast(list[str], content)
796
text_prompt = "\n".join(texts)
797
mm_placeholder_counts = mm_parser.mm_placeholder_counts()
798
if mm_placeholder_counts:
@@ -866,7 +867,7 @@ def _parse_chat_message_content(
867
message: ChatCompletionMessageParam,
868
mm_tracker: BaseMultiModalItemTracker,
869
content_format: _ChatTemplateContentFormat,
869
-) -> List[ConversationMessage]:
870
+) -> list[ConversationMessage]:
871
role = message["role"]
872
content = message.get("content")
873
@@ -900,7 +901,7 @@ def _parse_chat_message_content(
901
return result
902
903
903
-def _postprocess_messages(messages: List[ConversationMessage]) -> None:
904
+def _postprocess_messages(messages: list[ConversationMessage]) -> None:
905
# per the Transformers docs & maintainers, tool call arguments in
906
# assistant-role messages with tool_calls need to be dicts not JSON str -
907
# this is how tool-use chat templates will expect them moving forwards
@@ -916,12 +917,12 @@ def _postprocess_messages(messages: List[ConversationMessage]) -> None:
917
918
919
def parse_chat_messages(
919
- messages: List[ChatCompletionMessageParam],
920
+ messages: list[ChatCompletionMessageParam],
921
model_config: ModelConfig,
922
tokenizer: AnyTokenizer,
923
content_format: _ChatTemplateContentFormat,
923
-) -> Tuple[List[ConversationMessage], Optional[MultiModalDataDict]]:
924
- conversation: List[ConversationMessage] = []
924
+) -> tuple[list[ConversationMessage], Optional[MultiModalDataDict]]:
925
+ conversation: list[ConversationMessage] = []
926
mm_tracker = MultiModalItemTracker(model_config, tokenizer)
927
928
for msg in messages:
@@ -939,12 +940,12 @@ def parse_chat_messages(
940
941
942
def parse_chat_messages_futures(
942
- messages: List[ChatCompletionMessageParam],
943
+ messages: list[ChatCompletionMessageParam],
944
model_config: ModelConfig,
945
tokenizer: AnyTokenizer,
946
content_format: _ChatTemplateContentFormat,
946
-) -> Tuple[List[ConversationMessage], Awaitable[Optional[MultiModalDataDict]]]:
947
- conversation: List[ConversationMessage] = []
947
+) -> tuple[list[ConversationMessage], Awaitable[Optional[MultiModalDataDict]]]:
948
+ conversation: list[ConversationMessage] = []
949
mm_tracker = AsyncMultiModalItemTracker(model_config, tokenizer)
950
951
for msg in messages:
@@ -963,7 +964,7 @@ def parse_chat_messages_futures(
964
965
def apply_hf_chat_template(
966
tokenizer: Union[PreTrainedTokenizer, PreTrainedTokenizerFast],
966
- conversation: List[ConversationMessage],
967
+ conversation: list[ConversationMessage],
968
chat_template: Optional[str],
969
*,
970
tokenize: bool = False, # Different from HF's default
@@ -985,10 +986,10 @@ def apply_hf_chat_template(
986
987
def apply_mistral_chat_template(
988
tokenizer: MistralTokenizer,
988
- messages: List[ChatCompletionMessageParam],
989
+ messages: list[ChatCompletionMessageParam],
990
chat_template: Optional[str] = None,
991
**kwargs: Any,
991
-) -> List[int]:
992
+) -> list[int]:
993
if chat_template is not None:
994
logger.warning_once(
995
"'chat_template' cannot be overridden for mistral tokenizer.")
vllm/entrypoints/cli/openai.py
+5
-5
@@ -5,7 +5,7 @@ import argparse
5
import os
6
import signal
7
import sys
8
-from typing import List, Optional, Tuple
8
+from typing import Optional
9
10
from openai import OpenAI
11
from openai.types.chat import ChatCompletionMessageParam
@@ -23,7 +23,7 @@ def _register_signal_handlers():
23
signal.signal(signal.SIGTSTP, signal_handler)
24
25
26
-def _interactive_cli(args: argparse.Namespace) -> Tuple[str, OpenAI]:
26
+def _interactive_cli(args: argparse.Namespace) -> tuple[str, OpenAI]:
27
_register_signal_handlers()
28
29
base_url = args.url
@@ -43,7 +43,7 @@ def _interactive_cli(args: argparse.Namespace) -> Tuple[str, OpenAI]:
43
44
def chat(system_prompt: Optional[str], model_name: str,
45
client: OpenAI) -> None:
46
- conversation: List[ChatCompletionMessageParam] = []
46
+ conversation: list[ChatCompletionMessageParam] = []
47
if system_prompt is not None:
48
conversation.append({"role": "system", "content": system_prompt})
49
@@ -100,7 +100,7 @@ class ChatCommand(CLISubcommand):
100
def cmd(args: argparse.Namespace) -> None:
101
model_name, client = _interactive_cli(args)
102
system_prompt = args.system_prompt
103
- conversation: List[ChatCompletionMessageParam] = []
103
+ conversation: list[ChatCompletionMessageParam] = []
104
if system_prompt is not None:
105
conversation.append({"role": "system", "content": system_prompt})
106
@@ -168,5 +168,5 @@ class CompleteCommand(CLISubcommand):
168
return complete_parser
169
170
171
-def cmd_init() -> List[CLISubcommand]:
171
+def cmd_init() -> list[CLISubcommand]:
172
return [ChatCommand(), CompleteCommand()]
vllm/entrypoints/cli/serve.py
+1
-2
@@ -1,7 +1,6 @@
1
# SPDX-License-Identifier: Apache-2.0
2
3
import argparse
4
-from typing import List
4
5
import uvloop
6
@@ -59,5 +58,5 @@ class ServeSubcommand(CLISubcommand):
58
return make_arg_parser(serve_parser)
59
60
62
-def cmd_init() -> List[CLISubcommand]:
61
+def cmd_init() -> list[CLISubcommand]:
62
return [ServeSubcommand()]
vllm/entrypoints/llm.py
+105
-105
@@ -2,9 +2,9 @@
2
3
import itertools
4
import warnings
5
+from collections.abc import Sequence
6
from contextlib import contextmanager
6
-from typing import (Any, Callable, ClassVar, Dict, List, Optional, Sequence,
7
- Tuple, Type, Union, cast, overload)
7
+from typing import Any, Callable, ClassVar, Optional, Union, cast, overload
8
9
import cloudpickle
10
import torch.nn as nn
@@ -177,11 +177,11 @@ class LLM:
177
disable_custom_all_reduce: bool = False,
178
disable_async_output_proc: bool = False,
179
hf_overrides: Optional[HfOverrides] = None,
180
- mm_processor_kwargs: Optional[Dict[str, Any]] = None,
180
+ mm_processor_kwargs: Optional[dict[str, Any]] = None,
181
# After positional args are removed, move this right below `model`
182
task: TaskOption = "auto",
183
override_pooler_config: Optional[PoolerConfig] = None,
184
- compilation_config: Optional[Union[int, Dict[str, Any]]] = None,
184
+ compilation_config: Optional[Union[int, dict[str, Any]]] = None,
185
**kwargs,
186
) -> None:
187
'''
@@ -246,7 +246,7 @@ class LLM:
246
self.request_counter = Counter()
247
248
@staticmethod
249
- def get_engine_class() -> Type[LLMEngine]:
249
+ def get_engine_class() -> type[LLMEngine]:
250
if envs.VLLM_USE_V1:
251
# Lazy import: the v1 package isn't distributed
252
from vllm.v1.engine.llm_engine import LLMEngine as V1LLMEngine
@@ -283,11 +283,11 @@ class LLM:
283
Sequence[SamplingParams]]] = None,
284
*,
285
use_tqdm: bool = True,
286
- lora_request: Optional[Union[List[LoRARequest], LoRARequest]] = None,
286
+ lora_request: Optional[Union[list[LoRARequest], LoRARequest]] = None,
287
prompt_adapter_request: Optional[PromptAdapterRequest] = None,
288
guided_options_request: Optional[Union[LLMGuidedOptions,
289
GuidedDecodingRequest]] = None,
290
- ) -> List[RequestOutput]:
290
+ ) -> list[RequestOutput]:
291
...
292
293
@overload # LEGACY: single (prompt + optional token ids)
@@ -296,30 +296,30 @@ class LLM:
296
self,
297
prompts: str,
298
sampling_params: Optional[Union[SamplingParams,
299
- List[SamplingParams]]] = None,
300
- prompt_token_ids: Optional[List[int]] = None,
299
+ list[SamplingParams]]] = None,
300
+ prompt_token_ids: Optional[list[int]] = None,
301
use_tqdm: bool = True,
302
- lora_request: Optional[Union[List[LoRARequest], LoRARequest]] = None,
302
+ lora_request: Optional[Union[list[LoRARequest], LoRARequest]] = None,
303
prompt_adapter_request: Optional[PromptAdapterRequest] = None,
304
guided_options_request: Optional[Union[LLMGuidedOptions,
305
GuidedDecodingRequest]] = None,
306
- ) -> List[RequestOutput]:
306
+ ) -> list[RequestOutput]:
307
...
308
309
@overload # LEGACY: multi (prompt + optional token ids)
310
@deprecated("'prompt_token_ids' will become part of 'prompts'")
311
def generate(
312
self,
313
- prompts: List[str],
313
+ prompts: list[str],
314
sampling_params: Optional[Union[SamplingParams,
315
- List[SamplingParams]]] = None,
316
- prompt_token_ids: Optional[List[List[int]]] = None,
315
+ list[SamplingParams]]] = None,
316
+ prompt_token_ids: Optional[list[list[int]]] = None,
317
use_tqdm: bool = True,
318
- lora_request: Optional[Union[List[LoRARequest], LoRARequest]] = None,
318
+ lora_request: Optional[Union[list[LoRARequest], LoRARequest]] = None,
319
prompt_adapter_request: Optional[PromptAdapterRequest] = None,
320
guided_options_request: Optional[Union[LLMGuidedOptions,
321
GuidedDecodingRequest]] = None,
322
- ) -> List[RequestOutput]:
322
+ ) -> list[RequestOutput]:
323
...
324
325
@overload # LEGACY: single (token ids + optional prompt)
@@ -328,32 +328,32 @@ class LLM:
328
self,
329
prompts: Optional[str] = None,
330
sampling_params: Optional[Union[SamplingParams,
331
- List[SamplingParams]]] = None,
331
+ list[SamplingParams]]] = None,
332
*,
333
- prompt_token_ids: List[int],
333
+ prompt_token_ids: list[int],
334
use_tqdm: bool = True,
335
- lora_request: Optional[Union[List[LoRARequest], LoRARequest]] = None,
335
+ lora_request: Optional[Union[list[LoRARequest], LoRARequest]] = None,
336
prompt_adapter_request: Optional[PromptAdapterRequest] = None,
337
guided_options_request: Optional[Union[LLMGuidedOptions,
338
GuidedDecodingRequest]] = None,
339
- ) -> List[RequestOutput]:
339
+ ) -> list[RequestOutput]:
340
...
341
342
@overload # LEGACY: multi (token ids + optional prompt)
343
@deprecated("'prompt_token_ids' will become part of 'prompts'")
344
def generate(
345
self,
346
- prompts: Optional[List[str]] = None,
346
+ prompts: Optional[list[str]] = None,
347
sampling_params: Optional[Union[SamplingParams,
348
- List[SamplingParams]]] = None,
348
+ list[SamplingParams]]] = None,
349
*,
350
- prompt_token_ids: List[List[int]],
350
+ prompt_token_ids: list[list[int]],
351
use_tqdm: bool = True,
352
- lora_request: Optional[Union[List[LoRARequest], LoRARequest]] = None,
352
+ lora_request: Optional[Union[list[LoRARequest], LoRARequest]] = None,
353
prompt_adapter_request: Optional[PromptAdapterRequest] = None,
354
guided_options_request: Optional[Union[LLMGuidedOptions,
355
GuidedDecodingRequest]] = None,
356
- ) -> List[RequestOutput]:
356
+ ) -> list[RequestOutput]:
357
...
358
359
@overload # LEGACY: single or multi token ids [pos-only]
@@ -362,13 +362,13 @@ class LLM:
362
self,
363
prompts: None,
364
sampling_params: None,
365
- prompt_token_ids: Union[List[int], List[List[int]]],
365
+ prompt_token_ids: Union[list[int], list[list[int]]],
366
use_tqdm: bool = True,
367
- lora_request: Optional[Union[List[LoRARequest], LoRARequest]] = None,
367
+ lora_request: Optional[Union[list[LoRARequest], LoRARequest]] = None,
368
prompt_adapter_request: Optional[PromptAdapterRequest] = None,
369
guided_options_request: Optional[Union[LLMGuidedOptions,
370
GuidedDecodingRequest]] = None,
371
- ) -> List[RequestOutput]:
371
+ ) -> list[RequestOutput]:
372
...
373
374
@deprecate_kwargs(
@@ -379,17 +379,17 @@ class LLM:
379
def generate(
380
self,
381
prompts: Union[Union[PromptType, Sequence[PromptType]],
382
- Optional[Union[str, List[str]]]] = None,
382
+ Optional[Union[str, list[str]]]] = None,
383
sampling_params: Optional[Union[SamplingParams,
384
Sequence[SamplingParams]]] = None,
385
- prompt_token_ids: Optional[Union[List[int], List[List[int]]]] = None,
385
+ prompt_token_ids: Optional[Union[list[int], list[list[int]]]] = None,
386
use_tqdm: bool = True,
387
- lora_request: Optional[Union[List[LoRARequest], LoRARequest]] = None,
387
+ lora_request: Optional[Union[list[LoRARequest], LoRARequest]] = None,
388
prompt_adapter_request: Optional[PromptAdapterRequest] = None,
389
guided_options_request: Optional[Union[LLMGuidedOptions,
390
GuidedDecodingRequest]] = None,
391
- priority: Optional[List[int]] = None,
392
- ) -> List[RequestOutput]:
391
+ priority: Optional[list[int]] = None,
392
+ ) -> list[RequestOutput]:
393
"""Generates the completions for the input prompts.
394
395
This class automatically batches the given prompts, considering
@@ -440,7 +440,7 @@ class LLM:
440
441
if prompt_token_ids is not None:
442
parsed_prompts = self._convert_v1_inputs(
443
- prompts=cast(Optional[Union[str, List[str]]], prompts),
443
+ prompts=cast(Optional[Union[str, list[str]]], prompts),
444
prompt_token_ids=prompt_token_ids,
445
)
446
else:
@@ -473,8 +473,8 @@ class LLM:
473
def collective_rpc(self,
474
method: Union[str, Callable[..., _R]],
475
timeout: Optional[float] = None,
476
- args: Tuple = (),
477
- kwargs: Optional[Dict[str, Any]] = None) -> List[_R]:
476
+ args: tuple = (),
477
+ kwargs: Optional[dict[str, Any]] = None) -> list[_R]:
478
"""
479
Execute an RPC call on all workers.
480
@@ -510,9 +510,9 @@ class LLM:
510
511
def beam_search(
512
self,
513
- prompts: List[Union[TokensPrompt, TextPrompt]],
513
+ prompts: list[Union[TokensPrompt, TextPrompt]],
514
params: BeamSearchParams,
515
- ) -> List[BeamSearchOutput]:
515
+ ) -> list[BeamSearchOutput]:
516
"""
517
Generate sequences using beam search.
518
@@ -543,7 +543,7 @@ class LLM:
543
beam_search_params = SamplingParams(logprobs=2 * beam_width,
544
max_tokens=1,
545
temperature=temperature)
546
- instances: List[BeamSearchInstance] = []
546
+ instances: list[BeamSearchInstance] = []
547
548
for prompt in prompts:
549
if is_token_prompt(prompt):
@@ -553,12 +553,12 @@ class LLM:
553
instances.append(BeamSearchInstance(prompt_tokens))
554
555
for _ in range(max_tokens):
556
- all_beams: List[BeamSearchSequence] = list(
556
+ all_beams: list[BeamSearchSequence] = list(
557
sum((instance.beams for instance in instances), []))
558
pos = [0] + list(
559
itertools.accumulate(
560
len(instance.beams) for instance in instances))
561
- instance_start_and_end: List[Tuple[int, int]] = list(
561
+ instance_start_and_end: list[tuple[int, int]] = list(
562
zip(pos[:-1], pos[1:]))
563
564
if len(all_beams) == 0:
@@ -620,19 +620,19 @@ class LLM:
620
621
def chat(
622
self,
623
- messages: Union[List[ChatCompletionMessageParam],
624
- List[List[ChatCompletionMessageParam]]],
623
+ messages: Union[list[ChatCompletionMessageParam],
624
+ list[list[ChatCompletionMessageParam]]],
625
sampling_params: Optional[Union[SamplingParams,
626
- List[SamplingParams]]] = None,
626
+ list[SamplingParams]]] = None,
627
use_tqdm: bool = True,
628
lora_request: Optional[LoRARequest] = None,
629
chat_template: Optional[str] = None,
630
chat_template_content_format: ChatTemplateContentFormatOption = "auto",
631
add_generation_prompt: bool = True,
632
continue_final_message: bool = False,
633
- tools: Optional[List[Dict[str, Any]]] = None,
634
- mm_processor_kwargs: Optional[Dict[str, Any]] = None,
635
- ) -> List[RequestOutput]:
633
+ tools: Optional[list[dict[str, Any]]] = None,
634
+ mm_processor_kwargs: Optional[dict[str, Any]] = None,
635
+ ) -> list[RequestOutput]:
636
"""
637
Generate responses for a chat conversation.
638
@@ -678,17 +678,17 @@ class LLM:
678
A list of ``RequestOutput`` objects containing the generated
679
responses in the same order as the input messages.
680
"""
681
- list_of_messages: List[List[ChatCompletionMessageParam]]
681
+ list_of_messages: list[list[ChatCompletionMessageParam]]
682
683
# Handle multi and single conversations
684
if is_list_of(messages, list):
685
- # messages is List[List[...]]
686
- list_of_messages = cast(List[List[ChatCompletionMessageParam]],
685
+ # messages is list[list[...]]
686
+ list_of_messages = cast(list[list[ChatCompletionMessageParam]],
687
messages)
688
else:
689
- # messages is List[...]
689
+ # messages is list[...]
690
list_of_messages = [
691
- cast(List[ChatCompletionMessageParam], messages)
691
+ cast(list[ChatCompletionMessageParam], messages)
692
]
693
694
tokenizer = self.get_tokenizer()
@@ -699,7 +699,7 @@ class LLM:
699
tokenizer,
700
)
701
702
- prompts: List[Union[TokensPrompt, TextPrompt]] = []
702
+ prompts: list[Union[TokensPrompt, TextPrompt]] = []
703
704
for msgs in list_of_messages:
705
# NOTE: _parse_chat_message_content_parts() currently doesn't
@@ -712,7 +712,7 @@ class LLM:
712
content_format=resolved_content_format,
713
)
714
715
- prompt_data: Union[str, List[int]]
715
+ prompt_data: Union[str, list[int]]
716
if isinstance(tokenizer, MistralTokenizer):
717
prompt_data = apply_mistral_chat_template(
718
tokenizer,
@@ -762,9 +762,9 @@ class LLM:
762
Sequence[PoolingParams]]] = None,
763
*,
764
use_tqdm: bool = True,
765
- lora_request: Optional[Union[List[LoRARequest], LoRARequest]] = None,
765
+ lora_request: Optional[Union[list[LoRARequest], LoRARequest]] = None,
766
prompt_adapter_request: Optional[PromptAdapterRequest] = None,
767
- ) -> List[PoolingRequestOutput]:
767
+ ) -> list[PoolingRequestOutput]:
768
...
769
770
@overload # LEGACY: single (prompt + optional token ids)
@@ -774,25 +774,25 @@ class LLM:
774
prompts: str,
775
pooling_params: Optional[Union[PoolingParams,
776
Sequence[PoolingParams]]] = None,
777
- prompt_token_ids: Optional[List[int]] = None,
777
+ prompt_token_ids: Optional[list[int]] = None,
778
use_tqdm: bool = True,
779
- lora_request: Optional[Union[List[LoRARequest], LoRARequest]] = None,
779
+ lora_request: Optional[Union[list[LoRARequest], LoRARequest]] = None,
780
prompt_adapter_request: Optional[PromptAdapterRequest] = None,
781
- ) -> List[PoolingRequestOutput]:
781
+ ) -> list[PoolingRequestOutput]:
782
...
783
784
@overload # LEGACY: multi (prompt + optional token ids)
785
@deprecated("'prompt_token_ids' will become part of 'prompts'")
786
def encode(
787
self,
788
- prompts: List[str],
788
+ prompts: list[str],
789
pooling_params: Optional[Union[PoolingParams,
790
Sequence[PoolingParams]]] = None,
791
- prompt_token_ids: Optional[List[List[int]]] = None,
791
+ prompt_token_ids: Optional[list[list[int]]] = None,
792
use_tqdm: bool = True,
793
- lora_request: Optional[Union[List[LoRARequest], LoRARequest]] = None,
793
+ lora_request: Optional[Union[list[LoRARequest], LoRARequest]] = None,
794
prompt_adapter_request: Optional[PromptAdapterRequest] = None,
795
- ) -> List[PoolingRequestOutput]:
795
+ ) -> list[PoolingRequestOutput]:
796
...
797
798
@overload # LEGACY: single (token ids + optional prompt)
@@ -803,26 +803,26 @@ class LLM:
803
pooling_params: Optional[Union[PoolingParams,
804
Sequence[PoolingParams]]] = None,
805
*,
806
- prompt_token_ids: List[int],
806
+ prompt_token_ids: list[int],
807
use_tqdm: bool = True,
808
- lora_request: Optional[Union[List[LoRARequest], LoRARequest]] = None,
808
+ lora_request: Optional[Union[list[LoRARequest], LoRARequest]] = None,
809
prompt_adapter_request: Optional[PromptAdapterRequest] = None,
810
- ) -> List[PoolingRequestOutput]:
810
+ ) -> list[PoolingRequestOutput]:
811
...
812
813
@overload # LEGACY: multi (token ids + optional prompt)
814
@deprecated("'prompt_token_ids' will become part of 'prompts'")
815
def encode(
816
self,
817
- prompts: Optional[List[str]] = None,
817
+ prompts: Optional[list[str]] = None,
818
pooling_params: Optional[Union[PoolingParams,
819
Sequence[PoolingParams]]] = None,
820
*,
821
- prompt_token_ids: List[List[int]],
821
+ prompt_token_ids: list[list[int]],
822
use_tqdm: bool = True,
823
- lora_request: Optional[Union[List[LoRARequest], LoRARequest]] = None,
823
+ lora_request: Optional[Union[list[LoRARequest], LoRARequest]] = None,
824
prompt_adapter_request: Optional[PromptAdapterRequest] = None,
825
- ) -> List[PoolingRequestOutput]:
825
+ ) -> list[PoolingRequestOutput]:
826
...
827
828
@overload # LEGACY: single or multi token ids [pos-only]
@@ -831,11 +831,11 @@ class LLM:
831
self,
832
prompts: None,
833
pooling_params: None,
834
- prompt_token_ids: Union[List[int], List[List[int]]],
834
+ prompt_token_ids: Union[list[int], list[list[int]]],
835
use_tqdm: bool = True,
836
- lora_request: Optional[Union[List[LoRARequest], LoRARequest]] = None,
836
+ lora_request: Optional[Union[list[LoRARequest], LoRARequest]] = None,
837
prompt_adapter_request: Optional[PromptAdapterRequest] = None,
838
- ) -> List[PoolingRequestOutput]:
838
+ ) -> list[PoolingRequestOutput]:
839
...
840
841
@deprecate_kwargs(
@@ -846,14 +846,14 @@ class LLM:
846
def encode(
847
self,
848
prompts: Union[Union[PromptType, Sequence[PromptType]],
849
- Optional[Union[str, List[str]]]] = None,
849
+ Optional[Union[str, list[str]]]] = None,
850
pooling_params: Optional[Union[PoolingParams,
851
Sequence[PoolingParams]]] = None,
852
- prompt_token_ids: Optional[Union[List[int], List[List[int]]]] = None,
852
+ prompt_token_ids: Optional[Union[list[int], list[list[int]]]] = None,
853
use_tqdm: bool = True,
854
- lora_request: Optional[Union[List[LoRARequest], LoRARequest]] = None,
854
+ lora_request: Optional[Union[list[LoRARequest], LoRARequest]] = None,
855
prompt_adapter_request: Optional[PromptAdapterRequest] = None,
856
- ) -> List[PoolingRequestOutput]:
856
+ ) -> list[PoolingRequestOutput]:
857
"""Apply pooling to the hidden states corresponding to the input
858
prompts.
859
@@ -898,7 +898,7 @@ class LLM:
898
899
if prompt_token_ids is not None:
900
parsed_prompts = self._convert_v1_inputs(
901
- prompts=cast(Optional[Union[str, List[str]]], prompts),
901
+ prompts=cast(Optional[Union[str, list[str]]], prompts),
902
prompt_token_ids=prompt_token_ids,
903
)
904
else:
@@ -926,9 +926,9 @@ class LLM:
926
/,
927
*,
928
use_tqdm: bool = True,
929
- lora_request: Optional[Union[List[LoRARequest], LoRARequest]] = None,
929
+ lora_request: Optional[Union[list[LoRARequest], LoRARequest]] = None,
930
prompt_adapter_request: Optional[PromptAdapterRequest] = None,
931
- ) -> List[EmbeddingRequestOutput]:
931
+ ) -> list[EmbeddingRequestOutput]:
932
"""
933
Generate an embedding vector for each prompt.
934
@@ -966,9 +966,9 @@ class LLM:
966
/,
967
*,
968
use_tqdm: bool = True,
969
- lora_request: Optional[Union[List[LoRARequest], LoRARequest]] = None,
969
+ lora_request: Optional[Union[list[LoRARequest], LoRARequest]] = None,
970
prompt_adapter_request: Optional[PromptAdapterRequest] = None,
971
- ) -> List[ClassificationRequestOutput]:
971
+ ) -> list[ClassificationRequestOutput]:
972
"""
973
Generate class logits for each prompt.
974
@@ -1003,29 +1003,29 @@ class LLM:
1003
def _embedding_score(
1004
self,
1005
tokenizer: AnyTokenizer,
1006
- text_1: List[Union[str, TextPrompt, TokensPrompt]],
1007
- text_2: List[Union[str, TextPrompt, TokensPrompt]],
1006
+ text_1: list[Union[str, TextPrompt, TokensPrompt]],
1007
+ text_2: list[Union[str, TextPrompt, TokensPrompt]],
1008
truncate_prompt_tokens: Optional[int] = None,
1009
use_tqdm: bool = True,
1010
- lora_request: Optional[Union[List[LoRARequest], LoRARequest]] = None,
1010
+ lora_request: Optional[Union[list[LoRARequest], LoRARequest]] = None,
1011
prompt_adapter_request: Optional[PromptAdapterRequest] = None,
1012
- ) -> List[ScoringRequestOutput]:
1012
+ ) -> list[ScoringRequestOutput]:
1013
1014
- encoded_output: List[PoolingRequestOutput] = self.encode(
1014
+ encoded_output: list[PoolingRequestOutput] = self.encode(
1015
text_1 + text_2,
1016
use_tqdm=use_tqdm,
1017
lora_request=lora_request,
1018
prompt_adapter_request=prompt_adapter_request)
1019
1020
- encoded_output_1: List[PoolingRequestOutput] = encoded_output[
1020
+ encoded_output_1: list[PoolingRequestOutput] = encoded_output[
1021
0:len(text_1)]
1022
- encoded_output_2: List[PoolingRequestOutput] = encoded_output[
1022
+ encoded_output_2: list[PoolingRequestOutput] = encoded_output[
1023
len(text_1):]
1024
1025
if len(encoded_output_1) == 1:
1026
encoded_output_1 = encoded_output_1 * len(encoded_output_2)
1027
1028
- scores: List[PoolingRequestOutput] = []
1028
+ scores: list[PoolingRequestOutput] = []
1029
1030
scores = _cosine_similarity(tokenizer=tokenizer,
1031
embed_1=encoded_output_1,
@@ -1038,13 +1038,13 @@ class LLM:
1038
def _cross_encoding_score(
1039
self,
1040
tokenizer: AnyTokenizer,
1041
- text_1: List[str],
1042
- text_2: List[str],
1041
+ text_1: list[str],
1042
+ text_2: list[str],
1043
truncate_prompt_tokens: Optional[int] = None,
1044
use_tqdm: bool = True,
1045
- lora_request: Optional[Union[List[LoRARequest], LoRARequest]] = None,
1045
+ lora_request: Optional[Union[list[LoRARequest], LoRARequest]] = None,
1046
prompt_adapter_request: Optional[PromptAdapterRequest] = None,
1047
- ) -> List[ScoringRequestOutput]:
1047
+ ) -> list[ScoringRequestOutput]:
1048
1049
if isinstance(tokenizer, MistralTokenizer):
1050
raise ValueError(
@@ -1057,7 +1057,7 @@ class LLM:
1057
1058
pooling_params = PoolingParams()
1059
1060
- tokenization_kwargs: Dict[str, Any] = {}
1060
+ tokenization_kwargs: dict[str, Any] = {}
1061
if truncate_prompt_tokens is not None:
1062
tokenization_kwargs["truncation"] = True
1063
tokenization_kwargs["max_length"] = truncate_prompt_tokens
@@ -1094,9 +1094,9 @@ class LLM:
1094
*,
1095
truncate_prompt_tokens: Optional[int] = None,
1096
use_tqdm: bool = True,
1097
- lora_request: Optional[Union[List[LoRARequest], LoRARequest]] = None,
1097
+ lora_request: Optional[Union[list[LoRARequest], LoRARequest]] = None,
1098
prompt_adapter_request: Optional[PromptAdapterRequest] = None,
1099
- ) -> List[ScoringRequestOutput]:
1099
+ ) -> list[ScoringRequestOutput]:
1100
"""Generate similarity scores for all pairs ``<text,text_pair>``.
1101
1102
The inputs can be ``1 -> 1``, ``1 -> N`` or ``N -> N``.
@@ -1162,12 +1162,12 @@ class LLM:
1162
if isinstance(text_1, (str, dict)):
1163
# Convert a single prompt to a list.
1164
text_1 = [text_1]
1165
- input_text_1: List[str] = [ensure_str(t) for t in text_1]
1165
+ input_text_1: list[str] = [ensure_str(t) for t in text_1]
1166
1167
if isinstance(text_2, (str, dict)):
1168
# Convert a single prompt to a list.
1169
text_2 = [text_2]
1170
- input_text_2: List[str] = [ensure_str(t) for t in text_2]
1170
+ input_text_2: list[str] = [ensure_str(t) for t in text_2]
1171
1172
_validate_score_input_lens(input_text_1, input_text_2)
1173
@@ -1226,8 +1226,8 @@ class LLM:
1226
# LEGACY
1227
def _convert_v1_inputs(
1228
self,
1229
- prompts: Optional[Union[str, List[str]]],
1230
- prompt_token_ids: Optional[Union[List[int], List[List[int]]]],
1229
+ prompts: Optional[Union[str, list[str]]],
1230
+ prompt_token_ids: Optional[Union[list[int], list[list[int]]]],
1231
):
1232
# skip_tokenizer_init is now checked in engine
1233
@@ -1252,7 +1252,7 @@ class LLM:
1252
raise ValueError("Either prompts or prompt_token_ids must be "
1253
"provided.")
1254
1255
- parsed_prompts: List[PromptType] = []
1255
+ parsed_prompts: list[PromptType] = []
1256
for i in range(num_requests):
1257
item: PromptType
1258
@@ -1275,7 +1275,7 @@ class LLM:
1275
lora_request: Optional[Union[Sequence[LoRARequest], LoRARequest]],
1276
prompt_adapter_request: Optional[PromptAdapterRequest],
1277
guided_options: Optional[GuidedDecodingRequest] = None,
1278
- priority: Optional[List[int]] = None,
1278
+ priority: Optional[list[int]] = None,
1279
) -> None:
1280
if guided_options is not None:
1281
warnings.warn(
@@ -1357,7 +1357,7 @@ class LLM:
1357
1358
def _run_engine(
1359
self, *, use_tqdm: bool
1360
- ) -> List[Union[RequestOutput, PoolingRequestOutput]]:
1360
+ ) -> list[Union[RequestOutput, PoolingRequestOutput]]:
1361
# Initialize tqdm.
1362
if use_tqdm:
1363
num_requests = self.llm_engine.get_num_unfinished_requests()
@@ -1370,7 +1370,7 @@ class LLM:
1370
)
1371
1372
# Run the engine.
1373
- outputs: List[Union[RequestOutput, PoolingRequestOutput]] = []
1373
+ outputs: list[Union[RequestOutput, PoolingRequestOutput]] = []
1374
total_in_toks = 0
1375
total_out_toks = 0
1376
while self.llm_engine.has_unfinished_requests():
vllm/entrypoints/logger.py
+2
-2
@@ -1,6 +1,6 @@
1
# SPDX-License-Identifier: Apache-2.0
2
3
-from typing import List, Optional, Union
3
+from typing import Optional, Union
4
5
from vllm.logger import init_logger
6
from vllm.lora.request import LoRARequest
@@ -22,7 +22,7 @@ class RequestLogger:
22
self,
23
request_id: str,
24
prompt: Optional[str],
25
- prompt_token_ids: Optional[List[int]],
25
+ prompt_token_ids: Optional[list[int]],
26
params: Optional[Union[SamplingParams, PoolingParams,
27
BeamSearchParams]],
28
lora_request: Optional[LoRARequest],
vllm/entrypoints/openai/api_server.py
+5
-4
@@ -13,10 +13,11 @@ import socket
13
import tempfile
14
import uuid
15
from argparse import Namespace
16
+from collections.abc import AsyncIterator
17
from contextlib import asynccontextmanager
18
from functools import partial
19
from http import HTTPStatus
19
-from typing import Annotated, AsyncIterator, Dict, Optional, Set, Tuple, Union
20
+from typing import Annotated, Optional, Union
21
22
import uvloop
23
from fastapi import APIRouter, Depends, FastAPI, Form, HTTPException, Request
@@ -93,7 +94,7 @@ prometheus_multiproc_dir: tempfile.TemporaryDirectory
94
# Cannot use __name__ (https://github.com/vllm-project/vllm/pull/4765)
95
logger = init_logger('vllm.entrypoints.openai.api_server')
96
96
-_running_tasks: Set[asyncio.Task] = set()
97
+_running_tasks: set[asyncio.Task] = set()
98
99
100
@asynccontextmanager
@@ -587,7 +588,7 @@ async def do_rerank_v2(request: RerankRequest, raw_request: Request):
588
return await do_rerank(request, raw_request)
589
590
590
-TASK_HANDLERS: Dict[str, Dict[str, tuple]] = {
591
+TASK_HANDLERS: dict[str, dict[str, tuple]] = {
592
"generate": {
593
"messages": (ChatCompletionRequest, create_chat_completion),
594
"default": (CompletionRequest, create_completion),
@@ -894,7 +895,7 @@ async def init_app_state(
895
state.task = model_config.task
896
897
897
-def create_server_socket(addr: Tuple[str, int]) -> socket.socket:
898
+def create_server_socket(addr: tuple[str, int]) -> socket.socket:
899
family = socket.AF_INET
900
if is_valid_ipv6_address(addr[0]):
901
family = socket.AF_INET6
vllm/entrypoints/openai/cli_args.py
+4
-3
@@ -8,7 +8,8 @@ purposes.
8
import argparse
9
import json
10
import ssl
11
-from typing import List, Optional, Sequence, Union, get_args
11
+from collections.abc import Sequence
12
+from typing import Optional, Union, get_args
13
14
from vllm.engine.arg_utils import AsyncEngineArgs, nullable_str
15
from vllm.entrypoints.chat_utils import (ChatTemplateContentFormatOption,
@@ -33,7 +34,7 @@ class LoRAParserAction(argparse.Action):
34
if isinstance(values, str):
35
raise TypeError("Expected values to be a list")
36
36
- lora_list: List[LoRAModulePath] = []
37
+ lora_list: list[LoRAModulePath] = []
38
for item in values:
39
if item in [None, '']: # Skip if item is None or empty string
40
continue
@@ -69,7 +70,7 @@ class PromptAdapterParserAction(argparse.Action):
70
if isinstance(values, str):
71
raise TypeError("Expected values to be a list")
72
72
- adapter_list: List[PromptAdapterPath] = []
73
+ adapter_list: list[PromptAdapterPath] = []
74
for item in values:
75
name, path = item.split('=')
76
adapter_list.append(PromptAdapterPath(name, path))
vllm/entrypoints/openai/logits_processors.py
+12
-11
@@ -1,7 +1,8 @@
1
# SPDX-License-Identifier: Apache-2.0
2
3
+from collections.abc import Iterable
4
from functools import lru_cache, partial
4
-from typing import Dict, FrozenSet, Iterable, List, Optional, Union
5
+from typing import Optional, Union
6
7
import torch
8
@@ -14,10 +15,10 @@ class AllowedTokenIdsLogitsProcessor:
15
specific set of token ids."""
16
17
def __init__(self, allowed_ids: Iterable[int]):
17
- self.allowed_ids: Optional[List[int]] = list(allowed_ids)
18
+ self.allowed_ids: Optional[list[int]] = list(allowed_ids)
19
self.mask: Optional[torch.Tensor] = None
20
20
- def __call__(self, token_ids: List[int],
21
+ def __call__(self, token_ids: list[int],
22
logits: torch.Tensor) -> torch.Tensor:
23
if self.mask is None:
24
self.mask = torch.ones((logits.shape[-1], ),
@@ -31,7 +32,7 @@ class AllowedTokenIdsLogitsProcessor:
32
33
@lru_cache(maxsize=32)
34
def _get_allowed_token_ids_logits_processor(
34
- allowed_token_ids: FrozenSet[int],
35
+ allowed_token_ids: frozenset[int],
36
vocab_size: int,
37
) -> LogitsProcessor:
38
if not allowed_token_ids:
@@ -43,8 +44,8 @@ def _get_allowed_token_ids_logits_processor(
44
45
46
def logit_bias_logits_processor(
46
- logit_bias: Dict[int, float],
47
- token_ids: List[int],
47
+ logit_bias: dict[int, float],
48
+ token_ids: list[int],
49
logits: torch.Tensor,
50
) -> torch.Tensor:
51
for token_id, bias in logit_bias.items():
@@ -53,16 +54,16 @@ def logit_bias_logits_processor(
54
55
56
def get_logits_processors(
56
- logit_bias: Optional[Union[Dict[int, float], Dict[str, float]]],
57
- allowed_token_ids: Optional[List[int]],
57
+ logit_bias: Optional[Union[dict[int, float], dict[str, float]]],
58
+ allowed_token_ids: Optional[list[int]],
59
tokenizer: AnyTokenizer,
59
-) -> List[LogitsProcessor]:
60
- logits_processors: List[LogitsProcessor] = []
60
+) -> list[LogitsProcessor]:
61
+ logits_processors: list[LogitsProcessor] = []
62
if logit_bias:
63
try:
64
# Convert token_id to integer
65
# Clamp the bias between -100 and 100 per OpenAI API spec
65
- clamped_logit_bias: Dict[int, float] = {
66
+ clamped_logit_bias: dict[int, float] = {
67
int(token_id): min(100.0, max(-100.0, bias))
68
for token_id, bias in logit_bias.items()
69
}
vllm/entrypoints/openai/protocol.py
+64
-64
@@ -5,13 +5,13 @@
5
import re
6
import time
7
from argparse import Namespace
8
-from typing import Any, ClassVar, Dict, List, Literal, Optional, Set, Union
8
+from typing import Annotated, Any, ClassVar, Literal, Optional, Union
9
10
import torch
11
from fastapi import UploadFile
12
from pydantic import (BaseModel, ConfigDict, Field, TypeAdapter,
13
ValidationInfo, field_validator, model_validator)
14
-from typing_extensions import Annotated, TypeAlias
14
+from typing_extensions import TypeAlias
15
16
from vllm.entrypoints.chat_utils import ChatCompletionMessageParam
17
from vllm.logger import init_logger
@@ -47,7 +47,7 @@ class OpenAIBaseModel(BaseModel):
47
model_config = ConfigDict(extra="allow")
48
49
# Cache class field names
50
- field_names: ClassVar[Optional[Set[str]]] = None
50
+ field_names: ClassVar[Optional[set[str]]] = None
51
52
@model_validator(mode="wrap")
53
@classmethod
@@ -105,12 +105,12 @@ class ModelCard(OpenAIBaseModel):
105
root: Optional[str] = None
106
parent: Optional[str] = None
107
max_model_len: Optional[int] = None
108
- permission: List[ModelPermission] = Field(default_factory=list)
108
+ permission: list[ModelPermission] = Field(default_factory=list)
109
110
111
class ModelList(OpenAIBaseModel):
112
object: str = "list"
113
- data: List[ModelCard] = Field(default_factory=list)
113
+ data: list[ModelCard] = Field(default_factory=list)
114
115
116
class PromptTokenUsageInfo(OpenAIBaseModel):
@@ -134,7 +134,7 @@ class JsonSchemaResponseFormat(OpenAIBaseModel):
134
description: Optional[str] = None
135
# schema is the field in openai but that causes conflicts with pydantic so
136
# instead use json_schema with an alias
137
- json_schema: Optional[Dict[str, Any]] = Field(default=None, alias='schema')
137
+ json_schema: Optional[dict[str, Any]] = Field(default=None, alias='schema')
138
strict: Optional[bool] = None
139
140
@@ -152,7 +152,7 @@ class StreamOptions(OpenAIBaseModel):
152
class FunctionDefinition(OpenAIBaseModel):
153
name: str
154
description: Optional[str] = None
155
- parameters: Optional[Dict[str, Any]] = None
155
+ parameters: Optional[dict[str, Any]] = None
156
157
158
class ChatCompletionToolsParam(OpenAIBaseModel):
@@ -171,15 +171,15 @@ class ChatCompletionNamedToolChoiceParam(OpenAIBaseModel):
171
172
class LogitsProcessorConstructor(BaseModel):
173
qualname: str
174
- args: Optional[List[Any]] = None
175
- kwargs: Optional[Dict[str, Any]] = None
174
+ args: Optional[list[Any]] = None
175
+ kwargs: Optional[dict[str, Any]] = None
176
177
178
-LogitsProcessors = List[Union[str, LogitsProcessorConstructor]]
178
+LogitsProcessors = list[Union[str, LogitsProcessorConstructor]]
179
180
181
def get_logits_processors(processors: Optional[LogitsProcessors],
182
- pattern: Optional[str]) -> Optional[List[Any]]:
182
+ pattern: Optional[str]) -> Optional[list[Any]]:
183
if processors and pattern:
184
logits_processors = []
185
for processor in processors:
@@ -212,10 +212,10 @@ def get_logits_processors(processors: Optional[LogitsProcessors],
212
class ChatCompletionRequest(OpenAIBaseModel):
213
# Ordered by official OpenAI API documentation
214
# https://platform.openai.com/docs/api-reference/chat/create
215
- messages: List[ChatCompletionMessageParam]
215
+ messages: list[ChatCompletionMessageParam]
216
model: Optional[str] = None
217
frequency_penalty: Optional[float] = 0.0
218
- logit_bias: Optional[Dict[str, float]] = None
218
+ logit_bias: Optional[dict[str, float]] = None
219
logprobs: Optional[bool] = False
220
top_logprobs: Optional[int] = 0
221
# TODO(#9845): remove max_tokens when field is removed from OpenAI API
@@ -228,12 +228,12 @@ class ChatCompletionRequest(OpenAIBaseModel):
228
presence_penalty: Optional[float] = 0.0
229
response_format: Optional[ResponseFormat] = None
230
seed: Optional[int] = Field(None, ge=_LONG_INFO.min, le=_LONG_INFO.max)
231
- stop: Optional[Union[str, List[str]]] = Field(default_factory=list)
231
+ stop: Optional[Union[str, list[str]]] = Field(default_factory=list)
232
stream: Optional[bool] = False
233
stream_options: Optional[StreamOptions] = None
234
temperature: Optional[float] = None
235
top_p: Optional[float] = None
236
- tools: Optional[List[ChatCompletionToolsParam]] = None
236
+ tools: Optional[list[ChatCompletionToolsParam]] = None
237
tool_choice: Optional[Union[Literal["none"], Literal["auto"],
238
ChatCompletionNamedToolChoiceParam]] = "none"
239
@@ -248,7 +248,7 @@ class ChatCompletionRequest(OpenAIBaseModel):
248
min_p: Optional[float] = None
249
repetition_penalty: Optional[float] = None
250
length_penalty: float = 1.0
251
- stop_token_ids: Optional[List[int]] = Field(default_factory=list)
251
+ stop_token_ids: Optional[list[int]] = Field(default_factory=list)
252
include_stop_str_in_output: bool = False
253
ignore_eos: bool = False
254
min_tokens: int = 0
@@ -290,7 +290,7 @@ class ChatCompletionRequest(OpenAIBaseModel):
290
"special tokens so this should be set to false (as is the "
291
"default)."),
292
)
293
- documents: Optional[List[Dict[str, str]]] = Field(
293
+ documents: Optional[list[dict[str, str]]] = Field(
294
default=None,
295
description=
296
("A list of dicts representing documents that will be accessible to "
@@ -307,12 +307,12 @@ class ChatCompletionRequest(OpenAIBaseModel):
307
"allowed, so you must provide a chat template if the tokenizer "
308
"does not define one."),
309
)
310
- chat_template_kwargs: Optional[Dict[str, Any]] = Field(
310
+ chat_template_kwargs: Optional[dict[str, Any]] = Field(
311
default=None,
312
description=("Additional kwargs to pass to the template renderer. "
313
"Will be accessible by the chat template."),
314
)
315
- mm_processor_kwargs: Optional[Dict[str, Any]] = Field(
315
+ mm_processor_kwargs: Optional[dict[str, Any]] = Field(
316
default=None,
317
description=("Additional kwargs to pass to the HF processor."),
318
)
@@ -325,7 +325,7 @@ class ChatCompletionRequest(OpenAIBaseModel):
325
description=(
326
"If specified, the output will follow the regex pattern."),
327
)
328
- guided_choice: Optional[List[str]] = Field(
328
+ guided_choice: Optional[list[str]] = Field(
329
default=None,
330
description=(
331
"If specified, the output will be exactly one of the choices."),
@@ -643,17 +643,17 @@ class CompletionRequest(OpenAIBaseModel):
643
# Ordered by official OpenAI API documentation
644
# https://platform.openai.com/docs/api-reference/completions/create
645
model: Optional[str] = None
646
- prompt: Union[List[int], List[List[int]], str, List[str]]
646
+ prompt: Union[list[int], list[list[int]], str, list[str]]
647
best_of: Optional[int] = None
648
echo: Optional[bool] = False
649
frequency_penalty: Optional[float] = 0.0
650
- logit_bias: Optional[Dict[str, float]] = None
650
+ logit_bias: Optional[dict[str, float]] = None
651
logprobs: Optional[int] = None
652
max_tokens: Optional[int] = 16
653
n: int = 1
654
presence_penalty: Optional[float] = 0.0
655
seed: Optional[int] = Field(None, ge=_LONG_INFO.min, le=_LONG_INFO.max)
656
- stop: Optional[Union[str, List[str]]] = Field(default_factory=list)
656
+ stop: Optional[Union[str, list[str]]] = Field(default_factory=list)
657
stream: Optional[bool] = False
658
stream_options: Optional[StreamOptions] = None
659
suffix: Optional[str] = None
@@ -667,14 +667,14 @@ class CompletionRequest(OpenAIBaseModel):
667
min_p: Optional[float] = None
668
repetition_penalty: Optional[float] = None
669
length_penalty: float = 1.0
670
- stop_token_ids: Optional[List[int]] = Field(default_factory=list)
670
+ stop_token_ids: Optional[list[int]] = Field(default_factory=list)
671
include_stop_str_in_output: bool = False
672
ignore_eos: bool = False
673
min_tokens: int = 0
674
skip_special_tokens: bool = True
675
spaces_between_special_tokens: bool = True
676
truncate_prompt_tokens: Optional[Annotated[int, Field(ge=1)]] = None
677
- allowed_token_ids: Optional[List[int]] = None
677
+ allowed_token_ids: Optional[list[int]] = None
678
prompt_logprobs: Optional[int] = None
679
# doc: end-completion-sampling-params
680
@@ -701,7 +701,7 @@ class CompletionRequest(OpenAIBaseModel):
701
description=(
702
"If specified, the output will follow the regex pattern."),
703
)
704
- guided_choice: Optional[List[str]] = Field(
704
+ guided_choice: Optional[list[str]] = Field(
705
default=None,
706
description=(
707
"If specified, the output will be exactly one of the choices."),
@@ -908,7 +908,7 @@ class EmbeddingCompletionRequest(OpenAIBaseModel):
908
# Ordered by official OpenAI API documentation
909
# https://platform.openai.com/docs/api-reference/embeddings
910
model: Optional[str] = None
911
- input: Union[List[int], List[List[int]], str, List[str]]
911
+ input: Union[list[int], list[list[int]], str, list[str]]
912
encoding_format: Literal["float", "base64"] = "float"
913
dimensions: Optional[int] = None
914
user: Optional[str] = None
@@ -940,7 +940,7 @@ class EmbeddingCompletionRequest(OpenAIBaseModel):
940
941
class EmbeddingChatRequest(OpenAIBaseModel):
942
model: Optional[str] = None
943
- messages: List[ChatCompletionMessageParam]
943
+ messages: list[ChatCompletionMessageParam]
944
945
encoding_format: Literal["float", "base64"] = "float"
946
dimensions: Optional[int] = None
@@ -969,12 +969,12 @@ class EmbeddingChatRequest(OpenAIBaseModel):
969
"allowed, so you must provide a chat template if the tokenizer "
970
"does not define one."),
971
)
972
- chat_template_kwargs: Optional[Dict[str, Any]] = Field(
972
+ chat_template_kwargs: Optional[dict[str, Any]] = Field(
973
default=None,
974
description=("Additional kwargs to pass to the template renderer. "
975
"Will be accessible by the chat template."),
976
)
977
- mm_processor_kwargs: Optional[Dict[str, Any]] = Field(
977
+ mm_processor_kwargs: Optional[dict[str, Any]] = Field(
978
default=None,
979
description=("Additional kwargs to pass to the HF processor."),
980
)
@@ -1008,8 +1008,8 @@ PoolingRequest = Union[PoolingCompletionRequest, PoolingChatRequest]
1008
1009
class ScoreRequest(OpenAIBaseModel):
1010
model: Optional[str] = None
1011
- text_1: Union[List[str], str]
1012
- text_2: Union[List[str], str]
1011
+ text_1: Union[list[str], str]
1012
+ text_2: Union[list[str], str]
1013
truncate_prompt_tokens: Optional[Annotated[int, Field(ge=1)]] = None
1014
1015
# doc: begin-score-pooling-params
@@ -1033,7 +1033,7 @@ class ScoreRequest(OpenAIBaseModel):
1033
class RerankRequest(OpenAIBaseModel):
1034
model: Optional[str] = None
1035
query: str
1036
- documents: List[str]
1036
+ documents: list[str]
1037
top_n: int = Field(default_factory=lambda: 0)
1038
truncate_prompt_tokens: Optional[Annotated[int, Field(ge=1)]] = None
1039
@@ -1073,14 +1073,14 @@ class RerankResponse(OpenAIBaseModel):
1073
id: str
1074
model: str
1075
usage: RerankUsage
1076
- results: List[RerankResult]
1076
+ results: list[RerankResult]
1077
1078
1079
class CompletionLogProbs(OpenAIBaseModel):
1080
- text_offset: List[int] = Field(default_factory=list)
1081
- token_logprobs: List[Optional[float]] = Field(default_factory=list)
1082
- tokens: List[str] = Field(default_factory=list)
1083
- top_logprobs: List[Optional[Dict[str,
1080
+ text_offset: list[int] = Field(default_factory=list)
1081
+ token_logprobs: list[Optional[float]] = Field(default_factory=list)
1082
+ tokens: list[str] = Field(default_factory=list)
1083
+ top_logprobs: list[Optional[dict[str,
1084
float]]] = Field(default_factory=list)
1085
1086
@@ -1096,7 +1096,7 @@ class CompletionResponseChoice(OpenAIBaseModel):
1096
"to stop, None if the completion finished for some other reason "
1097
"including encountering the EOS token"),
1098
)
1099
- prompt_logprobs: Optional[List[Optional[Dict[int, Logprob]]]] = None
1099
+ prompt_logprobs: Optional[list[Optional[dict[int, Logprob]]]] = None
1100
1101
1102
class CompletionResponse(OpenAIBaseModel):
@@ -1104,7 +1104,7 @@ class CompletionResponse(OpenAIBaseModel):
1104
object: str = "text_completion"
1105
created: int = Field(default_factory=lambda: int(time.time()))
1106
model: str
1107
- choices: List[CompletionResponseChoice]
1107
+ choices: list[CompletionResponseChoice]
1108
usage: UsageInfo
1109
1110
@@ -1127,14 +1127,14 @@ class CompletionStreamResponse(OpenAIBaseModel):
1127
object: str = "text_completion"
1128
created: int = Field(default_factory=lambda: int(time.time()))
1129
model: str
1130
- choices: List[CompletionResponseStreamChoice]
1130
+ choices: list[CompletionResponseStreamChoice]
1131
usage: Optional[UsageInfo] = Field(default=None)
1132
1133
1134
class EmbeddingResponseData(OpenAIBaseModel):
1135
index: int
1136
object: str = "embedding"
1137
- embedding: Union[List[float], str]
1137
+ embedding: Union[list[float], str]
1138
1139
1140
class EmbeddingResponse(OpenAIBaseModel):
@@ -1142,14 +1142,14 @@ class EmbeddingResponse(OpenAIBaseModel):
1142
object: str = "list"
1143
created: int = Field(default_factory=lambda: int(time.time()))
1144
model: str
1145
- data: List[EmbeddingResponseData]
1145
+ data: list[EmbeddingResponseData]
1146
usage: UsageInfo
1147
1148
1149
class PoolingResponseData(OpenAIBaseModel):
1150
index: int
1151
object: str = "pooling"
1152
- data: Union[List[List[float]], List[float], str]
1152
+ data: Union[list[list[float]], list[float], str]
1153
1154
1155
class PoolingResponse(OpenAIBaseModel):
@@ -1157,7 +1157,7 @@ class PoolingResponse(OpenAIBaseModel):
1157
object: str = "list"
1158
created: int = Field(default_factory=lambda: int(time.time()))
1159
model: str
1160
- data: List[PoolingResponseData]
1160
+ data: list[PoolingResponseData]
1161
usage: UsageInfo
1162
1163
@@ -1172,7 +1172,7 @@ class ScoreResponse(OpenAIBaseModel):
1172
object: str = "list"
1173
created: int = Field(default_factory=lambda: int(time.time()))
1174
model: str
1175
- data: List[ScoreResponseData]
1175
+ data: list[ScoreResponseData]
1176
usage: UsageInfo
1177
1178
@@ -1205,7 +1205,7 @@ class ExtractedToolCallInformation(BaseModel):
1205
tools_called: bool
1206
1207
# extracted tool calls
1208
- tool_calls: List[ToolCall]
1208
+ tool_calls: list[ToolCall]
1209
1210
# content - per OpenAI spec, content AND tool calls can be returned rarely
1211
# But some models will do this intentionally
@@ -1216,21 +1216,21 @@ class ChatMessage(OpenAIBaseModel):
1216
role: str
1217
reasoning_content: Optional[str] = None
1218
content: Optional[str] = None
1219
- tool_calls: List[ToolCall] = Field(default_factory=list)
1219
+ tool_calls: list[ToolCall] = Field(default_factory=list)
1220
1221
1222
class ChatCompletionLogProb(OpenAIBaseModel):
1223
token: str
1224
logprob: float = -9999.0
1225
- bytes: Optional[List[int]] = None
1225
+ bytes: Optional[list[int]] = None
1226
1227
1228
class ChatCompletionLogProbsContent(ChatCompletionLogProb):
1229
- top_logprobs: List[ChatCompletionLogProb] = Field(default_factory=list)
1229
+ top_logprobs: list[ChatCompletionLogProb] = Field(default_factory=list)
1230
1231
1232
class ChatCompletionLogProbs(OpenAIBaseModel):
1233
- content: Optional[List[ChatCompletionLogProbsContent]] = None
1233
+ content: Optional[list[ChatCompletionLogProbsContent]] = None
1234
1235
1236
class ChatCompletionResponseChoice(OpenAIBaseModel):
@@ -1248,16 +1248,16 @@ class ChatCompletionResponse(OpenAIBaseModel):
1248
object: Literal["chat.completion"] = "chat.completion"
1249
created: int = Field(default_factory=lambda: int(time.time()))
1250
model: str
1251
- choices: List[ChatCompletionResponseChoice]
1251
+ choices: list[ChatCompletionResponseChoice]
1252
usage: UsageInfo
1253
- prompt_logprobs: Optional[List[Optional[Dict[int, Logprob]]]] = None
1253
+ prompt_logprobs: Optional[list[Optional[dict[int, Logprob]]]] = None
1254
1255
1256
class DeltaMessage(OpenAIBaseModel):
1257
role: Optional[str] = None
1258
content: Optional[str] = None
1259
reasoning_content: Optional[str] = None
1260
- tool_calls: List[DeltaToolCall] = Field(default_factory=list)
1260
+ tool_calls: list[DeltaToolCall] = Field(default_factory=list)
1261
1262
1263
class ChatCompletionResponseStreamChoice(OpenAIBaseModel):
@@ -1273,7 +1273,7 @@ class ChatCompletionStreamResponse(OpenAIBaseModel):
1273
object: Literal["chat.completion.chunk"] = "chat.completion.chunk"
1274
created: int = Field(default_factory=lambda: int(time.time()))
1275
model: str
1276
- choices: List[ChatCompletionResponseStreamChoice]
1276
+ choices: list[ChatCompletionResponseStreamChoice]
1277
usage: Optional[UsageInfo] = Field(default=None)
1278
1279
@@ -1358,7 +1358,7 @@ class TokenizeCompletionRequest(OpenAIBaseModel):
1358
1359
class TokenizeChatRequest(OpenAIBaseModel):
1360
model: Optional[str] = None
1361
- messages: List[ChatCompletionMessageParam]
1361
+ messages: list[ChatCompletionMessageParam]
1362
1363
add_generation_prompt: bool = Field(
1364
default=True,
@@ -1393,12 +1393,12 @@ class TokenizeChatRequest(OpenAIBaseModel):
1393
"allowed, so you must provide a chat template if the tokenizer "
1394
"does not define one."),
1395
)
1396
- chat_template_kwargs: Optional[Dict[str, Any]] = Field(
1396
+ chat_template_kwargs: Optional[dict[str, Any]] = Field(
1397
default=None,
1398
description=("Additional kwargs to pass to the template renderer. "
1399
"Will be accessible by the chat template."),
1400
)
1401
- mm_processor_kwargs: Optional[Dict[str, Any]] = Field(
1401
+ mm_processor_kwargs: Optional[dict[str, Any]] = Field(
1402
default=None,
1403
description=("Additional kwargs to pass to the HF processor."),
1404
)
@@ -1419,12 +1419,12 @@ TokenizeRequest = Union[TokenizeCompletionRequest, TokenizeChatRequest]
1419
class TokenizeResponse(OpenAIBaseModel):
1420
count: int
1421
max_model_len: int
1422
- tokens: List[int]
1422
+ tokens: list[int]
1423
1424
1425
class DetokenizeRequest(OpenAIBaseModel):
1426
model: Optional[str] = None
1427
- tokens: List[int]
1427
+ tokens: list[int]
1428
1429
1430
class DetokenizeResponse(OpenAIBaseModel):
@@ -1492,7 +1492,7 @@ class TranscriptionRequest(OpenAIBaseModel):
1492
to automatically increase the temperature until certain thresholds are hit.
1493
"""
1494
1495
- timestamp_granularities: List[Literal["word", "segment"]] = Field(
1495
+ timestamp_granularities: list[Literal["word", "segment"]] = Field(
1496
alias="timestamp_granularities[]", default=[])
1497
"""The timestamp granularities to populate for this transcription.
1498
@@ -1580,7 +1580,7 @@ class TranscriptionSegment(OpenAIBaseModel):
1580
text: str
1581
"""Text content of the segment."""
1582
1583
- tokens: List[int]
1583
+ tokens: list[int]
1584
"""Array of token IDs for the text content."""
1585
1586
@@ -1594,8 +1594,8 @@ class TranscriptionResponseVerbose(OpenAIBaseModel):
1594
text: str
1595
"""The transcribed text."""
1596
1597
- segments: Optional[List[TranscriptionSegment]] = None
1597
+ segments: Optional[list[TranscriptionSegment]] = None
1598
"""Segments of the transcribed text and their corresponding details."""
1599
1600
- words: Optional[List[TranscriptionWord]] = None
1600
+ words: Optional[list[TranscriptionWord]] = None
1601
"""Extracted words and their corresponding timestamps."""
vllm/entrypoints/openai/reasoning_parsers/abs_reasoning_parsers.py
+11
-10
@@ -1,8 +1,9 @@
1
# SPDX-License-Identifier: Apache-2.0
2
3
import os
4
+from collections.abc import Sequence
5
from functools import cached_property
5
-from typing import Callable, Dict, List, Optional, Sequence, Tuple, Type, Union
6
+from typing import Callable, Optional, Union
7
8
from vllm.entrypoints.openai.protocol import (ChatCompletionRequest,
9
DeltaMessage)
@@ -25,14 +26,14 @@ class ReasoningParser:
26
self.model_tokenizer = tokenizer
27
28
@cached_property
28
- def vocab(self) -> Dict[str, int]:
29
+ def vocab(self) -> dict[str, int]:
30
# NOTE: Only PreTrainedTokenizerFast is guaranteed to have .vocab
31
# whereas all tokenizers have .get_vocab()
32
return self.model_tokenizer.get_vocab()
33
34
def extract_reasoning_content(
35
self, model_output: str, request: ChatCompletionRequest
35
- ) -> Tuple[Optional[str], Optional[str]]:
36
+ ) -> tuple[Optional[str], Optional[str]]:
37
"""
38
Extract reasoning content from a complete model-generated string.
39
@@ -47,7 +48,7 @@ class ReasoningParser:
48
The request object that was used to generate the model_output.
49
50
Returns:
50
- Tuple[Optional[str], Optional[str]]
51
+ tuple[Optional[str], Optional[str]]
52
A tuple containing the reasoning content and the content.
53
"""
54
@@ -77,10 +78,10 @@ class ReasoningParser:
78
79
80
class ReasoningParserManager:
80
- reasoning_parsers: Dict[str, Type] = {}
81
+ reasoning_parsers: dict[str, type] = {}
82
83
@classmethod
83
- def get_reasoning_parser(cls, name) -> Type:
84
+ def get_reasoning_parser(cls, name) -> type:
85
"""
86
Get reasoning parser by name which is registered by `register_module`.
87
@@ -94,8 +95,8 @@ class ReasoningParserManager:
95
96
@classmethod
97
def _register_module(cls,
97
- module: Type,
98
- module_name: Optional[Union[str, List[str]]] = None,
98
+ module: type,
99
+ module_name: Optional[Union[str, list[str]]] = None,
100
force: bool = True) -> None:
101
if not issubclass(module, ReasoningParser):
102
raise TypeError("module must be subclass of ReasoningParser, "
@@ -114,9 +115,9 @@ class ReasoningParserManager:
115
@classmethod
116
def register_module(
117
cls,
117
- name: Optional[Union[str, List[str]]] = None,
118
+ name: Optional[Union[str, list[str]]] = None,
119
force: bool = True,
119
- module: Union[Type, None] = None) -> Union[type, Callable]:
120
+ module: Union[type, None] = None) -> Union[type, Callable]:
121
"""
122
Register module with the given name or name list. it can be used as a
123
decoder(with module as None) or normal function(with module as not
vllm/entrypoints/openai/reasoning_parsers/deepseek_r1_reasoning_parser.py
+3
-2
@@ -1,7 +1,8 @@
1
# SPDX-License-Identifier: Apache-2.0
2
3
import re
4
-from typing import Optional, Sequence, Tuple, Union
4
+from collections.abc import Sequence
5
+from typing import Optional, Union
6
7
from transformers import PreTrainedTokenizerBase
8
@@ -122,7 +123,7 @@ class DeepSeekR1ReasoningParser(ReasoningParser):
123
124
def extract_reasoning_content(
125
self, model_output: str, request: ChatCompletionRequest
125
- ) -> Tuple[Optional[str], Optional[str]]:
126
+ ) -> tuple[Optional[str], Optional[str]]:
127
128
# DeepSeek R1 doesn't generate <think> now.
129
# Thus we assume the reasoning content is always at the start.
vllm/entrypoints/openai/run_batch.py
+5
-4
@@ -2,9 +2,10 @@
2
3
import asyncio
4
import tempfile
5
+from collections.abc import Awaitable
6
from http import HTTPStatus
7
from io import StringIO
7
-from typing import Awaitable, Callable, List, Optional
8
+from typing import Callable, Optional
9
10
import aiohttp
11
import torch
@@ -143,7 +144,7 @@ async def read_file(path_or_url: str) -> str:
144
145
146
async def write_local_file(output_path: str,
146
- batch_outputs: List[BatchRequestOutput]) -> None:
147
+ batch_outputs: list[BatchRequestOutput]) -> None:
148
"""
149
Write the responses to a local file.
150
output_path: The path to write the responses to.
@@ -204,7 +205,7 @@ async def upload_data(output_url: str, data_or_file: str,
205
f"Error message: {str(e)}.") from e
206
207
207
-async def write_file(path_or_url: str, batch_outputs: List[BatchRequestOutput],
208
+async def write_file(path_or_url: str, batch_outputs: list[BatchRequestOutput],
209
output_tmp_dir: str) -> None:
210
"""
211
Write batch_outputs to a file or upload to a URL.
@@ -353,7 +354,7 @@ async def main(args):
354
logger.info("Reading batch from %s...", args.input_file)
355
356
# Submit all requests in the file to the engine "concurrently".
356
- response_futures: List[Awaitable[BatchRequestOutput]] = []
357
+ response_futures: list[Awaitable[BatchRequestOutput]] = []
358
for request_json in (await read_file(args.input_file)).strip().split("\n"):
359
# Skip empty lines.
360
request_json = request_json.strip()
vllm/entrypoints/openai/serving_chat.py
+15
-16
@@ -3,10 +3,9 @@
3
import asyncio
4
import json
5
import time
6
-from typing import (AsyncGenerator, AsyncIterator, Callable, Dict, Final, List,
7
- Optional)
8
-from typing import Sequence as GenericSequence
9
-from typing import Union
6
+from collections.abc import AsyncGenerator, AsyncIterator
7
+from collections.abc import Sequence as GenericSequence
8
+from typing import Callable, Final, Optional, Union
9
10
from fastapi import Request
11
@@ -205,7 +204,7 @@ class OpenAIServingChat(OpenAIServing):
204
raw_request.state.request_metadata = request_metadata
205
206
# Schedule the request and get the result generator.
208
- generators: List[AsyncGenerator[RequestOutput, None]] = []
207
+ generators: list[AsyncGenerator[RequestOutput, None]] = []
208
try:
209
for i, engine_prompt in enumerate(engine_prompts):
210
sampling_params: Union[SamplingParams, BeamSearchParams]
@@ -282,7 +281,7 @@ class OpenAIServingChat(OpenAIServing):
281
result_generator: AsyncIterator[RequestOutput],
282
request_id: str,
283
model_name: str,
285
- conversation: List[ConversationMessage],
284
+ conversation: list[ConversationMessage],
285
tokenizer: AnyTokenizer,
286
request_metadata: RequestResponseMetadata,
287
) -> AsyncGenerator[str, None]:
@@ -310,7 +309,7 @@ class OpenAIServingChat(OpenAIServing):
309
should_stream_with_reasoning_parsing = (
310
self._should_stream_with_reasoning_parsing(request))
311
313
- all_previous_token_ids: Optional[List[List[int]]]
312
+ all_previous_token_ids: Optional[list[list[int]]]
313
314
# Only one of these will be used, thus previous_texts and
315
# all_previous_token_ids will not be used twice in the same iteration.
@@ -339,7 +338,7 @@ class OpenAIServingChat(OpenAIServing):
338
# Prepare the tool parser if it's needed
339
try:
340
if tool_choice_auto and self.tool_parser:
342
- tool_parsers: List[Optional[ToolParser]] = [
341
+ tool_parsers: list[Optional[ToolParser]] = [
342
self.tool_parser(tokenizer)
343
] * num_choices
344
else:
@@ -406,7 +405,7 @@ class OpenAIServingChat(OpenAIServing):
405
# Send response to echo the input portion of the
406
# last message
407
if request.echo:
409
- last_msg_content: Union[str, List[Dict[str, str]]] = ""
408
+ last_msg_content: Union[str, list[dict[str, str]]] = ""
409
if conversation and "content" in conversation[
410
-1] and conversation[-1].get("role") == role:
411
last_msg_content = conversation[-1]["content"] or ""
@@ -674,7 +673,7 @@ class OpenAIServingChat(OpenAIServing):
673
result_generator: AsyncIterator[RequestOutput],
674
request_id: str,
675
model_name: str,
677
- conversation: List[ConversationMessage],
676
+ conversation: list[ConversationMessage],
677
tokenizer: AnyTokenizer,
678
request_metadata: RequestResponseMetadata,
679
) -> Union[ErrorResponse, ChatCompletionResponse]:
@@ -693,7 +692,7 @@ class OpenAIServingChat(OpenAIServing):
692
693
assert final_res is not None
694
696
- choices: List[ChatCompletionResponseChoice] = []
695
+ choices: list[ChatCompletionResponseChoice] = []
696
697
role = self.get_chat_request_role(request)
698
for output in final_res.outputs:
@@ -812,7 +811,7 @@ class OpenAIServingChat(OpenAIServing):
811
choices.append(choice_data)
812
813
if request.echo:
815
- last_msg_content: Union[str, List[Dict[str, str]]] = ""
814
+ last_msg_content: Union[str, list[dict[str, str]]] = ""
815
if conversation and "content" in conversation[-1] and conversation[
816
-1].get("role") == role:
817
last_msg_content = conversation[-1]["content"] or ""
@@ -853,8 +852,8 @@ class OpenAIServingChat(OpenAIServing):
852
return response
853
854
def _get_top_logprobs(
856
- self, logprobs: Dict[int, Logprob], top_logprobs: Optional[int],
857
- tokenizer: AnyTokenizer) -> List[ChatCompletionLogProb]:
855
+ self, logprobs: dict[int, Logprob], top_logprobs: Optional[int],
856
+ tokenizer: AnyTokenizer) -> list[ChatCompletionLogProb]:
857
return [
858
ChatCompletionLogProb(token=(token := self._get_decoded_token(
859
p[1],
@@ -871,12 +870,12 @@ class OpenAIServingChat(OpenAIServing):
870
def _create_chat_logprobs(
871
self,
872
token_ids: GenericSequence[int],
874
- top_logprobs: GenericSequence[Optional[Dict[int, Logprob]]],
873
+ top_logprobs: GenericSequence[Optional[dict[int, Logprob]]],
874
tokenizer: AnyTokenizer,
875
num_output_top_logprobs: Optional[int] = None,
876
) -> ChatCompletionLogProbs:
877
"""Create OpenAI-style logprobs."""
879
- logprobs_content: List[ChatCompletionLogProbsContent] = []
878
+ logprobs_content: list[ChatCompletionLogProbsContent] = []
879
880
for i, token_id in enumerate(token_ids):
881
step_top_logprobs = top_logprobs[i]
vllm/entrypoints/openai/serving_completion.py
+16
-16
@@ -2,9 +2,9 @@
2
3
import asyncio
4
import time
5
-from typing import AsyncGenerator, AsyncIterator, Dict, List, Optional
6
-from typing import Sequence as GenericSequence
7
-from typing import Tuple, Union, cast
5
+from collections.abc import AsyncGenerator, AsyncIterator
6
+from collections.abc import Sequence as GenericSequence
7
+from typing import Optional, Union, cast
8
9
from fastapi import Request
10
@@ -113,7 +113,7 @@ class OpenAIServingCompletion(OpenAIServing):
113
return self.create_error_response(str(e))
114
115
# Schedule the request and get the result generator.
116
- generators: List[AsyncGenerator[RequestOutput, None]] = []
116
+ generators: list[AsyncGenerator[RequestOutput, None]] = []
117
try:
118
for i, engine_prompt in enumerate(engine_prompts):
119
sampling_params: Union[SamplingParams, BeamSearchParams]
@@ -189,7 +189,7 @@ class OpenAIServingCompletion(OpenAIServing):
189
request_metadata=request_metadata)
190
191
# Non-streaming response
192
- final_res_batch: List[Optional[RequestOutput]] = [None] * num_prompts
192
+ final_res_batch: list[Optional[RequestOutput]] = [None] * num_prompts
193
try:
194
async for i, res in result_generator:
195
final_res_batch[i] = res
@@ -203,7 +203,7 @@ class OpenAIServingCompletion(OpenAIServing):
203
if final_res.prompt is None:
204
final_res.prompt = request_prompts[i]["prompt"]
205
206
- final_res_batch_checked = cast(List[RequestOutput],
206
+ final_res_batch_checked = cast(list[RequestOutput],
207
final_res_batch)
208
209
response = self.request_output_to_completion_response(
@@ -237,7 +237,7 @@ class OpenAIServingCompletion(OpenAIServing):
237
async def completion_stream_generator(
238
self,
239
request: CompletionRequest,
240
- result_generator: AsyncIterator[Tuple[int, RequestOutput]],
240
+ result_generator: AsyncIterator[tuple[int, RequestOutput]],
241
request_id: str,
242
created_time: int,
243
model_name: str,
@@ -270,7 +270,7 @@ class OpenAIServingCompletion(OpenAIServing):
270
num_prompt_tokens[prompt_idx] = len(res.prompt_token_ids)
271
272
delta_token_ids: GenericSequence[int]
273
- out_logprobs: Optional[GenericSequence[Optional[Dict[
273
+ out_logprobs: Optional[GenericSequence[Optional[dict[
274
int, Logprob]]]]
275
276
for output in res.outputs:
@@ -381,7 +381,7 @@ class OpenAIServingCompletion(OpenAIServing):
381
382
def request_output_to_completion_response(
383
self,
384
- final_res_batch: List[RequestOutput],
384
+ final_res_batch: list[RequestOutput],
385
request: CompletionRequest,
386
request_id: str,
387
created_time: int,
@@ -389,7 +389,7 @@ class OpenAIServingCompletion(OpenAIServing):
389
tokenizer: AnyTokenizer,
390
request_metadata: RequestResponseMetadata,
391
) -> CompletionResponse:
392
- choices: List[CompletionResponseChoice] = []
392
+ choices: list[CompletionResponseChoice] = []
393
num_prompt_tokens = 0
394
num_generated_tokens = 0
395
@@ -406,7 +406,7 @@ class OpenAIServingCompletion(OpenAIServing):
406
prompt_text = final_res.prompt
407
408
token_ids: GenericSequence[int]
409
- out_logprobs: Optional[GenericSequence[Optional[Dict[int,
409
+ out_logprobs: Optional[GenericSequence[Optional[dict[int,
410
Logprob]]]]
411
412
for output in final_res.outputs:
@@ -480,16 +480,16 @@ class OpenAIServingCompletion(OpenAIServing):
480
def _create_completion_logprobs(
481
self,
482
token_ids: GenericSequence[int],
483
- top_logprobs: GenericSequence[Optional[Dict[int, Logprob]]],
483
+ top_logprobs: GenericSequence[Optional[dict[int, Logprob]]],
484
num_output_top_logprobs: int,
485
tokenizer: AnyTokenizer,
486
initial_text_offset: int = 0,
487
) -> CompletionLogProbs:
488
"""Create logprobs for OpenAI Completion API."""
489
- out_text_offset: List[int] = []
490
- out_token_logprobs: List[Optional[float]] = []
491
- out_tokens: List[str] = []
492
- out_top_logprobs: List[Optional[Dict[str, float]]] = []
489
+ out_text_offset: list[int] = []
490
+ out_token_logprobs: list[Optional[float]] = []
491
+ out_tokens: list[str] = []
492
+ out_top_logprobs: list[Optional[dict[str, float]]] = []
493
494
last_token_len = 0
495
vllm/entrypoints/openai/serving_embedding.py
+8
-7
@@ -3,7 +3,8 @@
3
import asyncio
4
import base64
5
import time
6
-from typing import AsyncGenerator, Final, List, Literal, Optional, Union, cast
6
+from collections.abc import AsyncGenerator
7
+from typing import Final, Literal, Optional, Union, cast
8
9
import numpy as np
10
from fastapi import Request
@@ -31,7 +32,7 @@ logger = init_logger(__name__)
32
def _get_embedding(
33
output: EmbeddingOutput,
34
encoding_format: Literal["float", "base64"],
34
-) -> Union[List[float], str]:
35
+) -> Union[list[float], str]:
36
if encoding_format == "float":
37
return output.embedding
38
elif encoding_format == "base64":
@@ -143,7 +144,7 @@ class OpenAIServingEmbedding(OpenAIServing):
144
return self.create_error_response(str(e))
145
146
# Schedule the request and get the result generator.
146
- generators: List[AsyncGenerator[PoolingRequestOutput, None]] = []
147
+ generators: list[AsyncGenerator[PoolingRequestOutput, None]] = []
148
try:
149
pooling_params = request.to_pooling_params()
150
@@ -178,7 +179,7 @@ class OpenAIServingEmbedding(OpenAIServing):
179
num_prompts = len(engine_prompts)
180
181
# Non-streaming response
181
- final_res_batch: List[Optional[PoolingRequestOutput]]
182
+ final_res_batch: list[Optional[PoolingRequestOutput]]
183
final_res_batch = [None] * num_prompts
184
try:
185
async for i, res in result_generator:
@@ -186,7 +187,7 @@ class OpenAIServingEmbedding(OpenAIServing):
187
188
assert all(final_res is not None for final_res in final_res_batch)
189
189
- final_res_batch_checked = cast(List[PoolingRequestOutput],
190
+ final_res_batch_checked = cast(list[PoolingRequestOutput],
191
final_res_batch)
192
193
response = self.request_output_to_embedding_response(
@@ -206,13 +207,13 @@ class OpenAIServingEmbedding(OpenAIServing):
207
208
def request_output_to_embedding_response(
209
self,
209
- final_res_batch: List[PoolingRequestOutput],
210
+ final_res_batch: list[PoolingRequestOutput],
211
request_id: str,
212
created_time: int,
213
model_name: str,
214
encoding_format: Literal["float", "base64"],
215
) -> EmbeddingResponse:
215
- items: List[EmbeddingResponseData] = []
216
+ items: list[EmbeddingResponseData] = []
217
num_prompt_tokens = 0
218
219
for idx, final_res in enumerate(final_res_batch):
vllm/entrypoints/openai/serving_engine.py
+21
-22
@@ -1,15 +1,14 @@
1
# SPDX-License-Identifier: Apache-2.0
2
3
import json
4
+from collections.abc import Iterable, Iterator, Mapping, Sequence
5
from concurrent.futures.thread import ThreadPoolExecutor
6
from http import HTTPStatus
6
-from typing import (Any, Callable, Dict, Iterable, Iterator, List, Mapping,
7
- Optional, Sequence, Tuple, TypedDict, Union)
7
+from typing import Annotated, Any, Callable, Optional, TypedDict, Union
8
9
from fastapi import Request
10
from pydantic import Field
11
from starlette.datastructures import Headers
12
-from typing_extensions import Annotated
12
13
from vllm.config import ModelConfig
14
from vllm.engine.protocol import EngineClient
@@ -64,10 +63,10 @@ AnyRequest = Union[CompletionLikeRequest, ChatLikeRequest,
63
64
class TextTokensPrompt(TypedDict):
65
prompt: str
67
- prompt_token_ids: List[int]
66
+ prompt_token_ids: list[int]
67
68
70
-RequestPrompt = Union[List[int], str, TextTokensPrompt]
69
+RequestPrompt = Union[list[int], str, TextTokensPrompt]
70
71
72
class OpenAIServing:
@@ -144,7 +143,7 @@ class OpenAIServing:
143
144
def _maybe_get_adapters(
145
self, request: AnyRequest
147
- ) -> Union[Tuple[None, None], Tuple[LoRARequest, None], Tuple[
146
+ ) -> Union[tuple[None, None], tuple[LoRARequest, None], tuple[
147
None, PromptAdapterRequest]]:
148
if self._is_model_supported(request.model):
149
return None, None
@@ -188,7 +187,7 @@ class OpenAIServing:
187
self,
188
request: AnyRequest,
189
tokenizer: AnyTokenizer,
191
- prompt_ids: List[int],
190
+ prompt_ids: list[int],
191
truncate_prompt_tokens: Optional[Annotated[int, Field(ge=1)]],
192
) -> TextTokensPrompt:
193
if truncate_prompt_tokens is None:
@@ -203,7 +202,7 @@ class OpenAIServing:
202
def _validate_input(
203
self,
204
request: AnyRequest,
206
- input_ids: List[int],
205
+ input_ids: list[int],
206
input_text: str,
207
) -> TextTokensPrompt:
208
token_num = len(input_ids)
@@ -259,7 +258,7 @@ class OpenAIServing:
258
self,
259
request: AnyRequest,
260
tokenizer: AnyTokenizer,
262
- prompt_input: Union[str, List[int]],
261
+ prompt_input: Union[str, list[int]],
262
truncate_prompt_tokens: Optional[Annotated[int, Field(ge=1)]] = None,
263
add_special_tokens: bool = True,
264
) -> TextTokensPrompt:
@@ -280,7 +279,7 @@ class OpenAIServing:
279
self,
280
request: AnyRequest,
281
tokenizer: AnyTokenizer,
283
- prompt_inputs: Iterable[Union[str, List[int]]],
282
+ prompt_inputs: Iterable[Union[str, list[int]]],
283
truncate_prompt_tokens: Optional[Annotated[int, Field(ge=1)]] = None,
284
add_special_tokens: bool = True,
285
) -> Iterator[TextTokensPrompt]:
@@ -309,10 +308,10 @@ class OpenAIServing:
308
self,
309
request: AnyRequest,
310
tokenizer: AnyTokenizer,
312
- input_or_inputs: Union[str, List[str], List[int], List[List[int]]],
311
+ input_or_inputs: Union[str, list[str], list[int], list[list[int]]],
312
truncate_prompt_tokens: Optional[Annotated[int, Field(ge=1)]] = None,
313
add_special_tokens: bool = True,
315
- ) -> List[TextTokensPrompt]:
314
+ ) -> list[TextTokensPrompt]:
315
"""
316
Tokenize/detokenize depending on the input format.
317
@@ -344,10 +343,10 @@ class OpenAIServing:
343
self,
344
request: CompletionLikeRequest,
345
tokenizer: AnyTokenizer,
347
- input_or_inputs: Union[str, List[str], List[int], List[List[int]]],
346
+ input_or_inputs: Union[str, list[str], list[int], list[list[int]]],
347
truncate_prompt_tokens: Optional[Annotated[int, Field(ge=1)]] = None,
348
add_special_tokens: bool = True,
350
- ) -> Tuple[List[TextTokensPrompt], List[TokensPrompt]]:
349
+ ) -> tuple[list[TextTokensPrompt], list[TokensPrompt]]:
350
request_prompts = await self._tokenize_prompt_input_or_inputs_async(
351
request,
352
tokenizer,
@@ -367,19 +366,19 @@ class OpenAIServing:
366
self,
367
request: ChatLikeRequest,
368
tokenizer: AnyTokenizer,
370
- messages: List[ChatCompletionMessageParam],
369
+ messages: list[ChatCompletionMessageParam],
370
chat_template: Optional[str],
371
chat_template_content_format: ChatTemplateContentFormatOption,
372
add_generation_prompt: bool = True,
373
continue_final_message: bool = False,
375
- tool_dicts: Optional[List[Dict[str, Any]]] = None,
376
- documents: Optional[List[Dict[str, str]]] = None,
377
- chat_template_kwargs: Optional[Dict[str, Any]] = None,
374
+ tool_dicts: Optional[list[dict[str, Any]]] = None,
375
+ documents: Optional[list[dict[str, str]]] = None,
376
+ chat_template_kwargs: Optional[dict[str, Any]] = None,
377
tool_parser: Optional[Callable[[AnyTokenizer], ToolParser]] = None,
378
truncate_prompt_tokens: Optional[Annotated[int, Field(ge=1)]] = None,
379
add_special_tokens: bool = False,
381
- ) -> Tuple[List[ConversationMessage], Sequence[RequestPrompt],
382
- List[TokensPrompt]]:
380
+ ) -> tuple[list[ConversationMessage], Sequence[RequestPrompt],
381
+ list[TokensPrompt]]:
382
resolved_content_format = resolve_chat_template_content_format(
383
chat_template,
384
chat_template_content_format,
@@ -392,7 +391,7 @@ class OpenAIServing:
391
content_format=resolved_content_format,
392
)
393
395
- _chat_template_kwargs: Dict[str, Any] = dict(
394
+ _chat_template_kwargs: dict[str, Any] = dict(
395
chat_template=chat_template,
396
add_generation_prompt=add_generation_prompt,
397
continue_final_message=continue_final_message,
@@ -401,7 +400,7 @@ class OpenAIServing:
400
)
401
_chat_template_kwargs.update(chat_template_kwargs or {})
402
404
- request_prompt: Union[str, List[int]]
403
+ request_prompt: Union[str, list[int]]
404
if isinstance(tokenizer, MistralTokenizer):
405
request_prompt = apply_mistral_chat_template(
406
tokenizer,
vllm/entrypoints/openai/serving_models.py
+5
-5
@@ -4,7 +4,7 @@ import json
4
import pathlib
5
from dataclasses import dataclass
6
from http import HTTPStatus
7
-from typing import List, Optional, Union
7
+from typing import Optional, Union
8
9
from vllm.config import ModelConfig
10
from vllm.engine.protocol import EngineClient
@@ -53,10 +53,10 @@ class OpenAIServingModels:
53
self,
54
engine_client: EngineClient,
55
model_config: ModelConfig,
56
- base_model_paths: List[BaseModelPath],
56
+ base_model_paths: list[BaseModelPath],
57
*,
58
- lora_modules: Optional[List[LoRAModulePath]] = None,
59
- prompt_adapters: Optional[List[PromptAdapterPath]] = None,
58
+ lora_modules: Optional[list[LoRAModulePath]] = None,
59
+ prompt_adapters: Optional[list[PromptAdapterPath]] = None,
60
):
61
super().__init__()
62
@@ -65,7 +65,7 @@ class OpenAIServingModels:
65
self.engine_client = engine_client
66
67
self.static_lora_modules = lora_modules
68
- self.lora_requests: List[LoRARequest] = []
68
+ self.lora_requests: list[LoRARequest] = []
69
self.lora_id_counter = AtomicCounter(0)
70
71
self.prompt_adapter_requests = []
vllm/entrypoints/openai/serving_pooling.py
+8
-7
@@ -3,7 +3,8 @@
3
import asyncio
4
import base64
5
import time
6
-from typing import AsyncGenerator, Final, List, Literal, Optional, Union, cast
6
+from collections.abc import AsyncGenerator
7
+from typing import Final, Literal, Optional, Union, cast
8
9
import numpy as np
10
from fastapi import Request
@@ -29,7 +30,7 @@ logger = init_logger(__name__)
30
def _get_data(
31
output: PoolingOutput,
32
encoding_format: Literal["float", "base64"],
32
-) -> Union[List[float], str]:
33
+) -> Union[list[float], str]:
34
if encoding_format == "float":
35
return output.data.tolist()
36
elif encoding_format == "base64":
@@ -139,7 +140,7 @@ class OpenAIServingPooling(OpenAIServing):
140
return self.create_error_response(str(e))
141
142
# Schedule the request and get the result generator.
142
- generators: List[AsyncGenerator[PoolingRequestOutput, None]] = []
143
+ generators: list[AsyncGenerator[PoolingRequestOutput, None]] = []
144
try:
145
pooling_params = request.to_pooling_params()
146
@@ -174,7 +175,7 @@ class OpenAIServingPooling(OpenAIServing):
175
num_prompts = len(engine_prompts)
176
177
# Non-streaming response
177
- final_res_batch: List[Optional[PoolingRequestOutput]]
178
+ final_res_batch: list[Optional[PoolingRequestOutput]]
179
final_res_batch = [None] * num_prompts
180
try:
181
async for i, res in result_generator:
@@ -182,7 +183,7 @@ class OpenAIServingPooling(OpenAIServing):
183
184
assert all(final_res is not None for final_res in final_res_batch)
185
185
- final_res_batch_checked = cast(List[PoolingRequestOutput],
186
+ final_res_batch_checked = cast(list[PoolingRequestOutput],
187
final_res_batch)
188
189
response = self.request_output_to_pooling_response(
@@ -202,13 +203,13 @@ class OpenAIServingPooling(OpenAIServing):
203
204
def request_output_to_pooling_response(
205
self,
205
- final_res_batch: List[PoolingRequestOutput],
206
+ final_res_batch: list[PoolingRequestOutput],
207
request_id: str,
208
created_time: int,
209
model_name: str,
210
encoding_format: Literal["float", "base64"],
211
) -> PoolingResponse:
211
- items: List[PoolingResponseData] = []
212
+ items: list[PoolingResponseData] = []
213
num_prompt_tokens = 0
214
215
for idx, final_res in enumerate(final_res_batch):
vllm/entrypoints/openai/serving_score.py
+25
-24
@@ -1,7 +1,8 @@
1
# SPDX-License-Identifier: Apache-2.0
2
import asyncio
3
import time
4
-from typing import Any, AsyncGenerator, Dict, List, Mapping, Optional, Union
4
+from collections.abc import AsyncGenerator, Mapping
5
+from typing import Any, Optional, Union
6
7
from fastapi import Request
8
@@ -48,8 +49,8 @@ class ServingScores(OpenAIServing):
49
async def _embedding_score(
50
self,
51
tokenizer: Union[PreTrainedTokenizer, PreTrainedTokenizerFast],
51
- texts_1: List[str],
52
- texts_2: List[str],
52
+ texts_1: list[str],
53
+ texts_2: list[str],
54
request: Union[RerankRequest, ScoreRequest],
55
request_id=str,
56
tokenization_kwargs: Optional[dict[str, Any]] = None,
@@ -57,11 +58,11 @@ class ServingScores(OpenAIServing):
58
prompt_adapter_request: Optional[Union[PromptAdapterRequest,
59
None]] = None,
60
trace_headers: Optional[Mapping[str, str]] = None,
60
- ) -> List[PoolingRequestOutput]:
61
+ ) -> list[PoolingRequestOutput]:
62
63
input_texts = texts_1 + texts_2
64
64
- engine_prompts: List[TokensPrompt] = []
65
+ engine_prompts: list[TokensPrompt] = []
66
tokenize_async = make_async(tokenizer.__call__,
67
executor=self._tokenizer_executor)
68
@@ -82,7 +83,7 @@ class ServingScores(OpenAIServing):
83
prompt_token_ids=text_token_prompt["prompt_token_ids"]))
84
85
# Schedule the request and get the result generator.
85
- generators: List[AsyncGenerator[PoolingRequestOutput, None]] = []
86
+ generators: list[AsyncGenerator[PoolingRequestOutput, None]] = []
87
pooling_params = request.to_pooling_params()
88
89
for i, engine_prompt in enumerate(engine_prompts):
@@ -108,16 +109,16 @@ class ServingScores(OpenAIServing):
109
result_generator = merge_async_iterators(*generators)
110
111
# Non-streaming response
111
- final_res_batch: List[PoolingRequestOutput] = []
112
+ final_res_batch: list[PoolingRequestOutput] = []
113
113
- embeddings: List[Optional[PoolingRequestOutput]] =\
114
+ embeddings: list[Optional[PoolingRequestOutput]] =\
115
[None] * len(engine_prompts)
116
117
async for i, res in result_generator:
118
embeddings[i] = res
119
119
- emb_texts_1: List[PoolingRequestOutput] = []
120
- emb_texts_2: List[PoolingRequestOutput] = []
120
+ emb_texts_1: list[PoolingRequestOutput] = []
121
+ emb_texts_2: list[PoolingRequestOutput] = []
122
123
for i in range(0, len(texts_1)):
124
assert (emb := embeddings[i]) is not None
@@ -139,8 +140,8 @@ class ServingScores(OpenAIServing):
140
async def _cross_encoding_score(
141
self,
142
tokenizer: Union[AnyTokenizer],
142
- texts_1: List[str],
143
- texts_2: List[str],
143
+ texts_1: list[str],
144
+ texts_2: list[str],
145
request: Union[RerankRequest, ScoreRequest],
146
request_id=str,
147
tokenization_kwargs: Optional[dict[str, Any]] = None,
@@ -148,10 +149,10 @@ class ServingScores(OpenAIServing):
149
prompt_adapter_request: Optional[Union[PromptAdapterRequest,
150
None]] = None,
151
trace_headers: Optional[Mapping[str, str]] = None,
151
- ) -> List[PoolingRequestOutput]:
152
+ ) -> list[PoolingRequestOutput]:
153
153
- request_prompts: List[str] = []
154
- engine_prompts: List[TokensPrompt] = []
154
+ request_prompts: list[str] = []
155
+ engine_prompts: list[TokensPrompt] = []
156
157
if len(texts_1) == 1:
158
texts_1 = texts_1 * len(texts_2)
@@ -185,7 +186,7 @@ class ServingScores(OpenAIServing):
186
engine_prompts.append(engine_prompt)
187
188
# Schedule the request and get the result generator.
188
- generators: List[AsyncGenerator[PoolingRequestOutput, None]] = []
189
+ generators: list[AsyncGenerator[PoolingRequestOutput, None]] = []
190
191
pooling_params = request.to_pooling_params()
192
@@ -212,7 +213,7 @@ class ServingScores(OpenAIServing):
213
result_generator = merge_async_iterators(*generators)
214
215
# Non-streaming response
215
- final_res_batch: List[
216
+ final_res_batch: list[
217
Optional[PoolingRequestOutput]] = [None] * len(engine_prompts)
218
219
async for i, res in result_generator:
@@ -228,9 +229,9 @@ class ServingScores(OpenAIServing):
229
request_id: str,
230
raw_request: Optional[Request] = None,
231
truncate_prompt_tokens: Optional[int] = None,
231
- ) -> List[PoolingRequestOutput]:
232
+ ) -> list[PoolingRequestOutput]:
233
233
- tokenization_kwargs: Dict[str, Any] = {}
234
+ tokenization_kwargs: dict[str, Any] = {}
235
if truncate_prompt_tokens is not None:
236
tokenization_kwargs["truncation"] = True
237
tokenization_kwargs["max_length"] = truncate_prompt_tokens
@@ -372,12 +373,12 @@ class ServingScores(OpenAIServing):
373
374
def request_output_to_score_response(
375
self,
375
- final_res_batch: List[PoolingRequestOutput],
376
+ final_res_batch: list[PoolingRequestOutput],
377
request_id: str,
378
created_time: int,
379
model_name: str,
380
) -> ScoreResponse:
380
- items: List[ScoreResponseData] = []
381
+ items: list[ScoreResponseData] = []
382
num_prompt_tokens = 0
383
384
for idx, final_res in enumerate(final_res_batch):
@@ -406,13 +407,13 @@ class ServingScores(OpenAIServing):
407
)
408
409
def request_output_to_rerank_response(
409
- self, final_res_batch: List[PoolingRequestOutput], request_id: str,
410
- model_name: str, documents: List[str],
410
+ self, final_res_batch: list[PoolingRequestOutput], request_id: str,
411
+ model_name: str, documents: list[str],
412
top_n: int) -> RerankResponse:
413
"""
414
Convert the output of do_rank to a RerankResponse
415
"""
415
- results: List[RerankResult] = []
416
+ results: list[RerankResult] = []
417
num_prompt_tokens = 0
418
for idx, final_res in enumerate(final_res_batch):
419
classify_res = ScoringRequestOutput.from_base(final_res)
vllm/entrypoints/openai/serving_tokenization.py
+2
-2
@@ -1,6 +1,6 @@
1
# SPDX-License-Identifier: Apache-2.0
2
3
-from typing import Final, List, Optional, Union
3
+from typing import Final, Optional, Union
4
5
from fastapi import Request
6
@@ -92,7 +92,7 @@ class OpenAIServingTokenization(OpenAIServing):
92
logger.exception("Error in preprocessing prompt inputs")
93
return self.create_error_response(str(e))
94
95
- input_ids: List[int] = []
95
+ input_ids: list[int] = []
96
for i, engine_prompt in enumerate(engine_prompts):
97
self._log_inputs(request_id,
98
request_prompts[i],
vllm/entrypoints/openai/serving_transcription.py
+2
-1
@@ -1,7 +1,8 @@
1
# SPDX-License-Identifier: Apache-2.0
2
import asyncio
3
import io
4
-from typing import AsyncGenerator, Optional, Union, cast
4
+from collections.abc import AsyncGenerator
5
+from typing import Optional, Union, cast
6
7
from fastapi import Request
8
vllm/entrypoints/openai/tool_parsers/abstract_tool_parser.py
+11
-10
@@ -1,8 +1,9 @@
1
# SPDX-License-Identifier: Apache-2.0
2
3
import os
4
+from collections.abc import Sequence
5
from functools import cached_property
5
-from typing import Callable, Dict, List, Optional, Sequence, Type, Union
6
+from typing import Callable, Optional, Union
7
8
from vllm.entrypoints.openai.protocol import (ChatCompletionRequest,
9
DeltaMessage,
@@ -22,16 +23,16 @@ class ToolParser:
23
"""
24
25
def __init__(self, tokenizer: AnyTokenizer):
25
- self.prev_tool_call_arr: List[Dict] = []
26
+ self.prev_tool_call_arr: list[dict] = []
27
# the index of the tool call that is currently being parsed
28
self.current_tool_id: int = -1
29
self.current_tool_name_sent: bool = False
29
- self.streamed_args_for_tool: List[str] = []
30
+ self.streamed_args_for_tool: list[str] = []
31
32
self.model_tokenizer = tokenizer
33
34
@cached_property
34
- def vocab(self) -> Dict[str, int]:
35
+ def vocab(self) -> dict[str, int]:
36
# NOTE: Only PreTrainedTokenizerFast is guaranteed to have .vocab
37
# whereas all tokenizers have .get_vocab()
38
return self.model_tokenizer.get_vocab()
@@ -79,10 +80,10 @@ class ToolParser:
80
81
82
class ToolParserManager:
82
- tool_parsers: Dict[str, Type] = {}
83
+ tool_parsers: dict[str, type] = {}
84
85
@classmethod
85
- def get_tool_parser(cls, name) -> Type:
86
+ def get_tool_parser(cls, name) -> type:
87
"""
88
Get tool parser by name which is registered by `register_module`.
89
@@ -95,8 +96,8 @@ class ToolParserManager:
96
97
@classmethod
98
def _register_module(cls,
98
- module: Type,
99
- module_name: Optional[Union[str, List[str]]] = None,
99
+ module: type,
100
+ module_name: Optional[Union[str, list[str]]] = None,
101
force: bool = True) -> None:
102
if not issubclass(module, ToolParser):
103
raise TypeError(
@@ -116,9 +117,9 @@ class ToolParserManager:
117
@classmethod
118
def register_module(
119
cls,
119
- name: Optional[Union[str, List[str]]] = None,
120
+ name: Optional[Union[str, list[str]]] = None,
121
force: bool = True,
121
- module: Union[Type, None] = None) -> Union[type, Callable]:
122
+ module: Union[type, None] = None) -> Union[type, Callable]:
123
"""
124
Register module with the given name or name list. it can be used as a
125
decoder(with module as None) or normal function(with module as not
vllm/entrypoints/openai/tool_parsers/granite_20b_fc_tool_parser.py
+3
-2
@@ -2,8 +2,9 @@
2
3
import json
4
import re
5
+from collections.abc import Sequence
6
from json import JSONDecoder
6
-from typing import Dict, Sequence, Union
7
+from typing import Union
8
9
import partial_json_parser
10
from partial_json_parser.core.options import Allow
@@ -145,7 +146,7 @@ class Granite20bFCToolParser(ToolParser):
146
return None
147
148
# select as the current tool call the one we're on the state at
148
- current_tool_call: Dict = tool_call_arr[self.current_tool_id] \
149
+ current_tool_call: dict = tool_call_arr[self.current_tool_id] \
150
if len(tool_call_arr) > 0 else {}
151
152
# case -- if no tokens have been streamed for the tool, e.g.
vllm/entrypoints/openai/tool_parsers/granite_tool_parser.py
+3
-2
@@ -1,7 +1,8 @@
1
# SPDX-License-Identifier: Apache-2.0
2
3
import json
4
-from typing import Dict, Sequence, Union
4
+from collections.abc import Sequence
5
+from typing import Union
6
7
import partial_json_parser
8
from partial_json_parser.core.options import Allow
@@ -136,7 +137,7 @@ class GraniteToolParser(ToolParser):
137
return None
138
139
# select as the current tool call the one we're on the state at
139
- current_tool_call: Dict = tool_call_arr[self.current_tool_id]
140
+ current_tool_call: dict = tool_call_arr[self.current_tool_id]
141
142
delta = None
143
# case: we are starting a new tool in the array
vllm/entrypoints/openai/tool_parsers/hermes_tool_parser.py
+4
-3
@@ -2,7 +2,8 @@
2
3
import json
4
import re
5
-from typing import Dict, List, Sequence, Union
5
+from collections.abc import Sequence
6
+from typing import Union
7
8
import partial_json_parser
9
from partial_json_parser.core.options import Allow
@@ -33,9 +34,9 @@ class Hermes2ProToolParser(ToolParser):
34
self.model_tokenizer = self.model_tokenizer.tokenizer
35
36
self.current_tool_name_sent: bool = False
36
- self.prev_tool_call_arr: List[Dict] = []
37
+ self.prev_tool_call_arr: list[dict] = []
38
self.current_tool_id: int = -1
38
- self.streamed_args_for_tool: List[str] = [
39
+ self.streamed_args_for_tool: list[str] = [
40
] # map what has been streamed for each tool so far to a list
41
42
self.tool_call_start_token: str = "<tool_call>"
vllm/entrypoints/openai/tool_parsers/internlm2_tool_parser.py
+3
-2
@@ -1,7 +1,8 @@
1
# SPDX-License-Identifier: Apache-2.0
2
3
import json
4
-from typing import Dict, Sequence, Union
4
+from collections.abc import Sequence
5
+from typing import Union
6
7
import partial_json_parser
8
from partial_json_parser.core.options import Allow
@@ -90,7 +91,7 @@ class Internlm2ToolParser(ToolParser):
91
# tool calls are generated in an object in inernlm2
92
# it's not support parallel tool calls
93
try:
93
- tool_call_arr: Dict = partial_json_parser.loads(
94
+ tool_call_arr: dict = partial_json_parser.loads(
95
parsable_arr, flags)
96
except partial_json_parser.core.exceptions.MalformedJSON:
97
logger.debug('not enough tokens to parse into JSON yet')
vllm/entrypoints/openai/tool_parsers/jamba_tool_parser.py
+6
-5
@@ -2,7 +2,8 @@
2
3
import json
4
import re
5
-from typing import Dict, List, Sequence, Union
5
+from collections.abc import Sequence
6
+from typing import Union
7
8
import partial_json_parser
9
from partial_json_parser.core.options import Allow
@@ -35,9 +36,9 @@ class JambaToolParser(ToolParser):
36
)
37
38
self.current_tool_name_sent: bool = False
38
- self.prev_tool_call_arr: List[Dict] = []
39
+ self.prev_tool_call_arr: list[dict] = []
40
self.current_tool_id: int = -1
40
- self.streamed_args_for_tool: List[str] = [
41
+ self.streamed_args_for_tool: list[str] = [
42
] # map what has been streamed for each tool so far to a list
43
44
self.tool_calls_start_token: str = "<tool_calls>"
@@ -157,7 +158,7 @@ class JambaToolParser(ToolParser):
158
# tool calls are generated in an array, so do partial JSON
159
# parsing on the entire array
160
try:
160
- tool_call_arr: List[Dict] = partial_json_parser.loads(
161
+ tool_call_arr: list[dict] = partial_json_parser.loads(
162
parsable_arr, flags)
163
except partial_json_parser.core.exceptions.MalformedJSON:
164
logger.debug('not enough tokens to parse into JSON yet')
@@ -165,7 +166,7 @@ class JambaToolParser(ToolParser):
166
167
# select as the current tool call the one we're on the state at
168
168
- current_tool_call: Dict = tool_call_arr[self.current_tool_id] \
169
+ current_tool_call: dict = tool_call_arr[self.current_tool_id] \
170
if len(tool_call_arr) > 0 else {}
171
172
# case -- if no tokens have been streamed for the tool, e.g.
vllm/entrypoints/openai/tool_parsers/llama_tool_parser.py
+6
-5
@@ -2,8 +2,9 @@
2
3
import json
4
import re
5
+from collections.abc import Sequence
6
from json import JSONDecoder
6
-from typing import Dict, List, Sequence, Union
7
+from typing import Union
8
9
import partial_json_parser
10
from partial_json_parser.core.options import Allow
@@ -40,10 +41,10 @@ class Llama3JsonToolParser(ToolParser):
41
42
# initialize properties used for state when parsing tool calls in
43
# streaming mode
43
- self.prev_tool_call_arr: List[Dict] = []
44
+ self.prev_tool_call_arr: list[dict] = []
45
self.current_tool_id: int = -1
46
self.current_tool_name_sent: bool = False
46
- self.streamed_args_for_tool: List[str] = [
47
+ self.streamed_args_for_tool: list[str] = [
48
] # map what has been streamed for each tool so far to a list
49
self.bot_token = "<|python_tag|>"
50
self.bot_token_id = tokenizer.encode(self.bot_token,
@@ -78,7 +79,7 @@ class Llama3JsonToolParser(ToolParser):
79
start_idx += end_idx + len('; ')
80
function_call_arr.append(obj)
81
81
- tool_calls: List[ToolCall] = [
82
+ tool_calls: list[ToolCall] = [
83
ToolCall(
84
type="function",
85
function=FunctionCall(
@@ -152,7 +153,7 @@ class Llama3JsonToolParser(ToolParser):
153
return None
154
155
# select as the current tool call the one we're on the state at
155
- current_tool_call: Dict = tool_call_arr[self.current_tool_id] \
156
+ current_tool_call: dict = tool_call_arr[self.current_tool_id] \
157
if len(tool_call_arr) > 0 else {}
158
159
# case -- if no tokens have been streamed for the tool, e.g.
vllm/entrypoints/openai/tool_parsers/mistral_tool_parser.py
+7
-6
@@ -2,9 +2,10 @@
2
3
import json
4
import re
5
+from collections.abc import Sequence
6
from random import choices
7
from string import ascii_letters, digits
7
-from typing import Dict, List, Sequence, Union
8
+from typing import Union
9
10
import partial_json_parser
11
from partial_json_parser.core.options import Allow
@@ -56,10 +57,10 @@ class MistralToolParser(ToolParser):
57
58
# initialize properties used for state when parsing tool calls in
59
# streaming mode
59
- self.prev_tool_call_arr: List[Dict] = []
60
+ self.prev_tool_call_arr: list[dict] = []
61
self.current_tool_id: int = -1
62
self.current_tool_name_sent: bool = False
62
- self.streamed_args_for_tool: List[str] = [
63
+ self.streamed_args_for_tool: list[str] = [
64
] # map what has been streamed for each tool so far to a list
65
self.bot_token = "[TOOL_CALLS]"
66
self.bot_token_id = self.vocab.get(self.bot_token)
@@ -104,7 +105,7 @@ class MistralToolParser(ToolParser):
105
function_call_arr = json.loads(raw_tool_call)
106
107
# Tool Call
107
- tool_calls: List[MistralToolCall] = [
108
+ tool_calls: list[MistralToolCall] = [
109
MistralToolCall(
110
type="function",
111
function=FunctionCall(
@@ -172,7 +173,7 @@ class MistralToolParser(ToolParser):
173
# tool calls are generated in an array, so do partial JSON
174
# parsing on the entire array
175
try:
175
- tool_call_arr: List[Dict] = partial_json_parser.loads(
176
+ tool_call_arr: list[dict] = partial_json_parser.loads(
177
parsable_arr, flags)
178
except partial_json_parser.core.exceptions.MalformedJSON:
179
logger.debug('not enough tokens to parse into JSON yet')
@@ -180,7 +181,7 @@ class MistralToolParser(ToolParser):
181
182
# select as the current tool call the one we're on the state at
183
183
- current_tool_call: Dict = tool_call_arr[self.current_tool_id] \
184
+ current_tool_call: dict = tool_call_arr[self.current_tool_id] \
185
if len(tool_call_arr) > 0 else {}
186
187
# case -- if no tokens have been streamed for the tool, e.g.
vllm/entrypoints/openai/tool_parsers/pythonic_tool_parser.py
+3
-2
@@ -3,7 +3,8 @@
3
import ast
4
import json
5
import re
6
-from typing import Any, Sequence, Tuple, Union
6
+from collections.abc import Sequence
7
+from typing import Any, Union
8
9
from transformers import PreTrainedTokenizerBase
10
@@ -204,7 +205,7 @@ def _handle_single_tool(call: ast.Call) -> ToolCall:
205
arguments=json.dumps(arguments)))
206
207
207
-def _make_valid_python(text: str) -> Union[Tuple[str, str], None]:
208
+def _make_valid_python(text: str) -> Union[tuple[str, str], None]:
209
bracket_stack = []
210
for index, char in enumerate(text):
211
if char in {"[", "(", "{"}:
vllm/entrypoints/openai/tool_parsers/utils.py
+3
-3
@@ -2,7 +2,7 @@
2
3
import json
4
from json import JSONDecodeError, JSONDecoder
5
-from typing import Any, List, Tuple
5
+from typing import Any
6
7
import partial_json_parser
8
from partial_json_parser.core.options import Allow
@@ -82,7 +82,7 @@ def extract_intermediate_diff(curr: str, old: str) -> str:
82
return diff
83
84
85
-def find_all_indices(string: str, substring: str) -> List[int]:
85
+def find_all_indices(string: str, substring: str) -> list[int]:
86
"""
87
Find all (starting) indices of a substring in a given string. Useful for
88
tool call extraction
@@ -99,7 +99,7 @@ def find_all_indices(string: str, substring: str) -> List[int]:
99
100
# partial_json_parser doesn't support extra data and
101
# JSONDecorder.raw_decode doesn't support partial JSON
102
-def partial_json_loads(input_str: str, flags: Allow) -> Tuple[Any, int]:
102
+def partial_json_loads(input_str: str, flags: Allow) -> tuple[Any, int]:
103
try:
104
return (partial_json_parser.loads(input_str, flags), len(input_str))
105
except JSONDecodeError as e:
vllm/entrypoints/score_utils.py
+7
-7
@@ -1,5 +1,5 @@
1
# SPDX-License-Identifier: Apache-2.0
2
-from typing import List, Union
2
+from typing import Union
3
4
from torch.nn import CosineSimilarity
5
@@ -10,12 +10,12 @@ from vllm.transformers_utils.tokenizer import (PreTrainedTokenizer,
10
11
def _cosine_similarity(
12
tokenizer: Union[PreTrainedTokenizer, PreTrainedTokenizerFast],
13
- embed_1: List[PoolingRequestOutput],
14
- embed_2: List[PoolingRequestOutput],
15
-) -> List[PoolingRequestOutput]:
13
+ embed_1: list[PoolingRequestOutput],
14
+ embed_2: list[PoolingRequestOutput],
15
+) -> list[PoolingRequestOutput]:
16
17
scorer = CosineSimilarity(0)
18
- scores: Union[List[PoolingRequestOutput]] = []
18
+ scores: Union[list[PoolingRequestOutput]] = []
19
20
for emb_1, emb_2 in zip(embed_1, embed_2):
21
pair_score = scorer(emb_1.outputs.data, emb_2.outputs.data)
@@ -38,8 +38,8 @@ def _cosine_similarity(
38
39
40
def _validate_score_input_lens(
41
- texts_1: Union[List[str], List[dict]],
42
- texts_2: Union[List[str], List[dict]],
41
+ texts_1: Union[list[str], list[dict]],
42
+ texts_2: Union[list[str], list[dict]],
43
):
44
if len(texts_1) > 1 and len(texts_1) != len(texts_2):
45
raise ValueError("Input lengths must be either 1:1, 1:N or N:N")
vllm/envs.py
+4
-4
@@ -2,7 +2,7 @@
2
3
import os
4
import tempfile
5
-from typing import TYPE_CHECKING, Any, Callable, Dict, List, Optional
5
+from typing import TYPE_CHECKING, Any, Callable, Optional
6
7
if TYPE_CHECKING:
8
VLLM_HOST_IP: str = ""
@@ -67,12 +67,12 @@ if TYPE_CHECKING:
67
VLLM_ALLOW_LONG_MAX_MODEL_LEN: bool = False
68
VLLM_TEST_FORCE_FP8_MARLIN: bool = False
69
VLLM_RPC_TIMEOUT: int = 10000 # ms
70
- VLLM_PLUGINS: Optional[List[str]] = None
70
+ VLLM_PLUGINS: Optional[list[str]] = None
71
VLLM_TORCH_PROFILER_DIR: Optional[str] = None
72
VLLM_USE_TRITON_AWQ: bool = False
73
VLLM_ALLOW_RUNTIME_LORA_UPDATING: bool = False
74
VLLM_SKIP_P2P_CHECK: bool = False
75
- VLLM_DISABLED_KERNELS: List[str] = []
75
+ VLLM_DISABLED_KERNELS: list[str] = []
76
VLLM_USE_V1: bool = False
77
VLLM_ROCM_FP8_PADDING: bool = True
78
VLLM_ENABLE_V1_MULTIPROCESSING: bool = True
@@ -123,7 +123,7 @@ def maybe_convert_int(value: Optional[str]) -> Optional[int]:
123
124
# begin-env-vars-definition
125
126
-environment_variables: Dict[str, Callable[[], Any]] = {
126
+environment_variables: dict[str, Callable[[], Any]] = {
127
128
# ================== Installation Time Env Vars ==================
129
vllm/forward_context.py
+3
-3
@@ -4,7 +4,7 @@ import time
4
from collections import defaultdict
5
from contextlib import contextmanager
6
from dataclasses import dataclass
7
-from typing import TYPE_CHECKING, Any, Dict, List, Optional
7
+from typing import TYPE_CHECKING, Any, Optional
8
9
import torch
10
import torch.distributed as dist
@@ -28,13 +28,13 @@ batchsize_forward_time: defaultdict = defaultdict(list)
28
@dataclass
29
class ForwardContext:
30
# copy from vllm_config.compilation_config.static_forward_context
31
- attn_layers: Dict[str, Any]
31
+ attn_layers: dict[str, Any]
32
# TODO: extend to support per-layer dynamic forward context
33
attn_metadata: "AttentionMetadata" # set dynamically for each forward pass
34
# TODO: remove after making all virtual_engines share the same kv cache
35
virtual_engine: int # set dynamically for each forward pass
36
num_tokens_across_dp: Optional[
37
- List[int]] = None # set dynamically for each forward pass
37
+ list[int]] = None # set dynamically for each forward pass
38
39
40
_forward_context: Optional[ForwardContext] = None
vllm/logger.py
+1
-1
@@ -109,7 +109,7 @@ def _configure_vllm_root_logger() -> None:
109
custom_config = json.loads(file.read())
110
111
if not isinstance(custom_config, dict):
112
- raise ValueError("Invalid logging config. Expected Dict, got %s.",
112
+ raise ValueError("Invalid logging config. Expected dict, got %s.",
113
type(custom_config).__name__)
114
logging_config = custom_config
115
vllm/logits_process.py
+8
-8
@@ -1,13 +1,13 @@
1
# SPDX-License-Identifier: Apache-2.0
2
3
-from typing import Callable, List, Tuple, Union
3
+from typing import Callable, Union
4
5
import torch
6
7
from vllm.transformers_utils.tokenizer import AnyTokenizer, MistralTokenizer
8
9
-LogitsProcessor = Union[Callable[[List[int], torch.Tensor], torch.Tensor],
10
- Callable[[List[int], List[int], torch.Tensor],
9
+LogitsProcessor = Union[Callable[[list[int], torch.Tensor], torch.Tensor],
10
+ Callable[[list[int], list[int], torch.Tensor],
11
torch.Tensor]]
12
"""LogitsProcessor is a function that takes a list
13
of previously generated tokens, the logits tensor
@@ -17,9 +17,9 @@ to sample from."""
17
18
19
def get_bad_words_logits_processors(
20
- bad_words: List[str],
21
- tokenizer: AnyTokenizer) -> List[LogitsProcessor]:
22
- bad_words_ids: List[List[int]] = list()
20
+ bad_words: list[str],
21
+ tokenizer: AnyTokenizer) -> list[LogitsProcessor]:
22
+ bad_words_ids: list[list[int]] = list()
23
24
for bad_word in bad_words:
25
# To prohibit words both at the beginning
@@ -51,13 +51,13 @@ class NoBadWordsLogitsProcessor:
51
_SMALLEST_LOGIT = float("-inf")
52
_NEUTRAL_LOGIT = 0.0
53
54
- def __init__(self, bad_words_ids: List[List[int]]):
54
+ def __init__(self, bad_words_ids: list[list[int]]):
55
self.bad_words_ids = bad_words_ids
56
self.word_bias: torch.FloatTensor = None
57
58
def __call__(
59
self,
60
- past_tokens_ids: Union[List[int], Tuple[int]],
60
+ past_tokens_ids: Union[list[int], tuple[int]],
61
logits: torch.FloatTensor,
62
) -> torch.Tensor:
63
if self.word_bias is None:
vllm/outputs.py
+12
-12
@@ -1,10 +1,10 @@
1
# SPDX-License-Identifier: Apache-2.0
2
3
import time
4
+from collections.abc import MutableSequence
5
+from collections.abc import Sequence as GenericSequence
6
from dataclasses import dataclass
5
-from typing import Dict, Generic, List, MutableSequence, Optional
6
-from typing import Sequence as GenericSequence
7
-from typing import Union
7
+from typing import Generic, Optional, Union
8
9
import torch
10
from typing_extensions import TypeVar, deprecated
@@ -109,14 +109,14 @@ class RequestOutput:
109
self,
110
request_id: str,
111
prompt: Optional[str],
112
- prompt_token_ids: Optional[List[int]],
112
+ prompt_token_ids: Optional[list[int]],
113
prompt_logprobs: Optional[PromptLogprobs],
114
- outputs: List[CompletionOutput],
114
+ outputs: list[CompletionOutput],
115
finished: bool,
116
metrics: Optional[RequestMetrics] = None,
117
lora_request: Optional[LoRARequest] = None,
118
encoder_prompt: Optional[str] = None,
119
- encoder_prompt_token_ids: Optional[List[int]] = None,
119
+ encoder_prompt_token_ids: Optional[list[int]] = None,
120
num_cached_tokens: Optional[int] = None,
121
*,
122
multi_modal_placeholders: Optional[MultiModalPlaceholderDict] = None,
@@ -139,9 +139,9 @@ class RequestOutput:
139
cls,
140
request_id: str,
141
prompt: Optional[str],
142
- prompt_token_ids: Optional[List[int]],
142
+ prompt_token_ids: Optional[list[int]],
143
text: str,
144
- token_ids: List[int],
144
+ token_ids: list[int],
145
logprobs: Optional[SampleLogprobs],
146
prompt_logprobs: Optional[PromptLogprobs],
147
cumulative_logprob: Optional[float],
@@ -189,7 +189,7 @@ class RequestOutput:
189
@classmethod
190
def from_seq_group(
191
cls, seq_group: SequenceGroup, use_cache: bool,
192
- seq_id_to_seq_group: Dict[str, SequenceGroupBase]
192
+ seq_id_to_seq_group: dict[str, SequenceGroupBase]
193
) -> Optional["RequestOutput"]:
194
finished = seq_group.is_finished()
195
@@ -363,12 +363,12 @@ class PoolingRequestOutput(Generic[_O]):
363
Args:
364
request_id (str): A unique identifier for the pooling request.
365
outputs (PoolingOutput): The pooling results for the given input.
366
- prompt_token_ids (List[int]): A list of token IDs used in the prompt.
366
+ prompt_token_ids (list[int]): A list of token IDs used in the prompt.
367
finished (bool): A flag indicating whether the pooling is completed.
368
"""
369
370
def __init__(self, request_id: str, outputs: _O,
371
- prompt_token_ids: List[int], finished: bool):
371
+ prompt_token_ids: list[int], finished: bool):
372
self.request_id = request_id
373
self.prompt_token_ids = prompt_token_ids
374
self.finished = finished
@@ -407,7 +407,7 @@ class RequestOutputFactory:
407
408
@staticmethod
409
def create(seq_group: SequenceGroup,
410
- seq_id_to_seq_group: Dict[str, SequenceGroupBase],
410
+ seq_id_to_seq_group: dict[str, SequenceGroupBase],
411
use_cache: bool = False):
412
if seq_group.pooled_data is not None:
413
return PoolingRequestOutput.from_seq_group(seq_group)
vllm/sampling_params.py
+26
-27
@@ -4,11 +4,10 @@ import copy
4
from dataclasses import dataclass
5
from enum import Enum, IntEnum
6
from functools import cached_property
7
-from typing import Any, Dict, List, Optional, Set, Union
7
+from typing import Annotated, Any, Optional, Union
8
9
import msgspec
10
from pydantic import BaseModel
11
-from typing_extensions import Annotated
11
12
from vllm.logger import init_logger
13
from vllm.logits_process import LogitsProcessor
@@ -29,9 +28,9 @@ class SamplingType(IntEnum):
28
@dataclass
29
class GuidedDecodingParams:
30
"""One of these fields will be used to build a logit processor."""
32
- json: Optional[Union[str, Dict]] = None
31
+ json: Optional[Union[str, dict]] = None
32
regex: Optional[str] = None
34
- choice: Optional[List[str]] = None
33
+ choice: Optional[list[str]] = None
34
grammar: Optional[str] = None
35
json_object: Optional[bool] = None
36
"""These are other options that can be set"""
@@ -40,9 +39,9 @@ class GuidedDecodingParams:
39
40
@staticmethod
41
def from_optional(
43
- json: Optional[Union[Dict, BaseModel, str]] = None,
42
+ json: Optional[Union[dict, BaseModel, str]] = None,
43
regex: Optional[str] = None,
45
- choice: Optional[List[str]] = None,
44
+ choice: Optional[list[str]] = None,
45
grammar: Optional[str] = None,
46
json_object: Optional[bool] = None,
47
backend: Optional[str] = None,
@@ -72,7 +71,7 @@ class GuidedDecodingParams:
71
"""
72
return (self.backend or "").split(":")[0]
73
75
- def backend_options(self) -> List[str]:
74
+ def backend_options(self) -> list[str]:
75
"""Return the backend options as a list of strings."""
76
if not self.backend or ":" not in self.backend:
77
return []
@@ -144,12 +143,12 @@ class SamplingParams(
143
considered, relative to the probability of the most likely token.
144
Must be in [0, 1]. Set to 0 to disable this.
145
seed: Random seed to use for the generation.
147
- stop: List of strings that stop the generation when they are generated.
146
+ stop: list of strings that stop the generation when they are generated.
147
The returned output will not contain the stop strings.
149
- stop_token_ids: List of tokens that stop the generation when they are
148
+ stop_token_ids: list of tokens that stop the generation when they are
149
generated. The returned output will contain the stop tokens unless
150
the stop tokens are special tokens.
152
- bad_words: List of words that are not allowed to be generated.
151
+ bad_words: list of words that are not allowed to be generated.
152
More precisely, only the last token of a corresponding
153
token sequence is not allowed when the next generated token
154
can complete the sequence.
@@ -172,7 +171,7 @@ class SamplingParams(
171
skip_special_tokens: Whether to skip special tokens in the output.
172
spaces_between_special_tokens: Whether to add spaces between special
173
tokens in the output. Defaults to True.
175
- logits_processors: List of functions that modify logits based on
174
+ logits_processors: list of functions that modify logits based on
175
previously generated tokens, and optionally prompt tokens as
176
a first argument.
177
truncate_prompt_tokens: If set to an integer k, will use only the last k
@@ -198,9 +197,9 @@ class SamplingParams(
197
top_k: int = -1
198
min_p: float = 0.0
199
seed: Optional[int] = None
201
- stop: Optional[Union[str, List[str]]] = None
202
- stop_token_ids: Optional[List[int]] = None
203
- bad_words: Optional[List[str]] = None
200
+ stop: Optional[Union[str, list[str]]] = None
201
+ stop_token_ids: Optional[list[int]] = None
202
+ bad_words: Optional[list[str]] = None
203
ignore_eos: bool = False
204
max_tokens: Optional[int] = 16
205
min_tokens: int = 0
@@ -212,8 +211,8 @@ class SamplingParams(
211
detokenize: bool = True
212
skip_special_tokens: bool = True
213
spaces_between_special_tokens: bool = True
215
- # Optional[List[LogitsProcessor]] type. We use Any here because
216
- # Optional[List[LogitsProcessor]] type is not supported by msgspec.
214
+ # Optional[list[LogitsProcessor]] type. We use Any here because
215
+ # Optional[list[LogitsProcessor]] type is not supported by msgspec.
216
logits_processors: Optional[Any] = None
217
include_stop_str_in_output: bool = False
218
truncate_prompt_tokens: Optional[Annotated[int, msgspec.Meta(ge=1)]] = None
@@ -222,12 +221,12 @@ class SamplingParams(
221
# The below fields are not supposed to be used as an input.
222
# They are set in post_init.
223
output_text_buffer_length: int = 0
225
- _all_stop_token_ids: Set[int] = msgspec.field(default_factory=set)
224
+ _all_stop_token_ids: set[int] = msgspec.field(default_factory=set)
225
226
# Fields used to construct logits processors
227
guided_decoding: Optional[GuidedDecodingParams] = None
229
- logit_bias: Optional[Dict[int, float]] = None
230
- allowed_token_ids: Optional[List[int]] = None
228
+ logit_bias: Optional[dict[int, float]] = None
229
+ allowed_token_ids: Optional[list[int]] = None
230
231
@staticmethod
232
def from_optional(
@@ -241,9 +240,9 @@ class SamplingParams(
240
top_k: int = -1,
241
min_p: float = 0.0,
242
seed: Optional[int] = None,
244
- stop: Optional[Union[str, List[str]]] = None,
245
- stop_token_ids: Optional[List[int]] = None,
246
- bad_words: Optional[List[str]] = None,
243
+ stop: Optional[Union[str, list[str]]] = None,
244
+ stop_token_ids: Optional[list[int]] = None,
245
+ bad_words: Optional[list[str]] = None,
246
include_stop_str_in_output: bool = False,
247
ignore_eos: bool = False,
248
max_tokens: Optional[int] = 16,
@@ -253,13 +252,13 @@ class SamplingParams(
252
detokenize: bool = True,
253
skip_special_tokens: bool = True,
254
spaces_between_special_tokens: bool = True,
256
- logits_processors: Optional[List[LogitsProcessor]] = None,
255
+ logits_processors: Optional[list[LogitsProcessor]] = None,
256
truncate_prompt_tokens: Optional[Annotated[int,
257
msgspec.Meta(ge=1)]] = None,
258
output_kind: RequestOutputKind = RequestOutputKind.CUMULATIVE,
259
guided_decoding: Optional[GuidedDecodingParams] = None,
261
- logit_bias: Optional[Union[Dict[int, float], Dict[str, float]]] = None,
262
- allowed_token_ids: Optional[List[int]] = None,
260
+ logit_bias: Optional[Union[dict[int, float], dict[str, float]]] = None,
261
+ allowed_token_ids: Optional[list[int]] = None,
262
) -> "SamplingParams":
263
if logit_bias is not None:
264
# Convert token_id to integer
@@ -435,7 +434,7 @@ class SamplingParams(
434
435
def update_from_generation_config(
436
self,
438
- generation_config: Dict[str, Any],
437
+ generation_config: dict[str, Any],
438
model_eos_token_id: Optional[int] = None) -> None:
439
"""Update if there are non-default values from generation_config"""
440
@@ -468,7 +467,7 @@ class SamplingParams(
467
return SamplingType.RANDOM
468
469
@property
471
- def all_stop_token_ids(self) -> Set[int]:
470
+ def all_stop_token_ids(self) -> set[int]:
471
return self._all_stop_token_ids
472
473
def clone(self) -> "SamplingParams":
vllm/sequence.py
+66
-66
@@ -5,11 +5,11 @@ import enum
5
from abc import ABC, abstractmethod
6
from array import array
7
from collections import defaultdict
8
+from collections.abc import Mapping
9
+from collections.abc import Sequence as GenericSequence
10
from dataclasses import dataclass, field
11
from functools import reduce
10
-from typing import Any, Callable, DefaultDict, Dict, List, Mapping, Optional
11
-from typing import Sequence as GenericSequence
12
-from typing import Set, Tuple, Union
12
+from typing import Any, Callable, Optional, Union
13
14
import msgspec
15
import torch
@@ -50,9 +50,9 @@ class Logprob:
50
51
# {token_id -> logprob} per each sequence group. None if the corresponding
52
# sequence group doesn't require prompt logprob.
53
-PromptLogprobs = List[Optional[Dict[int, Logprob]]]
53
+PromptLogprobs = list[Optional[dict[int, Logprob]]]
54
# {token_id -> logprob} for each sequence group.
55
-SampleLogprobs = List[Dict[int, Logprob]]
55
+SampleLogprobs = list[dict[int, Logprob]]
56
57
58
class SequenceStatus(enum.IntEnum):
@@ -129,7 +129,7 @@ class SequenceDataDelta(
129
omit_defaults=True): # type: ignore[call-arg]
130
"""Delta SequenceData to send to workers per step."""
131
# A new token to be appended to existing SequenceData.
132
- new_output_token_ids: List[int]
132
+ new_output_token_ids: list[int]
133
# Overwriting existing `cumulative_logprob`
134
new_cumulative_logprob: float
135
# Overwriting existing `num_computed_tokens`.
@@ -152,7 +152,7 @@ class SequenceData(msgspec.Struct,
152
output_token_ids: The token IDs of the output.
153
cumulative_logprob: The cumulative log probability of the output.
154
"""
155
- # NOTE: we cannot use Union[List, array] because msgspec cannot support
155
+ # NOTE: we cannot use Union[list, array] because msgspec cannot support
156
# union of 2 list types.
157
_prompt_token_ids: array
158
_output_token_ids: array = msgspec.field(
@@ -160,25 +160,25 @@ class SequenceData(msgspec.Struct,
160
161
### The below fields should not be passed as an argument ###
162
_cumulative_logprob: float = 0.0
163
- _prompt_token_ids_tuple: Tuple[int,
163
+ _prompt_token_ids_tuple: tuple[int,
164
...] = msgspec.field(default_factory=tuple)
165
# The number of tokens that are computed (that run against the model).
166
_num_computed_tokens: int = 0
167
# The number of tokens with prefix cache hit.
168
_num_cached_tokens: int = 0
169
_stage: SequenceStage = SequenceStage.PREFILL
170
- _cached_all_token_ids: List[int] = msgspec.field(default_factory=list)
170
+ _cached_all_token_ids: list[int] = msgspec.field(default_factory=list)
171
172
# It is used to get delta input. It is reset when `get_delta_and_reset`
173
# is called.
174
- _new_appended_tokens: List[int] = msgspec.field(default_factory=list)
174
+ _new_appended_tokens: list[int] = msgspec.field(default_factory=list)
175
176
# It is used to compute mrope_position_ids.
177
_mrope_position_delta: Optional[int] = None
178
179
@staticmethod
180
def from_prompt_token_counts(
181
- *token_counts: Tuple[int, int]) -> "SequenceData":
181
+ *token_counts: tuple[int, int]) -> "SequenceData":
182
"""
183
Construct a :class:`SequenceData` instance by concatenating
184
prompt token sequences.
@@ -220,14 +220,14 @@ class SequenceData(msgspec.Struct,
220
def __post_init__(self) -> None:
221
assert self._prompt_token_ids.typecode == "l"
222
assert self._output_token_ids.typecode == "l"
223
- self._prompt_token_ids_tuple: Tuple[int, ...] = tuple(
223
+ self._prompt_token_ids_tuple: tuple[int, ...] = tuple(
224
self._prompt_token_ids)
225
self._update_cached_all_tokens()
226
227
def _update_cached_all_tokens(self):
228
assert isinstance(self._prompt_token_ids, array)
229
assert isinstance(self._output_token_ids, array)
230
- self._cached_all_token_ids: List[int] = list(self._prompt_token_ids +
230
+ self._cached_all_token_ids: list[int] = list(self._prompt_token_ids +
231
self._output_token_ids)
232
233
@property
@@ -235,7 +235,7 @@ class SequenceData(msgspec.Struct,
235
return self._cumulative_logprob
236
237
@property
238
- def prompt_token_ids(self) -> Tuple[int, ...]:
238
+ def prompt_token_ids(self) -> tuple[int, ...]:
239
return self._prompt_token_ids_tuple
240
241
@prompt_token_ids.setter
@@ -252,7 +252,7 @@ class SequenceData(msgspec.Struct,
252
return self._prompt_token_ids
253
254
@property
255
- def output_token_ids(self) -> Tuple[int, ...]:
255
+ def output_token_ids(self) -> tuple[int, ...]:
256
return tuple(self._output_token_ids)
257
258
@output_token_ids.setter
@@ -295,12 +295,12 @@ class SequenceData(msgspec.Struct,
295
def get_output_len(self) -> int:
296
return len(self._output_token_ids)
297
298
- def get_token_ids(self) -> List[int]:
298
+ def get_token_ids(self) -> list[int]:
299
return self._cached_all_token_ids
300
301
def get_prefix_token_ids(
302
self, num_tokens: int
303
- ) -> Tuple[Tuple[int, ...], Optional[Tuple[int, ...]]]:
303
+ ) -> tuple[tuple[int, ...], Optional[tuple[int, ...]]]:
304
"""Get prefix tokens, and make the return value hashable"""
305
prompt_length = self.get_prompt_len()
306
if num_tokens > prompt_length:
@@ -351,10 +351,10 @@ class SequenceData(msgspec.Struct,
351
return self._prompt_token_ids[-1]
352
return self._output_token_ids[-1]
353
354
- def get_prompt_token_ids(self) -> Tuple[int, ...]:
354
+ def get_prompt_token_ids(self) -> tuple[int, ...]:
355
return self.prompt_token_ids
356
357
- def get_output_token_ids(self) -> Tuple[int, ...]:
357
+ def get_output_token_ids(self) -> tuple[int, ...]:
358
return self.output_token_ids
359
360
def get_delta_and_reset(self) -> SequenceDataDelta:
@@ -432,7 +432,7 @@ class Sequence:
432
self.prefix_offset = 0
433
self.read_offset = 0
434
# Input + output tokens
435
- self.tokens: Optional[List[str]] = None
435
+ self.tokens: Optional[list[str]] = None
436
437
@property
438
def n_blocks(self) -> int:
@@ -443,7 +443,7 @@ class Sequence:
443
return self.inputs.prompt
444
445
@property
446
- def prompt_token_ids(self) -> List[int]:
446
+ def prompt_token_ids(self) -> list[int]:
447
return self.inputs.prompt_token_ids
448
449
@property
@@ -451,7 +451,7 @@ class Sequence:
451
return self.inputs.prompt_embeds
452
453
@property
454
- def token_type_ids(self) -> List[int]:
454
+ def token_type_ids(self) -> list[int]:
455
return self.inputs.token_type_ids
456
457
@property
@@ -463,7 +463,7 @@ class Sequence:
463
return self.inputs.multi_modal_placeholders
464
465
@property
466
- def mm_processor_kwargs(self) -> Dict[str, Any]:
466
+ def mm_processor_kwargs(self) -> dict[str, Any]:
467
return self.inputs.mm_processor_kwargs
468
469
@property
@@ -548,7 +548,7 @@ class Sequence:
548
"""Reset the sequence states for recomputation."""
549
self.data.reset_state_for_recompute()
550
551
- def append_token_id(self, token_id: int, logprobs: Dict[int,
551
+ def append_token_id(self, token_id: int, logprobs: dict[int,
552
Logprob]) -> None:
553
assert token_id in logprobs
554
self.output_logprobs.append(logprobs)
@@ -563,16 +563,16 @@ class Sequence:
563
def get_output_len(self) -> int:
564
return self.data.get_output_len()
565
566
- def get_token_ids(self) -> List[int]:
566
+ def get_token_ids(self) -> list[int]:
567
return self.data.get_token_ids()
568
569
- def get_prompt_token_ids(self) -> Tuple[int, ...]:
569
+ def get_prompt_token_ids(self) -> tuple[int, ...]:
570
return self.data.get_prompt_token_ids()
571
572
def get_last_token_id(self) -> int:
573
return self.data.get_last_token_id()
574
575
- def get_output_token_ids(self) -> Tuple[int, ...]:
575
+ def get_output_token_ids(self) -> tuple[int, ...]:
576
return self.data.get_output_token_ids()
577
578
def get_cumulative_logprob(self) -> float:
@@ -644,7 +644,7 @@ class SequenceGroup:
644
def __init__(
645
self,
646
request_id: str,
647
- seqs: List[Sequence],
647
+ seqs: list[Sequence],
648
arrival_time: float,
649
sampling_params: Optional[SamplingParams] = None,
650
lora_request: Optional[LoRARequest] = None,
@@ -686,7 +686,7 @@ class SequenceGroup:
686
return self.first_seq.prompt
687
688
@property
689
- def prompt_token_ids(self) -> List[int]:
689
+ def prompt_token_ids(self) -> list[int]:
690
return self.first_seq.prompt_token_ids
691
692
@property
@@ -698,7 +698,7 @@ class SequenceGroup:
698
if self.encoder_seq is not None else None)
699
700
@property
701
- def encoder_prompt_token_ids(self) -> Optional[List[int]]:
701
+ def encoder_prompt_token_ids(self) -> Optional[list[int]]:
702
# There are either 0 or 1 encoder sequences
703
# If one is present, its prompt token ids are
704
# distinct from the decoder's.
@@ -706,7 +706,7 @@ class SequenceGroup:
706
if self.encoder_seq is not None else None)
707
708
@property
709
- def token_type_ids(self) -> Optional[List[int]]:
709
+ def token_type_ids(self) -> Optional[list[int]]:
710
return self.first_seq.token_type_ids
711
712
@property
@@ -726,7 +726,7 @@ class SequenceGroup:
726
return {}
727
728
@property
729
- def mm_processor_kwargs(self) -> Dict[str, Any]:
729
+ def mm_processor_kwargs(self) -> dict[str, Any]:
730
if self.first_seq.multi_modal_data:
731
return self.first_seq.mm_processor_kwargs
732
elif self.encoder_seq is not None:
@@ -823,7 +823,7 @@ class SequenceGroup:
823
def get_seqs(
824
self,
825
status: Optional[SequenceStatus] = None,
826
- ) -> List[Sequence]:
826
+ ) -> list[Sequence]:
827
if status is None:
828
return self.seqs
829
@@ -838,7 +838,7 @@ class SequenceGroup:
838
def get_encoder_seq(self) -> Optional[Sequence]:
839
return self.encoder_seq
840
841
- def get_finished_seqs(self) -> List[Sequence]:
841
+ def get_finished_seqs(self) -> list[Sequence]:
842
if self.is_single_seq:
843
return self.seqs if self.first_seq.is_finished() else []
844
@@ -897,13 +897,13 @@ class SequenceGroupMetadataDelta(
897
After sending the first SequenceGroupMetadata, vLLM scheduler
898
only sends delta to reduce the data payload size.
899
"""
900
- seq_data_delta: Dict[int, SequenceDataDelta]
900
+ seq_data_delta: dict[int, SequenceDataDelta]
901
request_id: str
902
- block_tables: Dict[int, List[int]]
902
+ block_tables: dict[int, list[int]]
903
is_prompt: bool
904
do_sample: bool = True
905
token_chunk_size: Optional[int] = None
906
- computed_block_nums: Optional[List[int]] = None
906
+ computed_block_nums: Optional[list[int]] = None
907
state: Optional[SequenceGroupState] = msgspec.field(
908
default_factory=lambda: SequenceGroupState())
909
@@ -947,23 +947,23 @@ class SequenceGroupMetadata(
947
948
request_id: str
949
is_prompt: bool
950
- seq_data: Dict[int, SequenceData]
950
+ seq_data: dict[int, SequenceData]
951
sampling_params: Optional[SamplingParams]
952
- block_tables: Dict[int, List[int]]
952
+ block_tables: dict[int, list[int]]
953
do_sample: bool = True
954
pooling_params: Optional[PoolingParams] = None
955
lora_request: Optional[LoRARequest] = None
956
- computed_block_nums: Optional[List[int]] = None
956
+ computed_block_nums: Optional[list[int]] = None
957
state: Optional[SequenceGroupState] = msgspec.field(
958
default_factory=lambda: SequenceGroupState())
959
# "MultiModalDataDict" types. We have to use Any due to msgspec
960
# doesn't allow to have union of 2 different dicts.
961
- token_type_ids: Optional[List[int]] = None
961
+ token_type_ids: Optional[list[int]] = None
962
multi_modal_data: Optional[Any] = None
963
multi_modal_placeholders: Optional[MultiModalPlaceholderDict] = None
964
- mm_processor_kwargs: Optional[Dict[str, Any]] = None
964
+ mm_processor_kwargs: Optional[dict[str, Any]] = None
965
encoder_seq_data: Optional[SequenceData] = None
966
- cross_block_table: Optional[List[int]] = None
966
+ cross_block_table: Optional[list[int]] = None
967
prompt_adapter_request: Optional[PromptAdapterRequest] = None
968
token_chunk_size: Optional[int] = None
969
@@ -1042,7 +1042,7 @@ class SequenceOutput(
1042
"""
1043
parent_seq_id: int
1044
output_token: int
1045
- logprobs: Dict[int, Logprob]
1045
+ logprobs: dict[int, Logprob]
1046
1047
def __repr__(self) -> str:
1048
return (f"SequenceOutput(parent_seq_id={self.parent_seq_id}, "
@@ -1076,7 +1076,7 @@ class CompletionSequenceGroupOutput(
1076
array_like=True): # type: ignore[call-arg]
1077
"""The model output associated with a completion sequence group."""
1078
__metaclass__ = SequenceGroupOutput
1079
- samples: List[SequenceOutput]
1079
+ samples: list[SequenceOutput]
1080
# Prompt logprob for each prompt query token.
1081
prompt_logprobs: Optional[PromptLogprobs]
1082
@@ -1119,7 +1119,7 @@ class IntermediateTensors:
1119
contains the hidden states and residuals for a request.
1120
"""
1121
1122
- tensors: Dict[str, torch.Tensor]
1122
+ tensors: dict[str, torch.Tensor]
1123
1124
def __init__(self, tensors):
1125
# manually define this function, so that
@@ -1155,7 +1155,7 @@ class PoolerOutput(
1155
omit_defaults=True, # type: ignore[call-arg]
1156
array_like=True): # type: ignore[call-arg]
1157
"""The output from a pooling operation in the pooling model."""
1158
- outputs: List[PoolingSequenceGroupOutput]
1158
+ outputs: list[PoolingSequenceGroupOutput]
1159
1160
def __getitem__(self, idx: int) -> PoolingSequenceGroupOutput:
1161
return self.outputs[idx]
@@ -1172,7 +1172,7 @@ class PoolerOutput(
1172
1173
1174
def get_all_seq_ids(
1175
- seq_group_metadata_list: List[SequenceGroupMetadata]) -> List[int]:
1175
+ seq_group_metadata_list: list[SequenceGroupMetadata]) -> list[int]:
1176
"""Given a list of SequenceGroupMetadata, create a list of all
1177
sequence ids.
1178
"""
@@ -1180,13 +1180,13 @@ def get_all_seq_ids(
1180
1181
1182
def get_all_seq_ids_and_request_ids(
1183
- seq_group_metadata_list: List[SequenceGroupMetadata]
1184
-) -> Tuple[List[int], Dict[str, Set[int]]]:
1183
+ seq_group_metadata_list: list[SequenceGroupMetadata]
1184
+) -> tuple[list[int], dict[str, set[int]]]:
1185
"""Given a list of SequenceGroupMetadata, create a list of all
1186
sequence ids.
1187
"""
1188
- seq_ids: List[int] = []
1189
- request_id_seq_ids_mapping: DefaultDict[str, Set[int]] = defaultdict(set)
1188
+ seq_ids: list[int] = []
1189
+ request_id_seq_ids_mapping: defaultdict[str, set[int]] = defaultdict(set)
1190
for sg in seq_group_metadata_list:
1191
for seq_id in sg.seq_data:
1192
seq_ids.append(seq_id)
@@ -1206,14 +1206,14 @@ class HiddenStates(msgspec.Struct, array_like=True,
1206
# all tokens, whereas for decode step, it use used for last accepted tokens.
1207
hidden_states: torch.Tensor
1208
# The sequence group metadata list. Only needed for decode step.
1209
- seq_group_metadata_list: Optional[List[SequenceGroupMetadata]] = None
1209
+ seq_group_metadata_list: Optional[list[SequenceGroupMetadata]] = None
1210
# Scorer hidden states of the 2nd last token proposed by the proposer (
1211
# irrespective of whether it was accepted or not). Only used for cases when
1212
# last proposed token is accepted (i.e., in case of bonus tokens). For the
1213
# case of no bonus tokens, these are ignored.
1214
second_last_token_hidden_states: Optional[torch.Tensor] = None
1215
1216
- _seq_ids: List[int] = msgspec.field(default_factory=list)
1216
+ _seq_ids: list[int] = msgspec.field(default_factory=list)
1217
1218
def __post_init__(self):
1219
if self.seq_group_metadata_list is not None:
@@ -1221,12 +1221,12 @@ class HiddenStates(msgspec.Struct, array_like=True,
1221
self._seq_ids = get_all_seq_ids(self.seq_group_metadata_list)
1222
1223
@property
1224
- def seq_ids(self) -> List[int]:
1224
+ def seq_ids(self) -> list[int]:
1225
return self._seq_ids
1226
1227
def update(self,
1228
hidden_states: torch.Tensor,
1229
- seq_group_metadata_list: List[SequenceGroupMetadata],
1229
+ seq_group_metadata_list: list[SequenceGroupMetadata],
1230
second_last_token_hidden_states: Optional[torch.Tensor] = None):
1231
"""Update hidden states from target model invocation. Only used for
1232
decode steps"""
@@ -1244,7 +1244,7 @@ class HiddenStates(msgspec.Struct, array_like=True,
1244
])
1245
1246
def prune(self,
1247
- seq_group_metadata_list: List[SequenceGroupMetadata]) -> None:
1247
+ seq_group_metadata_list: list[SequenceGroupMetadata]) -> None:
1248
"""Prune to provided list of sequence ids. Only used for decode steps.
1249
"""
1250
# Currently this prunes all seq_ids not present in
@@ -1287,16 +1287,16 @@ class ExecuteModelRequest(
1287
"""The model execution request, containing CPU metadata only. The LLM
1288
engine should create an instance of this class for each request batch."""
1289
# The sequence group metadata list.
1290
- seq_group_metadata_list: List[Union[SequenceGroupMetadata,
1290
+ seq_group_metadata_list: list[Union[SequenceGroupMetadata,
1291
SequenceGroupMetadataDelta]]
1292
# Blocks to swap in. List of CPU -> GPU block number.
1293
- blocks_to_swap_in: List[Tuple[int,
1293
+ blocks_to_swap_in: list[tuple[int,
1294
int]] = msgspec.field(default_factory=list)
1295
# Blocks to swap out. List of GPU -> CPU block number.
1296
- blocks_to_swap_out: List[Tuple[int,
1296
+ blocks_to_swap_out: list[tuple[int,
1297
int]] = msgspec.field(default_factory=list)
1298
# Blocks to copy. Source to dest block.
1299
- blocks_to_copy: List[Tuple[int, int]] = msgspec.field(default_factory=list)
1299
+ blocks_to_copy: list[tuple[int, int]] = msgspec.field(default_factory=list)
1300
# Virtual engine ID for pipeline parallel.
1301
virtual_engine: int = 0
1302
# The number of slots for lookahead decoding.
@@ -1310,7 +1310,7 @@ class ExecuteModelRequest(
1310
# The step index for spec model input.
1311
spec_step_idx: Optional[int] = None
1312
# Finished request ids since last step.
1313
- finished_requests_ids: List[str] = msgspec.field(default_factory=list)
1313
+ finished_requests_ids: list[str] = msgspec.field(default_factory=list)
1314
# The last sampled token ids for multi step decoding.
1315
last_sampled_token_ids: Optional[torch.Tensor] = None
1316
# Async callback
@@ -1344,7 +1344,7 @@ class ExecuteModelRequest(
1344
return state.current_step
1345
1346
def clone(
1347
- self, seq_group_metadata_list: List[Union[SequenceGroupMetadata,
1347
+ self, seq_group_metadata_list: list[Union[SequenceGroupMetadata,
1348
SequenceGroupMetadataDelta]]
1349
) -> "ExecuteModelRequest":
1350
"""Clone the request with a new sequence group metadata list."""
@@ -1371,13 +1371,13 @@ class SequenceGroupBase:
1371
assembled_seq_group: Optional[SequenceGroup] = None
1372
1373
# seq id to a unique index inside this group
1374
- seq_id_to_index: Dict[str, int] = field(default_factory=dict)
1374
+ seq_id_to_index: dict[str, int] = field(default_factory=dict)
1375
1376
# seq ids to be finished
1377
- to_be_finished: Dict[str, SequenceGroup] = field(default_factory=dict)
1377
+ to_be_finished: dict[str, SequenceGroup] = field(default_factory=dict)
1378
1379
# seq id to finished sequences
1380
- finished_reqs: Dict[str, SequenceGroup] = field(default_factory=dict)
1380
+ finished_reqs: dict[str, SequenceGroup] = field(default_factory=dict)
1381
1382
streaming: bool = False
1383
vllm/tracing.py
+2
-1
@@ -1,7 +1,8 @@
1
# SPDX-License-Identifier: Apache-2.0
2
3
import os
4
-from typing import Mapping, Optional
4
+from collections.abc import Mapping
5
+from typing import Optional
6
7
from vllm.logger import init_logger
8
from vllm.utils import run_once
vllm/utils.py
+38
-38
@@ -28,12 +28,12 @@ import warnings
28
import weakref
29
from asyncio import FIRST_COMPLETED, AbstractEventLoop, Task
30
from collections import OrderedDict, UserDict, defaultdict
31
-from collections.abc import Hashable, Iterable, Mapping
31
+from collections.abc import (AsyncGenerator, Awaitable, Generator, Hashable,
32
+ Iterable, Iterator, Mapping)
33
from dataclasses import dataclass, field
34
from functools import cache, lru_cache, partial, wraps
34
-from typing import (TYPE_CHECKING, Any, AsyncGenerator, Awaitable, Callable,
35
- Dict, Generator, Generic, Iterator, List, Literal,
36
- NamedTuple, Optional, Tuple, Type, TypeVar, Union)
35
+from typing import (TYPE_CHECKING, Any, Callable, Generic, Literal, NamedTuple,
36
+ Optional, TypeVar, Union)
37
from uuid import uuid4
38
39
import cloudpickle
@@ -400,7 +400,7 @@ def _next_task(iterator: AsyncGenerator[T, None],
400
401
async def merge_async_iterators(
402
*iterators: AsyncGenerator[T,
403
- None], ) -> AsyncGenerator[Tuple[int, T], None]:
403
+ None], ) -> AsyncGenerator[tuple[int, T], None]:
404
"""Merge multiple asynchronous iterators into a single iterator.
405
406
This method handle the case where some iterators finish before others.
@@ -433,7 +433,7 @@ async def merge_async_iterators(
433
434
435
async def collect_from_async_generator(
436
- iterator: AsyncGenerator[T, None]) -> List[T]:
436
+ iterator: AsyncGenerator[T, None]) -> list[T]:
437
"""Collect all items from an async generator into a list."""
438
items = []
439
async for item in iterator:
@@ -560,7 +560,7 @@ def find_process_using_port(port: int) -> Optional[psutil.Process]:
560
return None
561
562
563
-def update_environment_variables(envs: Dict[str, str]):
563
+def update_environment_variables(envs: dict[str, str]):
564
for k, v in envs.items():
565
if k in os.environ and os.environ[k] != v:
566
logger.warning(
@@ -569,7 +569,7 @@ def update_environment_variables(envs: Dict[str, str]):
569
os.environ[k] = v
570
571
572
-def chunk_list(lst: List[T], chunk_size: int):
572
+def chunk_list(lst: list[T], chunk_size: int):
573
"""Yield successive chunk_size chunks from lst."""
574
for i in range(0, len(lst), chunk_size):
575
yield lst[i:i + chunk_size]
@@ -642,7 +642,7 @@ def create_kv_caches_with_random_flash(
642
model_dtype: Optional[Union[str, torch.dtype]] = None,
643
seed: int = 0,
644
device: Optional[str] = "cuda",
645
-) -> Tuple[List[torch.Tensor], List[torch.Tensor]]:
645
+) -> tuple[list[torch.Tensor], list[torch.Tensor]]:
646
from vllm.platforms import current_platform
647
current_platform.seed_everything(seed)
648
@@ -650,8 +650,8 @@ def create_kv_caches_with_random_flash(
650
key_value_cache_shape = (num_blocks, 2, block_size, num_heads, head_size)
651
scale = head_size**-0.5
652
653
- key_caches: List[torch.Tensor] = []
654
- value_caches: List[torch.Tensor] = []
653
+ key_caches: list[torch.Tensor] = []
654
+ value_caches: list[torch.Tensor] = []
655
656
for _ in range(num_layers):
657
key_value_cache = torch.empty(size=key_value_cache_shape,
@@ -679,7 +679,7 @@ def create_kv_caches_with_random(
679
model_dtype: Optional[Union[str, torch.dtype]] = None,
680
seed: int = 0,
681
device: Optional[str] = "cuda",
682
-) -> Tuple[List[torch.Tensor], List[torch.Tensor]]:
682
+) -> tuple[list[torch.Tensor], list[torch.Tensor]]:
683
684
if cache_dtype == "fp8" and head_size % 16:
685
raise ValueError(
@@ -693,7 +693,7 @@ def create_kv_caches_with_random(
693
scale = head_size**-0.5
694
x = 16 // torch.tensor([], dtype=torch_dtype).element_size()
695
key_cache_shape = (num_blocks, num_heads, head_size // x, block_size, x)
696
- key_caches: List[torch.Tensor] = []
696
+ key_caches: list[torch.Tensor] = []
697
for _ in range(num_layers):
698
key_cache = torch.empty(size=key_cache_shape,
699
dtype=torch_dtype,
@@ -708,7 +708,7 @@ def create_kv_caches_with_random(
708
key_caches.append(key_cache)
709
710
value_cache_shape = (num_blocks, num_heads, head_size, block_size)
711
- value_caches: List[torch.Tensor] = []
711
+ value_caches: list[torch.Tensor] = []
712
for _ in range(num_layers):
713
value_cache = torch.empty(size=value_cache_shape,
714
dtype=torch_dtype,
@@ -754,7 +754,7 @@ class DeviceMemoryProfiler:
754
755
756
def make_ndarray_with_pad(
757
- x: List[List[T]],
757
+ x: list[list[T]],
758
pad: T,
759
dtype: npt.DTypeLike,
760
*,
@@ -779,7 +779,7 @@ def make_ndarray_with_pad(
779
780
781
def make_tensor_with_pad(
782
- x: List[List[T]],
782
+ x: list[list[T]],
783
pad: T,
784
dtype: torch.dtype,
785
*,
@@ -831,7 +831,7 @@ def is_list_of(
831
typ: Union[type[T], tuple[type[T], ...]],
832
*,
833
check: Literal["first", "all"] = "first",
834
-) -> TypeIs[List[T]]:
834
+) -> TypeIs[list[T]]:
835
if not isinstance(value, list):
836
return False
837
@@ -843,8 +843,8 @@ def is_list_of(
843
assert_never(check)
844
845
846
-JSONTree = Union[Dict[str, "JSONTree[T]"], List["JSONTree[T]"],
847
- Tuple["JSONTree[T]", ...], T]
846
+JSONTree = Union[dict[str, "JSONTree[T]"], list["JSONTree[T]"],
847
+ tuple["JSONTree[T]", ...], T]
848
"""A nested JSON structure where the leaves need not be JSON-serializable."""
849
850
@@ -859,7 +859,7 @@ def json_map_leaves(func: Callable[[T], U], value: JSONTree[T]) -> JSONTree[U]:
859
return func(value)
860
861
862
-def flatten_2d_lists(lists: List[List[T]]) -> List[T]:
862
+def flatten_2d_lists(lists: list[list[T]]) -> list[T]:
863
"""Flatten a list of lists to a single list."""
864
return [item for sublist in lists for item in sublist]
865
@@ -1226,7 +1226,7 @@ class FlexibleArgumentParser(argparse.ArgumentParser):
1226
1227
return value
1228
1229
- def _pull_args_from_config(self, args: List[str]) -> List[str]:
1229
+ def _pull_args_from_config(self, args: list[str]) -> list[str]:
1230
"""Method to pull arguments specified in the config file
1231
into the command-line args variable.
1232
@@ -1291,7 +1291,7 @@ class FlexibleArgumentParser(argparse.ArgumentParser):
1291
1292
return args
1293
1294
- def _load_config_file(self, file_path: str) -> List[str]:
1294
+ def _load_config_file(self, file_path: str) -> list[str]:
1295
"""Loads a yaml file and returns the key value pairs as a
1296
flattened list with argparse like pattern
1297
```yaml
@@ -1313,9 +1313,9 @@ class FlexibleArgumentParser(argparse.ArgumentParser):
1313
%s supplied", extension)
1314
1315
# only expecting a flat dictionary of atomic types
1316
- processed_args: List[str] = []
1316
+ processed_args: list[str] = []
1317
1318
- config: Dict[str, Union[int, str]] = {}
1318
+ config: dict[str, Union[int, str]] = {}
1319
try:
1320
with open(file_path) as config_file:
1321
config = yaml.safe_load(config_file)
@@ -1399,7 +1399,7 @@ def resolve_mm_processor_kwargs(
1399
*,
1400
requires_kw_only: bool = True,
1401
allow_var_kwargs: bool = False,
1402
-) -> Dict[str, Any]:
1402
+) -> dict[str, Any]:
1403
"""Applies filtering to eliminate invalid mm_processor_kwargs, i.e.,
1404
those who are not explicit keywords to the given callable (of one is
1405
given; otherwise no filtering is done), then merges the kwarg dicts,
@@ -1440,7 +1440,7 @@ def get_allowed_kwarg_only_overrides(
1440
*,
1441
requires_kw_only: bool = True,
1442
allow_var_kwargs: bool = False,
1443
-) -> Dict[str, Any]:
1443
+) -> dict[str, Any]:
1444
"""
1445
Given a callable which has one or more keyword only params and a dict
1446
mapping param names to values, drop values that can be not be kwarg
@@ -1531,9 +1531,9 @@ class AtomicCounter:
1531
# Adapted from: https://stackoverflow.com/a/47212782/5082708
1532
class LazyDict(Mapping[str, T], Generic[T]):
1533
1534
- def __init__(self, factory: Dict[str, Callable[[], T]]):
1534
+ def __init__(self, factory: dict[str, Callable[[], T]]):
1535
self._factory = factory
1536
- self._dict: Dict[str, T] = {}
1536
+ self._dict: dict[str, T] = {}
1537
1538
def __getitem__(self, key: str) -> T:
1539
if key not in self._dict:
@@ -1552,9 +1552,9 @@ class LazyDict(Mapping[str, T], Generic[T]):
1552
return len(self._factory)
1553
1554
1555
-class ClassRegistry(UserDict[Type[T], _V]):
1555
+class ClassRegistry(UserDict[type[T], _V]):
1556
1557
- def __getitem__(self, key: Type[T]) -> _V:
1557
+ def __getitem__(self, key: type[T]) -> _V:
1558
for cls in key.mro():
1559
if cls in self.data:
1560
return self.data[cls]
@@ -1584,8 +1584,8 @@ def weak_ref_tensor(tensor: torch.Tensor) -> torch.Tensor:
1584
1585
1586
def weak_ref_tensors(
1587
- tensors: Union[torch.Tensor, List[torch.Tensor], Tuple[torch.Tensor]]
1588
-) -> Union[torch.Tensor, List[torch.Tensor], Tuple[torch.Tensor]]:
1587
+ tensors: Union[torch.Tensor, list[torch.Tensor], tuple[torch.Tensor]]
1588
+) -> Union[torch.Tensor, list[torch.Tensor], tuple[torch.Tensor]]:
1589
"""
1590
Convenience function to create weak references to tensors,
1591
for single tensor, list of tensors or tuple of tensors.
@@ -1857,7 +1857,7 @@ vllm_lib = Library("vllm", "FRAGMENT") # noqa
1857
def direct_register_custom_op(
1858
op_name: str,
1859
op_func: Callable,
1860
- mutates_args: List[str],
1860
+ mutates_args: list[str],
1861
fake_impl: Optional[Callable] = None,
1862
target_lib: Optional[Library] = None,
1863
dispatch_key: str = "CUDA",
@@ -2177,8 +2177,8 @@ def get_mp_context():
2177
2178
2179
def bind_kv_cache(
2180
- ctx: Dict[str, Any],
2181
- kv_cache: List[List[torch.Tensor]], # [virtual_engine][layer_index]
2180
+ ctx: dict[str, Any],
2181
+ kv_cache: list[list[torch.Tensor]], # [virtual_engine][layer_index]
2182
) -> None:
2183
# Bind the kv_cache tensor to Attention modules, similar to
2184
# ctx[layer_name].kv_cache[ve]=kv_cache[ve][extract_layer_index(layer_name)]
@@ -2210,8 +2210,8 @@ def bind_kv_cache(
2210
forward_ctx.kv_cache[ve] = ve_kv_cache[kv_cache_idx]
2211
2212
2213
-def run_method(obj: Any, method: Union[str, bytes, Callable], args: Tuple[Any],
2214
- kwargs: Dict[str, Any]) -> Any:
2213
+def run_method(obj: Any, method: Union[str, bytes, Callable], args: tuple[Any],
2214
+ kwargs: dict[str, Any]) -> Any:
2215
"""
2216
Run a method of an object with the given arguments and keyword arguments.
2217
If the method is string, it will be converted to a method using getattr.
@@ -2263,7 +2263,7 @@ def import_pynvml():
2263
return pynvml
2264
2265
2266
-def warn_for_unimplemented_methods(cls: Type[T]) -> Type[T]:
2266
+def warn_for_unimplemented_methods(cls: type[T]) -> type[T]:
2267
"""
2268
A replacement for `abc.ABC`.
2269
When we use `abc.ABC`, subclasses will fail to instantiate
vllm/v1/attention/backends/flash_attn.py
+9
-9
@@ -1,7 +1,7 @@
1
# SPDX-License-Identifier: Apache-2.0
2
"""Attention layer with FlashAttention."""
3
from dataclasses import dataclass
4
-from typing import TYPE_CHECKING, Any, Dict, List, Optional, Tuple, Type
4
+from typing import TYPE_CHECKING, Any, Optional
5
6
import numpy as np
7
import torch
@@ -30,7 +30,7 @@ class FlashAttentionBackend(AttentionBackend):
30
accept_output_buffer: bool = True
31
32
@staticmethod
33
- def get_supported_head_sizes() -> List[int]:
33
+ def get_supported_head_sizes() -> list[int]:
34
return [32, 64, 96, 128, 160, 192, 224, 256]
35
36
@staticmethod
@@ -38,15 +38,15 @@ class FlashAttentionBackend(AttentionBackend):
38
return "FLASH_ATTN_VLLM_V1"
39
40
@staticmethod
41
- def get_impl_cls() -> Type["FlashAttentionImpl"]:
41
+ def get_impl_cls() -> type["FlashAttentionImpl"]:
42
return FlashAttentionImpl
43
44
@staticmethod
45
- def get_metadata_cls() -> Type["AttentionMetadata"]:
45
+ def get_metadata_cls() -> type["AttentionMetadata"]:
46
return FlashAttentionMetadata
47
48
@staticmethod
49
- def get_builder_cls() -> Type["FlashAttentionMetadataBuilder"]:
49
+ def get_builder_cls() -> type["FlashAttentionMetadataBuilder"]:
50
return FlashAttentionMetadataBuilder
51
52
@staticmethod
@@ -55,7 +55,7 @@ class FlashAttentionBackend(AttentionBackend):
55
block_size: int,
56
num_kv_heads: int,
57
head_size: int,
58
- ) -> Tuple[int, ...]:
58
+ ) -> tuple[int, ...]:
59
if block_size % 16 != 0:
60
raise ValueError("Block size must be a multiple of 16.")
61
return (2, num_blocks, block_size, num_kv_heads, head_size)
@@ -158,10 +158,10 @@ class FlashAttentionImpl(AttentionImpl):
158
head_size: int,
159
scale: float,
160
num_kv_heads: int,
161
- alibi_slopes: Optional[List[float]],
161
+ alibi_slopes: Optional[list[float]],
162
sliding_window: Optional[int],
163
kv_cache_dtype: str,
164
- blocksparse_params: Optional[Dict[str, Any]] = None,
164
+ blocksparse_params: Optional[dict[str, Any]] = None,
165
logits_soft_cap: Optional[float] = None,
166
attn_type: AttentionType = AttentionType.DECODER,
167
) -> None:
@@ -381,7 +381,7 @@ def cascade_attention(
381
max_kv_len: int,
382
softmax_scale: float,
383
alibi_slopes: Optional[torch.Tensor],
384
- sliding_window: Tuple[int, int],
384
+ sliding_window: tuple[int, int],
385
logits_soft_cap: float,
386
block_table: torch.Tensor,
387
common_prefix_len: int,
vllm/v1/attention/backends/mla/common.py
+10
-11
@@ -195,8 +195,7 @@ return curr_o @ W_O
195
import functools
196
from abc import abstractmethod
197
from dataclasses import dataclass
198
-from typing import (TYPE_CHECKING, Any, Dict, Generic, List, Optional, Tuple,
199
- Type, TypeVar)
198
+from typing import TYPE_CHECKING, Any, Generic, Optional, TypeVar
199
200
import torch
201
from compressed_tensors.quantization import QuantizationStrategy
@@ -250,11 +249,11 @@ class MLACommonBackend(AttentionBackend):
249
return "TRITON_MLA_VLLM_V1"
250
251
@staticmethod
253
- def get_metadata_cls() -> Type["AttentionMetadata"]:
252
+ def get_metadata_cls() -> type["AttentionMetadata"]:
253
return MLACommonMetadata
254
255
@staticmethod
257
- def get_builder_cls() -> Type["MLACommonMetadataBuilder"]:
256
+ def get_builder_cls() -> type["MLACommonMetadataBuilder"]:
257
return MLACommonMetadataBuilder
258
259
@staticmethod
@@ -263,11 +262,11 @@ class MLACommonBackend(AttentionBackend):
262
block_size: int,
263
num_kv_heads: int, # assumed to be 1 for MLA
264
head_size: int,
266
- ) -> Tuple[int, ...]:
265
+ ) -> tuple[int, ...]:
266
return (num_blocks, block_size, head_size)
267
268
@staticmethod
270
- def get_supported_head_sizes() -> List[int]:
269
+ def get_supported_head_sizes() -> list[int]:
270
return [576]
271
272
@staticmethod
@@ -317,8 +316,8 @@ class MLACommonMetadata:
316
has_context: bool = False
317
context_chunk_cu_seq_lens: Optional[torch.Tensor] = None
318
context_chunk_starts: Optional[torch.Tensor] = None
320
- context_chunk_seq_tot: Optional[List[int]] = None
321
- context_chunk_max_seq_lens: Optional[List[int]] = None
319
+ context_chunk_seq_tot: Optional[list[int]] = None
320
+ context_chunk_max_seq_lens: Optional[list[int]] = None
321
chunked_prefill_workspace: Optional[torch.Tensor] = None
322
323
def __post_init__(self):
@@ -538,10 +537,10 @@ class MLACommonImpl(MLAAttentionImpl[T], Generic[T]):
537
head_size: int,
538
scale: float,
539
num_kv_heads: int,
541
- alibi_slopes: Optional[List[float]],
540
+ alibi_slopes: Optional[list[float]],
541
sliding_window: Optional[int],
542
kv_cache_dtype: str,
544
- blocksparse_params: Optional[Dict[str, Any]],
543
+ blocksparse_params: Optional[dict[str, Any]],
544
logits_soft_cap: Optional[float],
545
attn_type: str,
546
# MLA Specific Arguments
@@ -634,7 +633,7 @@ class MLACommonImpl(MLAAttentionImpl[T], Generic[T]):
633
#
634
# returns input_group_shape, weight_group_shape
635
def get_scale_group_shapes_for_fp8(layer: LinearBase) -> \
637
- Tuple[Tuple[int, int], Tuple[int, int]]:
636
+ tuple[tuple[int, int], tuple[int, int]]:
637
if isinstance(layer.quant_method, Fp8LinearMethod):
638
if layer.quant_method.block_quant:
639
weight_block_size = \
vllm/v1/attention/backends/mla/flashmla.py
+7
-7
@@ -1,7 +1,7 @@
1
# SPDX-License-Identifier: Apache-2.0
2
3
from dataclasses import dataclass
4
-from typing import Any, Dict, List, Optional, Tuple, Type
4
+from typing import Any, Optional
5
6
import torch
7
@@ -25,21 +25,21 @@ class FlashMLABackend(MLACommonBackend):
25
return "FLASHMLA_VLLM_V1"
26
27
@staticmethod
28
- def get_metadata_cls() -> Type["FlashMLAMetadata"]:
28
+ def get_metadata_cls() -> type["FlashMLAMetadata"]:
29
return FlashMLAMetadata
30
31
@staticmethod
32
- def get_builder_cls() -> Type["FlashMLAMetadataBuilder"]:
32
+ def get_builder_cls() -> type["FlashMLAMetadataBuilder"]:
33
return FlashMLAMetadataBuilder
34
35
@staticmethod
36
- def get_impl_cls() -> Type["FlashMLAImpl"]:
36
+ def get_impl_cls() -> type["FlashMLAImpl"]:
37
return FlashMLAImpl
38
39
40
@dataclass
41
class FlashMLAMetadata(MLACommonMetadata):
42
- decode_tile_scheduler_metadata: Optional[Tuple[torch.Tensor,
42
+ decode_tile_scheduler_metadata: Optional[tuple[torch.Tensor,
43
torch.Tensor]] = None
44
decode_num_splits: Optional[torch.Tensor] = None
45
@@ -76,10 +76,10 @@ class FlashMLAImpl(MLACommonImpl[FlashMLAMetadata]):
76
head_size: int,
77
scale: float,
78
num_kv_heads: int,
79
- alibi_slopes: Optional[List[float]],
79
+ alibi_slopes: Optional[list[float]],
80
sliding_window: Optional[int],
81
kv_cache_dtype: str,
82
- blocksparse_params: Optional[Dict[str, Any]],
82
+ blocksparse_params: Optional[dict[str, Any]],
83
logits_soft_cap: Optional[float],
84
attn_type: str,
85
# MLA Specific Arguments
vllm/v1/attention/backends/mla/triton_mla.py
+4
-4
@@ -1,6 +1,6 @@
1
# SPDX-License-Identifier: Apache-2.0
2
3
-from typing import Any, Dict, List, Optional, Type
3
+from typing import Any, Optional
4
5
import torch
6
@@ -21,7 +21,7 @@ class TritonMLABackend(MLACommonBackend):
21
return "TRITON_MLA_VLLM_V1"
22
23
@staticmethod
24
- def get_impl_cls() -> Type["TritonMLAImpl"]:
24
+ def get_impl_cls() -> type["TritonMLAImpl"]:
25
return TritonMLAImpl
26
27
@@ -33,10 +33,10 @@ class TritonMLAImpl(MLACommonImpl[MLACommonMetadata]):
33
head_size: int,
34
scale: float,
35
num_kv_heads: int,
36
- alibi_slopes: Optional[List[float]],
36
+ alibi_slopes: Optional[list[float]],
37
sliding_window: Optional[int],
38
kv_cache_dtype: str,
39
- blocksparse_params: Optional[Dict[str, Any]],
39
+ blocksparse_params: Optional[dict[str, Any]],
40
logits_soft_cap: Optional[float],
41
attn_type: str,
42
# MLA Specific Arguments
vllm/v1/attention/backends/pallas.py
+8
-8
@@ -1,7 +1,7 @@
1
# SPDX-License-Identifier: Apache-2.0
2
3
from dataclasses import dataclass
4
-from typing import Any, Dict, List, Optional, Tuple, Type
4
+from typing import Any, Optional
5
6
import torch
7
# Required to register custom ops.
@@ -22,15 +22,15 @@ class PallasAttentionBackend(AttentionBackend):
22
return "PALLAS_VLLM_V1"
23
24
@staticmethod
25
- def get_impl_cls() -> Type["PallasAttentionBackendImpl"]:
25
+ def get_impl_cls() -> type["PallasAttentionBackendImpl"]:
26
return PallasAttentionBackendImpl
27
28
@staticmethod
29
- def get_metadata_cls() -> Type["PallasMetadata"]:
29
+ def get_metadata_cls() -> type["PallasMetadata"]:
30
return PallasMetadata
31
32
@staticmethod
33
- def get_state_cls() -> Type["CommonAttentionState"]:
33
+ def get_state_cls() -> type["CommonAttentionState"]:
34
return CommonAttentionState
35
36
@staticmethod
@@ -39,7 +39,7 @@ class PallasAttentionBackend(AttentionBackend):
39
block_size: int,
40
num_kv_heads: int,
41
head_size: int,
42
- ) -> Tuple[int, ...]:
42
+ ) -> tuple[int, ...]:
43
return (num_kv_heads, num_blocks, block_size, head_size)
44
45
@staticmethod
@@ -77,10 +77,10 @@ class PallasAttentionBackendImpl(AttentionImpl):
77
head_size: int,
78
scale: float,
79
num_kv_heads: int,
80
- alibi_slopes: Optional[List[float]],
80
+ alibi_slopes: Optional[list[float]],
81
sliding_window: Optional[int],
82
kv_cache_dtype: str,
83
- blocksparse_params: Optional[Dict[str, Any]] = None,
83
+ blocksparse_params: Optional[dict[str, Any]] = None,
84
logits_soft_cap: Optional[float] = None,
85
attn_type: str = AttentionType.DECODER,
86
) -> None:
@@ -120,7 +120,7 @@ class PallasAttentionBackendImpl(AttentionImpl):
120
query: torch.Tensor,
121
key: torch.Tensor,
122
value: torch.Tensor,
123
- kv_cache: Tuple[torch.Tensor, torch.Tensor],
123
+ kv_cache: tuple[torch.Tensor, torch.Tensor],
124
attn_metadata: PallasMetadata,
125
output: Optional[torch.Tensor] = None,
126
) -> torch.Tensor:
vllm/v1/attention/backends/rocm_attn.py
+8
-8
@@ -1,6 +1,6 @@
1
# SPDX-License-Identifier: Apache-2.0
2
"""Attention layer with PagedAttention on rocm"""
3
-from typing import Any, Dict, List, Optional, Tuple, Type
3
+from typing import Any, Optional
4
5
import torch
6
@@ -20,7 +20,7 @@ class ROCmAttentionBackend(AttentionBackend):
20
accept_output_buffer: bool = True
21
22
@staticmethod
23
- def get_supported_head_sizes() -> List[int]:
23
+ def get_supported_head_sizes() -> list[int]:
24
return [32, 64, 96, 128, 160, 192, 224, 256]
25
26
@staticmethod
@@ -28,11 +28,11 @@ class ROCmAttentionBackend(AttentionBackend):
28
return "ROCM_ATTN_VLLM_V1"
29
30
@staticmethod
31
- def get_impl_cls() -> Type["ROCmAttentionImpl"]:
31
+ def get_impl_cls() -> type["ROCmAttentionImpl"]:
32
return ROCmAttentionImpl
33
34
@staticmethod
35
- def get_metadata_cls() -> Type["AttentionMetadata"]:
35
+ def get_metadata_cls() -> type["AttentionMetadata"]:
36
return FlashAttentionMetadata
37
38
@staticmethod
@@ -41,7 +41,7 @@ class ROCmAttentionBackend(AttentionBackend):
41
block_size: int,
42
num_kv_heads: int,
43
head_size: int,
44
- ) -> Tuple[int, ...]:
44
+ ) -> tuple[int, ...]:
45
if block_size % 16 != 0:
46
raise ValueError("Block size must be a multiple of 16.")
47
return (2, num_blocks, block_size, num_kv_heads, head_size)
@@ -51,7 +51,7 @@ class ROCmAttentionBackend(AttentionBackend):
51
return False
52
53
@staticmethod
54
- def get_builder_cls() -> Type["FlashAttentionMetadataBuilder"]:
54
+ def get_builder_cls() -> type["FlashAttentionMetadataBuilder"]:
55
return FlashAttentionMetadataBuilder
56
57
@@ -63,10 +63,10 @@ class ROCmAttentionImpl(AttentionImpl):
63
head_size: int,
64
scale: float,
65
num_kv_heads: int,
66
- alibi_slopes: Optional[List[float]],
66
+ alibi_slopes: Optional[list[float]],
67
sliding_window: Optional[int],
68
kv_cache_dtype: str,
69
- blocksparse_params: Optional[Dict[str, Any]] = None,
69
+ blocksparse_params: Optional[dict[str, Any]] = None,
70
logits_soft_cap: Optional[float] = None,
71
attn_type: AttentionType = AttentionType.DECODER,
72
) -> None:
vllm/v1/core/block_pool.py
+9
-8
@@ -1,6 +1,7 @@
1
# SPDX-License-Identifier: Apache-2.0
2
from collections import defaultdict
3
-from typing import Dict, Iterable, List, Optional
3
+from collections.abc import Iterable
4
+from typing import Optional
5
6
from vllm.logger import init_logger
7
from vllm.v1.core.kv_cache_utils import (BlockHashType, FreeKVCacheBlockQueue,
@@ -29,7 +30,7 @@ class BlockPool:
30
self.num_gpu_blocks = num_gpu_blocks
31
self.enable_caching = enable_caching
32
# All kv-cache blocks.
32
- self.blocks: List[KVCacheBlock] = [
33
+ self.blocks: list[KVCacheBlock] = [
34
KVCacheBlock(idx) for idx in range(num_gpu_blocks)
35
]
36
# Free block queue that constructs and manipulates a doubly linked
@@ -46,7 +47,7 @@ class BlockPool:
47
# if there is already an identical block in the cache. This is because
48
# we want to make sure the allocated block IDs won't change so that
49
# block tables are append-only.
49
- self.cached_block_hash_to_block: Dict[BlockHashType, Dict[
50
+ self.cached_block_hash_to_block: dict[BlockHashType, dict[
51
int, KVCacheBlock]] = defaultdict(dict)
52
53
def get_cached_block(self,
@@ -69,8 +70,8 @@ class BlockPool:
70
def cache_full_blocks(
71
self,
72
request: Request,
72
- blocks: List[KVCacheBlock],
73
- block_hashes: List[BlockHashType],
73
+ blocks: list[KVCacheBlock],
74
+ block_hashes: list[BlockHashType],
75
num_cached_blocks: int,
76
num_full_blocks: int,
77
block_size: int,
@@ -146,7 +147,7 @@ class BlockPool:
147
self.cached_block_hash_to_block[block_hash][blk.block_id] = blk
148
prev_block_hash_value = block_hash.hash_value
149
149
- def get_new_blocks(self, num_blocks: int) -> List[KVCacheBlock]:
150
+ def get_new_blocks(self, num_blocks: int) -> list[KVCacheBlock]:
151
"""Get new blocks from the free block pool.
152
153
Note that we do not check block cache in this function.
@@ -161,7 +162,7 @@ class BlockPool:
162
raise ValueError(
163
f"Cannot get {num_blocks} free blocks from the pool")
164
164
- ret: List[KVCacheBlock] = []
165
+ ret: list[KVCacheBlock] = []
166
idx = 0
167
while idx < num_blocks:
168
# First allocate blocks.
@@ -200,7 +201,7 @@ class BlockPool:
201
return True
202
return False
203
203
- def touch(self, blocks: List[KVCacheBlock]) -> None:
204
+ def touch(self, blocks: list[KVCacheBlock]) -> None:
205
"""Touch a block increases its reference count by 1, and may remove
206
the block from the free queue. This is used when a block is hit by
207
another request with the same prefix.
vllm/v1/core/encoder_cache_manager.py
+8
-8
@@ -1,6 +1,6 @@
1
# SPDX-License-Identifier: Apache-2.0
2
3
-from typing import TYPE_CHECKING, Dict, List, Set, Tuple
3
+from typing import TYPE_CHECKING
4
5
from vllm.logger import init_logger
6
from vllm.multimodal import MULTIMODAL_REGISTRY
@@ -18,9 +18,9 @@ class EncoderCacheManager:
18
self.cache_size = cache_size
19
self.num_free_slots = cache_size
20
# req_id -> cached input ids
21
- self.cached: Dict[str, Set[int]] = {}
22
- # List of [req_id, input_id]
23
- self.freed: List[Tuple[str, int]] = []
21
+ self.cached: dict[str, set[int]] = {}
22
+ # list of [req_id, input_id]
23
+ self.freed: list[tuple[str, int]] = []
24
25
def has_cache(self, request: Request, input_id: int) -> bool:
26
req_id = request.request_id
@@ -37,7 +37,7 @@ class EncoderCacheManager:
37
self.cached[req_id].add(input_id)
38
self.num_free_slots -= request.get_num_encoder_tokens(input_id)
39
40
- def get_cached_input_ids(self, request: Request) -> Set[int]:
40
+ def get_cached_input_ids(self, request: Request) -> set[int]:
41
return self.cached.get(request.request_id, set())
42
43
def free_encoder_input(self, request: Request, input_id: int) -> None:
@@ -58,7 +58,7 @@ class EncoderCacheManager:
58
for input_id in input_ids:
59
self.free_encoder_input(request, input_id)
60
61
- def get_freed_ids(self) -> List[Tuple[str, int]]:
61
+ def get_freed_ids(self) -> list[tuple[str, int]]:
62
freed = self.freed
63
self.freed = []
64
return freed
@@ -67,7 +67,7 @@ class EncoderCacheManager:
67
def compute_encoder_budget(
68
model_config: "ModelConfig",
69
scheduler_config: "SchedulerConfig",
70
-) -> Tuple[int, int]:
70
+) -> tuple[int, int]:
71
"""Compute the encoder cache budget based on the model and scheduler
72
configurations.
73
@@ -97,7 +97,7 @@ def compute_encoder_budget(
97
def _compute_encoder_budget_multimodal(
98
model_config: "ModelConfig",
99
scheduler_config: "SchedulerConfig",
100
-) -> Tuple[int, int]:
100
+) -> tuple[int, int]:
101
"""Compute the encoder cache budget based on the model and scheduler
102
configurations for a multimodal model.
103
vllm/v1/core/kv_cache_manager.py
+10
-9
@@ -1,7 +1,8 @@
1
# SPDX-License-Identifier: Apache-2.0
2
3
from collections import defaultdict
4
-from typing import DefaultDict, Dict, Iterable, List, Optional, Tuple
4
+from collections.abc import Iterable
5
+from typing import Optional
6
7
from vllm.logger import init_logger
8
from vllm.utils import cdiv
@@ -52,20 +53,20 @@ class KVCacheManager:
53
# Mapping from request ID to blocks to track the blocks allocated
54
# for each request, so that we can free the blocks when the request
55
# is finished.
55
- self.req_to_blocks: DefaultDict[str,
56
- List[KVCacheBlock]] = defaultdict(list)
56
+ self.req_to_blocks: defaultdict[str,
57
+ list[KVCacheBlock]] = defaultdict(list)
58
59
# Mapping from request ID to kv block hashes.
60
# This is to avoid recomputing the block hashes for each call of
61
# `get_computed_blocks` or `allocate_slots`.
61
- self.req_to_block_hashes: DefaultDict[
62
- str, List[BlockHashType]] = defaultdict(list)
62
+ self.req_to_block_hashes: defaultdict[
63
+ str, list[BlockHashType]] = defaultdict(list)
64
65
# {req_id: The number of cached blocks for this given request}
66
# This is used to track the number of cached blocks for each request.
67
# This is only used to track the RUNNING requests, we do not track the
68
# data for reempted ones.
68
- self.num_cached_block: Dict[str, int] = {}
69
+ self.num_cached_block: dict[str, int] = {}
70
self.prefix_cache_stats = PrefixCacheStats()
71
72
@property
@@ -88,7 +89,7 @@ class KVCacheManager:
89
return stats
90
91
def get_computed_blocks(
91
- self, request: Request) -> Tuple[List[KVCacheBlock], int]:
92
+ self, request: Request) -> tuple[list[KVCacheBlock], int]:
93
"""Get the computed (cached) blocks for the request.
94
Note that the computed blocks must be full.
95
@@ -136,8 +137,8 @@ class KVCacheManager:
137
self,
138
request: Request,
139
num_tokens: int,
139
- new_computed_blocks: Optional[List[KVCacheBlock]] = None
140
- ) -> Optional[List[KVCacheBlock]]:
140
+ new_computed_blocks: Optional[list[KVCacheBlock]] = None
141
+ ) -> Optional[list[KVCacheBlock]]:
142
"""Add slots for a request with new tokens to append.
143
144
Args:
vllm/v1/core/kv_cache_utils.py
+16
-16
@@ -3,7 +3,7 @@
3
from collections import deque
4
from collections.abc import Sequence
5
from dataclasses import dataclass
6
-from typing import Any, List, NamedTuple, Optional, Tuple
6
+from typing import Any, NamedTuple, Optional
7
8
from vllm.config import VllmConfig
9
from vllm.logger import init_logger
@@ -25,7 +25,7 @@ class BlockHashType(NamedTuple):
25
# Hash value of the block in an integer.
26
hash_value: int
27
# Token IDs in the block.
28
- token_ids: Tuple[int, ...]
28
+ token_ids: tuple[int, ...]
29
# Extra keys for the block.
30
extra_keys: Optional[Any] = None
31
@@ -45,7 +45,7 @@ class PrefixCachingMetrics:
45
self.aggregated_query_total = 0
46
self.aggregated_query_hit = 0
47
# A deque of (requests, queries, hits) for the most recent requests.
48
- self.query_queue: deque[Tuple[int, int, int]] = deque()
48
+ self.query_queue: deque[tuple[int, int, int]] = deque()
49
50
def observe(self, stats: PrefixCacheStats):
51
"""Observe the prefix caching for a set of requests.
@@ -164,7 +164,7 @@ class FreeKVCacheBlockQueue:
164
blocks: A list of KVCacheBlock objects.
165
"""
166
167
- def __init__(self, blocks: List[KVCacheBlock]) -> None:
167
+ def __init__(self, blocks: list[KVCacheBlock]) -> None:
168
self.num_free_blocks = len(blocks)
169
170
# Initialize the doubly linked list of free blocks.
@@ -233,7 +233,7 @@ class FreeKVCacheBlockQueue:
233
block.next_free_block = None
234
self.num_free_blocks += 1
235
236
- def get_all_free_blocks(self) -> List[KVCacheBlock]:
236
+ def get_all_free_blocks(self) -> list[KVCacheBlock]:
237
"""Get all free blocks in the free list. Mainly used for testing.
238
239
Returns:
@@ -264,7 +264,7 @@ def need_extra_keys(request: Request) -> bool:
264
265
def _gen_mm_extra_hash_keys(request: Request, start_token_idx: int,
266
end_token_idx: int,
267
- start_mm_idx: int) -> Tuple[List[Any], int]:
267
+ start_mm_idx: int) -> tuple[list[Any], int]:
268
"""Generate extra keys related to MultiModal request for block hash
269
computation. For multi-modal inputs, the extra keys are
270
(mm_hash, start_offset) that indicate a mm input contained in the
@@ -279,7 +279,7 @@ def _gen_mm_extra_hash_keys(request: Request, start_token_idx: int,
279
Returns:
280
A tuple of extra keys and the next multi-modal index.
281
"""
282
- extra_keys: List[Any] = []
282
+ extra_keys: list[Any] = []
283
284
mm_positions, mm_hashes = request.mm_positions, request.mm_hashes
285
if not mm_positions:
@@ -331,7 +331,7 @@ def _gen_mm_extra_hash_keys(request: Request, start_token_idx: int,
331
return extra_keys, curr_mm_idx
332
333
334
-def _gen_lora_extra_hash_keys(request: Request) -> List[int]:
334
+def _gen_lora_extra_hash_keys(request: Request) -> list[int]:
335
"""Generate extra keys related to LoRA for block hash computation.
336
337
Args:
@@ -348,7 +348,7 @@ def _gen_lora_extra_hash_keys(request: Request) -> List[int]:
348
349
def generate_block_hash_extra_keys(
350
request: Request, start_token_idx: int, end_token_idx: int,
351
- start_mm_idx: int) -> Tuple[Optional[Tuple[Any, ...]], int]:
351
+ start_mm_idx: int) -> tuple[Optional[tuple[Any, ...]], int]:
352
"""Generate extra keys for the block hash. The extra keys can come from
353
the multi-modal inputs and request specific metadata (e.g., LoRA ID).
354
@@ -361,12 +361,12 @@ def generate_block_hash_extra_keys(
361
Returns:
362
A tuple of extra keys and the next multi-modal index.
363
"""
364
- mm_extra_keys: List[Any]
364
+ mm_extra_keys: list[Any]
365
mm_extra_keys, new_start_mm_idx = _gen_mm_extra_hash_keys(
366
request, start_token_idx, end_token_idx, start_mm_idx)
367
- lora_extra_keys: List[int] = _gen_lora_extra_hash_keys(request)
367
+ lora_extra_keys: list[int] = _gen_lora_extra_hash_keys(request)
368
369
- extra_keys: List[Any] = lora_extra_keys + mm_extra_keys
369
+ extra_keys: list[Any] = lora_extra_keys + mm_extra_keys
370
371
if not extra_keys:
372
return None, new_start_mm_idx
@@ -377,7 +377,7 @@ def generate_block_hash_extra_keys(
377
def hash_block_tokens(
378
parent_block_hash: Optional[int],
379
curr_block_token_ids: Sequence[int],
380
- extra_keys: Optional[Tuple[Any, ...]] = None) -> BlockHashType:
380
+ extra_keys: Optional[tuple[Any, ...]] = None) -> BlockHashType:
381
"""Computes a hash value corresponding to the contents of a block and
382
the contents of the preceding block(s). The hash value is used for
383
prefix caching. We use LRU cache for this function to avoid recomputing
@@ -410,7 +410,7 @@ def hash_block_tokens(
410
411
412
def hash_request_tokens(block_size: int,
413
- request: Request) -> List[BlockHashType]:
413
+ request: Request) -> list[BlockHashType]:
414
"""Computes hash values of a chain of blocks given a sequence of
415
token IDs. The hash value is used for prefix caching.
416
@@ -554,8 +554,8 @@ def _get_kv_cache_config_uniform_type(vllm_config: VllmConfig,
554
555
556
def get_kv_cache_configs(vllm_config: VllmConfig,
557
- kv_cache_specs: List[KVCacheSpec],
558
- available_memory: int) -> List[KVCacheConfig]:
557
+ kv_cache_specs: list[KVCacheSpec],
558
+ available_memory: int) -> list[KVCacheConfig]:
559
"""
560
Generates the KV cache configuration for a model
561
TODO: support hybrid models with more than one type of KV cache.
vllm/v1/core/scheduler.py
+23
-22
@@ -2,7 +2,8 @@
2
3
import time
4
from collections import deque
5
-from typing import Deque, Dict, Iterable, List, Optional, Set, Tuple, Union
5
+from collections.abc import Iterable
6
+from typing import Optional, Union
7
8
from vllm.config import (CacheConfig, LoRAConfig, ModelConfig, SchedulerConfig,
9
SpeculativeConfig)
@@ -57,24 +58,24 @@ class Scheduler:
58
self.block_size = self.cache_config.block_size
59
60
# req_id -> Request
60
- self.requests: Dict[str, Request] = {}
61
+ self.requests: dict[str, Request] = {}
62
# Priority queues for requests.
62
- self.waiting: Deque[Request] = deque()
63
- self.running: List[Request] = []
63
+ self.waiting: deque[Request] = deque()
64
+ self.running: list[Request] = []
65
# The requests that have been scheduled and are being executed
66
# by the executor.
66
- self.scheduled_req_ids: Set[str] = set()
67
+ self.scheduled_req_ids: set[str] = set()
68
69
# The request IDs that are finished in between the previous and the
70
# current steps. This is used to notify the workers about the finished
71
# requests so that they can free the cached states for those requests.
72
# This is flushed at the end of each scheduling step.
72
- self.finished_req_ids: Set[str] = set()
73
+ self.finished_req_ids: set[str] = set()
74
75
# OPTIMIZATION: Cache the CachedRequestData objects to avoid creating
76
# them at each scheduling step.
77
# Request id -> CachedRequestData
77
- self._cached_reqs_data: Dict[str, CachedRequestData] = {}
78
+ self._cached_reqs_data: dict[str, CachedRequestData] = {}
79
80
# Encoder-related.
81
# Calculate encoder cache size if applicable
@@ -108,19 +109,19 @@ class Scheduler:
109
# chunked prefills, prefix caching, speculative decoding,
110
# and the "jump decoding" optimization in the future.
111
111
- scheduled_new_reqs: List[Request] = []
112
- scheduled_resumed_reqs: List[Request] = []
113
- scheduled_running_reqs: List[Request] = []
114
- preempted_reqs: List[Request] = []
112
+ scheduled_new_reqs: list[Request] = []
113
+ scheduled_resumed_reqs: list[Request] = []
114
+ scheduled_running_reqs: list[Request] = []
115
+ preempted_reqs: list[Request] = []
116
116
- req_to_new_block_ids: Dict[str, List[int]] = {}
117
- num_scheduled_tokens: Dict[str, int] = {}
117
+ req_to_new_block_ids: dict[str, list[int]] = {}
118
+ num_scheduled_tokens: dict[str, int] = {}
119
token_budget = self.max_num_scheduled_tokens
120
# Encoder-related.
120
- scheduled_encoder_inputs: Dict[str, List[int]] = {}
121
+ scheduled_encoder_inputs: dict[str, list[int]] = {}
122
encoder_budget = self.max_num_encoder_input_tokens
123
# Spec decode-related.
123
- scheduled_spec_decode_tokens: Dict[str, List[int]] = {}
124
+ scheduled_spec_decode_tokens: dict[str, list[int]] = {}
125
126
# For logging.
127
scheduled_timestamp = time.monotonic()
@@ -211,7 +212,7 @@ class Scheduler:
212
encoder_budget = new_encoder_budget
213
214
# Record the LoRAs in scheduled_running_reqs
214
- requested_loras: Set[int] = set()
215
+ requested_loras: set[int] = set()
216
if self.lora_config:
217
requested_loras = set(
218
req.lora_request.lora_int_id for req in scheduled_running_reqs
@@ -378,7 +379,7 @@ class Scheduler:
379
request: Request,
380
num_scheduled_tokens: int,
381
num_scheduled_spec_tokens: int,
381
- new_block_ids: List[int],
382
+ new_block_ids: list[int],
383
resumed_from_preemption: bool,
384
) -> "CachedRequestData":
385
# OPTIMIZATION: Cache the CachedRequestData objects to avoid creating
@@ -407,7 +408,7 @@ class Scheduler:
408
num_computed_tokens: int,
409
num_new_tokens: int,
410
encoder_budget: int,
410
- ) -> Tuple[List[int], int, int]:
411
+ ) -> tuple[list[int], int, int]:
412
"""
413
Determine which encoder inputs need to be scheduled in the current step,
414
and update `num_new_tokens` and encoder token budget accordingly.
@@ -427,7 +428,7 @@ class Scheduler:
428
if not request.has_encoder_inputs():
429
return [], num_new_tokens, encoder_budget
430
430
- encoder_inputs_to_schedule: List[int] = []
431
+ encoder_inputs_to_schedule: list[int] = []
432
mm_positions = request.mm_positions
433
assert mm_positions is not None
434
assert len(mm_positions) > 0
@@ -482,8 +483,8 @@ class Scheduler:
483
prompt_logprobs_dict = model_runner_output.prompt_logprobs_dict
484
num_scheduled_tokens = scheduler_output.num_scheduled_tokens
485
485
- new_running: List[Request] = []
486
- outputs: List[EngineCoreOutput] = []
486
+ new_running: list[Request] = []
487
+ outputs: list[EngineCoreOutput] = []
488
489
# NOTE(woosuk): As len(self.running) can be up to 1K or more, the below
490
# loop can be a performance bottleneck. We should do our best to avoid
@@ -543,7 +544,7 @@ class Scheduler:
544
545
stopped = False
546
new_logprobs = None
546
- new_token_ids: List[int] = []
547
+ new_token_ids: list[int] = []
548
549
if request.num_computed_tokens >= request.num_tokens:
550
for output_token_id in generated_token_ids:
vllm/v1/core/scheduler_output.py
+21
-21
@@ -1,7 +1,7 @@
1
# SPDX-License-Identifier: Apache-2.0
2
3
from dataclasses import dataclass
4
-from typing import TYPE_CHECKING, Dict, List, Optional, Set, Tuple
4
+from typing import TYPE_CHECKING, Optional
5
6
if TYPE_CHECKING:
7
from vllm.lora.request import LoRARequest
@@ -15,13 +15,13 @@ if TYPE_CHECKING:
15
class NewRequestData:
16
17
req_id: str
18
- prompt_token_ids: List[int]
18
+ prompt_token_ids: list[int]
19
prompt: Optional[str]
20
- mm_inputs: List["MultiModalKwargs"]
21
- mm_hashes: List[str]
22
- mm_positions: List["PlaceholderRange"]
20
+ mm_inputs: list["MultiModalKwargs"]
21
+ mm_hashes: list[str]
22
+ mm_positions: list["PlaceholderRange"]
23
sampling_params: "SamplingParams"
24
- block_ids: List[int]
24
+ block_ids: list[int]
25
num_computed_tokens: int
26
lora_request: Optional["LoRARequest"]
27
@@ -29,7 +29,7 @@ class NewRequestData:
29
def from_request(
30
cls,
31
request: "Request",
32
- block_ids: List[int],
32
+ block_ids: list[int],
33
) -> "NewRequestData":
34
return cls(
35
req_id=request.request_id,
@@ -53,8 +53,8 @@ class CachedRequestData:
53
# the request's block IDs. If True, new_block_ids will be used as the
54
# request's block IDs instead of appending to the existing block IDs.
55
resumed_from_preemption: bool
56
- new_token_ids: List[int]
57
- new_block_ids: List[int]
56
+ new_token_ids: list[int]
57
+ new_block_ids: list[int]
58
num_computed_tokens: int
59
60
@classmethod
@@ -62,8 +62,8 @@ class CachedRequestData:
62
cls,
63
request: "Request",
64
resumed_from_preemption: bool,
65
- new_token_ids: List[int],
66
- new_block_ids: List[int],
65
+ new_token_ids: list[int],
66
+ new_block_ids: list[int],
67
) -> "CachedRequestData":
68
return cls(
69
req_id=request.request_id,
@@ -77,29 +77,29 @@ class CachedRequestData:
77
@dataclass
78
class SchedulerOutput:
79
80
- # List of the requests that are scheduled for the first time.
80
+ # list of the requests that are scheduled for the first time.
81
# We cache the request's data in each worker process, so that we don't
82
# need to re-send it every scheduling step.
83
- scheduled_new_reqs: List[NewRequestData]
84
- # List of the requests that have been scheduled before.
83
+ scheduled_new_reqs: list[NewRequestData]
84
+ # list of the requests that have been scheduled before.
85
# Since the request's data is already cached in the worker processes,
86
# we only send the diff to minimize the communication cost.
87
- scheduled_cached_reqs: List[CachedRequestData]
87
+ scheduled_cached_reqs: list[CachedRequestData]
88
89
# req_id -> num_scheduled_tokens
90
# Number of tokens scheduled for each request.
91
- num_scheduled_tokens: Dict[str, int]
91
+ num_scheduled_tokens: dict[str, int]
92
# Total number of tokens scheduled for all requests.
93
# Equal to sum(num_scheduled_tokens.values())
94
total_num_scheduled_tokens: int
95
# req_id -> spec_token_ids
96
# If a request does not have any spec decode tokens, it will not be
97
# included in the dictionary.
98
- scheduled_spec_decode_tokens: Dict[str, List[int]]
98
+ scheduled_spec_decode_tokens: dict[str, list[int]]
99
# req_id -> encoder input indices that need processing.
100
# E.g., if a request has [0, 1], it could mean the vision encoder needs
101
# to process that the request's 0-th and 1-th images in the current step.
102
- scheduled_encoder_inputs: Dict[str, List[int]]
102
+ scheduled_encoder_inputs: dict[str, list[int]]
103
# Number of common prefix blocks for all requests.
104
# This can be used for cascade attention.
105
num_common_prefix_blocks: int
@@ -107,7 +107,7 @@ class SchedulerOutput:
107
# Request IDs that are finished in between the previous and the current
108
# steps. This is used to notify the workers about the finished requests
109
# so that they can free the cached states for those requests.
110
- finished_req_ids: Set[str]
111
- # List of (req_id, encoder_input_index) tuples.
110
+ finished_req_ids: set[str]
111
+ # list of (req_id, encoder_input_index) tuples.
112
# Used to free the encoder cache.
113
- free_encoder_input_ids: List[Tuple[str, int]]
113
+ free_encoder_input_ids: list[tuple[str, int]]
vllm/v1/engine/__init__.py
+8
-8
@@ -2,7 +2,7 @@
2
3
import enum
4
import time
5
-from typing import Any, List, Optional, Union
5
+from typing import Any, Optional, Union
6
7
import msgspec
8
@@ -51,10 +51,10 @@ class EngineCoreRequest(
51
# NOTE(ywang96): original text prompt is needed when a request is added to
52
# Detokenizer, but set to None when it is added to EngineCoreClient.
53
prompt: Optional[str]
54
- prompt_token_ids: List[int]
55
- mm_inputs: Optional[List[Optional[MultiModalKwargs]]]
56
- mm_hashes: Optional[List[str]]
57
- mm_placeholders: Optional[List[PlaceholderRange]]
54
+ prompt_token_ids: list[int]
55
+ mm_inputs: Optional[list[Optional[MultiModalKwargs]]]
56
+ mm_hashes: Optional[list[str]]
57
+ mm_placeholders: Optional[list[PlaceholderRange]]
58
sampling_params: SamplingParams
59
eos_token_id: Optional[int]
60
arrival_time: float
@@ -93,14 +93,14 @@ class EngineCoreOutput(
93
gc=False): # type: ignore[call-arg]
94
95
request_id: str
96
- new_token_ids: List[int]
96
+ new_token_ids: list[int]
97
98
new_logprobs: Optional[LogprobsLists] = None
99
new_prompt_logprobs_tensors: Optional[LogprobsTensors] = None
100
101
finish_reason: Optional[FinishReason] = None
102
stop_reason: Union[int, str, None] = None
103
- events: Optional[List[EngineCoreEvent]] = None
103
+ events: Optional[list[EngineCoreEvent]] = None
104
105
@property
106
def finished(self) -> bool:
@@ -129,7 +129,7 @@ class EngineCoreOutputs(
129
# e.g. columnwise layout
130
131
# [num_reqs]
132
- outputs: List[EngineCoreOutput] = []
132
+ outputs: list[EngineCoreOutput] = []
133
scheduler_stats: Optional[SchedulerStats] = None
134
timestamp: float = 0.0
135
vllm/v1/engine/async_llm.py
+5
-4
@@ -2,7 +2,8 @@
2
3
import asyncio
4
import os
5
-from typing import AsyncGenerator, List, Mapping, Optional, Set, Type, Union
5
+from collections.abc import AsyncGenerator, Mapping
6
+from typing import Optional, Union
7
8
import numpy as np
9
@@ -39,7 +40,7 @@ class AsyncLLM(EngineClient):
40
def __init__(
41
self,
42
vllm_config: VllmConfig,
42
- executor_class: Type[Executor],
43
+ executor_class: type[Executor],
44
log_stats: bool,
45
usage_context: UsageContext = UsageContext.ENGINE_CONTEXT,
46
input_registry: InputRegistry = INPUT_REGISTRY,
@@ -54,7 +55,7 @@ class AsyncLLM(EngineClient):
55
56
self.log_requests = log_requests
57
self.log_stats = log_stats
57
- self.stat_loggers: List[StatLoggerBase] = []
58
+ self.stat_loggers: list[StatLoggerBase] = []
59
if self.log_stats:
60
self.stat_loggers.extend([
61
LoggingStatLogger(),
@@ -400,7 +401,7 @@ class AsyncLLM(EngineClient):
401
"""Remove an already loaded LoRA adapter."""
402
return await self.engine_core.remove_lora_async(lora_id)
403
403
- async def list_loras(self) -> Set[int]:
404
+ async def list_loras(self) -> set[int]:
405
"""List all registered adapters."""
406
return await self.engine_core.list_loras_async()
407
vllm/v1/engine/core.py
+8
-8
@@ -7,7 +7,7 @@ import time
7
from concurrent.futures import Future
8
from inspect import isclass, signature
9
from multiprocessing.connection import Connection
10
-from typing import Any, List, Optional, Set, Tuple, Type
10
+from typing import Any, Optional
11
12
import msgspec
13
import psutil
@@ -42,7 +42,7 @@ class EngineCore:
42
def __init__(
43
self,
44
vllm_config: VllmConfig,
45
- executor_class: Type[Executor],
45
+ executor_class: type[Executor],
46
log_stats: bool,
47
):
48
assert vllm_config.model_config.runner_type != "pooling"
@@ -80,7 +80,7 @@ class EngineCore:
80
# schedule and execute batches, and is required by pipeline parallelism
81
# to eliminate pipeline bubbles.
82
self.batch_queue_size = self.model_executor.max_concurrent_batches
83
- self.batch_queue: Optional[queue.Queue[Tuple[Future[ModelRunnerOutput],
83
+ self.batch_queue: Optional[queue.Queue[tuple[Future[ModelRunnerOutput],
84
SchedulerOutput]]] = None
85
if self.batch_queue_size > 1:
86
logger.info("Batch queue is enabled with size %d",
@@ -88,7 +88,7 @@ class EngineCore:
88
self.batch_queue = queue.Queue(self.batch_queue_size)
89
90
def _initialize_kv_caches(self,
91
- vllm_config: VllmConfig) -> Tuple[int, int]:
91
+ vllm_config: VllmConfig) -> tuple[int, int]:
92
start = time.time()
93
94
# Get all kv cache needed by the model
@@ -134,7 +134,7 @@ class EngineCore:
134
135
self.scheduler.add_request(req)
136
137
- def abort_requests(self, request_ids: List[str]):
137
+ def abort_requests(self, request_ids: list[str]):
138
"""Abort requests from the scheduler."""
139
140
# TODO: The scheduler doesn't really need to know the
@@ -228,7 +228,7 @@ class EngineCore:
228
def remove_lora(self, lora_id: int) -> bool:
229
return self.model_executor.remove_lora(lora_id)
230
231
- def list_loras(self) -> Set[int]:
231
+ def list_loras(self) -> set[int]:
232
return self.model_executor.list_loras()
233
234
def pin_lora(self, lora_id: int) -> bool:
@@ -244,7 +244,7 @@ class EngineCoreProc(EngineCore):
244
output_path: str,
245
ready_pipe: Connection,
246
vllm_config: VllmConfig,
247
- executor_class: Type[Executor],
247
+ executor_class: type[Executor],
248
log_stats: bool,
249
):
250
super().__init__(vllm_config, executor_class, log_stats)
@@ -254,7 +254,7 @@ class EngineCoreProc(EngineCore):
254
# and to overlap some serialization/deserialization with the
255
# model forward pass.
256
# Threads handle Socket <-> Queues and core_busy_loop uses Queue.
257
- self.input_queue: queue.Queue[Tuple[EngineCoreRequestType,
257
+ self.input_queue: queue.Queue[tuple[EngineCoreRequestType,
258
Any]] = queue.Queue()
259
self.output_queue: queue.Queue[EngineCoreOutputs] = queue.Queue()
260
threading.Thread(target=self.process_input_socket,
vllm/v1/engine/core_client.py
+17
-17
@@ -10,7 +10,7 @@ from abc import ABC, abstractmethod
10
from concurrent.futures import Future
11
from dataclasses import dataclass
12
from threading import Thread
13
-from typing import Any, Dict, List, Optional, Set, Type, Union
13
+from typing import Any, Optional, Union
14
15
import zmq
16
import zmq.asyncio
@@ -48,7 +48,7 @@ class EngineCoreClient(ABC):
48
multiprocess_mode: bool,
49
asyncio_mode: bool,
50
vllm_config: VllmConfig,
51
- executor_class: Type[Executor],
51
+ executor_class: type[Executor],
52
log_stats: bool,
53
) -> "EngineCoreClient":
54
@@ -94,7 +94,7 @@ class EngineCoreClient(ABC):
94
async def execute_dummy_batch_async(self) -> None:
95
raise NotImplementedError
96
97
- def abort_requests(self, request_ids: List[str]) -> None:
97
+ def abort_requests(self, request_ids: list[str]) -> None:
98
raise NotImplementedError
99
100
def add_lora(self, lora_request: LoRARequest) -> bool:
@@ -103,7 +103,7 @@ class EngineCoreClient(ABC):
103
def remove_lora(self, lora_id: int) -> bool:
104
raise NotImplementedError
105
106
- def list_loras(self) -> Set[int]:
106
+ def list_loras(self) -> set[int]:
107
raise NotImplementedError
108
109
def pin_lora(self, lora_id: int) -> bool:
@@ -127,7 +127,7 @@ class EngineCoreClient(ABC):
127
async def wake_up_async(self) -> None:
128
raise NotImplementedError
129
130
- async def abort_requests_async(self, request_ids: List[str]) -> None:
130
+ async def abort_requests_async(self, request_ids: list[str]) -> None:
131
raise NotImplementedError
132
133
async def add_lora_async(self, lora_request: LoRARequest) -> bool:
@@ -136,7 +136,7 @@ class EngineCoreClient(ABC):
136
async def remove_lora_async(self, lora_id: int) -> bool:
137
raise NotImplementedError
138
139
- async def list_loras_async(self) -> Set[int]:
139
+ async def list_loras_async(self) -> set[int]:
140
raise NotImplementedError
141
142
async def pin_lora_async(self, lora_id: int) -> bool:
@@ -162,7 +162,7 @@ class InprocClient(EngineCoreClient):
162
def add_request(self, request: EngineCoreRequest) -> None:
163
self.engine_core.add_request(request)
164
165
- def abort_requests(self, request_ids: List[str]) -> None:
165
+ def abort_requests(self, request_ids: list[str]) -> None:
166
if len(request_ids) > 0:
167
self.engine_core.abort_requests(request_ids)
168
@@ -190,7 +190,7 @@ class InprocClient(EngineCoreClient):
190
def remove_lora(self, lora_id: int) -> bool:
191
return self.engine_core.remove_lora(lora_id)
192
193
- def list_loras(self) -> Set[int]:
193
+ def list_loras(self) -> set[int]:
194
return self.engine_core.list_loras()
195
196
def pin_lora(self, lora_id: int) -> bool:
@@ -239,7 +239,7 @@ class MPClient(EngineCoreClient):
239
self,
240
asyncio_mode: bool,
241
vllm_config: VllmConfig,
242
- executor_class: Type[Executor],
242
+ executor_class: type[Executor],
243
log_stats: bool,
244
):
245
# The child processes will send SIGUSR1 when unrecoverable
@@ -293,14 +293,14 @@ class MPClient(EngineCoreClient):
293
294
self.output_socket = resources.output_socket
295
self.input_socket = resources.input_socket
296
- self.utility_results: Dict[int, AnyFuture] = {}
296
+ self.utility_results: dict[int, AnyFuture] = {}
297
298
def shutdown(self):
299
self._finalizer()
300
301
302
def _process_utility_output(output: UtilityOutput,
303
- utility_results: Dict[int, AnyFuture]):
303
+ utility_results: dict[int, AnyFuture]):
304
"""Set the result from a utility method in the waiting future"""
305
future = utility_results.pop(output.call_id)
306
if output.failure_message is not None:
@@ -312,7 +312,7 @@ def _process_utility_output(output: UtilityOutput,
312
class SyncMPClient(MPClient):
313
"""Synchronous client for multi-proc EngineCore."""
314
315
- def __init__(self, vllm_config: VllmConfig, executor_class: Type[Executor],
315
+ def __init__(self, vllm_config: VllmConfig, executor_class: type[Executor],
316
log_stats: bool):
317
super().__init__(
318
asyncio_mode=False,
@@ -373,7 +373,7 @@ class SyncMPClient(MPClient):
373
request.prompt = None
374
self._send_input(EngineCoreRequestType.ADD, request)
375
376
- def abort_requests(self, request_ids: List[str]) -> None:
376
+ def abort_requests(self, request_ids: list[str]) -> None:
377
if len(request_ids) > 0:
378
self._send_input(EngineCoreRequestType.ABORT, request_ids)
379
@@ -389,7 +389,7 @@ class SyncMPClient(MPClient):
389
def remove_lora(self, lora_id: int) -> bool:
390
return self._call_utility("remove_lora", lora_id)
391
392
- def list_loras(self) -> Set[int]:
392
+ def list_loras(self) -> set[int]:
393
return self._call_utility("list_loras")
394
395
def pin_lora(self, lora_id: int) -> bool:
@@ -408,7 +408,7 @@ class SyncMPClient(MPClient):
408
class AsyncMPClient(MPClient):
409
"""Asyncio-compatible client for multi-proc EngineCore."""
410
411
- def __init__(self, vllm_config: VllmConfig, executor_class: Type[Executor],
411
+ def __init__(self, vllm_config: VllmConfig, executor_class: type[Executor],
412
log_stats: bool):
413
super().__init__(
414
asyncio_mode=True,
@@ -471,7 +471,7 @@ class AsyncMPClient(MPClient):
471
request.prompt = None
472
await self._send_input(EngineCoreRequestType.ADD, request)
473
474
- async def abort_requests_async(self, request_ids: List[str]) -> None:
474
+ async def abort_requests_async(self, request_ids: list[str]) -> None:
475
if len(request_ids) > 0:
476
await self._send_input(EngineCoreRequestType.ABORT, request_ids)
477
@@ -496,7 +496,7 @@ class AsyncMPClient(MPClient):
496
async def remove_lora_async(self, lora_id: int) -> bool:
497
return await self._call_utility_async("remove_lora", lora_id)
498
499
- async def list_loras_async(self) -> Set[int]:
499
+ async def list_loras_async(self) -> set[int]:
500
return await self._call_utility_async("list_loras")
501
502
async def pin_lora_async(self, lora_id: int) -> bool:
vllm/v1/engine/detokenizer.py
+6
-6
@@ -1,7 +1,7 @@
1
# SPDX-License-Identifier: Apache-2.0
2
3
from dataclasses import dataclass
4
-from typing import List, Optional
4
+from typing import Optional
5
6
from vllm.engine.output_processor.stop_checker import StopChecker
7
from vllm.logger import init_logger
@@ -17,12 +17,12 @@ class IncrementalDetokenizer:
17
18
# Generation data
19
output_text: str
20
- tokens: List[str]
21
- token_ids: List[int]
20
+ tokens: list[str]
21
+ token_ids: list[int]
22
prompt_len: int
23
24
# Stop strings
25
- stop: List[str]
25
+ stop: list[str]
26
include_stop_str_in_output: bool
27
28
# Metadata for incremental detokenization
@@ -41,7 +41,7 @@ class IncrementalDetokenizer:
41
_last_output_text_offset: int = 0
42
43
@property
44
- def output_token_ids(self) -> List[int]:
44
+ def output_token_ids(self) -> list[int]:
45
return self.token_ids[self.prompt_len:]
46
47
@classmethod
@@ -84,7 +84,7 @@ class IncrementalDetokenizer:
84
stop_buffer_length=stop_buffer_length,
85
)
86
87
- def update(self, new_token_ids: List[int]) -> Optional[str]:
87
+ def update(self, new_token_ids: list[int]) -> Optional[str]:
88
"""
89
Update RequestState for the request_id by:
90
1) Detokenize the new token ids incrementally.
vllm/v1/engine/llm_engine.py
+9
-8
@@ -1,6 +1,7 @@
1
# SPDX-License-Identifier: Apache-2.0
2
3
-from typing import Dict, List, Mapping, Optional, Set, Type, Union
3
+from collections.abc import Mapping
4
+from typing import Optional, Union
5
6
from typing_extensions import TypeVar
7
@@ -36,10 +37,10 @@ class LLMEngine:
37
def __init__(
38
self,
39
vllm_config: VllmConfig,
39
- executor_class: Type[Executor],
40
+ executor_class: type[Executor],
41
log_stats: bool,
42
usage_context: UsageContext = UsageContext.ENGINE_CONTEXT,
42
- stat_loggers: Optional[Dict[str, StatLoggerBase]] = None,
43
+ stat_loggers: Optional[dict[str, StatLoggerBase]] = None,
44
input_registry: InputRegistry = INPUT_REGISTRY,
45
mm_registry: MultiModalRegistry = MULTIMODAL_REGISTRY,
46
use_cached_outputs: bool = False,
@@ -97,7 +98,7 @@ class LLMEngine:
98
cls,
99
engine_args: EngineArgs,
100
usage_context: UsageContext = UsageContext.ENGINE_CONTEXT,
100
- stat_loggers: Optional[Dict[str, StatLoggerBase]] = None,
101
+ stat_loggers: Optional[dict[str, StatLoggerBase]] = None,
102
enable_multiprocessing: bool = False,
103
) -> "LLMEngine":
104
"""Creates an LLM engine from the engine arguments."""
@@ -139,7 +140,7 @@ class LLMEngine:
140
def validate_outputs(cls, outputs, output_type):
141
return outputs
142
142
- def abort_request(self, request_ids: List[str]) -> None:
143
+ def abort_request(self, request_ids: list[str]) -> None:
144
"""Remove request_ids from EngineCore and Detokenizer."""
145
146
self.engine_core.abort_requests(request_ids)
@@ -199,7 +200,7 @@ class LLMEngine:
200
# 3) Add the request to EngineCore.
201
self.engine_core.add_request(request)
202
202
- def step(self) -> List[RequestOutput]:
203
+ def step(self) -> list[RequestOutput]:
204
205
if self.should_execute_dummy_batch:
206
self.should_execute_dummy_batch = False
@@ -241,7 +242,7 @@ class LLMEngine:
242
243
def get_tokenizer_group(
244
self,
244
- group_type: Type[_G] = BaseTokenizerGroup,
245
+ group_type: type[_G] = BaseTokenizerGroup,
246
) -> _G:
247
tokenizer_group = self.tokenizer
248
@@ -263,7 +264,7 @@ class LLMEngine:
264
"""Remove an already loaded LoRA adapter."""
265
return self.engine_core.remove_lora(lora_id)
266
266
- def list_loras(self) -> Set[int]:
267
+ def list_loras(self) -> set[int]:
268
"""List all registered adapters."""
269
return self.engine_core.list_loras()
270
vllm/v1/engine/logprobs.py
+6
-6
@@ -2,7 +2,7 @@
2
3
import itertools
4
from dataclasses import dataclass
5
-from typing import Dict, List, Optional
5
+from typing import Optional
6
7
from vllm.logger import init_logger
8
from vllm.sequence import Logprob, PromptLogprobs, SampleLogprobs
@@ -151,12 +151,12 @@ class LogprobsProcessor:
151
152
@staticmethod
153
def _make_logprob_dict(
154
- logprobs: List[float],
155
- logprob_token_ids: List[int],
156
- decoded_tokens: List[str],
154
+ logprobs: list[float],
155
+ logprob_token_ids: list[int],
156
+ decoded_tokens: list[str],
157
rank: int,
158
num_logprobs: int,
159
- ) -> Dict[int, Logprob]:
159
+ ) -> dict[int, Logprob]:
160
"""Make a Logprob dictionary for a position.
161
162
Args:
@@ -168,7 +168,7 @@ class LogprobsProcessor:
168
by the user (in addition to sampled logprob)
169
170
Returns:
171
- Dict[token id, Logprob]
171
+ dict[token id, Logprob]
172
"""
173
174
# We do not need a special case for the sampled token
vllm/v1/engine/mm_input_cache.py
+9
-9
@@ -1,6 +1,6 @@
1
# SPDX-License-Identifier: Apache-2.0
2
3
-from typing import Any, Dict, List, Optional
3
+from typing import Any, Optional
4
5
from vllm.config import ModelConfig
6
from vllm.envs import VLLM_MM_INPUT_CACHE_SIZE
@@ -68,10 +68,10 @@ class MMInputCacheClient:
68
def process_inputs(
69
self,
70
mm_data: MultiModalDataDict,
71
- mm_hashes: Optional[List[str]],
72
- mm_processor_kwargs: Optional[Dict[str, Any]],
73
- precomputed_mm_inputs: Optional[List[MultiModalKwargs]],
74
- ) -> List[MultiModalKwargs]:
71
+ mm_hashes: Optional[list[str]],
72
+ mm_processor_kwargs: Optional[dict[str, Any]],
73
+ precomputed_mm_inputs: Optional[list[MultiModalKwargs]],
74
+ ) -> list[MultiModalKwargs]:
75
if precomputed_mm_inputs is None:
76
image_inputs = mm_data["image"]
77
if not isinstance(image_inputs, list):
@@ -88,7 +88,7 @@ class MMInputCacheClient:
88
# Process each image input separately, so that later we can schedule
89
# them in a fine-grained manner.
90
# Apply caching (if enabled) and reuse precomputed inputs (if provided)
91
- ret_inputs: List[MultiModalKwargs] = []
91
+ ret_inputs: list[MultiModalKwargs] = []
92
for input_id in range(num_inputs):
93
if self.mm_debug_cache_hit_ratio_steps is not None:
94
self.cache_hit_ratio(self.mm_debug_cache_hit_ratio_steps)
@@ -133,9 +133,9 @@ class MMInputCacheServer:
133
134
def get_and_update(
135
self,
136
- mm_inputs: List[Optional[MultiModalKwargs]],
137
- mm_hashes: List[str],
138
- ) -> List[MultiModalKwargs]:
136
+ mm_inputs: list[Optional[MultiModalKwargs]],
137
+ mm_hashes: list[str],
138
+ ) -> list[MultiModalKwargs]:
139
assert len(mm_inputs) == len(mm_hashes)
140
141
if not self.use_cache:
vllm/v1/engine/output_processor.py
+10
-10
@@ -2,7 +2,7 @@
2
3
import asyncio
4
from dataclasses import dataclass
5
-from typing import Dict, List, Optional, Union
5
+from typing import Optional, Union
6
7
from vllm.outputs import RequestOutput
8
from vllm.sampling_params import RequestOutputKind
@@ -18,8 +18,8 @@ from vllm.v1.metrics.stats import (IterationStats, LoRARequestStates,
18
@dataclass
19
class OutputProcessorOutput:
20
21
- request_outputs: List[RequestOutput]
22
- reqs_to_abort: List[str]
21
+ request_outputs: list[RequestOutput]
22
+ reqs_to_abort: list[str]
23
24
25
class RequestState:
@@ -30,7 +30,7 @@ class RequestState:
30
lora_name: Optional[str],
31
output_kind: RequestOutputKind,
32
prompt: Optional[str],
33
- prompt_token_ids: List[int],
33
+ prompt_token_ids: list[int],
34
logprobs_processor: LogprobsProcessor,
35
detokenizer: IncrementalDetokenizer,
36
arrival_time: float,
@@ -90,7 +90,7 @@ class OutputProcessor:
90
):
91
self.log_stats = log_stats
92
self.tokenizer = tokenizer
93
- self.request_states: Dict[str, RequestState] = {}
93
+ self.request_states: dict[str, RequestState] = {}
94
self.lora_states = LoRARequestStates()
95
96
def is_request_active(self, request_id: str) -> bool:
@@ -104,7 +104,7 @@ class OutputProcessor:
104
105
def abort_requests(
106
self,
107
- request_ids: List[str],
107
+ request_ids: list[str],
108
) -> None:
109
for request_id in request_ids:
110
req_state = self.request_states.pop(request_id, None)
@@ -130,7 +130,7 @@ class OutputProcessor:
130
131
def process_outputs(
132
self,
133
- engine_core_outputs: List[EngineCoreOutput],
133
+ engine_core_outputs: list[EngineCoreOutput],
134
engine_core_timestamp: Optional[float] = None,
135
iteration_stats: Optional[IterationStats] = None,
136
) -> OutputProcessorOutput:
@@ -158,8 +158,8 @@ class OutputProcessor:
158
**********************************************************
159
"""
160
161
- request_outputs: List[RequestOutput] = []
162
- reqs_to_abort: List[str] = []
161
+ request_outputs: list[RequestOutput] = []
162
+ reqs_to_abort: list[str] = []
163
for engine_core_output in engine_core_outputs:
164
req_id = engine_core_output.request_id
165
req_state = self.request_states.get(req_id)
@@ -265,7 +265,7 @@ class OutputProcessor:
265
@staticmethod
266
def _make_request_output(
267
request_state: RequestState,
268
- new_token_ids: List[int],
268
+ new_token_ids: list[int],
269
finish_reason: Optional[FinishReason],
270
stop_reason: Union[int, str, None],
271
) -> Optional[RequestOutput]:
vllm/v1/engine/parallel_sampling.py
+8
-8
@@ -1,8 +1,8 @@
1
# SPDX-License-Identifier: Apache-2.0
2
3
+from collections.abc import AsyncGenerator, Mapping
4
from copy import copy
4
-from typing import (AsyncGenerator, Dict, List, Mapping, Optional, Protocol,
5
- Tuple, Union)
5
+from typing import Optional, Protocol, Union
6
7
from vllm.inputs import PromptType
8
from vllm.lora.request import LoRARequest
@@ -137,7 +137,7 @@ class ParallelSamplingRequest:
137
key=lambda x: x.index)
138
return self.request_output
139
140
- def get_child_info(self, index: int) -> Tuple[str, SamplingParams]:
140
+ def get_child_info(self, index: int) -> tuple[str, SamplingParams]:
141
"""Get child request ID and sampling params.
142
143
Args:
@@ -237,9 +237,9 @@ class SyncParallelSamplingManager:
237
238
def __init__(self):
239
# Parent req ID -> parent request manager
240
- self.parent_reqs: Dict[str, ParallelSamplingRequest] = {}
240
+ self.parent_reqs: dict[str, ParallelSamplingRequest] = {}
241
# Child req ID -> (child req index, parent req ID)
242
- self.child_reqs: Dict[str, Tuple[int, str]] = {}
242
+ self.child_reqs: dict[str, tuple[int, str]] = {}
243
244
def _register_parent_request(self, req: ParallelSamplingRequest) -> None:
245
"""Register parallel sampling parent request."""
@@ -299,8 +299,8 @@ class SyncParallelSamplingManager:
299
300
def step(
301
self,
302
- outputs: List[RequestOutput],
303
- ) -> List[RequestOutput]:
302
+ outputs: list[RequestOutput],
303
+ ) -> list[RequestOutput]:
304
"""Build parallel sampling request outputs.
305
306
Extract child request outputs, aggregate them
@@ -355,7 +355,7 @@ async def generate_parallel_sampling_async(
355
parent_req = ParallelSamplingRequest(request_id, sampling_params)
356
357
# Aggregate generators for n child requests
358
- gens: List[AsyncGenerator[RequestOutput, None]] = []
358
+ gens: list[AsyncGenerator[RequestOutput, None]] = []
359
for idx in range(parent_req.n):
360
child_req_id, child_params = parent_req.get_child_info(idx)
361
child_gen = generate(
vllm/v1/engine/processor.py
+2
-1
@@ -1,7 +1,8 @@
1
# SPDX-License-Identifier: Apache-2.0
2
3
import time
4
-from typing import Mapping, Optional, Union
4
+from collections.abc import Mapping
5
+from typing import Optional, Union
6
7
from vllm.config import CacheConfig, LoRAConfig, ModelConfig
8
from vllm.inputs import (INPUT_REGISTRY, InputRegistry, ProcessorInputs,
vllm/v1/executor/abstract.py
+5
-5
@@ -1,7 +1,7 @@
1
# SPDX-License-Identifier: Apache-2.0
2
3
from concurrent.futures import Future
4
-from typing import List, Type, Union
4
+from typing import Union
5
6
import torch
7
import torch.distributed as dist
@@ -22,8 +22,8 @@ class Executor(ExecutorBase):
22
For methods shared by v0 and v1, define them in ExecutorBase"""
23
24
@staticmethod
25
- def get_class(vllm_config: VllmConfig) -> Type["Executor"]:
26
- executor_class: Type[Executor]
25
+ def get_class(vllm_config: VllmConfig) -> type["Executor"]:
26
+ executor_class: type[Executor]
27
parallel_config = vllm_config.parallel_config
28
distributed_executor_backend = (
29
parallel_config.distributed_executor_backend)
@@ -53,7 +53,7 @@ class Executor(ExecutorBase):
53
return executor_class
54
55
def initialize_from_config(self,
56
- kv_cache_configs: List[KVCacheConfig]) -> None:
56
+ kv_cache_configs: list[KVCacheConfig]) -> None:
57
"""
58
Initialize the KV caches and begin the model execution loop of the
59
underlying workers.
@@ -69,7 +69,7 @@ class Executor(ExecutorBase):
69
# operators can be applied to all workers.
70
return min(output)
71
72
- def get_kv_cache_specs(self) -> List[KVCacheSpec]:
72
+ def get_kv_cache_specs(self) -> list[KVCacheSpec]:
73
output = self.collective_rpc("get_kv_cache_spec")
74
return output
75
vllm/v1/executor/multiproc_executor.py
+5
-5
@@ -10,7 +10,7 @@ from dataclasses import dataclass
10
from enum import Enum, auto
11
from functools import partial
12
from multiprocessing.process import BaseProcess
13
-from typing import Any, Callable, Dict, List, Optional, Tuple, Union
13
+from typing import Any, Callable, Optional, Union
14
15
import cloudpickle
16
import psutil
@@ -77,7 +77,7 @@ class MultiprocExecutor(Executor):
77
scheduler_output_handle = self.rpc_broadcast_mq.export_handle()
78
79
# Create workers
80
- self.workers: List[WorkerProcHandle] = []
80
+ self.workers: list[WorkerProcHandle] = []
81
for rank in range(self.world_size):
82
worker = WorkerProc.make_worker_process(self.vllm_config, rank,
83
rank,
@@ -94,8 +94,8 @@ class MultiprocExecutor(Executor):
94
def collective_rpc(self,
95
method: Union[str, Callable],
96
timeout: Optional[float] = None,
97
- args: Tuple = (),
98
- kwargs: Optional[Dict] = None) -> List[Any]:
97
+ args: tuple = (),
98
+ kwargs: Optional[dict] = None) -> list[Any]:
99
start_time = time.monotonic()
100
kwargs = kwargs or {}
101
@@ -208,7 +208,7 @@ class WorkerProc:
208
self.rank = rank
209
wrapper = WorkerWrapperBase(vllm_config=vllm_config, rpc_rank=rank)
210
# TODO: move `init_worker` to executor level as a collective rpc call
211
- all_kwargs: List[Dict] = [
211
+ all_kwargs: list[dict] = [
212
{} for _ in range(vllm_config.parallel_config.world_size)
213
]
214
all_kwargs[rank] = {
vllm/v1/kv_cache_interface.py
+3
-4
@@ -1,7 +1,6 @@
1
# SPDX-License-Identifier: Apache-2.0
2
3
from dataclasses import dataclass
4
-from typing import Dict, List
4
5
import torch
6
@@ -74,7 +73,7 @@ class FullAttentionSpec(KVCacheSpecBase):
73
return cdiv(num_tokens, self.block_size) * self.page_size_bytes
74
75
77
-KVCacheSpec = Dict[str, KVCacheSpecBase]
76
+KVCacheSpec = dict[str, KVCacheSpecBase]
77
78
79
@dataclass
@@ -95,7 +94,7 @@ class KVCacheConfig:
94
"""The number of KV cache blocks"""
95
num_blocks: int
96
"""layer_name -> how to initialize KV cache for that layer"""
98
- tensors: Dict[str, KVCacheTensor]
97
+ tensors: dict[str, KVCacheTensor]
98
"""
99
A list of kv-cache groups. Each group includes a set of layers with
100
the same kv-cache spec, and the total page_size of layers inside a group
@@ -108,6 +107,6 @@ class KVCacheConfig:
107
3. (not implemented yet) A model with 2 full attention layers and 4 sliding
108
window attention layers: three groups, (full * 2), (sw * 2), (sw * 2).
109
"""
111
- groups: List[List[str]]
110
+ groups: list[list[str]]
111
"""the KVCacheSpec of the model"""
112
kv_cache_spec: KVCacheSpec
vllm/v1/metrics/loggers.py
+9
-9
@@ -2,7 +2,7 @@
2
3
import time
4
from abc import ABC, abstractmethod
5
-from typing import Dict, List, Optional
5
+from typing import Optional
6
7
import numpy as np
8
import prometheus_client
@@ -35,8 +35,8 @@ class LoggingStatLogger(StatLoggerBase):
35
self.last_log_time = now
36
37
# Tracked stats over current local logging interval.
38
- self.num_prompt_tokens: List[int] = []
39
- self.num_generation_tokens: List[int] = []
38
+ self.num_prompt_tokens: list[int] = []
39
+ self.num_generation_tokens: list[int] = []
40
41
# Prefix cache metrics. TODO: Make the interval configurable.
42
self.prefix_caching_metrics = PrefixCachingMetrics()
@@ -52,7 +52,7 @@ class LoggingStatLogger(StatLoggerBase):
52
self.num_generation_tokens.append(
53
iteration_stats.num_generation_tokens)
54
55
- def _get_throughput(self, tracked_stats: List[int], now: float) -> float:
55
+ def _get_throughput(self, tracked_stats: list[int], now: float) -> float:
56
# Compute summary metrics for tracked stats
57
return float(np.sum(tracked_stats) / (now - self.last_log_time))
58
@@ -147,7 +147,7 @@ class PrometheusStatLogger(StatLoggerBase):
147
documentation="Number of generation tokens processed.",
148
labelnames=labelnames).labels(*labelvalues)
149
150
- self.counter_request_success: Dict[FinishReason,
150
+ self.counter_request_success: dict[FinishReason,
151
prometheus_client.Counter] = {}
152
counter_request_success_base = prometheus_client.Counter(
153
name="vllm:request_success_total",
@@ -338,14 +338,14 @@ class PrometheusStatLogger(StatLoggerBase):
338
prometheus_client.REGISTRY.unregister(collector)
339
340
341
-def build_buckets(mantissa_lst: List[int], max_value: int) -> List[int]:
341
+def build_buckets(mantissa_lst: list[int], max_value: int) -> list[int]:
342
"""
343
Builds a list of buckets with increasing powers of 10 multiplied by
344
mantissa values until the value exceeds the specified maximum.
345
346
"""
347
exponent = 0
348
- buckets: List[int] = []
348
+ buckets: list[int] = []
349
while True:
350
for m in mantissa_lst:
351
value = m * 10**exponent
@@ -356,7 +356,7 @@ def build_buckets(mantissa_lst: List[int], max_value: int) -> List[int]:
356
exponent += 1
357
358
359
-def build_1_2_5_buckets(max_value: int) -> List[int]:
359
+def build_1_2_5_buckets(max_value: int) -> list[int]:
360
"""
361
Example:
362
>>> build_1_2_5_buckets(100)
@@ -365,7 +365,7 @@ def build_1_2_5_buckets(max_value: int) -> List[int]:
365
return build_buckets([1, 2, 5], max_value)
366
367
368
-def build_cudagraph_buckets(vllm_config: VllmConfig) -> List[int]:
368
+def build_cudagraph_buckets(vllm_config: VllmConfig) -> list[int]:
369
if not vllm_config.model_config.enforce_eager:
370
buckets = vllm_config.compilation_config.\
371
cudagraph_capture_sizes.copy()
vllm/v1/metrics/stats.py
+10
-10
@@ -2,7 +2,7 @@
2
3
import time
4
from dataclasses import dataclass, field
5
-from typing import TYPE_CHECKING, Dict, List, Optional, Set
5
+from typing import TYPE_CHECKING, Optional
6
7
if TYPE_CHECKING:
8
from vllm.outputs import RequestOutput
@@ -39,8 +39,8 @@ class SchedulerStats:
39
40
@dataclass
41
class LoRAStats:
42
- waiting_requests: Set[str] = field(default_factory=set)
43
- running_requests: Set[str] = field(default_factory=set)
42
+ waiting_requests: set[str] = field(default_factory=set)
43
+ running_requests: set[str] = field(default_factory=set)
44
45
46
@dataclass
@@ -81,11 +81,11 @@ class IterationStats:
81
self.num_generation_tokens = 0
82
self.num_prompt_tokens = 0
83
self.num_preempted_reqs = 0
84
- self.finished_requests: List[FinishedRequestStats] = []
85
- self.time_to_first_tokens_iter: List[float] = []
86
- self.time_per_output_tokens_iter: List[float] = []
87
- self.waiting_lora_adapters: Dict[str, int] = {}
88
- self.running_lora_adapters: Dict[str, int] = {}
84
+ self.finished_requests: list[FinishedRequestStats] = []
85
+ self.time_to_first_tokens_iter: list[float] = []
86
+ self.time_per_output_tokens_iter: list[float] = []
87
+ self.waiting_lora_adapters: dict[str, int] = {}
88
+ self.running_lora_adapters: dict[str, int] = {}
89
90
def _time_since(self, start: float) -> float:
91
"""Calculate an interval relative to this iteration's timestamp."""
@@ -132,7 +132,7 @@ class IterationStats:
132
if num_new_generation_tokens > 0:
133
req_stats.last_token_ts = engine_core_timestamp
134
135
- def update_from_events(self, req_id: str, events: List["EngineCoreEvent"],
135
+ def update_from_events(self, req_id: str, events: list["EngineCoreEvent"],
136
is_prefilling: bool, req_stats: RequestStateStats,
137
lora_stats: Optional[LoRAStats]):
138
# Avoid circular dependency
@@ -185,7 +185,7 @@ class LoRARequestStates:
185
"""Per-LoRA request state stats."""
186
187
def __init__(self):
188
- self.lora_name_to_stats: Dict[str, LoRAStats] = {}
188
+ self.lora_name_to_stats: dict[str, LoRAStats] = {}
189
190
def get_stats(self, req_state: 'RequestState') -> Optional[LoRAStats]:
191
if req_state.lora_name is None:
vllm/v1/outputs.py
+10
-10
@@ -1,7 +1,7 @@
1
# SPDX-License-Identifier: Apache-2.0
2
3
from dataclasses import dataclass
4
-from typing import Dict, List, NamedTuple, Optional
4
+from typing import NamedTuple, Optional
5
6
import torch
7
@@ -9,11 +9,11 @@ import torch
9
class LogprobsLists(NamedTuple):
10
11
# [num_reqs, max_num_logprobs + 1]
12
- logprob_token_ids: List[List[int]]
12
+ logprob_token_ids: list[list[int]]
13
# [num_reqs, max_num_logprobs + 1]
14
- logprobs: List[List[float]]
14
+ logprobs: list[list[float]]
15
# [num_reqs]
16
- sampled_token_ranks: List[int]
16
+ sampled_token_ranks: list[int]
17
18
def slice(self, start: int, end: int):
19
return LogprobsLists(
@@ -52,23 +52,23 @@ class SamplerOutput:
52
53
54
# ModelRunnerOutput is serialized and sent to the scheduler process.
55
-# This is expensive for torch.Tensor so prefer to use List instead.
55
+# This is expensive for torch.Tensor so prefer to use list instead.
56
@dataclass
57
class ModelRunnerOutput:
58
59
# [num_reqs]
60
- req_ids: List[str]
60
+ req_ids: list[str]
61
# req_id -> index
62
- req_id_to_index: Dict[str, int]
62
+ req_id_to_index: dict[str, int]
63
64
# num_reqs x num_generated_tokens
65
# num_generated_tokens is the number of tokens
66
# generated in the current step. It can be different for
67
# each request due to speculative/jump decoding.
68
- sampled_token_ids: List[List[int]]
68
+ sampled_token_ids: list[list[int]]
69
70
# num_reqs x num_spec_tokens
71
- spec_token_ids: Optional[List[List[int]]]
71
+ spec_token_ids: Optional[list[list[int]]]
72
73
# [num_reqs, max_num_logprobs + 1]
74
# [num_reqs, max_num_logprobs + 1]
@@ -79,4 +79,4 @@ class ModelRunnerOutput:
79
# [prompt_len, num_prompt_logprobs]
80
# [prompt_len, num_prompt_logprobs]
81
# [prompt_len]
82
- prompt_logprobs_dict: Dict[str, Optional[LogprobsTensors]]
82
+ prompt_logprobs_dict: dict[str, Optional[LogprobsTensors]]
vllm/v1/request.py
+12
-12
@@ -1,7 +1,7 @@
1
# SPDX-License-Identifier: Apache-2.0
2
3
import enum
4
-from typing import TYPE_CHECKING, List, Optional, Union
4
+from typing import TYPE_CHECKING, Optional, Union
5
6
from vllm.lora.request import LoRARequest
7
from vllm.sampling_params import SamplingParams
@@ -20,10 +20,10 @@ class Request:
20
self,
21
request_id: str,
22
prompt: Optional[str],
23
- prompt_token_ids: List[int],
24
- multi_modal_inputs: Optional[List["MultiModalKwargs"]],
25
- multi_modal_hashes: Optional[List[str]],
26
- multi_modal_placeholders: Optional[List["PlaceholderRange"]],
23
+ prompt_token_ids: list[int],
24
+ multi_modal_inputs: Optional[list["MultiModalKwargs"]],
25
+ multi_modal_hashes: Optional[list[str]],
26
+ multi_modal_placeholders: Optional[list["PlaceholderRange"]],
27
sampling_params: SamplingParams,
28
eos_token_id: Optional[int],
29
arrival_time: float,
@@ -36,7 +36,7 @@ class Request:
36
self.lora_request = lora_request
37
38
self.status = RequestStatus.WAITING
39
- self.events: List[EngineCoreEvent] = []
39
+ self.events: list[EngineCoreEvent] = []
40
self.stop_reason: Union[int, str, None] = None
41
assert sampling_params.max_tokens is not None
42
self.max_tokens = sampling_params.max_tokens
@@ -44,15 +44,15 @@ class Request:
44
self.prompt = prompt
45
self.prompt_token_ids = prompt_token_ids
46
self.num_prompt_tokens = len(self.prompt_token_ids)
47
- self._output_token_ids: List[int] = []
48
- self._all_token_ids: List[int] = self.prompt_token_ids.copy()
49
- self.spec_token_ids: List[int] = []
47
+ self._output_token_ids: list[int] = []
48
+ self._all_token_ids: list[int] = self.prompt_token_ids.copy()
49
+ self.spec_token_ids: list[int] = []
50
self.num_computed_tokens = 0
51
52
# Multi-modal related
53
self.mm_positions = multi_modal_placeholders or []
54
self.mm_inputs = multi_modal_inputs or []
55
- self.mm_hashes: List[str] = multi_modal_hashes or []
55
+ self.mm_hashes: list[str] = multi_modal_hashes or []
56
57
# Sanity check
58
assert len(self.mm_inputs) == len(self.mm_positions)
@@ -89,7 +89,7 @@ class Request:
89
EngineCoreEvent.new_event(EngineCoreEventType.SCHEDULED,
90
timestamp))
91
92
- def take_events(self) -> Optional[List[EngineCoreEvent]]:
92
+ def take_events(self) -> Optional[list[EngineCoreEvent]]:
93
if not self.events:
94
return None
95
events, self.events = self.events, []
@@ -97,7 +97,7 @@ class Request:
97
98
def append_output_token_ids(
99
self,
100
- token_ids: Union[int, List[int]],
100
+ token_ids: Union[int, list[int]],
101
) -> None:
102
if isinstance(token_ids, int):
103
token_ids = [token_ids]
vllm/v1/sample/metadata.py
+5
-5
@@ -1,7 +1,7 @@
1
# SPDX-License-Identifier: Apache-2.0
2
3
from dataclasses import dataclass
4
-from typing import Dict, List, Optional, Set, Tuple
4
+from typing import Optional
5
6
import torch
7
@@ -17,7 +17,7 @@ class SamplingMetadata:
17
top_k: Optional[torch.Tensor]
18
min_p: Optional[torch.Tensor]
19
20
- generators: Dict[int, torch.Generator]
20
+ generators: dict[int, torch.Generator]
21
22
# None means no logprobs, 0 means sampled token logprobs only
23
max_num_logprobs: Optional[int]
@@ -28,12 +28,12 @@ class SamplingMetadata:
28
presence_penalties: torch.Tensor
29
repetition_penalties: torch.Tensor
30
31
- output_token_ids: List[List[int]]
31
+ output_token_ids: list[list[int]]
32
33
# req_index -> (min_tokens, stop_token_ids)
34
- min_tokens: Dict[int, Tuple[int, Set[int]]]
34
+ min_tokens: dict[int, tuple[int, set[int]]]
35
36
- logit_bias: List[Optional[Dict[int, float]]]
36
+ logit_bias: list[Optional[dict[int, float]]]
37
38
# `allowed_token_ids_mask` is a 2D bool tensor of shape (max batch size,
39
# vocab size).
vllm/v1/sample/ops/penalties.py
+5
-7
@@ -1,7 +1,5 @@
1
# SPDX-License-Identifier: Apache-2.0
2
3
-from typing import Dict, List, Set, Tuple
4
-
3
import torch
4
5
from vllm.model_executor.layers.utils import apply_penalties
@@ -9,13 +7,13 @@ from vllm.utils import is_pin_memory_available, make_tensor_with_pad
7
8
9
def apply_min_token_penalties(
12
- logits: torch.Tensor, output_token_ids: List[List[int]],
13
- min_tokens: Dict[int, Tuple[int, Set[int]]]) -> None:
10
+ logits: torch.Tensor, output_token_ids: list[list[int]],
11
+ min_tokens: dict[int, tuple[int, set[int]]]) -> None:
12
"""
13
Applies minimum token penalty by setting the logits of the stop tokens
14
to -inf.
15
"""
18
- min_tokens_logits_to_penalize: List[Tuple[int, int]] = []
16
+ min_tokens_logits_to_penalize: list[tuple[int, int]] = []
17
for index, (min_token, stop_token_ids) in min_tokens.items():
18
if len(output_token_ids[index]) < min_token:
19
for stop_token_id in stop_token_ids:
@@ -30,7 +28,7 @@ def apply_all_penalties(
28
presence_penalties: torch.Tensor,
29
frequency_penalties: torch.Tensor,
30
repetition_penalties: torch.Tensor,
33
- output_token_ids: List[List[int]],
31
+ output_token_ids: list[list[int]],
32
) -> torch.Tensor:
33
"""
34
Applies presence, frequency and repetition penalties to the logits.
@@ -43,7 +41,7 @@ def apply_all_penalties(
41
repetition_penalties)
42
43
46
-def _convert_to_tensors(output_token_ids: List[List[int]], vocab_size: int,
44
+def _convert_to_tensors(output_token_ids: list[list[int]], vocab_size: int,
45
device: torch.device) -> torch.Tensor:
46
"""
47
Convert the different list data structures to tensors.
vllm/v1/sample/ops/topk_topp_sampler.py
+5
-5
@@ -1,6 +1,6 @@
1
# SPDX-License-Identifier: Apache-2.0
2
3
-from typing import Dict, Optional
3
+from typing import Optional
4
5
import torch
6
import torch.nn as nn
@@ -54,7 +54,7 @@ class TopKTopPSampler(nn.Module):
54
def forward_native(
55
self,
56
logits: torch.Tensor,
57
- generators: Dict[int, torch.Generator],
57
+ generators: dict[int, torch.Generator],
58
k: Optional[torch.Tensor],
59
p: Optional[torch.Tensor],
60
) -> torch.Tensor:
@@ -66,7 +66,7 @@ class TopKTopPSampler(nn.Module):
66
def forward_cuda(
67
self,
68
logits: torch.Tensor,
69
- generators: Dict[int, torch.Generator],
69
+ generators: dict[int, torch.Generator],
70
k: Optional[torch.Tensor],
71
p: Optional[torch.Tensor],
72
) -> torch.Tensor:
@@ -117,7 +117,7 @@ def apply_top_k_top_p(
117
118
def random_sample(
119
probs: torch.Tensor,
120
- generators: Dict[int, torch.Generator],
120
+ generators: dict[int, torch.Generator],
121
) -> torch.Tensor:
122
"""Randomly sample from the probabilities.
123
@@ -143,7 +143,7 @@ def flashinfer_sample(
143
probs: torch.Tensor,
144
k: Optional[torch.Tensor],
145
p: Optional[torch.Tensor],
146
- generators: Dict[int, torch.Generator],
146
+ generators: dict[int, torch.Generator],
147
) -> torch.Tensor:
148
"""Sample from the probabilities using FlashInfer.
149
vllm/v1/sample/rejection_sampler.py
+3
-4
@@ -1,5 +1,4 @@
1
# SPDX-License-Identifier: Apache-2.0
2
-from typing import List
2
3
import torch
4
import torch.nn as nn
@@ -54,7 +53,7 @@ class RejectionSampler(nn.Module):
53
else:
54
self.forward_method = self.forward_native
55
57
- def forward(self, draft_token_ids: List[List[int]],
56
+ def forward(self, draft_token_ids: list[list[int]],
57
target_probs: torch.Tensor,
58
sampling_metadata: SamplingMetadata) -> SamplerOutput:
59
if not sampling_metadata.all_greedy:
@@ -66,7 +65,7 @@ class RejectionSampler(nn.Module):
65
66
def flashinfer_sample(
67
self,
69
- draft_token_ids: List[List[int]],
68
+ draft_token_ids: list[list[int]],
69
target_probs: torch.Tensor,
70
sampling_metadata: SamplingMetadata,
71
) -> SamplerOutput:
@@ -119,7 +118,7 @@ class RejectionSampler(nn.Module):
118
# TODO: The following method can be optimized for better performance.
119
def forward_native(
120
self,
122
- draft_token_ids: List[List[int]],
121
+ draft_token_ids: list[list[int]],
122
target_probs: torch.Tensor,
123
sampling_metadata: SamplingMetadata,
124
) -> SamplerOutput:
vllm/v1/stats/common.py
+9
-9
@@ -4,7 +4,7 @@ import time
4
from dataclasses import dataclass
5
from dataclasses import field as dataclass_field
6
from enum import IntEnum
7
-from typing import ClassVar, Dict, List, Optional, Set
7
+from typing import ClassVar, Optional
8
9
import msgspec
10
from msgspec import field as msgspec_field
@@ -78,7 +78,7 @@ class RequestStatsUpdate(
78
▼
79
FINISHED (All could go to FINISHED)
80
"""
81
- _VALID_TRANSITIONS: ClassVar[Dict[Type, Set[Type]]] = {
81
+ _VALID_TRANSITIONS: ClassVar[dict[Type, set[Type]]] = {
82
Type.ARRIVED: {
83
Type.INPUT_PROCESSED,
84
Type.FINISHED,
@@ -140,7 +140,7 @@ class RequestStatsUpdate(
140
finish_reason: Optional[str] = None
141
142
# Non-optional fields for each update type.
143
- _REQUIRED_FIELDS: ClassVar[Dict[Type, List[str]]] = {
143
+ _REQUIRED_FIELDS: ClassVar[dict[Type, list[str]]] = {
144
Type.INPUT_PROCESSED: ["num_prompt_tokens", "sampling_params"],
145
Type.PREFILLING: ["num_computed_tokens", "num_cached_tokens"],
146
Type.DETOKENIZED: ["num_new_tokens"],
@@ -218,13 +218,13 @@ class RequestStats:
218
# 2. the request was preempted and resumed. It is equivalent to running
219
# a prefill of the original prefill tokens + generated output tokens
220
# before preemption.
221
- prefill_start_ts_s_lst: List[float] = dataclass_field(default_factory=list)
221
+ prefill_start_ts_s_lst: list[float] = dataclass_field(default_factory=list)
222
223
# A list of timestamps when a token is decoded by the engine core.
224
- decoding_ts_s_lst: List[float] = dataclass_field(default_factory=list)
224
+ decoding_ts_s_lst: list[float] = dataclass_field(default_factory=list)
225
226
# A sorted list of timestamps for each output token.
227
- output_token_ts_s_lst: List[float] = dataclass_field(default_factory=list)
227
+ output_token_ts_s_lst: list[float] = dataclass_field(default_factory=list)
228
229
# First token's timestamp.
230
first_token_ts_s: Optional[float] = None
@@ -241,7 +241,7 @@ class RequestStats:
241
# metric to measure the impact of preemption other than observation of
242
# large P99 TPOT. Ideally we could quantify the impact of preemption by
243
# measuring the number of tokens re-computed due to preemption.
244
- preempted_ts_s_lst: List[float] = dataclass_field(default_factory=list)
244
+ preempted_ts_s_lst: list[float] = dataclass_field(default_factory=list)
245
246
# Timestamp when the request was finished at the engine core.
247
finished_ts_s: Optional[float] = None
@@ -308,7 +308,7 @@ class RequestStats:
308
return self.e2e_latency_s - self.first_token_latency_s
309
310
@property
311
- def output_token_latency_s_lst(self) -> List[float]:
311
+ def output_token_latency_s_lst(self) -> list[float]:
312
if len(self.output_token_ts_s_lst) == 0:
313
return []
314
latency_s_lst = []
@@ -442,7 +442,7 @@ class EngineCoreStatsSnapshot(
442
default_factory=SchedulerStats)
443
444
# Per request stats updates.
445
- requests_stats_updates: List[RequestStatsUpdate] = msgspec_field(
445
+ requests_stats_updates: list[RequestStatsUpdate] = msgspec_field(
446
default_factory=list)
447
448
# Engine core's queue stats.
vllm/v1/utils.py
+10
-10
@@ -5,8 +5,8 @@ import os
5
import weakref
6
from collections import defaultdict
7
from collections.abc import Sequence
8
-from typing import (TYPE_CHECKING, Any, Callable, Dict, Generic, List,
9
- Optional, TypeVar, Union, overload)
8
+from typing import (TYPE_CHECKING, Any, Callable, Generic, Optional, TypeVar,
9
+ Union, overload)
10
11
import torch
12
@@ -24,7 +24,7 @@ T = TypeVar("T")
24
25
class ConstantList(Generic[T], Sequence):
26
27
- def __init__(self, x: List[T]) -> None:
27
+ def __init__(self, x: list[T]) -> None:
28
self._x = x
29
30
def append(self, item):
@@ -57,10 +57,10 @@ class ConstantList(Generic[T], Sequence):
57
...
58
59
@overload
60
- def __getitem__(self, s: slice, /) -> List[T]:
60
+ def __getitem__(self, s: slice, /) -> list[T]:
61
...
62
63
- def __getitem__(self, item: Union[int, slice]) -> Union[T, List[T]]:
63
+ def __getitem__(self, item: Union[int, slice]) -> Union[T, list[T]]:
64
return self._x[item]
65
66
@overload
@@ -71,7 +71,7 @@ class ConstantList(Generic[T], Sequence):
71
def __setitem__(self, s: slice, value: T, /):
72
...
73
74
- def __setitem__(self, item: Union[int, slice], value: Union[T, List[T]]):
74
+ def __setitem__(self, item: Union[int, slice], value: Union[T, list[T]]):
75
raise Exception("Cannot set item in a constant list")
76
77
def __delitem__(self, item):
@@ -99,7 +99,7 @@ class BackgroundProcHandle:
99
output_path: str,
100
process_name: str,
101
target_fn: Callable,
102
- process_kwargs: Dict[Any, Any],
102
+ process_kwargs: dict[Any, Any],
103
):
104
context = get_mp_context()
105
reader, writer = context.Pipe(duplex=False)
@@ -146,9 +146,9 @@ def shutdown(proc: multiprocessing.Process, input_path: str, output_path: str):
146
147
148
def bind_kv_cache(
149
- kv_caches: Dict[str, torch.Tensor],
150
- forward_context: Dict[str, "Attention"],
151
- runner_kv_caches: List[torch.Tensor],
149
+ kv_caches: dict[str, torch.Tensor],
150
+ forward_context: dict[str, "Attention"],
151
+ runner_kv_caches: list[torch.Tensor],
152
) -> None:
153
"""
154
Bind the allocated KV cache to both ModelRunner and forward context so
vllm/v1/worker/block_table.py
+2
-4
@@ -1,7 +1,5 @@
1
# SPDX-License-Identifier: Apache-2.0
2
3
-from typing import List
4
-
3
import numpy as np
4
import torch
5
@@ -40,7 +38,7 @@ class BlockTable:
38
39
def append_row(
40
self,
43
- block_ids: List[int],
41
+ block_ids: list[int],
42
row_idx: int,
43
) -> None:
44
if not block_ids:
@@ -50,7 +48,7 @@ class BlockTable:
48
self.num_blocks_per_row[row_idx] += num_blocks
49
self.block_table_np[row_idx, start:start + num_blocks] = block_ids
50
53
- def add_row(self, block_ids: List[int], row_idx: int) -> None:
51
+ def add_row(self, block_ids: list[int], row_idx: int) -> None:
52
self.num_blocks_per_row[row_idx] = 0
53
self.append_row(block_ids, row_idx)
54
vllm/v1/worker/gpu_input_batch.py
+31
-31
@@ -2,7 +2,7 @@
2
# Datastructures defining an input batch
3
4
from dataclasses import dataclass
5
-from typing import TYPE_CHECKING, Dict, List, Optional, Set, Tuple, cast
5
+from typing import TYPE_CHECKING, Optional, cast
6
7
import numpy as np
8
import torch
@@ -24,16 +24,16 @@ if TYPE_CHECKING:
24
class CachedRequestState:
25
26
req_id: str
27
- prompt_token_ids: List[int]
27
+ prompt_token_ids: list[int]
28
prompt: Optional[str]
29
- mm_inputs: List[MultiModalKwargs]
30
- mm_positions: List["PlaceholderRange"]
29
+ mm_inputs: list[MultiModalKwargs]
30
+ mm_positions: list["PlaceholderRange"]
31
sampling_params: SamplingParams
32
generator: Optional[torch.Generator]
33
34
- block_ids: List[int]
34
+ block_ids: list[int]
35
num_computed_tokens: int
36
- output_token_ids: List[int]
36
+ output_token_ids: list[int]
37
38
mrope_positions: Optional[torch.Tensor] = None
39
mrope_position_delta: Optional[int] = None
@@ -63,8 +63,8 @@ class InputBatch:
63
self.pin_memory = pin_memory
64
self.vocab_size = vocab_size
65
66
- self._req_ids: List[Optional[str]] = []
67
- self.req_id_to_index: Dict[str, int] = {}
66
+ self._req_ids: list[Optional[str]] = []
67
+ self.req_id_to_index: dict[str, int] = {}
68
69
# TODO(woosuk): This buffer could be too large if max_model_len is big.
70
# Find a way to reduce the CPU memory usage.
@@ -106,8 +106,8 @@ class InputBatch:
106
device="cpu",
107
pin_memory=pin_memory)
108
self.temperature_cpu = self.temperature_cpu_tensor.numpy()
109
- self.greedy_reqs: Set[str] = set()
110
- self.random_reqs: Set[str] = set()
109
+ self.greedy_reqs: set[str] = set()
110
+ self.random_reqs: set[str] = set()
111
112
self.top_p = torch.empty((max_num_reqs, ),
113
dtype=torch.float32,
@@ -117,7 +117,7 @@ class InputBatch:
117
device="cpu",
118
pin_memory=pin_memory)
119
self.top_p_cpu = self.top_p_cpu_tensor.numpy()
120
- self.top_p_reqs: Set[str] = set()
120
+ self.top_p_reqs: set[str] = set()
121
122
self.top_k = torch.empty((max_num_reqs, ),
123
dtype=torch.int32,
@@ -127,7 +127,7 @@ class InputBatch:
127
device="cpu",
128
pin_memory=pin_memory)
129
self.top_k_cpu = self.top_k_cpu_tensor.numpy()
130
- self.top_k_reqs: Set[str] = set()
130
+ self.top_k_reqs: set[str] = set()
131
132
self.min_p = torch.empty((max_num_reqs, ),
133
dtype=torch.float32,
@@ -137,7 +137,7 @@ class InputBatch:
137
device="cpu",
138
pin_memory=pin_memory)
139
self.min_p_cpu = self.min_p_cpu_tensor.numpy()
140
- self.min_p_reqs: Set[str] = set()
140
+ self.min_p_reqs: set[str] = set()
141
142
# Frequency penalty related data structures
143
self.frequency_penalties = torch.empty((max_num_reqs, ),
@@ -150,7 +150,7 @@ class InputBatch:
150
pin_memory=pin_memory)
151
self.frequency_penalties_cpu = \
152
self.frequency_penalties_cpu_tensor.numpy()
153
- self.frequency_penalties_reqs: Set[str] = set()
153
+ self.frequency_penalties_reqs: set[str] = set()
154
155
# Presence penalty related data structures
156
self.presence_penalties = torch.empty((max_num_reqs, ),
@@ -162,7 +162,7 @@ class InputBatch:
162
pin_memory=pin_memory)
163
self.presence_penalties_cpu = self.presence_penalties_cpu_tensor.numpy(
164
)
165
- self.presence_penalties_reqs: Set[str] = set()
165
+ self.presence_penalties_reqs: set[str] = set()
166
167
# Repetition penalty related data structures
168
self.repetition_penalties = torch.empty((max_num_reqs, ),
@@ -175,43 +175,43 @@ class InputBatch:
175
pin_memory=pin_memory)
176
self.repetition_penalties_cpu = \
177
self.repetition_penalties_cpu_tensor.numpy()
178
- self.repetition_penalties_reqs: Set[str] = set()
178
+ self.repetition_penalties_reqs: set[str] = set()
179
180
# req_index -> (min_tokens, stop_token_ids)
181
- self.min_tokens: Dict[int, Tuple[int, Set[int]]] = {}
181
+ self.min_tokens: dict[int, tuple[int, set[int]]] = {}
182
183
# lora related
184
self.request_lora_mapping = np.zeros((self.max_num_reqs, ),
185
dtype=np.int32)
186
- self.lora_id_to_request_ids: Dict[int, Set[str]] = {}
187
- self.lora_id_to_lora_request: Dict[int, LoRARequest] = {}
186
+ self.lora_id_to_request_ids: dict[int, set[str]] = {}
187
+ self.lora_id_to_lora_request: dict[int, LoRARequest] = {}
188
189
# req_index -> generator
190
# NOTE(woosuk): The indices of the requests that do not have their own
191
# generator should not be included in the dictionary.
192
- self.generators: Dict[int, torch.Generator] = {}
192
+ self.generators: dict[int, torch.Generator] = {}
193
194
- self.num_logprobs: Dict[str, int] = {}
194
+ self.num_logprobs: dict[str, int] = {}
195
# NOTE(rob): num_prompt_logprobs only includes reqs
196
# that are currently in the prefill phase.
197
- self.num_prompt_logprobs: Dict[str, int] = {}
197
+ self.num_prompt_logprobs: dict[str, int] = {}
198
199
- self.logit_bias: List[Optional[Dict[int,
199
+ self.logit_bias: list[Optional[dict[int,
200
float]]] = [None] * max_num_reqs
201
- self.has_allowed_token_ids: Set[str] = set()
201
+ self.has_allowed_token_ids: set[str] = set()
202
self.allowed_token_ids_mask: Optional[torch.Tensor] = None
203
self.allowed_token_ids_mask_cpu_tensor: Optional[torch.Tensor] = None
204
205
- self.req_output_token_ids: List[Optional[List[int]]] = []
205
+ self.req_output_token_ids: list[Optional[list[int]]] = []
206
207
# This is updated each time the batch constituents change.
208
self.sampling_metadata = self._make_sampling_metadata()
209
210
@property
211
- def req_ids(self) -> List[str]:
211
+ def req_ids(self) -> list[str]:
212
# None elements should only be present transiently
213
# while performing state updates to the batch.
214
- return cast(List[str], self._req_ids)
214
+ return cast(list[str], self._req_ids)
215
216
def add_request(
217
self,
@@ -417,7 +417,7 @@ class InputBatch:
417
self.logit_bias[i2], self.logit_bias[i1]
418
self.block_table.swap_row(i1, i2)
419
420
- def condense(self, empty_req_indices: List[int]) -> None:
420
+ def condense(self, empty_req_indices: list[int]) -> None:
421
num_reqs = self.num_reqs
422
if num_reqs == 0:
423
# The batched states are empty.
@@ -550,7 +550,7 @@ class InputBatch:
550
frequency_penalties=self.frequency_penalties[:num_reqs],
551
presence_penalties=self.presence_penalties[:num_reqs],
552
repetition_penalties=self.repetition_penalties[:num_reqs],
553
- output_token_ids=cast(List[List[int]], self.req_output_token_ids),
553
+ output_token_ids=cast(list[list[int]], self.req_output_token_ids),
554
min_tokens=self.min_tokens,
555
no_penalties=self.no_penalties,
556
logit_bias=self.logit_bias[:num_reqs],
@@ -577,7 +577,7 @@ class InputBatch:
577
578
def make_lora_inputs(
579
self, num_scheduled_tokens: np.ndarray
580
- ) -> Tuple[Tuple[int, ...], Tuple[int, ...], Set[LoRARequest]]:
580
+ ) -> tuple[tuple[int, ...], tuple[int, ...], set[LoRARequest]]:
581
"""
582
Given the num_scheduled_tokens for each request in the batch, return
583
datastructures used to activate the current LoRAs.
@@ -593,7 +593,7 @@ class InputBatch:
593
prompt_lora_mapping = tuple(req_lora_mapping)
594
token_lora_mapping = tuple(
595
req_lora_mapping.repeat(num_scheduled_tokens))
596
- active_lora_requests: Set[LoRARequest] = set(
596
+ active_lora_requests: set[LoRARequest] = set(
597
self.lora_id_to_lora_request.values())
598
599
return prompt_lora_mapping, token_lora_mapping, active_lora_requests
vllm/v1/worker/gpu_model_runner.py
+17
-17
@@ -3,7 +3,7 @@
3
import gc
4
import time
5
import weakref
6
-from typing import TYPE_CHECKING, Dict, List, Optional, Tuple, Union
6
+from typing import TYPE_CHECKING, Optional, Union
7
8
import numpy as np
9
import torch
@@ -135,9 +135,9 @@ class GPUModelRunner(LoRAModelRunnerMixin):
135
136
# Lazy initialization
137
# self.model: nn.Module # Set after load_model
138
- self.kv_caches: List[torch.Tensor] = []
138
+ self.kv_caches: list[torch.Tensor] = []
139
# req_id -> (input_id -> encoder_output)
140
- self.encoder_cache: Dict[str, Dict[int, torch.Tensor]] = {}
140
+ self.encoder_cache: dict[str, dict[int, torch.Tensor]] = {}
141
142
# Set up speculative decoding.
143
self.use_spec_decode = False
@@ -158,7 +158,7 @@ class GPUModelRunner(LoRAModelRunnerMixin):
158
)
159
160
# Request states.
161
- self.requests: Dict[str, CachedRequestState] = {}
161
+ self.requests: dict[str, CachedRequestState] = {}
162
# Persistent batch.
163
self.input_batch = InputBatch(
164
max_num_reqs=self.max_num_reqs,
@@ -274,7 +274,7 @@ class GPUModelRunner(LoRAModelRunnerMixin):
274
# then resubmitted with the same ID. In this case, we treat them as two
275
# distinct requests - clearing the cached states for the first request
276
# and handling the second as a new request.
277
- removed_req_indices: List[int] = []
277
+ removed_req_indices: list[int] = []
278
for req_id in scheduler_output.finished_req_ids:
279
req_index = self.input_batch.remove_request(req_id)
280
if req_index is not None:
@@ -305,7 +305,7 @@ class GPUModelRunner(LoRAModelRunnerMixin):
305
assert req_index is not None
306
removed_req_indices.append(req_index)
307
308
- req_ids_to_add: List[str] = []
308
+ req_ids_to_add: list[str] = []
309
# Add new requests to the cached states.
310
for new_req_data in scheduler_output.scheduled_new_reqs:
311
req_id = new_req_data.req_id
@@ -446,7 +446,7 @@ class GPUModelRunner(LoRAModelRunnerMixin):
446
def _prepare_inputs(
447
self,
448
scheduler_output: "SchedulerOutput",
449
- ) -> Tuple[FlashAttentionMetadata, torch.Tensor]:
449
+ ) -> tuple[FlashAttentionMetadata, torch.Tensor]:
450
total_num_scheduled_tokens = scheduler_output.total_num_scheduled_tokens
451
assert total_num_scheduled_tokens > 0
452
num_reqs = self.input_batch.num_reqs
@@ -774,8 +774,8 @@ class GPUModelRunner(LoRAModelRunnerMixin):
774
return
775
776
# Batch the multi-modal inputs.
777
- mm_inputs: List[MultiModalKwargs] = []
778
- req_input_ids: List[Tuple[str, int]] = []
777
+ mm_inputs: list[MultiModalKwargs] = []
778
+ req_input_ids: list[tuple[str, int]] = []
779
for req_id, encoder_input_ids in scheduled_encoder_inputs.items():
780
req_state = self.requests[req_id]
781
for input_id in encoder_input_ids:
@@ -819,8 +819,8 @@ class GPUModelRunner(LoRAModelRunnerMixin):
819
def _gather_encoder_outputs(
820
self,
821
scheduler_output: "SchedulerOutput",
822
- ) -> List[torch.Tensor]:
823
- encoder_outputs: List[torch.Tensor] = []
822
+ ) -> list[torch.Tensor]:
823
+ encoder_outputs: list[torch.Tensor] = []
824
for req_id in self.input_batch.req_ids:
825
num_scheduled_tokens = scheduler_output.num_scheduled_tokens[
826
req_id]
@@ -1022,10 +1022,10 @@ class GPUModelRunner(LoRAModelRunnerMixin):
1022
1023
def generate_draft_token_ids(
1024
self,
1025
- sampled_token_ids: List[List[int]],
1026
- ) -> List[List[int]]:
1025
+ sampled_token_ids: list[list[int]],
1026
+ ) -> list[list[int]]:
1027
# TODO(woosuk): Optimize.
1028
- draft_token_ids: List[List[int]] = []
1028
+ draft_token_ids: list[list[int]] = []
1029
for i, sampled_ids in enumerate(sampled_token_ids):
1030
num_sampled_ids = len(sampled_ids)
1031
if not num_sampled_ids:
@@ -1069,12 +1069,12 @@ class GPUModelRunner(LoRAModelRunnerMixin):
1069
self,
1070
hidden_states: torch.Tensor,
1071
scheduler_output: "SchedulerOutput",
1072
- ) -> Dict[str, Optional[LogprobsTensors]]:
1072
+ ) -> dict[str, Optional[LogprobsTensors]]:
1073
num_prompt_logprobs_dict = self.input_batch.num_prompt_logprobs
1074
if not num_prompt_logprobs_dict:
1075
return {}
1076
1077
- prompt_logprobs_dict: Dict[str, Optional[LogprobsTensors]] = {}
1077
+ prompt_logprobs_dict: dict[str, Optional[LogprobsTensors]] = {}
1078
1079
# Since prompt logprobs are a rare feature, prioritize simple,
1080
# maintainable loop over optimal performance.
@@ -1365,7 +1365,7 @@ class GPUModelRunner(LoRAModelRunnerMixin):
1365
"Hybrid models with more than one KV cache type are not "
1366
"supported yet.")
1367
1368
- kv_caches: Dict[str, torch.Tensor] = {}
1368
+ kv_caches: dict[str, torch.Tensor] = {}
1369
1370
for layer_name, layer_spec in kv_cache_config.kv_cache_spec.items():
1371
tensor_config = kv_cache_config.tensors[layer_name]
vllm/v1/worker/gpu_worker.py
+2
-2
@@ -2,7 +2,7 @@
2
"""A GPU worker class."""
3
import gc
4
import os
5
-from typing import TYPE_CHECKING, Optional, Set
5
+from typing import TYPE_CHECKING, Optional
6
7
import torch
8
import torch.distributed
@@ -243,7 +243,7 @@ class Worker(WorkerBase):
243
def remove_lora(self, lora_id: int) -> bool:
244
return self.model_runner.remove_lora(lora_id)
245
246
- def list_loras(self) -> Set[int]:
246
+ def list_loras(self) -> set[int]:
247
return self.model_runner.list_loras()
248
249
def pin_lora(self, lora_id: int) -> bool:
vllm/v1/worker/lora_model_runner_mixin.py
+8
-9
@@ -4,7 +4,6 @@ Define LoRA functionality mixin for model runners.
4
"""
5
6
from contextlib import contextmanager
7
-from typing import Set, Tuple
7
8
import numpy as np
9
import torch.nn as nn
@@ -57,9 +56,9 @@ class LoRAModelRunnerMixin:
56
)
57
return self.lora_manager.create_lora_manager(model)
58
60
- def _set_active_loras(self, prompt_lora_mapping: Tuple[int, ...],
61
- token_lora_mapping: Tuple[int, ...],
62
- lora_requests: Set[LoRARequest]) -> None:
59
+ def _set_active_loras(self, prompt_lora_mapping: tuple[int, ...],
60
+ token_lora_mapping: tuple[int, ...],
61
+ lora_requests: set[LoRARequest]) -> None:
62
if not self.lora_manager:
63
raise RuntimeError("LoRA is not enabled.")
64
@@ -74,10 +73,10 @@ class LoRAModelRunnerMixin:
73
def set_active_loras(self, input_batch: InputBatch,
74
num_scheduled_tokens: np.ndarray) -> None:
75
77
- prompt_lora_mapping: Tuple[int, ...] # of size input_batch.num_reqs
78
- token_lora_mapping: Tuple[int,
76
+ prompt_lora_mapping: tuple[int, ...] # of size input_batch.num_reqs
77
+ token_lora_mapping: tuple[int,
78
...] # of size np.sum(num_scheduled_tokens)
80
- lora_requests: Set[LoRARequest]
79
+ lora_requests: set[LoRARequest]
80
prompt_lora_mapping, token_lora_mapping, lora_requests = \
81
input_batch.make_lora_inputs(num_scheduled_tokens)
82
return self._set_active_loras(prompt_lora_mapping, token_lora_mapping,
@@ -105,7 +104,7 @@ class LoRAModelRunnerMixin:
104
num_scheduled_tokens)
105
106
# Make dummy lora requests
108
- lora_requests: Set[LoRARequest] = {
107
+ lora_requests: set[LoRARequest] = {
108
LoRARequest(lora_name=f"warmup_{lora_id}",
109
lora_int_id=lora_id,
110
lora_path="/not/a/real/path")
@@ -143,7 +142,7 @@ class LoRAModelRunnerMixin:
142
raise RuntimeError("LoRA is not enabled.")
143
return self.lora_manager.pin_adapter(lora_id)
144
146
- def list_loras(self) -> Set[int]:
145
+ def list_loras(self) -> set[int]:
146
if not self.lora_manager:
147
raise RuntimeError("LoRA is not enabled.")
148
return self.lora_manager.list_adapters()
\ No newline at end of file
vllm/v1/worker/tpu_model_runner.py
+12
-12
@@ -1,6 +1,6 @@
1
# SPDX-License-Identifier: Apache-2.0
2
import time
3
-from typing import TYPE_CHECKING, Dict, List, Optional, Tuple, cast
3
+from typing import TYPE_CHECKING, Optional, cast
4
from unittest.mock import patch
5
6
import numpy as np
@@ -95,13 +95,13 @@ class TPUModelRunner:
95
)
96
97
# Request states.
98
- self.requests: Dict[str, CachedRequestState] = {}
98
+ self.requests: dict[str, CachedRequestState] = {}
99
100
# req_id -> (input_id -> encoder_output)
101
- self.encoder_cache: Dict[str, Dict[int, torch.Tensor]] = {}
101
+ self.encoder_cache: dict[str, dict[int, torch.Tensor]] = {}
102
103
# KV caches for forward pass
104
- self.kv_caches: List[Tuple[torch.Tensor, torch.Tensor]] = []
104
+ self.kv_caches: list[tuple[torch.Tensor, torch.Tensor]] = []
105
106
# Cached torch/numpy tensor
107
# The pytorch tensor and numpy array share the same buffer.
@@ -171,7 +171,7 @@ class TPUModelRunner:
171
# then resubmitted with the same ID. In this case, we treat them as two
172
# distinct requests - clearing the cached states for the first request
173
# and handling the second as a new request.
174
- removed_req_indices: List[int] = []
174
+ removed_req_indices: list[int] = []
175
for req_id in scheduler_output.finished_req_ids:
176
req_index = self.input_batch.remove_request(req_id)
177
if req_index is not None:
@@ -194,7 +194,7 @@ class TPUModelRunner:
194
assert req_index is not None
195
removed_req_indices.append(req_index)
196
197
- req_ids_to_add: List[str] = []
197
+ req_ids_to_add: list[str] = []
198
# Add new requests to the cached states.
199
for new_req_data in scheduler_output.scheduled_new_reqs:
200
req_id = new_req_data.req_id
@@ -453,7 +453,7 @@ class TPUModelRunner:
453
selected_token_ids = torch.argmax(logits, dim=-1, keepdim=True)
454
455
# Then, let's update the cache state.
456
- request_seq_lens: List[Tuple[int, CachedRequestState, int]] = []
456
+ request_seq_lens: list[tuple[int, CachedRequestState, int]] = []
457
for i, req_id in zip(range(num_reqs), self.input_batch.req_ids):
458
assert req_id is not None
459
req_state = self.requests[req_id]
@@ -473,9 +473,9 @@ class TPUModelRunner:
473
assert all(
474
req_id is not None for req_id in
475
self.input_batch.req_ids[:num_reqs]), "req_ids contains None"
476
- req_ids = cast(List[str], self.input_batch.req_ids[:num_reqs])
476
+ req_ids = cast(list[str], self.input_batch.req_ids[:num_reqs])
477
478
- prompt_logprobs_dict: Dict[str, Optional[LogprobsTensors]] = {}
478
+ prompt_logprobs_dict: dict[str, Optional[LogprobsTensors]] = {}
479
for req_id in self.input_batch.req_ids[:num_reqs]:
480
prompt_logprobs_dict[req_id] = None
481
@@ -612,7 +612,7 @@ class TPUModelRunner:
612
"Hybrid models with more than one KV cache type are not "
613
"supported yet.")
614
615
- kv_caches: Dict[str, torch.Tensor] = {}
615
+ kv_caches: dict[str, torch.Tensor] = {}
616
617
for layer_name, layer_spec in kv_cache_config.kv_cache_spec.items():
618
tensor_config = kv_cache_config.tensors[layer_name]
@@ -649,7 +649,7 @@ class ModelWrapperV1(nn.Module):
649
self,
650
token_ids: torch.Tensor,
651
position_ids: torch.Tensor,
652
- kv_caches: List[Tuple[torch.Tensor, torch.Tensor]],
652
+ kv_caches: list[tuple[torch.Tensor, torch.Tensor]],
653
) -> torch.Tensor:
654
"""Executes the forward pass of the model and samples the next token.
655
@@ -667,7 +667,7 @@ class ModelWrapperV1(nn.Module):
667
# [num_kv_heads, num_blocks, block_size, head_size]. To make it
668
# work, we need to flatten the first three dimensions and modify
669
# the slot_mapping accordingly.
670
- # kv_caches: List[Tuple[torch.Tensor, torch.Tensor]]
670
+ # kv_caches: list[tuple[torch.Tensor, torch.Tensor]]
671
num_kv_heads, num_blocks, block_size, _ = kv_caches[0][0].shape
672
slot_mapping = attn_metadata.slot_mapping
673
slot_mapping = slot_mapping.flatten()
vllm/v1/worker/tpu_worker.py
+3
-3
@@ -1,7 +1,7 @@
1
# SPDX-License-Identifier: Apache-2.0
2
"""A TPU worker class."""
3
import os
4
-from typing import Dict, List, Optional
4
+from typing import Optional
5
6
import torch
7
import torch.distributed
@@ -103,7 +103,7 @@ class TPUWorker:
103
self.model_runner = TPUModelRunner(self.vllm_config, self.device)
104
105
def determine_available_memory(self) -> int:
106
- kv_caches: Dict[str, torch.Tensor] = {}
106
+ kv_caches: dict[str, torch.Tensor] = {}
107
kv_cache_spec = self.model_runner.get_kv_cache_spec()
108
for layer_name, layer_spec in kv_cache_spec.items():
109
if isinstance(layer_spec, FullAttentionSpec):
@@ -118,7 +118,7 @@ class TPUWorker:
118
else:
119
raise NotImplementedError
120
121
- runner_kv_caches: List[torch.Tensor] = []
121
+ runner_kv_caches: list[torch.Tensor] = []
122
bind_kv_cache(
123
kv_caches,
124
self.vllm_config.compilation_config.static_forward_context,