Быстрый старт с обменом моделей llama для локальных LLM, совместимых с OpenAI

Горячая замена локальных LLM без изменения клиентов.

Содержимое страницы

Вскоре вы уже управляете несколькими инструментами: vLLM, llama.cpp и другими — каждый стек работает на своём собственном порту. При этом все последующие звенья цепочки по-прежнему ожидают один базовый URL /v1; иначе вам придётся постоянно перенастраивать порты, профили и разовые скрипты. llama-swap — это прокси для /v1, который размещается перед этими стеками.

llama-swap предоставляет единую точку входа, совместимую с OpenAI и Anthropic, с использованием YAML-файла, который сопоставляет каждое имя model с командой запуска соответствующего вышестоящего сервера (upstream). Запросите модель, и прокси запустит её или переключит на неё; при нехватке VRAM или необходимости совместного существования нескольких моделей настройте TTL и группы. В этом руководстве рассмотрены пути установки, практический config.yaml, HTTP-интерфейс и режимы сбоя, которые возникают при добавлении потоковой передачи и обратных прокси.

llama swap llm infographic Для более широкого сравнения вариантов хостинга LLM см. Хостинг LLM в 2026 году: локальные, self-hosted и облачные инфраструктуры в сравнении.

Обзор коммутатора моделей llama-swap для локальных LLM API с совместимостью с OpenAI

llama-swap — это легкий прокси-сервер, построенный на простой операционной модели: один бинарный файл, один YAML-конфигурационный файл, без зависимостей. Он написан на Go, что означает наличие одного статического бинарного файла рядом с остальной частью стека — не требуется Python-рантайм или настольное приложение. Он размещается перед любым вышестоящим сервером (upstream), совместимым с OpenAI и Anthropic, выступая слоем для переключения моделей.

Концептуально это отвечает на очень практичный вопрос, возникающий в локальных LLM-стеках:

Как переключать модели с клиентом, совместимым с OpenAI? С llama-swap вы продолжаете использовать обычные запросы /v1/..., но меняете запрашиваемую model. llama-swap считывает это значение model, загружает соответствующую конфигурацию сервера и, если «неверный» вышестоящий сервер запущен, заменяет его на правильный.

Несколько деталей дизайна имеют значение для конфигураций, приближенных к продакшену:

llama-swap распространяется под лицензией MIT и не собирает телеметрию — это всё равно стоит проверять для любого хоста, который обрабатывает реальные промпты. Он создан для запросной загрузки бэкендов, таких как llama.cpp, vLLM, Whisper и stable-diffusion.cpp, а не для привязки вас к одному конкретному движку инференса. По умолчанию (без специального группирования) он выполняет одну модель за раз: запросите другую model, и он остановит текущий вышестоящий сервер и запустит правильный. Для более чем одной резидентной модели или более тонкого управления совместимостью настройте groups.

Вот ментальная модель, которая, как правило, наиболее полезна разработчикам:

flowchart LR C[Ваше приложение или SDK\nКлиент, совместимый с OpenAI] -->|/v1/chat/completions\nmodel = qwen-coder| LS[Прокси llama-swap\nединственная конечная точка] LS -->|запускает или маршрутизирует на| U1[Вышестоящий сервер A\nllama-server] LS -->|запускает или маршрутизирует на| U2[Вышестоящий сервер B\nСервер OpenAI от vLLM] LS --> M[Конечные точки управления\nrunning, unload, events, metrics]

Именно поэтому прокси для переключения моделей отличается от «просто запуска модели»: это оркестрация и маршрутизация поверх одного или нескольких серверов инференса.

Сравнение llama-swap, Ollama, LM Studio и llama.cpp server

Все четыре варианта могут предоставить вам «локальный LLM API», но они оптимизированы для разных рабочих процессов. Самый быстрый способ выбора — определиться, нужен ли вам рантайм (загрузка + выполнение модели) или роутер/прокси (переключение + оркестрация между рантаймами).

llama-swap llama-swap делает упор на то, чтобы быть прозрачным прокси, который поддерживает конечные точки, совместимые с OpenAI (включая /v1/chat/completions, /v1/completions, /v1/embeddings и /v1/models), и маршрутизирует запросы на правильный вышестоящий сервер на основе запрошенной модели. Он также предоставляет операционные конечные точки, не связанные с инференсом, такие как /running, /logs/stream и веб-интерфейс на /ui.

