LLaMA-Factory 微调 Qwen3-VL 详细流程
使用 LLaMA-Factory 对 Qwen3-VL 多模态大模型进行微调(SFT)的完整流程。内容涵盖环境安装与依赖配置、模型下载、LoRA 微调启动、模型合并以及基于 vLLM 的部署与接口调用。通过命令行操作和配置文件修改,实现私有数据集的训练及高并发服务部署,适用于工业落地场景。

使用 LLaMA-Factory 对 Qwen3-VL 多模态大模型进行微调(SFT)的完整流程。内容涵盖环境安装与依赖配置、模型下载、LoRA 微调启动、模型合并以及基于 vLLM 的部署与接口调用。通过命令行操作和配置文件修改,实现私有数据集的训练及高并发服务部署,适用于工业落地场景。

目标:本文详细介绍多模态大模型使用 LLaMA-Factory 进行多模态模型微调(SFT)的全部流程,以及微调后合并和工业落地部署方案。具体包括:
示例模型:Qwen2.5-VL-Instruct, Qwen3-VL-Instruct
git clone --depth 1 https://github.com/hiyouga/LLaMA-Factory.git
从 ModelScope 或者 HuggingFace 下载模型到指定目录。比如 qwen3-vl。
modelscope download --model Qwen/Qwen3-VL-2B-Instruct --local_dir ./qwen3_vl_model 将模型下载到 models 目录下。在 Linux 系统上,一般直接使用命令行进行训练、合并、部署。
先使用默认数据集测试微调流程
在 LLaMA-Factory-main 目录下:
执行 CUDA_VISIBLE_DEVICES=6 llamafactory-cli train examples/train_lora/qwen2_5vl_lora_sft.yaml 开始训练画面。
编辑配置文件 vim examples/train_lora/qwen2_5vl_lora_sft.yaml:
### model
model_name_or_path: /data/hcb/LLaMA-Factory-main/qwen3_vl_model # 模型路径
image_max_pixels: 262144
video_max_pixels: 16384
trust_remote_code: true
### method
stage: sft
do_train: true
finetuning_type: lora
lora_rank: 8
lora_target: all
### dataset
dataset: mllm_demo,identity,alpaca_en_demo # video: mllm_video_demo 默认数据集,项目自带
template: qwen3_vl # 这里要改
cutoff_len: 2048
max_samples: 1000
overwrite_cache: true
preprocessing_num_workers: 16
dataloader_num_workers: 4
### output
output_dir: saves/qwen3vl-2b/lora/sft # lora 文件保存路径
logging_steps: 10
save_steps: 500
plot_loss: true
overwrite_output_dir: true
save_only_model: false
report_to: none # choices: [none, wandb, tensorboard, swanlab, mlflow]
### train
per_device_train_batch_size: 1
gradient_accumulation_steps: 8
learning_rate: 1.0e-4
num_train_epochs: 1.0
lr_scheduler_type: cosine
warmup_ratio: 0.1
bf16: true
ddp_timeout: 180000000
resume_from_checkpoint: null
### eval
# val_size: 0.1
# per_device_eval_batch_size: 1
# eval_strategy: steps
# eval_steps: 500
训练完成后 LoRA 模型存储在配置的目录中。
微调完成后,需要合并原模型和 LoRA 模型。
llamafactory-cli export examples/merge_lora/qwen2_5vl_lora_sft.yaml编辑合并脚本:vim examples/merge_lora/llama3_lora_sft.yaml
### Note: DO NOT use quantized model or quantization_bit when merging lora adapters
### model
model_name_or_path: /data/hcb/LLaMA-Factory-main/qwen3_vl_model # 原模型路径
adapter_name_or_path: saves/qwen3vl-2b/lora/sft # lora 路径
template: qwen3_vl # 模型格式
trust_remote_code: true
### export
export_dir: output/qwen3vl_lora_sft
export_size: 5
export_device: cpu # choices: [cpu, auto]
export_legacy_format: false
合并后的模型保存在配置的存储路径中。
目前使用 LLaMA-Factory 整个流程基本固化,主要就是构造不同的数据集。前面我们使用了官方提供的数据集进行了训练。现在我们构造自己的私有数据集,还是以文本类 SFT 任务为例。
制作训练数据集,要先认识 data 目录以及 dataset_info.json 文件。LLaMA-Factory-main 主目录下有一个 data 目录用来存放数据集文件以及数据集配置文件 (dataset_info.json)。
对于我们前面使用的训练数据 dataset: mllm_demo,我们可以在 dataset_info.json 中找到注册记录。
其对应的具体文件就是 file_name 指向的文件名,即 data 目录下的 mllm_demo.json 文件。其格式如下:
我们可以仿照这个格式构造自己的 SFT 任务的数据集。
LLaMA-Factory 支持的多种任务的数据集格式都在:https://github.com/hiyouga/LLaMA-Factory/blob/main/data/README.md
多模态 - 图像 构造 ShareGPT 格式参考:
在 dataset_info.json 文件中注册 tab_reg_samples.json 数据集。
LLaMA-Factory-main/data 新建图片存放目录 table_reg(与数据集中 images 下的路径一致)。将数据集中用到的图片上传到 table_reg 目录下。
我们需要把自己的数据使用脚本改造成上面的 json 格式。构造了一个根据图片识别其中表格的数据集。提示词中需要添加图像的占位符 然后在 images 列表中添加图片的具体路径。(可以添加多个图片。)
数据集配置完成后,在 examples/train_lora/qwen2_5vl_lora_sft.yaml 训练脚本中直接引入数据集。只修改 dataset:部分。
项目主目录下执行 vim examples/train_lora/qwen2_5vl_lora_sft.yaml
### model
model_name_or_path: /data/hcb/LLaMA-Factory-main/qwen3_vl_model # 模型路径
image_max_pixels: 262144
video_max_pixels: 16384
trust_remote_code: true
### method
stage: sft
do_train: true
finetuning_type: lora
lora_rank: 8
lora_target: all
### dataset
dataset: table_reg # 注册的数据集名称
template: qwen3_vl
cutoff_len: 2048
max_samples: 1000
overwrite_cache: true
preprocessing_num_workers: 16
dataloader_num_workers: 4
### output
output_dir: saves/qwen3vl-2b_table/lora/sft # lora 文件保存路径
logging_steps: 10
save_steps: 500
plot_loss: true
overwrite_output_dir: true
save_only_model: false
report_to: none # choices: [none, wandb, tensorboard, swanlab, mlflow]
### train
per_device_train_batch_size: 1
gradient_accumulation_steps: 8
learning_rate: 1.0e-4
num_train_epochs: 1.0
lr_scheduler_type: cosine
warmup_ratio: 0.1
bf16: true
ddp_timeout: 180000000
resume_from_checkpoint: null
### eval
# val_size: 0.1
# per_device_eval_batch_size: 1
# eval_strategy: steps
# eval_steps: 500
修改完成后执行训练:
CUDA_VISIBLE_DEVICES=6 llamafactory-cli train examples/train_lora/qwen2_5vl_lora_sft.yaml
后续合并步骤完全一样。
...待补充
LLaMA-Factory 也支持基本的模型部署,但是很多时候我们需要以接口调用的形式来使用大模型能力,常见的有 Ollama、vLLM、SGlang 等方式,为了支持产品落地支持高并发,我们一般使用 vLLM 部署模型,基于 OpenAI 风格进行接口调用。下面详细介绍一下使用 vLLM 部署模型并请求。
在当前虚拟环境中执行:pip install vllm==0.11.0 -i https://mirrors.tuna.tsinghua.edu.cn/pypi/web/simple/
直接启动我们上面微调合并后的模型:
# 启动 vLLM OpenAI 兼容 API 服务器
# 核心功能:将指定大模型以 OpenAI API 格式暴露服务,支持高并发、低延迟推理
export CUDA_VISIBLE_DEVICES=6
# 指定使用哪个 gpu
python -m vllm.entrypoints.openai.api_server \
--host 0.0.0.0 \
# 绑定所有网络接口,允许外部机器访问(仅内网环境建议使用)
--port 8003\
# API 服务监听端口,客户端通过该端口调用(自定义)
--model /data/hcb/LLaMA-Factory-main/output/qwen3vl_lora_sft \
# 模型文件本地路径
--served-model-name qwen3_vl \
# 对外暴露的模型名称(客户端调用时指定该名称)
--trust-remote-code \
# 信任模型仓库中的自定义代码(部分模型需要自定义加载逻辑)
--dtype float16 \
# 模型推理数据类型(float16 平衡性能和精度,适配多数 GPU)
--gpu-memory-utilization 0.8\
# GPU 显存利用率上限(根据实际情况调整)
--tp 1\
# 张量并行度(1 表示单卡推理,多卡时需调整为显卡数量)
# 上面是命令介绍 可以直接用下面这行启动
CUDA_VISIBLE_DEVICES=6 python -m vllm.entrypoints.openai.api_server --host 0.0.0.0 --port 8003 --model /data/hcb/LLaMA-Factory-main/output/qwen3vl_lora_sft --served-model-name qwen3_vl --trust-remote-code --dtype float16 --gpu-memory-utilization 0.8
启动成功。
import openai
import base64
import os
from openai import OpenAI
def encode_image(image_path):
"""将图像文件编码为 base64"""
with open(image_path, "rb") as image_file:
return base64.b64encode(image_file.read()).decode('utf-8')
def multimodal_chat(image_path=None, text_prompt="描述这张图片"):
""" 多模态聊天请求
Args:
image_path: 图像文件路径
text_prompt: 文本提示
"""
client = OpenAI(
api_key="Empty",
base_url="http://<server_ip>:8003/v1/" # 你的 vLLM 服务器地址和端口
)
# 构建消息内容
messages = [{"role": "system", "content": "你是一个多模态智能助手,可以理解和分析图像内容。"}]
# 如果有图像,添加多模态内容
if image_path and os.path.exists(image_path):
base64_image = encode_image(image_path)
user_content = [{"type": "text", "text": text_prompt}, {"type": "image_url", "image_url": {"url": f"data:image/jpeg;base64,{base64_image}"}}]
else:
# 如果没有图像,只发送文本
user_content = text_prompt
messages.append({"role": "user", "content": user_content})
payload = {
"model": "qwen3_vl", # 你设置的模型名称
"messages": messages,
"temperature": 0.1,
"max_tokens": 2000
}
print("请求 payload 结构:")
print(f"- 模型:{payload['model']}")
print(f"- 消息数量:{len(payload['messages'])}")
if image_path:
print(f"- 包含图像:{image_path}")
print(f"- 提示词:{text_prompt}")
try:
# 发送请求
response = client.chat.completions.create(**payload, timeout=30) # 多模态请求可能需要更长时间
return response
except Exception as e:
print(f"请求失败:{e}")
return None
if __name__ == "__main__":
# 直接测试特定图片
image_path = r"C:\Users\15941\Desktop\临时\副业\宠物\狗头舔脚\2.png" # 修改为你的图片路径
prompt = "描述这张图片中有什么"
if os.path.exists(image_path):
print(f"正在分析图片:{image_path}")
res = multimodal_chat(image_path=image_path, text_prompt=prompt)
if res and res.choices:
print("\n模型回复:")
print(res.choices[0].message.content)
else:
print("请求失败")
结果展示略。

微信公众号「极客日志」,在微信中扫描左侧二维码关注。展示文案:极客日志 zeeklog
使用加密算法(如AES、TripleDES、Rabbit或RC4)加密和解密文本明文。 在线工具,加密/解密文本在线工具,online
生成新的随机RSA私钥和公钥pem证书。 在线工具,RSA密钥对生成器在线工具,online
基于 Mermaid.js 实时预览流程图、时序图等图表,支持源码编辑与即时渲染。 在线工具,Mermaid 预览与可视化编辑在线工具,online
解析常见 curl 参数并生成 fetch、axios、PHP curl 或 Python requests 示例代码。 在线工具,curl 转代码在线工具,online
将字符串编码和解码为其 Base64 格式表示形式即可。 在线工具,Base64 字符串编码/解码在线工具,online
将字符串、文件或图像转换为其 Base64 表示形式。 在线工具,Base64 文件转换器在线工具,online