vllm部署LLM(qwen2.5,llama,deepseek)

目录

环境

qwen2.5-1.5b-instruct

模型下载

vllm 安装

验证安装

vllm 启动

查看当前模型列表

OpenAI Completions API(文本生成)

OpenAI Chat Completions API(chat 对话)

vllm 进程查看,kill

llama3

deepseek-蒸馏版 qwen


环境

Name: vllm
Version: 0.7.3

Name: torch
Version: 2.5.1

Name: transformers
Version: 4.49.0

cuda:V100-32GB

Version:12.1

qwen2.5-1.5b-instruct

模型下载

from modelscope import snapshot_download
model_dir = snapshot_download('Qwen/Qwen2.5-1.5B-Instruct', cache_dir='/root/autodl-tmp/')

 cache_dir 保存路径

vllm 安装

直接 pip 即可

pip install vllm

验证安装

安装好 vllm,下载好模型后,可以用以下代码试下 vllm 推理,如果正常会有运行结果

import os
import warnings
os.environ['CUDA_VISIBLE_DEVICES'] = '0'
warnings.filterwarnings('ignore')from transformers import AutoTokenizer
from vllm import LLM, SamplingParams
import pandas as pd
import timeclass vllmModel():def __init__(self, model_path, temperature=0.1, max_tokens=4096, tp_size=1):"""model_path: 模型路径temperature: 温度max_tokens: 模型最大输出 tokentp_size: gpu 数量,可以为 1 张卡卡,多余一张卡,必须是双数,如 2,4,6"""print(f'加载本地模型:{model_path}')self.tokenizer = AutoTokenizer.from_pretrained(model_path, trust_remote_code=True)self.llm = LLM(model=model_path,tensor_parallel_size=tp_size,max_model_len=4096,trust_remote_code=True,enforce_eager=True,dtype="float16",# 如果遇见 OOM 现象,建议开启下述参数# enable_chunked_prefill=True,# max_num_batched_tokens=8192)self.sampling_params = SamplingParams(temperature=temperature, max_tokens=max_tokens)print("模型加载完毕")def infer(self, prompts):"""prompts: prompt 列表"""prompts = [{"role": "user", "content": prompt} for prompt in prompts]inputs = []for prompt in prompts:_input = self.tokenizer.apply_chat_template([prompt], tokenize=False, add_generation_prompt=True)inputs.append(_input)outputs = self.llm.generate(prompts=inputs, sampling_params=self.sampling_params)result = []for output in outputs:text = output.outputs[0].textresult.append(text)return result# 加载模型
model_path = "/root/autodl-tmp/Qwen/Qwen2___5-1___5B-Instruct/"
llm = vllmModel(model_path)# infer
print(llm.infer(['你好', '你能做什么?']))

vllm 启动

qwen2.5 兼容 openai 的 api 服务,可以用一下命令启动:

VLLM_WORKER_MULTIPROC_METHOD=spawn \
vllm serve /root/autodl-tmp/Qwen/Qwen2___5-1___5B-Instruct \
--trust-remote-code \
--served-model-name qwen2_5_1_5 \
--gpu-memory-utilization 0.2 \
--tensor-parallel-size 1 \
--port 8000 \
--dtype=half

--dtype=half 跟 gpu 有关,因为我报错了,提示加这参数,是精度

--port 8000 开启端口为 8000

--trust-remote-code  允许执行远程代码

--served-model-name qwen2_5_1_5  模型名称定义,不是模型路径

--gpu-memory-utilization 0.2  gpu 显存占用,如果太高,我最开始 0.98,调用会崩掉

--tensor-parallel-size 1 使用 gpu 的数量

serve /root/autodl-tmp/Qwen/Qwen2___5-1___5B-Instruct 模型加载路径

--quantization awq 如果部署量化模型,即模型后缀为 AWQ,需要加上

vllm_use_v1=1 写在最开头,代表境变量为 1,表示你希望使用 vLLM 的 V1 API 版本。这通常涉及到API的设计,这个参数加上了,我这里不仅掉不通,一调就挂了,或者没多久也会自己挂,所以去掉

VLLM_WORKER_MULTIPROC_METHOD=spawn  写在最开头

这个变量指定在多进程模式下,worker(工作进程)启动的方法。在这个例子中,值被设置为 spawn。在Python的multiprocessing模块中有多种方法可以创建新进程,其中包括forkspawnforkserverspawn方法意味着每个新的进程都是通过启动一个全新的Python解释器实例来创建的。这种方法相较于fork更加安全,尤其是在使用非Unix平台(如Windows)时,因为fork可能会导致一些问题,比如子进程继承了父进程的所有资源,可能导致死锁或其他意外行为。

--max_model_len 4096 模型能够处理的最大序列长度(以token为单位),显存不够报错了,可以调小

CUDA_VISIBLE_DEVICES=0,2 写在最开头,指定使用哪张 gpu,这里是第 1,3 卡

启动成功会显示如下:

查看当前模型列表

curl http://localhost:8000/v1/models

{"object": "list","data": [{"id": "qwen2_5_1_5","object": "model","created": 1740235117,"owned_by": "vllm","root": "/root/autodl-tmp/Qwen/Qwen2___5-1___5B-Instruct","parent": null,"max_model_len": 32768,"permission": [{"id": "modelperm-514811fdf7464bc9bbd72db39850ef49","object": "model_permission","created": 1740235117,"allow_create_engine": false,"allow_sampling": true,"allow_logprobs": true,"allow_search_indices": false,"allow_view": true,"allow_fine_tuning": false,"organization": "*","group": null,"is_blocking": false}]}]
}

OpenAI Completions API(文本生成)

一般指文本生成类的使用,非 chat,即非对话的使用方式

curl http://localhost:8000/v1/completions \-H "Content-Type: application/json" \-d '{"model": "qwen2_5_1_5","prompt": "你好,你是?","max_tokens": 2048,"temperature": 0.7,"top_p": 0.8,"repetition_penalty": 1.05}'

加 repetition_penalty 之前,会有很多重复: 

加之后:

"max_tokens": 2048, 生成文本的最大长度(以token为单位)
"temperature": 0.7, 生成文本的随机性,值越小,创造能力越强,输出更加多样,适合创造场景
"top_p": 0.8, 核采样,类似温度,
"repetition_penalty": 1.05 用来减少重复词语出现的一个调节器。当其值大于1时(例如这里的 repetition_penalty: 1.05),会降低之前已经出现在生成文本中的词语被再次选中的概率。这有助于提高生成文本的新颖性,避免不必要的重复

{"id": "cmpl-adb0ffa50a1142a1880620126e341a70","object": "text_completion","created": 1740236869,"model": "qwen2_5_1_5","choices": [{"index": 0,"text": " 答案:我是小明。 A. 错误 B. 正确\nA. 错误\n\n解析:\"我是小明\"是一个常见的自我介绍,但它并不一定正确,因为每个人在回答\"你是谁\"的问题时,通常会提供自己真实的姓名或名字。\"小明\"可能是一个昵称或别名,这取决。。。。。。。。。。。。。。。。。。。","logprobs": null,"finish_reason": "length","stop_reason": null,"prompt_logprobs": null}],"usage": {"prompt_tokens": 4,"total_tokens": 2052,"completion_tokens": 2048,"prompt_tokens_details": null}
}

 python openai 接口:

from openai import OpenAI# 设置 OpenAI 的 API key 和 API base 来使用 vLLM 的 API server.
openai_api_key = "EMPTY"  # 如果不需要 API key,可以留空或设置为 "EMPTY"
openai_api_base = "http://localhost:8000/v1"client = OpenAI(api_key=openai_api_key,base_url=openai_api_base,
)# 创建 Completion 请求
completion_response = client.completions.create(model="qwen2_5_1_5",prompt="你好,你是?",max_tokens=2048,temperature=0.7,top_p=0.8,# 注意:OpenAI Python 客户端可能不直接支持 repetition_penalty,需要确认服务是否接受额外参数extra_body={"repetition_penalty": 1.05},
)# 检查响应并打印结果
if hasattr(completion_response, 'choices') and len(completion_response.choices) > 0:print("成功获取数据:")print(completion_response.choices[0].text)
else:print(f"请求失败,响应内容:{completion_response}")

python vllm 接口

import requests
import json# 设置请求的URL
url = "http://localhost:8000/v1/completions"# 设置请求头部
headers = {"Content-Type": "application/json"
}# 准备请求数据
data = {"model": "qwen2_5_1_5","prompt": "你好,你是?","max_tokens": 2048,"temperature": 0.7,"top_p": 0.8,"repetition_penalty": 1.05
}# 发送POST请求
response = requests.post(url, headers=headers, data=json.dumps(data))# 检查响应状态并打印结果
if response.status_code == 200:try:# 尝试解析响应中的 'choices' 字段,并获取生成的文本choices = response.json().get('choices', [])if choices:print("成功获取数据:")# 注意这里的 'text' 字段可能需要根据实际API响应结构调整print(choices[0].get('text', ''))else:print("没有获取到任何选择结果")except json.JSONDecodeError:print("无法解析JSON响应")
else:print(f"请求失败,状态码:{response.status_code}, 响应内容:{response.text}")

OpenAI Chat Completions API(chat 对话)

curl http://localhost:8000/v1/chat/completions \
-H "Content-Type: application/json" \
-d '{"model": "qwen2_5_1_5","messages": [{"role": "system", "content": "You are Qwen, created by Alibaba Cloud. You are a helpful assistant."},{"role": "user", "content": "你好,你是?"}],"temperature": 0.7,"top_p": 0.8,"repetition_penalty": 1.05,"max_tokens": 2048
}'