Ollama Ollama предоставляет собственный HTTP API (POST /api/chat, POST /api/generate и стандартный локальный порт по умолчанию 11434). keep_alive контролирует, как долго модель остается загруженной, включая 0 для немедленной выгрузки. Он подходит для пользователей, которые хотят скачать модель и начать чат с минимальной настройкой. llama-swap подходит для команд по каждой модели, смешанных бэкендов и одного URL, совместимого с OpenAI, для всех клиентов — оркестрация vLLM рядом с llama-server с различными флагами для каждой модели выходит за рамки того, на что нацелен Ollama.

LM Studio LM Studio — это настольное приложение с локальным API-сервером из вкладки Developer (localhost или LAN), включая режимы совместимости с OpenAI и совместимости с Anthropic, а также lms server start из терминала. Он подходит для цикла ориентированного на GUI: просматривайте модели, кликайте, тестируйте. llama-swap подходит для роли серверного типа: YAML, надзор за процессами, смешанные вышестоящие серверы, без сессии рабочего стола.

llama.cpp server llama-server предоставляет /v1/completions, /v1/chat/completions, /v1/responses, и стандартный паттерн заключается в том, чтобы направить клиента OpenAI на него через base_url. Установка этого сервера и флага, которые он действительно поддерживает, рассмотрены в Быстрый старт с llama.cpp. llama.cpp также поставляется с режимом роутера: запустите llama-server как роутер, --models-dir, затем POST /models/load и POST /models/unload, чтобы управлять моделями GGUF без отдельного прокси. Для полного руководства по настройке см. Режим роутера llama-server: динамическое переключение моделей без перезапусков. Если все модели находятся под одним роутером llama.cpp, дополнительный прокси часто не нужен. Когда llama.cpp должен работать рядом с vLLM или другими серверами, совместимыми с OpenAI, llama-swap предоставляет один интерфейс /v1 и множество процессов за ним.

Для похожих решений хостинга, совместимых с OpenAI, см. QuickStart для LocalAI: Запуск локальных LLM с совместимостью с OpenAI или QuickStart для SGLang: Установка, настройка и обслуживание LLM через OpenAI API

Установка коммутатора моделей llama-swap с Docker, Homebrew, WinGet или бинарными файлами

Linux, macOS и Windows поддерживаются на равных основаниях: Docker, Homebrew, WinGet, бинарные файлы GitHub или сборка из исходного кода. Популярные варианты: Docker на серверах без GUI, Homebrew или WinGet на рабочих станциях, автономные бинарные файлы, если объём установки должен быть минимальным.

Установка через Docker

Загрузите образ, соответствующий вашему оборудованию. Образы тесно отслеживают вышестоящие версии (ночные сборки) и поддерживают CUDA, Vulkan, Intel, MUSA и CPU — выберите тот, который соответствует вашему фактическому способу ускорения, а не «latest» по привычке.

# Примеры загрузки образов для платформ
docker pull ghcr.io/mostlygeek/llama-swap:cuda
docker pull ghcr.io/mostlygeek/llama-swap:vulkan
docker pull ghcr.io/mostlygeek/llama-swap:intel
docker pull ghcr.io/mostlygeek/llama-swap:musa
docker pull ghcr.io/mostlygeek/llama-swap:cpu

Если возможно, предпочитайте варианты образов non-root: меньше сожалений, если граница контейнера когда-либо нарушится.

Установка через Homebrew

На macOS и Linux используйте tap и установите:

brew tap mostlygeek/llama-swap
brew install llama-swap
llama-swap --config path/to/config.yaml --listen localhost:8080

Установка через WinGet

На Windows:

winget install llama-swap
winget upgrade llama-swap

Предварительно собранные бинарные файлы и релизы

В GitHub Releases доступны бинарные файлы для Linux, macOS, Windows и FreeBSD, если вы не хотите использовать менеджер пакетов. Номера релизов меняются быстро (например, v198, v197 в начале 2026 года) — фиксируйте версию в автоматизации, а не используйте «то, что было вчера».

Настройка llama-swap с config.yaml для переключения моделей, TTL и групп

Всё в llama-swap управляется конфигурацией. Минимальная жизнеспособная конфигурация — это просто словарь models: и cmd для каждой модели, часто запускающий llama-server с подстановкой ${PORT} для каждой модели.

