modelscope / ms-swift

Use PEFT or Full-parameter to finetune 300+ LLMs or 80+ MLLMs. (Qwen2, GLM4v, Internlm2.5, Yi, Llama3.1, Llava-Video, Internvl2, MiniCPM-V-2.6, Deepseek, Baichuan2, Gemma2, Phi3-Vision, ...)
https://swift.readthedocs.io/zh-cn/latest/Instruction/index.html
Apache License 2.0
3.38k stars 284 forks source link

agent部署如何实现openai function call的样式,而不是如文档中的react #1340

Closed lisenjie757 closed 2 weeks ago

lisenjie757 commented 2 months ago

按照Agent部署最佳实践.md文档和OpenAI教程,为什么使用gpt4接口时调用工具会直接返回工具和参数,并没有content,甚至可以同时生成多个tool,以及缺少参数时可以进行反问,我测试了文档里llama的demo,这种react格式还会生成无用的中间思考过程,缺少参数时也不会反问而是编造了个参数

是不是可以理解,现在的agent能力是你们封装了层prompt或template,去模拟openai api的工具调用样式,而openai调用工具的方式可能不是你们这样的,因为openai没有公布其中的细节?

以及你们agent使用方式和modelscope-agent,qwen-agent的有什么区别,他们调用工具也是类似你们封装了层template吗

hjh0119 commented 2 months ago

llm agent需要用相应的prompt来声明提供的tools以及回复格式, 我们这里采用了比较常用的react和toolbench格式, 中间的思考过程可以提升模型的思维能力(见论文)。

gpt4接口时调用工具会直接返回工具和参数,并没有content可能是因为封装时隐去了模型的回复部分。

如果你有更好的prompt或者实现方式, 欢迎告诉我们

lisenjie757 commented 2 months ago

llm agent需要用相应的prompt来声明提供的tools以及回复格式, 我们这里采用了比较常用的react和toolbench格式, 中间的思考过程可以提升模型的思维能力(见论文)。

gpt4接口时调用工具会直接返回工具和参数,并没有content可能是因为封装时隐去了模型的回复部分。

如果你有更好的prompt或者实现方式, 欢迎告诉我们

我调研了下,发现如InternLM2https://github.com/InternLM/InternLM/blob/main/chat/chat_format_zh-CN.md和GLM4https://github.com/THUDM/GLM-4/blob/main/finetune_demo/README.md 是原生就支持function call的,而如qwen2https://github.com/QwenLM/Qwen2?tab=readme-ov-file则需要搭配qwen-agent实现function call,而原生并不支持

我理解下,是不是因为InternLM2和GLM4的对话template本身就包含了有关function call的特殊token从而实现的fuction call,而如qwen-agent和swift是通过system prompt方式拼接大模型的输出回复实现的,是这样子吗?

如果是的话,我还想请教下,在swift中如何查看相关大模型的template的格式,以及如何用swift微调时修改原本template,例如微调qwen时使用glm的template使其原生支持funciton call能力,这样做是可行的吗?

hjh0119 commented 2 months ago

@lisenjie757 感谢调研

我调研了下,发现如InternLM2https://github.com/InternLM/InternLM/blob/main/chat/chat_format_zh-CN.md和GLM4https://github.com/THUDM/GLM-4/blob/main/finetune_demo/README.md 是原生就支持function call的

  1. 对于这些原生支持function call的模型, 我们未来会为模型对应的template设置对应的特殊token/prompt

是不是因为InternLM2和GLM4的对话template本身就包含了有关function call的特殊token从而实现的fuction call

  1. 特殊token与prompt的作用类似, 为了让模型理解场景和支持的工具信息

在swift中如何查看相关大模型的template的格式,以及如何用swift微调时修改原本template,例如微调qwen时使用glm的template使其原生支持funciton call能力,这样做是可行的吗?

  1. template的相关信息在/swift/llm/utils/template.py 文件中, 我们为每个模型设置了映射的template, 你也可以用参数--template 来使用其他template, 但一般效果不会好, 因为模型训练时依赖特定的template.
lisenjie757 commented 2 months ago
  1. 对于这些原生支持function call的模型, 我们未来会为模型对应的template设置对应的特殊token/prompt

关于这个我还有一点比较好奇,swift在微调时是如何用统一的数据格式去适配这么多开源大模型的template的,是会针对每一个开源大模型都写一个代码做适配处理嘛,是否有与官方repo的处理方式进行对齐,因为我很担心微调时swift的处理逻辑与官方repo的处理逻辑的不同而会带来潜在的问题

例如在Agent微调时按照swift文档数据的格式是这样的

{"tools":"{API_LIST}","messages": [{"role": "system", "content": "00000"}, {"role": "user", "content": "11111"}, {"role": "assistant", "content": "22222"}]}
{"tools":"{API_LIST}","messages": [{"role": "user", "content": "aaaaa"}, {"role": "assistant", "content": "bbbbb"}, {"role": "tool", "content": "ccccc"}, {"role": "assistant", "content": "ddddd"}]}
{"tools":"{API_LIST}","messages": [{"role": "user", "content": "AAAAA"}, {"role": "assistant", "content": "BBBBB"}, {"role": "tool", "content": "CCCCC"}, {"role": "assistant", "content": "DDDDD"}]}

那么对于qwen来说可能就是将tool的描述放到system prompt里,像这样

<|im_start|>system
xxxxx {API_LIST}<|im_end|>

而对于InternLM2则可能会放到特殊token里,如

<|im_start|>system name=<|plugin|>
{API_LIST}
<|im_end|>

以及诸如此类的处理细节,我相信会有很多

hjh0119 commented 2 months ago

对于这些原生支持function call的模型, 我们未来会为模型对应的template设置对应的特殊token/prompt

目前agent训练这部分我们给出了统一的三种tools prompt, 未来会为模型适配template

如何用统一的数据格式去适配模型

如下, template对齐官方实现, 这部分设置对推理和训练是统一的, 你可以参考template的encode方法

template的相关信息在/swift/llm/utils/template.py 文件中, 我们为每个模型设置了映射的template