add heartbeat check and auto migration
MixMaaS 是面向「MaaS 平台中模型混部的资源编排与性能优化」的原型系统,基于开源推理引擎 vLLM 构建统一控制面(Manager)与节点执行面(Node Agent),在不修改 vLLM 内部推理逻辑的前提下,解决多模型并发服务中的显存预算、部署位置选择、运行状态观测、请求路由与异常回收问题,并提供 Web 门户与 Grafana 监控形成「观测—决策—执行」闭环。
在普通 vLLM 部署方式下,每个模型服务通常由人工选择 GPU、端口和显存比例。多个模型同时部署时,即使是很小的模型也会按默认 gpu_memory_utilization=0.9 预留几乎整卡的 KV Cache 空间,导致同一张 GPU 无法继续加载其他模型(实验中第二个实例在 KV Cache 分配阶段直接 CUDA OOM)。
gpu_memory_utilization=0.9
MixMaaS 将模型实例、节点、GPU、显存预算和 endpoint 纳入统一元数据管理:部署前根据模型资源画像计算显存预算并自动折算 gpu_memory_utilization,由全局调度器按逻辑显存账本选择节点和 GPU,通过异步部署、健康检查与状态回调保证只有就绪实例被路由,卸载时以进程组为单位彻底回收。
gpu_memory_utilization
系统采用 Manager + Node Agent + vLLM Replica 三层架构:
Manager + Node Agent + vLLM Replica
实验结果:Qwen2.5-0.5B-Instruct 与 Qwen2.5-1.5B-Instruct 在同一张 32GB V100 上稳定混部(逻辑已分配 10240 MB);在主服务模型满足 streaming SLO(TTFT P99 1.060 s、TPOT P99 10.18 ms、Latency P99 3.219 s)的前提下,单 GPU 综合输出吞吐从 1496.47 tokens/s 提升到 4537.92 tokens/s(+203.2%),1200/1200 请求全部成功。
Qwen2.5-0.5B-Instruct
Qwen2.5-1.5B-Instruct
allocated/available_memory_mb
high/normal/low
free_memory/least_replicas/binpack
/v1/chat/completions
/v1/models
round_robin/first
/metrics
默认占用端口(host 网络模式下即宿主机端口,启动前请确认未被占用):
Python 依赖(src/MixMaaS/requirements.txt):fastapi、uvicorn、PyYAML、httpx、nvidia-ml-py、pydantic。
src/MixMaaS/requirements.txt
fastapi
uvicorn
PyYAML
httpx
nvidia-ml-py
pydantic
Node Agent 与测试依赖(src/MixMaaS/node_agent/requirements.txt):在上述基础上增加 pytest、pytest-asyncio、pytest-mock。
src/MixMaaS/node_agent/requirements.txt
pytest
pytest-asyncio
pytest-mock
容器镜像:
vllm/vllm-openai
BASE_IMAGE
quay.io/prometheus/prometheus:v2.54.1
grafana
monitoring/.env
GRAFANA_IMAGE
前端:零依赖——原生 HTML/CSS/JavaScript,无 Node、无打包构建,任意现代浏览器可直接运行。
模型权重:不随仓库分发。将 Qwen2.5-Instruct 系列模型目录放置于 src/MixMaaS/models/(容器内以只读方式挂载到 /models),模型名与路径、显存预算的对应关系见 src/MixMaaS/configs/base.yml 的 MODEL_RESOURCES。
src/MixMaaS/models/
/models
src/MixMaaS/configs/base.yml
MODEL_RESOURCES
mptzmxhbdzybpyxnyh/ ├── README.md # 本文档(项目根目录) ├── docs/ # 决赛提交文档(PDF) │ ├── 项目说明书.pdf # 决赛项目说明书 │ ├── 项目创新说明.pdf # 三项创新与已有工作对照、代码位置与验证依据 │ ├── 成员分工及主要贡献说明.pdf # 匿名化(A/B/C)成员分工与主要贡献 │ └── 人工智能及第三方工具使用说明.pdf # AI 与第三方工具使用声明及人工验证责任 ├── presentation/ # 决赛答辩 PPT 与演示视频 ├── tests/ # 实验证据 │ ├── images/ # exp1–exp4 实验截图与 charts 曲线图 │ └── results/exp3/ # 实验三 benchmark 原始 JSON ├── demo/ # 决赛演示:可运行/可复现/可部署三层证明 │ ├── quickstart/ # ① mock 模式全链路演示(无需 GPU/权重/Docker) │ ├── reproduce/ # ② GPU 实验分阶段复现 + 结论图重绘 │ ├── deploy/ # ③ 生产部署自检/验证与离线内网方案 │ └── evidence/ # 说明书论断 ↔ 证据映射表 └── src/MixMaaS/ # 系统源代码 ├── configs/base.yml # 默认配置:端口、调度策略、vLLM 参数、模型资源画像 ├── mixmass/ # Manager 控制面 │ ├── entrypoints/vllm/api_server.py # 统一入口(注册/部署/卸载/路由/代理,含 CORS) │ ├── llm_engine_manager.py # 核心编排器(预算计算、生命周期、路由) │ ├── global_scheduler/ # 放置与路由策略 │ ├── metadata/ # NodeInfo/GPUInfo/ModelInfo/Replica 与逻辑显存账本 │ ├── agent/ # 调用 Node Agent 的 HTTP 客户端 │ ├── config/ # YAML 配置与命令行覆盖 │ └── metrics.py # Manager /metrics 指标 ├── node_agent/ # 节点执行面 │ ├── main.py / server.py # 启动入口与本地控制 API │ ├── deployer.py # 部署编排:端口分配、启动、回调、回滚 │ ├── state.py # 线程安全实例表与端口池 │ ├── process_manager.py # CUDA_VISIBLE_DEVICES 绑定、进程组隔离、killpg 清理 │ ├── health_checker.py # 轮询本地 /v1/models 判定就绪 │ ├── monitor.py / metrics.py # NVML 采集与 Agent /metrics │ ├── http_client.py # 注册、心跳、状态回调客户端 │ ├── mock_vllm.py # 无 GPU 环境测试用 mock 服务 │ └── tests/ # 单元测试(28 例) ├── frontend/ # Web 门户(零构建静态前端) │ ├── index.html / styles.css │ ├── app.js # 监控视图 + 视图切换 │ └── manage.js # 管理视图(查询/部署/卸载/自动刷新) ├── benchmarks/benchmark_openai_stream.py # streaming 压测脚本 ├── docker/Dockerfile # 后端镜像(基于 vllm-openai) ├── monitoring/ # Docker Compose 监控栈(manager/node-agent/frontend/prometheus/grafana) ├── docs/ # API、实验、决赛文档与架构图 ├── DEPLOYMENT.md # 服务器部署手册 └── requirements.txt
方式 A:Docker 构建(推荐)
后端镜像 mixmaas-backend:local 基于 vLLM 官方镜像叠加本项目代码构建,前端与 Node Agent 复用同一镜像(前端由镜像内 Python HTTP Server 托管),无需单独构建前端:
mixmaas-backend:local
cd src/MixMaaS/monitoring sudo docker compose build # 或 docker compose up -d --build 一步构建并启动
基础镜像可通过构建参数替换(如使用华为云镜像源):docker compose build --build-arg BASE_IMAGE=<镜像地址>。
docker compose build --build-arg BASE_IMAGE=<镜像地址>
方式 B:源码环境准备(无编译步骤)
cd src/MixMaaS python3 -m venv .venv && source .venv/bin/activate pip install -r requirements.txt -r node_agent/requirements.txt
源码方式需自行准备 vLLM 0.8.5 环境(pip install vllm==0.8.5)与 NVIDIA 驱动;仅运行单元测试时不需要 GPU 与 vLLM。
pip install vllm==0.8.5
Docker Compose 启动(推荐)
cd src/MixMaaS mkdir -p models # 将模型权重放入该目录 cd monitoring printf 'GRAFANA_IMAGE=<grafana 镜像地址>\n' > .env # 可选,需要 Grafana 时配置 sudo docker compose up -d --build # Manager + Node Agent + 前端 + Prometheus sudo docker compose --profile grafana up -d grafana # Grafana(镜像可用时)
启动顺序由 Compose 依赖关系保证(Manager 健康后才启动 Node Agent)。多 Node Agent 场景需为额外节点分配不同宿主机端口并在 prometheus.yml 登记;若 Agent 地址需被外部客户端访问,修改 docker-compose.yml 中 MAAS_AGENT_ADVERTISE_HOST 为内网 IP。
prometheus.yml
docker-compose.yml
MAAS_AGENT_ADVERTISE_HOST
源码直接运行
cd src/MixMaaS # 1. Manager python3 -m mixmass.entrypoints.vllm.api_server --config-file configs/base.yml --port 8000 # 2. Node Agent(另开终端;启动后自动向 Manager 注册) python3 -m node_agent.main --manager-url http://127.0.0.1:8000 --node-id node-1 # 3. Web 门户(另开终端) cd frontend && python3 -m http.server 4173
访问地址与验证
http://<服务器IP>:4173
http://<服务器IP>:8000
src/MixMaaS/docs/API.md
http://<服务器IP>:13000
admin
mixmaas
http://<服务器IP>:19090
curl http://127.0.0.1:8000/health
curl http://127.0.0.1:8000/v1/nodes
完整的服务器部署流程(环境检查、镜像准备、端口检查、分阶段启动、防火墙与日常运维)见 部署手册。
前端为零构建纯静态门户(src/MixMaaS/frontend/),顶部页签切换两个视图:
src/MixMaaS/frontend/
fetch
configs/base.yml
localStorage
详细说明见 前端门户文档。
单元测试(无需 GPU 与真实 vLLM,NVML 与子进程均被 mock):
cd src/MixMaaS pip install -r requirements.txt -r node_agent/requirements.txt python3 -m pytest node_agent/tests -q # 预期:28 passed(覆盖 ProcessManager 进程组与清理、HealthChecker 就绪判定与超时、GPUMonitor 采集与降级)
全链路演示验证(无需 GPU/权重/vLLM/Docker,mock 模式,调度类步骤仍需 NVML):
bash demo/quickstart/run_demo.sh # 启动 Manager + mock Agent + 前端门户 python3 demo/quickstart/walkthrough.py --with-benchmark # 11 步自动验证,全 PASS 退出码 0 bash demo/quickstart/stop_demo.sh
功能验证(需 GPU 环境):
GET /v1/nodes
ready
GET /v1/gpus
POST /v1/models/deploy
deploying
running
allocated_memory_mb=10240
POST /v1/chat/completions
POST /v1/models/undeploy
allocated_memory_mb
curl -s -D - -o /dev/null -H "Origin: http://127.0.0.1:4173" http://127.0.0.1:8000/health
access-control-allow-origin: *
性能压测(streaming 逐 token 计时):
cd src/MixMaaS python3 benchmarks/benchmark_openai_stream.py \ --base-url http://127.0.0.1:8000 \ --model Qwen2.5-1.5B-Instruct \ --concurrency 8 --num-requests 200 --max-tokens 256 \ --output-json result.json
脚本输出 TTFT/TPOT/Latency 的均值与 P99、输出吞吐与成功率。完整实验步骤、对照组设置与原始数据见 实验说明;实验截图位于 tests/images/,实验三原始 JSON 位于 tests/results/exp3/。
tests/images/
tests/results/exp3/
METADATA_STORE=memory
allow_origins=["*"]
MAAS_NODE_ID
决赛演示视频:presentation/决赛演示视频.mp4——真实 GPU 服务器上的完整录屏,展示系统核心功能与实际效果;随仓库直接分发,无需外链下载。
版权所有:中国计算机学会技术支持:开源发展技术委员会 京ICP备13000930号-9 京公网安备 11010802047560号
MixMaaS
MixMaaS 是面向「MaaS 平台中模型混部的资源编排与性能优化」的原型系统,基于开源推理引擎 vLLM 构建统一控制面(Manager)与节点执行面(Node Agent),在不修改 vLLM 内部推理逻辑的前提下,解决多模型并发服务中的显存预算、部署位置选择、运行状态观测、请求路由与异常回收问题,并提供 Web 门户与 Grafana 监控形成「观测—决策—执行」闭环。
项目简介
在普通 vLLM 部署方式下,每个模型服务通常由人工选择 GPU、端口和显存比例。多个模型同时部署时,即使是很小的模型也会按默认
gpu_memory_utilization=0.9预留几乎整卡的 KV Cache 空间,导致同一张 GPU 无法继续加载其他模型(实验中第二个实例在 KV Cache 分配阶段直接 CUDA OOM)。MixMaaS 将模型实例、节点、GPU、显存预算和 endpoint 纳入统一元数据管理:部署前根据模型资源画像计算显存预算并自动折算
gpu_memory_utilization,由全局调度器按逻辑显存账本选择节点和 GPU,通过异步部署、健康检查与状态回调保证只有就绪实例被路由,卸载时以进程组为单位彻底回收。系统采用
Manager + Node Agent + vLLM Replica三层架构:实验结果:
Qwen2.5-0.5B-Instruct与Qwen2.5-1.5B-Instruct在同一张 32GB V100 上稳定混部(逻辑已分配 10240 MB);在主服务模型满足 streaming SLO(TTFT P99 1.060 s、TPOT P99 10.18 ms、Latency P99 3.219 s)的前提下,单 GPU 综合输出吞吐从 1496.47 tokens/s 提升到 4537.92 tokens/s(+203.2%),1200/1200 请求全部成功。应用场景
主要功能
allocated/available_memory_mb)与物理观测并列暴露;gpu_memory_utilization,解决默认预算下的同卡 OOM;high/normal/low(high 分散、low 填充碎片)与放置策略free_memory/least_replicas/binpack正交组合;/v1/chat/completions、/v1/models与 vLLM 接口一致,仅路由 RUNNING 副本,支持round_robin/first;/metrics,Prometheus 抓取,Grafana「MixMaaS 集群总览」仪表盘展示;系统环境
默认占用端口(host 网络模式下即宿主机端口,启动前请确认未被占用):
依赖要求
Python 依赖(
src/MixMaaS/requirements.txt):fastapi、uvicorn、PyYAML、httpx、nvidia-ml-py、pydantic。Node Agent 与测试依赖(
src/MixMaaS/node_agent/requirements.txt):在上述基础上增加pytest、pytest-asyncio、pytest-mock。容器镜像:
vllm/vllm-openai(vLLM 0.8.5,可通过构建参数BASE_IMAGE替换镜像源);quay.io/prometheus/prometheus:v2.54.1;grafanaprofile,镜像地址经monitoring/.env的GRAFANA_IMAGE配置)。前端:零依赖——原生 HTML/CSS/JavaScript,无 Node、无打包构建,任意现代浏览器可直接运行。
模型权重:不随仓库分发。将 Qwen2.5-Instruct 系列模型目录放置于
src/MixMaaS/models/(容器内以只读方式挂载到/models),模型名与路径、显存预算的对应关系见src/MixMaaS/configs/base.yml的MODEL_RESOURCES。目录结构
构建方法
方式 A:Docker 构建(推荐)
后端镜像
mixmaas-backend:local基于 vLLM 官方镜像叠加本项目代码构建,前端与 Node Agent 复用同一镜像(前端由镜像内 Python HTTP Server 托管),无需单独构建前端:基础镜像可通过构建参数替换(如使用华为云镜像源):
docker compose build --build-arg BASE_IMAGE=<镜像地址>。方式 B:源码环境准备(无编译步骤)
源码方式需自行准备 vLLM 0.8.5 环境(
pip install vllm==0.8.5)与 NVIDIA 驱动;仅运行单元测试时不需要 GPU 与 vLLM。运行方法
Docker Compose 启动(推荐)
启动顺序由 Compose 依赖关系保证(Manager 健康后才启动 Node Agent)。多 Node Agent 场景需为额外节点分配不同宿主机端口并在
prometheus.yml登记;若 Agent 地址需被外部客户端访问,修改docker-compose.yml中MAAS_AGENT_ADVERTISE_HOST为内网 IP。源码直接运行
访问地址与验证
http://<服务器IP>:4173;Manager API:http://<服务器IP>:8000(接口文档见src/MixMaaS/docs/API.md)http://<服务器IP>:13000(初始账号admin/ 密码mixmaas);Prometheus:http://<服务器IP>:19090curl http://127.0.0.1:8000/health、curl http://127.0.0.1:8000/v1/nodes(应看到节点 ready)完整的服务器部署流程(环境检查、镜像准备、端口检查、分阶段启动、防火墙与日常运维)见 部署手册。
Web 门户
前端为零构建纯静态门户(
src/MixMaaS/frontend/),顶部页签切换两个视图:fetch直连 Manager 控制面 API(Manager 已开启 CORS),提供:configs/base.yml,支持自由输入)、优先级、显存 MB、副本 ID、Tensor Parallel Size、Max Model Len、Dtype;localStorage。详细说明见 前端门户文档。
测试方法
单元测试(无需 GPU 与真实 vLLM,NVML 与子进程均被 mock):
全链路演示验证(无需 GPU/权重/vLLM/Docker,mock 模式,调度类步骤仍需 NVML):
功能验证(需 GPU 环境):
GET /v1/nodes中节点为ready、GET /v1/gpus能识别 GPU;POST /v1/models/deploy部署Qwen2.5-0.5B-Instruct与Qwen2.5-1.5B-Instruct,观察副本状态由deploying进入running,同卡混部后allocated_memory_mb=10240;POST /v1/chat/completions对两个模型发起推理请求,确认返回内容与 token usage 正常;POST /v1/models/undeploy卸载(重复调用应幂等),确认副本清空且allocated_memory_mb归零;curl -s -D - -o /dev/null -H "Origin: http://127.0.0.1:4173" http://127.0.0.1:8000/health应返回access-control-allow-origin: *。性能压测(streaming 逐 token 计时):
脚本输出 TTFT/TPOT/Latency 的均值与 P99、输出吞吐与成功率。完整实验步骤、对照组设置与原始数据见 实验说明;实验截图位于
tests/images/,实验三原始 JSON 位于tests/results/exp3/。已知限制
high/normal/low只影响部署放置(分散/填充),不影响 vLLM 内部请求调度、batch 组织或 CUDA kernel 执行顺序;METADATA_STORE=memory,Manager 重启后全局视图丢失,需依赖 Node Agent 重新注册与心跳恢复,运行中副本的平台侧账本不会自动重建;allow_origins=["*"],仅适合内网/实验环境,暴露公网前必须自行加访问控制;configs/base.yml的静态画像,尚不支持依据运行时占用自动标定;MAAS_NODE_ID并更新 Prometheus 抓取目标;文档导航
项目视频
决赛演示视频:presentation/决赛演示视频.mp4——真实 GPU 服务器上的完整录屏,展示系统核心功能与实际效果;随仓库直接分发,无需外链下载。