Система конфигурации идет гораздо дальше, чем просто «запуск процесса», и несколько вариантов стоит понять заранее, так как они непосредственно отвечают на частые вопросы (автовывгрузка, безопасность и клиенты, полагающиеся на /v1/models).

Глобальные настройки, которые вы действительно будете использовать

healthCheckTimeout — это время, которое llama-swap ждет, пока модель не станет здоровой после запуска (по умолчанию 120с, минимум 15с). Для загрузки моделей в несколько ГБ на медленных дисках увеличьте это значение, прежде чем винить прокси. globalTTL — это секунды простоя перед автовыгрузкой; по умолчанию 0 означает «никогда не выгружать», если вы не установите иначе — явно выбирайте TTL для чего-либо, выходящего за рамки учебной конфигурации, чтобы VRAM не заполнялась забытыми моделями. startPort задает начальное значение для макроса ${PORT} (по умолчанию 5800); присвоение детерминировано по алфавитному ID модели, что является преимуществом при отладке «кто забрал какой порт» и ловушкой, если вы небрежно переименовываете модели. includeAliasesInList определяет, отображаются ли алиасы как отдельные строки в /v1/models; включите, если ваш UI предлагает только перечисленные модели. apiKeys контролирует доступ ко всему, что доступно вне localhost: Basic, Bearer или x-api-key. llama-swap удаляет эти заголовки перед пересылкой, чтобы в логах вышестоящих серверов было менее вероятно сохранение секретов клиентов.

Настройки на уровне моделей, обеспечивающие эргономику продакшена

Для каждой модели cmd — единственное обязательное поле. proxy по умолчанию http://localhost:${PORT} — это цель пересылки для вышестоящего сервера этой модели. checkEndpoint по умолчанию /health; установите "none", если у бэкенда нет маршрута здоровья или холодный запуск превышает время, которое вы готовы ждать — не оставляйте сломанный /health и не удивляйтесь, почему ничего не достигает состояния ready. ttl: -1 наследует globalTTL, 0 никогда не выгружает, N > 0 выгружает после N секунд простоя — используйте TTL по модели, если одна модель должна оставаться дольше, а другая должна исчезнуть быстро. aliases и useModelName поддерживают стабильные имена, ориентированные на клиента, удовлетворяя требованиям вышестоящих серверов, которые требуют конкретного идентификатора. cmdStop не является необязательным для контейнеров: сопоставьте его с docker stop (или эквивалентом); без него вы получите POSIX SIGTERM / Windows taskkill для любого PID, запущенного llama-swap — нормально для «голого» бинарного файла, но неправильно для имени контейнера. concurrencyLimit ограничивает параллельные запросы на модель с HTTP 429 при превышении — установите его, если вы предпочитаете сбрасывать нагрузку, а не ждать в очереди вечно.

groups охватывают совместное существование (swap, exclusive) и модели всегда включенные (persistent). Хуки могут предварительно загружать при запуске; если вы предварительно загружаете несколько моделей одновременно без группы, ожидайте, что они будут конкурировать — сначала определите группу, чтобы предварительная загрузка соответствовала тому, как вы хотите, чтобы модели разделяли GPU.

Минимальный пример config.yaml для llama.cpp и vLLM

Этот пример направлен на то, чтобы быть «достаточно простым» для иллюстрации лучших практик: TTL по умолчанию, явная проверка здоровья, стабильные алиасы и группа, которая сохраняет небольшую «всегда включенную» модель запущенной, пока более крупные чат-модели переключаются.

# config.yaml
healthCheckTimeout: 180
globalTTL: 900            # 15 минут простоя, затем выгрузка
includeAliasesInList: true
startPort: 5800

# Необязательно, но рекомендуется для чего-либо, выходящего за рамки разработки на localhost
apiKeys:
  - "${env.LLAMASWAP_API_KEY}"

