前言AI 商业化的时代,大模型推理训练会被更加广泛的使用.比较理性的看待大模型的话,一个大模型被训练出来后,无外乎两个结果…
前言 AI 商业化的时代,大模型推理训练会被更加广泛的使用。比较理性的看待大模型的话,一个大模型被训练出来后,无外乎两个结果,第一个就是这个大模型没用,那就没有后续了;另一个结果就是发现这个模型很有用,那么就会全世界的使用,这时候主要的使用都来自于推理,不论是 openAI 还是 midjourney,用户都是在为每一次推理行为付费。随着时间的推移,模型训练和模型推理的使用比重会是三七开,甚至二八开。应该说模型推理会是未来的主要战场。 大模型推理是一个巨大的挑战,它的挑战体现在成本、性能和效率。其中成本最重要,因为大模型的成本挑战在于模型规模越来越大,使用的资源越来越多,而模型的运行平台 GPU 由于其稀缺性,价格很昂贵,这就导致每次模型推理的成本越来越高。而最终用户只为价值买单,而不会为推理成本买单,因此降低单位推理的成本是基础设施团队的首要任务。 在此基础上,性能是核心竞争力,特别是 ToC 领域的大模型,更快的推理和推理效果都是增加用户粘性的关键。 应该说大模型的商业化是一个不确定性较高的领域,成本和性能可以保障你始终在牌桌上。效率是能够保障你能在牌桌上赢牌。 进一步,效率。模型是需要持续更新,这就模型多久可以更新一次,更新一次要花多久的时间。谁的工程效率越高,谁就有机会迭代出有更有价值的模型。 img 近年来,容器和 Kubernetes 已经成为越来越多 AI 应用首选的运行环境和平台。一方面,Kubernetes 帮助用户标准化异构资源和运行时环境、简化运维流程;另一方面,AI 这种重度依赖 GPU 的场景可以利用 K8s 的弹性优势节省资源成本。在 AIGC/大模型的这波浪潮下,以 Kubernetes 上运行 AI 应用将变成一种事实标准。 — 节选自《云原生场景下,AIGC 模型服务的工程挑战和应对》 大模型训练和推理 大模型训练和推理是机器学习和深度学习领域的重要应用,但企业和个人往往面临着GPU管理复杂、资源利用率低,以及AI作业全生命周期管理中工程效率低下等挑战。本方案通过创建kubernetes集群,使用kserve+vLLM部署推理服务。适用于机器学习和深度学习任务中的以下场景: • 模型训练:基于Kubernetes集群微调开源模型,可以屏蔽底层资源和环境的复杂度,快速配置训练数据、提交训练任务,并自动运行和保存训练结果。 • 模型推理:基于Kubernetes集群部署推理服务,可以屏蔽底层资源和环境的复杂度,快速将微调后的模型部署成推理服务,将模型应用到实际业务场景中。 • GPU共享推理:支持GPU共享调度能力和显存隔离能力,可将多个推理服务部署在同一块GPU卡上,提高GPU的利用率的同时也能保证推理服务的稳定运行。 VLLM介绍 即使在高端 GPU 上,提供 LLM 模型的速度也可能出奇地慢,vLLM[1]是一种快速且易于使用的 LLM 推理引擎。它可以实现比 Huggingface 变压器高 10 倍至 20 倍的吞吐量。它支持连续批处理[2]以提高吞吐量和 GPU 利用率, vLLM支持分页注意力[3]以解决内存瓶颈,在自回归解码过程中,所有注意力键值张量(KV 缓存)都保留在 GPU 内存中以生成下一个令牌。 vLLM 是一个快速且易于使用的 LLM 推理和服务库。 vLLM 的速度很快: • 最先进的服务吞吐量 • 使用PagedAttention高效管理注意力键和值内存 • 连续批处理传入请求 • 使用 CUDA/HIP 图快速执行模型 • 量化:GPTQ[4]、AWQ[5]、SqueezeLLM[6]、FP8 KV 缓存 • 优化的 CUDA 内核 vLLM 灵活且易于使用: • 与流行的 HuggingFace 模型无缝集成 • 高吞吐量服务与各种解码算法,包括并行采样、波束搜索等 • 对分布式推理的张量并行支持 • 流输出 • 兼容 OpenAI 的 API 服务器 • 支持 NVIDIA GPU 和 AMD GPU • (实验性)前缀缓存支持 • (实验性)多lora支持 kserve介绍 KServe是一个针对 Kubernetes 的自定义资源,用于为任意框架提供机器学习(ML)模型服务。它旨在为常见 ML 框架(如TensorFlow、XGBoost、ScikitLearn、PyTorch 和 ONNX)的提供性高性能、标准化的推理协议,解决生产模型服务的使用案例。 KServe提供简单的Kubernetes CRD,可用于将单个或多个经过训练的模型(例如TFServing、TorchServe、Triton等推理服务器)部署到模型服务运行时。 KServe封装了自动扩展、网络、健康检查和服务器配置的复杂性,为 ML 部署带来了 GPU 自动扩展、零扩缩放和金丝雀发布等先进的服务特性。它使得生产 ML 服务变得简单、可插拔,并提供了完整的故事,包括预测、预处理、后处理和可解释性。 KServe中的ModelMesh 专为高规模、高密度和频繁变化的模型使用场景设计,智能地加载和卸载 AI 模型,以在用户响应和计算资源占用之间取得智能权衡。 KServe还提供基本API原语,可轻松构建自定义模型服务运行时。你也可以使用其他工具(例如BentoML)来构建你自己的自定义模型服务镜像。 • ⚙️ KServe的诞生背景:Kubeflow Summit 2019后,从Kubeflow分离出的KF Serving,最终发展为KServe。在2022年由Nvidia贡献了V2标准化推理协议,引起行业广泛关注。 • 🌐 KServe的功能与部署:是高度可扩展、基于Kubernetes的无服务器模型推理平台。支持云端或本地部署,具备服务器自动扩展、多种模型服务运行时等特性。 • 📈 KServe当前状态:拥有约60%的Kubeflow用户使用KServe;已有约10万次KServe Docker镜像下载;拥有20个核心贡献者和172名贡献者。 • 🖥️ KServe提供基本和高级特性,如规模化、请求处理、安全性、流量管理、分布式跟踪等,使机器学习工作流更加便捷。 • 🤖 KServe构建在Kubernetes之上,与Knative和Istio集成,提供了可扩展且高效的模型服务架构。 • 🛠️ KServe特性:支持多种模型服务运行时,如Triton、TF Serving等;推出的V2推理协议标准化了多种推理运行时;引入了推理图、批处理等功能。 • 🔄 Model Mesh与KServe整合:Model Mesh是IBM在KServe项目中贡献的技术,用于管理大量模型服务的静态Pods,提供高密度模型加载和路由请求功能,自动优化资源利用,旨在解决大规模、高密度的推断服务部署问题。 • 🚀KServe还支持Canary Rollout等功能,提供流量控制和版本管理,适用于各种生产用例。 为什么选择KServe? • KServe 是一个与云无关的标准模型推理平台,专为高度可扩展的用例而构建。 • 跨机器学习框架,提供高性能标准化推理协议。 • 支持现代无服务器推理工作负载,具有基于请求在CPU和GPU的自动缩放(包括缩放至零)。 • 使用ModelMesh 支持 高可扩展性、密度封装和智能路由 • 简单且可插入的生产服务:用于推理、预/后处理、监控和可解释性. • 高级部署:金丝雀部署、Pipeline、InferenceGraph 在k8s环境中,你可以使用Kserve InferenceServiceAPI 规范通过构建的 vLLM 推理服务器容器镜像来部署模型。 搭建kserve环境 你可以使用 KServe 快速安装脚本,在本地部署 KServe : curl -s “https://raw.githubusercontent.com/kserve/kserve/release-0.11/hack/quick_install.sh” | bash 执行结果查看 kubectl get pod -A NAMESPACE NAME READY STATUS RESTARTS AGE cert-manager cert-manager-76b7c557d5-xzd8b 1/1 Running 1 30m cert-manager cert-manager-cainjector-655d695d74-q2tjv 1/1 Running 6 30m cert-manager cert-manager-webhook-7955b9bb97-h4bm6 1/1 Running 3 30m istio-system istio-egressgateway-5547fcc8fc-z7sz9 1/1 Running 1 32m istio-system istio-ingressgateway-8f568d595-f4f5z 1/1 Running 1 32m istio-system istiod-568d797f55-k6476 1/1 Running 1 32m knative-serving activator-68b7698d74-tld8d 1/1 Running 1 31m knative-serving autoscaler-6c8884d6ff-dd6fn 1/1 Running 1 31m knative-serving controller-76cf997d95-fk6hv 1/1 Running 1 31m knative-serving domain-mapping-57fdbf97b-mg8r2 1/1 Running 1 31m knative-serving domainmapping-webhook-66c5f7d596-qxhtw 1/1 Running 5 31m knative-serving net-istio-controller-544874485d-4dlvr 1/1 Running 1 31m knative-serving net-istio-webhook-695d588d65-crfkf 1/1 Running 1 31m knative-serving webhook-7df8fd847b-dqx8s 1/1 Running 4 31m kserve kserve-controller-manager-0 2/2 Running 2 22m kube-system coredns-558bd4d5db-gkspn 1/1 Running 1 54m kube-system coredns-558bd4d5db-tsh95 1/1 Running 1 54m kube-system etcd-test-cluster-control-plane 1/1 Running 1 54m kube-system kindnet-49hl9 1/1 Running 1 54m kube-system kube-apiserver-test-cluster-control-plane 1/1 Running 1 54m kube-system kube-controller-manager-test-cluster-control-plane 1/1 Running 7 54m kube-system kube-proxy-mqvtb 1/1 Running 1 54m kube-system kube-scheduler-test-cluster-control-plane 1/1 Running 7 54m local-path-storage local-path-provisioner-778f7d66bf-4fzcg 1/1 Running 1 54m 基于Kserve和vLLM:在k8s上创建大模型推理服务 创建理服务InferenceService apiVersion: serving.kserve.io/v1beta1 kind: InferenceService metadata: namespace: kserve-test name: bloom spec: predictor: containers: – args: – –port – “8080” – –model – “/mnt/models” command: – python3 – -m – vllm.entrypoints.api_server env: – name: STORAGE_URI value: pvc://task-pv-claim/bloom-560m image: docker.io/kserve/vllmserver:latest imagePullPolicy: IfNotPresent name: kserve-container resources: limits: cpu: “5” memory: 20Gi nvidia.com/gpu: “1” requests: cpu: “5” memory: 20Gi nvidia.com/gpu: “1” 启动日志 $ kubectl -n kserve-test logs -f –tail=200 bloom-predictor-00001-deployment-66649d69bd-nw96r Defaulted container “kserve-container” out of: kserve-container, queue-proxy, storage-initializer (init) INFO 02-20 06:04:40 llm_engine.py:70] Initializing an LLM engine with config: model=’/mnt/models’, tokenizer=’/mnt/models’, tokenizer_mode=auto, trust_remote_code=False, dtype=torch.float16, use_dummy_weights=False, download_dir=None, use_np_weights=False, tensor_parallel_size=1, seed=0) INFO 02-20 06:04:54 llm_engine.py:196] # GPU blocks: 6600, # CPU blocks: 2730 INFO: Started server process [1] INFO: Waiting for application startup. INFO: Application startup complete. INFO: Uvicorn running on http://localhost:8080 (Press CTRL+C to quit) 使用Port Forward进行端口转发 INGRESS_GATEWAY_SERVICE=$(kubectl get svc –namespace istio-system –selector=”app=istio-ingressgateway” –output jsonpath='{.items[0].metadata.name}’) kubectl port-forward –namespace istio-system svc/${INGRESS_GATEWAY_SERVICE} 8080:80 进行LLM推理 来自具有 HOST 标头的 Ingress 网关 如果你没有 DNS,你仍然可以携带 HOST 标头,来请求入口网关外部 IP。 # start another terminal export INGRESS_HOST=localhost export INGRESS_PORT=8080 MODEL_NAME=bloom-560m SERVICE_HOSTNAME=$(kubectl –namespace kserve-test get inferenceservice bloom -o jsonpath='{.status.url}’ | cut -d “/” -f 3) #提示 {“error”:”TypeError : Type is not JSON serializable: bytes”} # 在你的 curl 请求中,尝试添加 -H “Content-Type: application/json” 头部。这样可以确保服务端正确地解析请求的 JSON 数据。 curl -v -H “Host: ${SERVICE_HOSTNAME}” -H “Content-Type: application/json” http://${INGRESS_HOST}:${INGRESS_PORT}/generate -d ‘{“prompt”: “San Francisco is a” }’ curl -v -H “Host: ${SERVICE_HOSTNAME}” -H “Content-Type: application/json” http://${INGRESS_HOST}:${INGRESS_PORT}/v1/completions -d ‘{ “model”: “/mnt/models”, “prompt”: “San Francisco is a”, “max_tokens”: 70, “temperature”: 0 }’ 预期输出 * About to connect() to localhost port 8080 (#0) * Trying ::1… * Connected to localhost (::1) port 8080 (#0) > POST /generate HTTP/1.1 > User-Agent: curl/7.29.0 > Accept: */* > Host: bloom.kserve-test.example.com > Content-Type: application/json > Content-Length: 33 > * upload completely sent off: 33 out of 33 bytes < HTTP/1.1 200 OK < content-length: 128 < content-type: application/json < date: Tue, 20 Feb 2024 07:34:23 GMT < server: istio-envoy < x-envoy-upstream-service-time: 287 http://${INGRESS_HOST}:${INGRESS_PORT}/v1/completions > -d ‘{ > “model”: “/mnt/models”, > “prompt”: “San Francisco is a”, > “max_tokens”: 70, > “temperature”: 0 > }’ * About to connect() to localhost port 8080 (#0) * Trying ::1… * Connected to localhost (::1) port 8080 (#0) > POST /v1/completions HTTP/1.1 > User-Agent: curl/7.29.0 > Accept: */* > Host: bloom.kserve-test.example.com > Content-Type: application/json > Content-Length: 130 > * upload completely sent off: 130 out of 130 bytes < HTTP/1.1 200 OK < content-length: 641 < content-type: application/json < date: Tue, 20 Feb 2024 09:37:47 GMT < server: istio-envoy < x-envoy-upstream-service-time: 589 http://${INGRESS_HOST}:${INGRESS_PORT}/v1/chat/completions > -d ‘{ > “model”: “/mnt/models”, > “messages”: [ > {“role”: “system”, “content”: “You are a helpful assistant.”}, > {“role”: “user”, “content”: “Who won the world series in 2020?”} > ] > }’ * About to connect() to localhost port 8080 (#0) * Trying ::1… * Connected to localhost (::1) port 8080 (#0) > POST /v1/chat/completions HTTP/1.1 > User-Agent: curl/7.29.0 > Accept: */* > Host: bloom.kserve-test.example.com > Content-Type: application/json > Content-Length: 223 > * upload completely sent off: 223 out of 223 bytes < HTTP/1.1 200 OK < content-length: 654 < content-type: application/json < date: Tue, 20 Feb 2024 09:56:34 GMT < server: istio-envoy < x-envoy-upstream-service-time: 814 < * Connection #0 to host localhost left intact {"id":"cmpl-af28c2d32b1f4a2aa24ad30f8fbbfa2b","object":"chat.completion","created":3795095,"model":"/mnt/models","choices":[{"index":0,"message":{"role":"assistant","content":"I have been on the road all year and was really happy to see the cheers in The Guardian site this year after the World Cup — for the first time in its history, a newspaper taking the time to cover the current World Cup (although not the one that was a fan favourite of mine and my wife). I am quite pleased with how well it went and I hope it will continue as much as possible."},"finish_reason":"stop"}],"usage":{"prompt_tokens":16,"total_tokens":100,"completion_tokens":84}} 有关聊天 API 的更深入示例和高级功能,你可以参考 OpenAI 官方文档[12]。 引用链接 [1] vLLM: https://github.com/vllm-project/vllm [2] 连续批处理: https://www.anyscale.com/blog/continuous-batching-llm-inference [3] vLLM支持分页注意力: https://vllm.ai/ [4] GPTQ: https://arxiv.org/abs/2210.17323 [5] AWQ: https://arxiv.org/abs/2306.00978 [6] SqueezeLLM: https://arxiv.org/abs/2306.07629 [7] 模型列表: https://platform.openai.com/docs/api-reference/models/list [8] 使用 OpenAI Chat API 查询模型: https://platform.openai.com/docs/api-reference/chat/completions/create [9] 通过输入提示查询模型: https://platform.openai.com/docs/api-reference/completions/create [10] vllm/vllm-openai: https://hub.docker.com/r/vllm/vllm-openai/tags [11] create chat completion: https://platform.openai.com/docs/api-reference/chat/completions/create [12] OpenAI 官方文档: https://platform.openai.com/docs/api-reference – END – 快速加 K8s学习交流群,与大佬共卷! 扫码加我微信,进群和大佬们零距
来源:K8S中文社区 · 原文链接