{"id": "chatcmpl-189df22813aa4b358e795596f0e2c420","object": "chat.completion","created": 1740238345,"model": "qwen2_5_1_5","choices": [{"index": 0,"message": {"role": "assistant","reasoning_content": null,"content": "你好!我是阿里云开发的一款语言模型,我叫通义千问。","tool_calls": []},"logprobs": null,"finish_reason": "stop","stop_reason": null}],"usage": {"prompt_tokens": 33,"total_tokens": 51,"completion_tokens": 18,"prompt_tokens_details": null},"prompt_logprobs": null
}

 python 代码 openai 接口

from openai import OpenAI# 设置 OpenAI 的 API key 和 API base 来使用 vLLM 的 API server.
openai_api_key = "EMPTY"
openai_api_base = "http://localhost:8000/v1"client = OpenAI(api_key=openai_api_key,base_url=openai_api_base,
)chat_response = client.chat.completions.create(model="qwen2_5_1_5",messages=[{"role": "system", "content": "You are Qwen, created by Alibaba Cloud. You are a helpful assistant."},{"role": "user", "content": "你是谁?"},],temperature=0.7,top_p=0.8,max_tokens=512,extra_body={"repetition_penalty": 1.05,},
)# 直接访问响应对象的属性,而不是尝试调用 .json()
print("Chat response:", chat_response.choices[0].message.content)