models:
  llama-chat:
    cmd: |
      llama-server --port ${PORT} --model /models/llama-chat.gguf
      --ctx-size 8192
    aliases:
      - "llama-chat-latest"
    # Использует значения по умолчанию:
    # proxy: http://localhost:${PORT}
    # checkEndpoint: /health
    # ttl: -1 (наследует globalTTL)

  qwen-coder:
    cmd: |
      llama-server --port ${PORT} --model /models/qwen-coder.gguf
      --ctx-size 8192
    aliases:
      - "qwen-coder-latest"

  vllm-coder:
    # Иллюстративный паттерн: управление контейнеризованным сервером, совместимым с OpenAI
    proxy: "http://127.0.0.1:${PORT}"
    cmd: |
      docker run --name ${MODEL_ID} --init --rm -p ${PORT}:8000 vllm/vllm-openai:latest
    cmdStop: docker stop ${MODEL_ID}
    checkEndpoint: "none"
    ttl: 0                 # никогда не выгружать автоматически (например, держать на GPU)

groups:
  chat-models:
    swap: true
    exclusive: true
    members: ["llama-chat", "qwen-coder"]

  always-on:
    persistent: true
    swap: false
    exclusive: false
    members: ["vllm-coder"]

Ничто из этого не является декоративным: cmd управляет процессом, proxy/checkEndpoint/ttl контролируют маршрутизацию и жизненный цикл, cmdStop — это то, что заставляет вышестоящие серверы на базе Docker действительно останавливаться, а groups — это то, что разделяет «одна большая модель за раз» и «эти две чат-модели могут сосуществовать, пока сервер эмбеддингов остается закрепленным».

Запуск и переключение моделей через конечные точки с совместимостью с OpenAI

Когда llama-swap работает, вы взаимодействуете с ним, как с любой другой конечной точкой, совместимой с OpenAI. Интерфейс API включает основные конечные точки, такие как /v1/chat/completions, /v1/completions, /v1/embeddings и /v1/models, и llama-swap использует запрошенную model, чтобы решить, какой вышестоящий сервер запустить и куда маршрутизировать.

Практический поток быстрого старта:

# 1) Запуск llama-swap
llama-swap --config ./config.yaml --listen localhost:8080
# 2) Открытие доступных моделей
curl http://localhost:8080/v1/models

Список моделей является функцией управления первого класса и включает поведение, такое как сортировка по ID, исключение моделей unlisted и опциональное включение алиасов.

# 3) Выполнение запроса чат-заполнения для конкретной модели
curl http://localhost:8080/v1/chat/completions \
  -H "Content-Type: application/json" \
  -H "Authorization: Bearer ${LLAMASWAP_API_KEY}" \
  -d '{
    "model": "qwen-coder",
    "messages": [{"role":"user","content":"Write a TypeScript function that retries fetch with backoff."}]
  }'

Если вы теперь повторите вызов с "model": "llama-chat", llama-swap переключит процессы вышестоящих серверов (если ваша конфигурация групп не позволяет им сосуществовать), потому что он извлекает запрошенную модель из запроса и загружает соответствующую конфигурацию сервера.

Если вы используете SDK, направьте клиент на http://localhost:8080/v1 — тот же трюк, что и при нацеливании Python-библиотеки OpenAI на llama-server, только стабильный URL теперь llama-swap, а поле model выбирает вышестоящий сервер.

from openai import OpenAI

client = OpenAI(
    base_url="http://localhost:8080/v1",
    api_key="sk-your-llamaswap-key"
)

resp = client.chat.completions.create(
    model="qwen-coder",
    messages=[{"role": "user", "content": "Explain the difference between mutexes and semaphores."}],
)
print(resp.choices[0].message.content)

Чтобы подогреть модель перед первым реальным запросом (спрятать задержку холодного старта), используйте /upstream/<model> — он автоматически загружает, если необходимо, и пересылает прямо на этот вышестоящий сервер. Простой способ убедиться, что веса резидентны, перед бенчмарком или скриптовым тестом.

Управление и мониторинг llama-swap через конечные точки API управления и SSE-события

llama-swap — это не просто «прокси»; он также предоставляет операционные конечные точки управления, которые позволяют вам строить инструменты вокруг жизненного цикла моделей и наблюдаемости.

Проверка того, что запущено GET /running возвращает состояние выполнения для загруженных моделей, включая значения состояния, такие как ready, starting, stopping, stopped и shutdown.

curl http://localhost:8080/running

Выгрузка моделей для освобождения VRAM Чтобы немедленно выгрузить всё, используйте конечную точку с версией API POST /api/models/unload. Чтобы выгрузить одну модель (по ID или алиасу), используйте POST /api/models/unload/<model>. Устаревший GET /unload существует для обратной совместимости.

