推理服务部署
推理服务架构
客户端请求
↓
API Gateway(限流/鉴权/路由)
↓
推理服务集群(多副本)
├── 推理实例1(GPU)
├── 推理实例2(GPU)
└── 推理实例3(GPU)
↓
模型仓库(Model Registry)TensorRT 模型优化
TensorRT 是 NVIDIA 的推理优化引擎,可将训练好的模型转换为高效推理格式:
python
import tensorrt as trt
import torch
import numpy as np
# 步骤1:将 PyTorch 模型导出为 ONNX
model = load_trained_model()
model.eval()
dummy_input = torch.randn(1, 3, 224, 224).cuda()
torch.onnx.export(
model,
dummy_input,
"model.onnx",
opset_version=17,
input_names=["input"],
output_names=["output"],
dynamic_axes={"input": {0: "batch_size"}} # 动态 batch
)
# 步骤2:使用 trtexec 转换为 TensorRT 引擎
# trtexec --onnx=model.onnx \
# --saveEngine=model.trt \
# --fp16 \ # 开启 FP16 精度
# --minShapes=input:1x3x224x224 \
# --optShapes=input:8x3x224x224 \
# --maxShapes=input:32x3x224x224
# 步骤3:加载 TensorRT 引擎推理
import tensorrt as trt
import pycuda.driver as cuda
import pycuda.autoinit
TRT_LOGGER = trt.Logger(trt.Logger.WARNING)
with open("model.trt", "rb") as f:
engine_data = f.read()
runtime = trt.Runtime(TRT_LOGGER)
engine = runtime.deserialize_cuda_engine(engine_data)
context = engine.create_execution_context()
# 推理
input_data = np.random.randn(8, 3, 224, 224).astype(np.float16)
# ... 执行推理vLLM 大语言模型推理
vLLM 是目前最流行的 LLM 推理框架,H3C AI Platform 原生集成:
python
from vllm import LLM, SamplingParams
# 加载模型(自动使用所有可用 GPU)
llm = LLM(
model="/models/Qwen2-72B-Instruct",
tensor_parallel_size=4, # 4 张 GPU 张量并行
gpu_memory_utilization=0.9,
max_model_len=8192,
dtype="bfloat16"
)
# 批量推理
prompts = [
"请介绍一下新华三公司的主要产品",
"什么是云计算的 IaaS 层?",
"解释一下 Kubernetes 的核心概念"
]
sampling_params = SamplingParams(
temperature=0.7,
top_p=0.9,
max_tokens=512
)
outputs = llm.generate(prompts, sampling_params)
for output in outputs:
print(f"问题: {output.prompt}")
print(f"回答: {output.outputs[0].text}")
print("---")vLLM OpenAI 兼容 API 服务
bash
# 启动 vLLM 服务(兼容 OpenAI API)
python -m vllm.entrypoints.openai.api_server \
--model /models/Qwen2-72B-Instruct \
--tensor-parallel-size 4 \
--host 0.0.0.0 \
--port 8000 \
--max-model-len 8192 \
--gpu-memory-utilization 0.9python
# 客户端调用(兼容 OpenAI SDK)
from openai import OpenAI
client = OpenAI(
base_url="http://inference.ai-platform.example.com:8000/v1",
api_key="not-needed" # vLLM 本地部署无需 key
)
response = client.chat.completions.create(
model="Qwen2-72B-Instruct",
messages=[
{"role": "system", "content": "你是新华三的技术专家助手"},
{"role": "user", "content": "请介绍 H3C CloudOS 的核心架构"}
],
temperature=0.7,
max_tokens=1024,
stream=True # 流式输出
)
for chunk in response:
if chunk.choices[0].delta.content:
print(chunk.choices[0].delta.content, end="", flush=True)Triton 推理服务器
NVIDIA Triton 是企业级推理服务框架,支持多框架模型:
模型仓库结构:
model_repository/
├── bert_classifier/
│ ├── config.pbtxt
│ └── 1/
│ └── model.onnx
├── resnet50/
│ ├── config.pbtxt
│ └── 1/
│ └── model.plan (TensorRT)
└── ensemble_pipeline/
├── config.pbtxt
└── 1/
└── (空,ensemble 无需模型文件)protobuf
# config.pbtxt 示例(BERT 分类器)
name: "bert_classifier"
platform: "onnxruntime_onnx"
max_batch_size: 32
input [
{
name: "input_ids"
data_type: TYPE_INT64
dims: [128] # 序列长度
},
{
name: "attention_mask"
data_type: TYPE_INT64
dims: [128]
}
]
output [
{
name: "logits"
data_type: TYPE_FP32
dims: [2] # 二分类
}
]
instance_group [
{
count: 2 # 2 个推理实例
kind: KIND_GPU
gpus: [0, 1] # 使用 GPU 0 和 1
}
]
dynamic_batching {
preferred_batch_size: [8, 16, 32]
max_queue_delay_microseconds: 5000 # 最大等待 5ms 凑批
}bash
# 启动 Triton 服务器
docker run --gpus all --rm \
-p 8000:8000 -p 8001:8001 -p 8002:8002 \
-v /path/to/model_repository:/models \
nvcr.io/nvidia/tritonserver:23.10-py3 \
tritonserver --model-repository=/models
# 检查模型状态
curl http://localhost:8000/v2/models/bert_classifier/ready
# 发送推理请求
curl -X POST http://localhost:8000/v2/models/bert_classifier/infer \
-H "Content-Type: application/json" \
-d '{
"inputs": [
{"name": "input_ids", "shape": [1, 128], "datatype": "INT64", "data": [...]},
{"name": "attention_mask", "shape": [1, 128], "datatype": "INT64", "data": [...]}
]
}'推理性能优化
量化(Quantization)
python
# INT8 量化(减少显存,提升吞吐)
from transformers import AutoModelForSequenceClassification
import torch
model = AutoModelForSequenceClassification.from_pretrained("bert-base-chinese")
# 动态量化(简单,精度损失小)
quantized_model = torch.quantization.quantize_dynamic(
model,
{torch.nn.Linear}, # 量化线性层
dtype=torch.qint8
)
# 性能对比:
# FP32:基准
# FP16:速度 ~2x,显存 ~0.5x
# INT8:速度 ~4x,显存 ~0.25x,精度损失 < 1%KV Cache 优化(LLM)
python
# vLLM 的 PagedAttention 自动管理 KV Cache
# 无需手动配置,但需要了解原理
# KV Cache 大小估算:
# 每个 token 的 KV Cache = 2 × num_layers × num_heads × head_dim × dtype_bytes
# 以 Llama-2-70B 为例:
# 2 × 80 × 64 × 128 × 2(FP16)= 2.6MB/token
# 8192 tokens × 2.6MB = 21GB(单请求)
# 因此 70B 模型推理需要大量显存用于 KV Cache