python vllm 接口

import requests
import json# 设置API的基本URL和端点
base_url = "http://localhost:8000/v1"
endpoint = "/chat/completions"url = base_url + endpoint# 设置请求头部
headers = {"Content-Type": "application/json",
}# 准备请求数据
data = {"model": "qwen2_5_1_5","messages": [{"role": "system", "content": "You are Qwen, created by Alibaba Cloud. You are a helpful assistant."},{"role": "user", "content": "你是谁?"},],"temperature": 0.7,"top_p": 0.8,"max_tokens": 512,"repetition_penalty": 1.05,  # 直接包含在请求体中
}# 发送POST请求
response = requests.post(url, headers=headers, data=json.dumps(data))# 检查响应状态并打印结果
if response.status_code == 200:print("Chat response:", response.json()['choices'][0]['message'])
else:print(f"请求失败,状态码:{response.status_code}, 响应内容:{response.text}")

vllm 进程查看,kill

ps aux | grep vllm

kill -9 6947

服务杀死了,但显存没释放

llama3

跟 qwen2.5 一样

deepseek-蒸馏版 qwen

vllm 启动需要加个参数 --enforce-eager

始终使用急切模式PyTorch,如果为False,则在混合模式下使用急切模式和CUDA图以获得最大性能和灵活性

vllm serve /root/autodl-tmp/deepseek-ai/DeepSeek-R1-Distill-Qwen-1___5B/ \
--trust-remote-code \
--served-model-name qwen2_5_1_5 \
--gpu-memory-utilization 0.7 \
--tensor-parallel-size 1 \
--max-model-len 32768 \
--dtype=half \
--enforce-eager

参数说明:VLLM参数解释-中文表格形式-CSDN博客

参考:

https://github.com/datawhalechina/self-llm/blob/master/models/Qwen2.5/03-Qwen2.5-7B-Instruct%20vLLM%20%E9%83%A8%E7%BD%B2%E8%B0%83%E7%94%A8.md

使用vLLM部署Qwen2.5-VL-7B-Instruct模型的详细指南_vllm qwen2.5-vl-CSDN博客

vLLM - Qwen

本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若转载,请注明出处:http://www.mzph.cn/web/70547.shtml

如若内容造成侵权/违法违规/事实不符,请联系多彩编程网进行投诉反馈email:809451989@qq.com,一经查实,立即删除!

相关文章

Python NumPy库使用指南:从入门到精通

1. 引言 NumPy(Numerical Python)是 Python 中用于科学计算的核心库之一。它提供了强大的多维数组对象(ndarray),以及一系列高效的数学函数,能够轻松处理大规模的数值数据。NumPy 是许多其他科学计算库(如 Pandas、Matplotlib、Scikit-learn 等)的基础。 本文将详细介…

15.2 智能销售顾问系统技术架构解密:构建企业级知识驱动型对话引擎

智能销售顾问系统技术架构解密:构建企业级知识驱动型对话引擎 关键词:RAG 架构设计、销售知识库系统、LoRA 微调优化、多模态交互引擎、高并发服务部署 1. 系统技术架构全景解析 1.1 核心架构设计图 #mermaid-svg-UBkTgaR5lf5WfGMa {font-family:"trebuchet ms",…

用PyTorch从零构建 DeepSeek R1:模型架构和分步训练详解

DeepSeek R1 的完整训练流程核心在于,在其基础模型 DeepSeek V3 之上,运用了多种强化学习策略。 本文将从一个可本地运行的基础模型起步,并参照其技术报告,完全从零开始构建 DeepSeek R1,理论结合实践,逐步…

爬虫基础入门之爬取豆瓣电影Top250-Re正则的使用

网址:豆瓣电影 Top 250 本案例所需要的模块 requests (用于发送HTTP请求)re (用于字符串匹配和操作) 确定需要爬取的数据 : 电影的名称电影的年份电影的评分电影评论人数 一. 发送请求 模拟浏览器向服务器发送请求 准备工作 -分析页面: F12 or 右击点击检查 查看…

力扣hot100——岛屿数量 岛屿问题经典dfs总结

给你一个由 1(陆地)和 0(水)组成的的二维网格,请你计算网格中岛屿的数量。 岛屿总是被水包围,并且每座岛屿只能由水平方向和/或竖直方向上相邻的陆地连接形成。 此外,你可以假设该网格的四条边…

FPGA DSP:Vivado 中带有 DDS 的 FIR 滤波器

本文使用 DDS 生成三个信号,并在 Vivado 中实现低通滤波器。低通滤波器将滤除相关信号。 介绍 用DDS生成三个信号,并在Vivado中实现低通滤波器。低通滤波器将滤除较快的信号。 本文分为几个主要部分: 信号生成:展示如何使用DDS&am…

MessageAuthenticator

MessageAuthenticator https://coova.github.io/JRadius/ https://coova.github.io/JRadius/ import org.tinyradius.packet.RadiusPacket; import org.tinyradius.util.RadiusUtil; import java.nio.charset.StandardCharsets;public class RadiusAuthUtils {/*** 生成 RADI…

Spring Boot嵌入式服务器深度解析:从配置到调优的全方位指南

文章目录 引言一、嵌入式服务器核心原理1.1 架构设计特点1.2 主流服务器对比 二、嵌入式服务器配置实战2.1 基础配置模板2.2 HTTPS安全配置 三、高级调优策略3.1 线程池优化(Tomcat示例)3.2 响应压缩配置3.3 访问日志配置 四、服务器切换实战4.1 切换至U…

基于CentOS7安装kubesphere和Kubernetes并接入外部ES收集日志

一、修改所有节点主机名 主节点就修改成master hostnamectl set-hostname master 然后输入bash刷新当前主机名 工作节点1就修改成node1 hostnamectl set-hostname node1 然后输入bash刷新当前主机名 二、全部节点安装依赖并同步时间 yum -y install socat conntrack ebta…

探索与Cursor协作创建一个完整的前后端分离的项目的最佳实践