# выгрузить все
curl -X POST http://localhost:8080/api/models/unload

# выгрузить одну модель
curl -X POST http://localhost:8080/api/models/unload/qwen-coder

Используйте эти конечные точки, когда VRAM нужно вернуть сейчас, вместо ожидания TTL — бенчмарки, быстрые переключения моделей или после загрузки чекпоинта намного большего, чем предполагалось.

Потоковая передача живых событий через SSE GET /api/events устанавливает поток Server-Sent Events и предназначен для обновлений в реальном времени, включая изменения статуса моделей, логи, метрики и количество запросов в работе.

curl -N http://localhost:8080/api/events

SSE и потоковая передача токенов ломаются, если любой промежуточный буферизирует — отключите буферизацию в nginx (или эквиваленте) для /api/events и /v1/chat/completions. llama-swap устанавливает X-Accel-Buffering: no на SSE; отключите буферизацию в прокси тоже — заголовки не являются заменой правильной конфигурации прокси.

Метрики и захват запросов GET /api/metrics возвращает метрики использования токенов, с сохранением в памяти, контролируемым metricsMaxInMemory (по умолчанию 1000). GET /api/captures/<id> может получать полные захваты запроса/ответа, но только когда настроено captureBuffer > 0.

Логи и веб-интерфейс

llama-swap предоставляет /ui для веб-интерфейса, а также операционные конечные точки логов, такие как /logs и /logs/stream для мониторинга в реальном времени.

llama-swap web UI for switching models

Если вы включите apiKeys, предполагайте защиту в несколько слоев: /health и части /ui остаются доступными без ключа — нормально для локальных границ доверия, не нормально, если хост находится в общей сети. Поместите llama-swap за чем-то, что обеспечивает вашу реальную политику; встроенная аутентификация предназначена для того, чтобы поддерживать порядочность случайных клиентов, а не для публичного многоагентного API.

Устранение неполадок при переключении моделей llama-swap в продакшене

Большинство проблем с llama-swap попадают в небольшой набор операционных категорий: потоковая передача через обратный прокси, проверки здоровья во время холодных запусков, порты и жизненный цикл процессов, и аутентификация.

Потоковая передача ломается за nginx или другим обратным прокси nginx с удовольствием буферизует ваши SSE и потоковые завершения. Отключите proxy_buffering (и proxy_cache) для /api/events и /v1/chat/completions. llama-swap издает X-Accel-Buffering: no на SSE, что помогает — но исправьте прокси всё равно.

Модель никогда не становится готовой По умолчанию, checkEndpoint для каждой модели — /health и должен возвращать HTTP 200, чтобы процесс считался готовым. Вы можете установить checkEndpoint на другой путь или на "none", чтобы полностью отключить проверки здоровья. Если загрузка больших моделей занимает больше времени, увеличьте healthCheckTimeout (по умолчанию 120с) или используйте настроенные проверки здоровья для вашего конкретного вышестоящего сервера.

Переключение моделей оставляет старый контейнер запущенным Если вышестоящий сервер — Docker или Podman, установите cmdStop — иначе llama-swap остановит обертку-процесс, а контейнер будет продолжать жевать VRAM на фоне.

Я получаю ответы 401 после включения безопасности Когда настроены apiKeys, llama-swap требует действительный ключ и принимает три метода (Basic auth, Bearer token, x-api-key). Он также удаляет заголовки аутентификации перед пересылкой на вышестоящий сервер.

Я получаю 429 Too Many Requests concurrencyLimit возвращает 429 при превышении — это по дизайну. Повысьте лимит, если вы недоукомплектовали его, или снизьте лимит, если не планировали троттлинг.

Конфликты портов или странные проблемы маршрутизации Избегайте захардкоженных портов в cmd; используйте ${PORT} и переместите startPort, если 5800+ конфликтует с чем-то другим. Помните, что порты присваиваются в алфавитном порядке по ID модели — переименуйте модель, и отображение портов сместится.

Чек-лист операционной отладки /running для истины, /logs/stream, когда запуск неясен, POST /api/models/unload, когда VRAM нужно вернуть сейчас. Эта тройка покрывает большинство сессий «почему GPU заполнен».

Подписаться

Получайте новые материалы про системы, инфраструктуру и AI engineering.