vLLM регулярно советуют как «более быстрый способ запускать модели». Формулировка вводит в заблуждение, и из-за неё люди тратят вечер на установку, чтобы обнаружить, что стало не быстрее, а хуже.
Правильная формулировка: vLLM даёт больше суммарной пропускной способности при многих одновременных запросах. Для одного человека, задающего вопросы по очереди, он не даёт ничего — и требует при этом больше видеопамяти, чем привычные инструменты.
Скажем это прямо в начале, чтобы вы не устанавливали его зря.
#Что понадобится
- Linux и видеокарта NVIDIA достаточно свежего поколения. Поддержка AMD существует, но она менее обкатана. Точные требования к вычислительным возможностям карты сверяйте с документацией проекта — они меняются между версиями.
- Заметно больше видеопамяти, чем для той же модели в GGUF. vLLM работает с весами в формате экосистемы обучения, а не с квантованными файлами GGUF; поддержка последних есть, но ограниченная. Модель класса 7B в половинной точности — это около 15 ГБ только весов.
- Python-окружение и готовность администрировать сервис.
#Шаг 1. Понять, откуда берётся выигрыш
Скорость генерации ограничена чтением весов модели из памяти: чтобы выдать один токен, движок читает всю модель. Это верно для одного запроса.
Теперь ключевая деталь: если запросов несколько и они обрабатываются вместе, веса читаются один раз на всю группу. Десять пользователей — десять токенов за то же чтение. Именно на этом стоит вся идея пакетной обработки.
vLLM добавляет к этому две вещи. Непрерывный батчинг — новые запросы подсаживаются в текущую группу, не дожидаясь, пока закончатся старые. И постраничное управление KV-кэшем — память под контексты разных запросов выделяется блоками, без резервирования максимума под каждый, что позволяет держать в работе больше одновременных сессий.
#Шаг 2. Посмотреть на границу спроса
Таблица ниже — не замер, а следствие описанного принципа: суммарная пропускная способность растёт почти линейно с числом одновременных запросов, пока движок не упрётся в вычисления, а скорость каждого отдельного пользователя при этом постепенно снижается. Точные значения зависят от модели и карты, и их нужно замерять у себя.
| Одновременных запросов | Скорость на пользователя | Суммарно |
|---|---|---|
| 1 | X | X |
| 4 | ~0,9X | ~3,6X |
| 10 | ~0,8X | ~8X |
| 32 | ~0,5X | ~16X |
Что здесь смотреть: разрыв между колонками. При одном пользователе они совпадают — и это ровно тот случай, когда vLLM не даёт ничего, потому что складывать нечего. При десяти одновременных запросах суммарная пропускная способность в восемь раз выше, чем у инструмента, обрабатывающего запросы по очереди.
Отсюда граница: vLLM начинает окупаться примерно с трёх-пяти постоянно активных пользователей или при пакетной обработке большого объёма текстов. Ниже этого порога он проигрывает по всем статьям: требует больше памяти, сложнее в установке и не даёт выигрыша.
Второе наблюдение из таблицы: скорость отдельного пользователя падает. При тридцати двух одновременных запросах каждый получает вдвое меньше токенов в секунду. Если у вас интерактивный сервис, это надо учитывать: суммарная пропускная способность и отзывчивость — конкурирующие величины. Что считать приемлемой скоростью для человека — в материале о том, сколько токенов в секунду это нормально.
#Шаг 3. Запустить
pip install vllm
vllm serve Qwen/Qwen2.5-7B-Instruct --max-model-len 8192 --gpu-memory-utilization 0.9
Сервер поднимает OpenAI-совместимый эндпоинт на порту 8000. Параметр --max-model-len задаёт максимальную длину контекста, --gpu-memory-utilization — долю видеопамяти, которую движок займёт под себя сразу при старте.
Второй параметр стоит понимать: vLLM резервирует память заранее, а не по мере надобности. Со значением 0,9 он займёт 90% карты в момент запуска и будет держать их всё время работы. Это правильное поведение для выделенного сервера и неприемлемое для рабочей машины.
Для нескольких видеокарт добавляется тензорный параллелизм:
vllm serve Qwen/Qwen2.5-7B-Instruct --tensor-parallel-size 2
В отличие от разделения по слоям, здесь карты действительно работают одновременно. Разбор разницы между режимами — в материале о двух видеокартах под одну модель.
#Проверка результата
Сервер отвечает:
curl http://localhost:8000/v1/models
Одиночный запрос проходит:
curl -s http://localhost:8000/v1/chat/completions -H "Content-Type: application/json" -d '{"model":"Qwen/Qwen2.5-7B-Instruct","messages":[{"role":"user","content":"Привет"}]}'
Выигрыш от батчинга виден. Это главная проверка, и без неё вся установка не имеет смысла. Запустите десять запросов параллельно и сравните суммарное время с временем десяти последовательных запросов. Если разница невелика — батчинг не работает, и проще вернуться к прежнему инструменту.
Корректная методика замера, включая прогрев и повторы, описана в материале о том, как измерить скорость локальной модели правильно.
#Что может пойти не так
Не хватает видеопамяти на модель, которая раньше запускалась. Ожидаемо: в GGUF она была квантована вчетверо, здесь — нет. Либо берите модель меньше, либо используйте поддерживаемые форматы квантованных весов, либо оставайтесь на прежнем инструменте.
Сервер занял всю карту, и больше ничего не работает. Уменьшите долю резервируемой памяти. Для машины, которая используется и для другого, значение выше 0,7 обычно неприемлемо.
Модель не поддерживается. Список поддерживаемых архитектур в vLLM отличается от списка в llama.cpp, причём в обе стороны. Проверяйте до установки, а не после.
Батчинг не даёт выигрыша. Скорее всего, запросы идут не одновременно, а по очереди: клиент отправляет следующий после получения предыдущего. Складывать нечего — движку нужны параллельные соединения.
Установка падает на сборке зависимостей. Это типично: пакет тесно связан с версиями драйвера и вычислительной библиотеки. Изолированное окружение и точное следование документации проекта здесь обязательны.
#Частые вопросы
#Нужен ли vLLM одному пользователю?
Нет. Для одного человека он не даёт ни скорости, ни удобства, а требует больше памяти и внимания. Обычный локальный сервер решает задачу лучше — как его поднять, описано в материале о llama.cpp server как своём OpenAI-совместимом эндпоинте.
#С какого числа пользователей он оправдан?
Ориентировочно с трёх-пяти постоянно активных или при пакетной обработке, где сотни и тысячи запросов идут подряд и латентность отдельного запроса неважна. Точная граница зависит от модели и карты.
#Работает ли vLLM с файлами GGUF?
Поддержка есть, но она ограниченная и не является основным сценарием. Штатный путь — веса в формате экосистемы обучения, при необходимости в поддерживаемых форматах квантизации. Если вы держите коллекцию GGUF, переход потребует перекачивать модели.
#Можно ли запустить vLLM на карте с 8 или 12 гигабайтами?
Формально да, для небольших моделей и с квантованными весами. Практически это неудобно: движок рассчитан на выделенную карту с запасом памяти, и на потребительской карте вы упрётесь в ограничения раньше, чем получите выигрыш.
#Чем vLLM отличается от простого сервера с несколькими слотами?
Непрерывным батчингом и постраничным управлением памятью контекстов. Простые серверы тоже умеют несколько слотов, но делят контекст между ними статически и не подсаживают новые запросы в текущую группу, поэтому масштабируются хуже.
#Что выбрать для сервиса на несколько человек?
Зависит от того, сколько их и насколько равномерна нагрузка. Общая архитектура такого решения, включая вопросы доступа и надёжности, разобрана в материале о том, как поднять свой ИИ-сервис.