探索与Cursor协作创建一个完整的前后端分离的项目的最佳实践 Cursor简介 Cursor在目前代表了AI编程技术的顶峰。在一定程度上可以说是当今AI时代的最强生产力代表。为此,不惜重金开了年费会员来紧跟时代步伐。当然cline、roo code、trae等开源或者免费产品也在紧追不舍。 C…

支持向量机(SVM)在 NLP 中的使用场景

支持向量机(Support Vector Machine, SVM)是一种强大的监督学习算法,广泛应用于分类任务中。由于其出色的分类性能和高效的计算特点,SVM 已经成为自然语言处理(NLP)领域中的一种经典模型。SVM 在 NLP 中的应用非常广泛,尤其在文本分类任务中,表现出色。 本文将探讨 SV…

nodejs:vue 3 + vite 作为前端,将 html 填入<iframe>,在线查询英汉词典

向 doubao.com/chat/ 提问: node.js js-mdict 作为后端,vue 3 vite 作为前端,编写在线查询英汉词典 后端部分(express js-mdict ) 详见上一篇:nodejs:express js-mdict 作为后端&#xff…

Jenkins 部署在 Mac 并在局域网内通过 ip 访问

Jenkins 部署在 Mac 并在局域网内通过 ip 访问 一、修改配置文件 打开文件 ~/Library/LaunchAgents/homebrew.mxcl.jenkins.plist 打开文件 /usr/local/opt/jenkins/homebrew.mxcl.jenkins.plist 两个文件目录不同&#xff0c;内容一样 <?xml version"1.0" e…

2通道12bit 10G USB高速示波器采集卡

概述 USB高速示波器采集卡 2通道&#xff0c;12位&#xff0c;10GSa/s 采样率 DC~2.5GHz 带宽 USB高速示波器采集卡是一款高速12bit多通道USB数字化仪它具有2通道10GSa/s采样率&#xff0c;模拟前端带宽从DC到2.5GHz&#xff0c;板载32GB DDR4存储&#xff0c;使其能够满足长…

Python|OpenCV-实现人物眨眼检测(21)

前言 本文是该专栏的第23篇,后面将持续分享OpenCV计算机视觉的干货知识,记得关注。 通过OpenCV库来实现人物的眨眼检测,首先是需要了解眨眼检测的基本原理。一般来说,是需要通过检测眼睛的状态,比如眼睛是否闭合来判断是否眨眼。对此,如果基于OpenCV,通过Python如何去实…

Qt | Excel创建、打开、读写、另存和关闭

01 如何在Qt中使用QXlsx库进行Excel文件的读写操作,包括创建新Excel、写入数据、读取数据以及文件保存和释放资源。通过实例展示了如何加载库、编写.h和.cpp文件,并演示了使用单元格引用和行列号进行数据操作的方法。 QXlsx是一个可以读写Excel文件的库。不依赖office以及…

AMBA-CHI协议详解(十九)

文章目录 4.6 Silent cache state transitions4.7 Cache state transitions at a Requester4.7.1 Read request transactions4.7.2 Dataless request transactions4.7.3 Write request transactions4.7.4 Atomic transactions4.7.5 Other request transactions4.6 Silent cache…

常见的“锁”有哪些?

悲观锁 悲观锁认为在并发环境中&#xff0c;数据随时可能被其他线程修改&#xff0c;因此在访问数据之前会先加锁&#xff0c;以防止其他线程对数据进行修改。常见的悲观锁实现有&#xff1a; 1.互斥锁 原理&#xff1a;互斥锁是一种最基本的锁类型&#xff0c;同一时间只允…

深入理解 Python 作用域:从基础到高级应用

在 Python 编程中&#xff0c;作用域是一个至关重要的概念&#xff0c;它决定了变量和函数的可见性与生命周期。正确理解和运用作用域规则&#xff0c;对于编写结构清晰、易于维护的代码起着关键作用。无论是简单的脚本还是复杂的大型项目&#xff0c;作用域都贯穿其中&#xf…

ubuntu磁盘清理垃圾文件

大头文件排查 #先查看是否是内存满了&#xff0c;USER 很高即是满了 du -f#抓大头思想&#xff0c;优先删除大文件#查看文件目录 内存占用量并排序&#xff0c;不断文件递归下去 du --max-depth1 -h /home/ -h | sort du --max-depth1 -h /home/big/ -h | sort 缓存文件清理…