跳到正文
Yayin Story Studio Yayin Story Studio 项目文档

Visindigo::Agent::Dialog Class

class Visindigo::Agent::Dialog

一次完整的对话及其执行入口. 详情...

头文件: #include <Agent/Dialog.h>
自以下版本: Visindigo 0.17.0

公开成员函数

(自 Visindigo 0.17.0 引入) Dialog()
(自 Visindigo 0.17.0 引入) virtual ~Dialog()
(自 Visindigo 0.17.0 引入) Visindigo::Agent::Dialog &addFunction(Visindigo::Agent::Function *function)
(自 Visindigo 0.17.0 引入) Visindigo::Agent::Dialog &addMCP(const Visindigo::Agent::MCP &server)
(自 Visindigo 0.17.0 引入) Visindigo::Agent::Dialog &addPrompt(const Visindigo::Agent::Prompt &prompt)
(自 Visindigo 0.17.0 引入) Visindigo::Agent::Dialog &addSkill(const Visindigo::Agent::Skill &skill)
(自 Visindigo 0.17.0 引入) void appendDelta(const QString &delta)
(自 Visindigo 0.17.0 引入) Visindigo::Agent::Dialog &appendMessage(const Visindigo::Agent::Message &message)
(自 Visindigo 0.17.0 引入) Visindigo::Agent::Dialog &appendMessage(Visindigo::Agent::Message::Role role, const QString &content)
(自 Visindigo 0.17.0 引入) Visindigo::Agent::Dialog &appendPrompt(const QString &name, const QMap<QString, QString> &variables = {})
(自 Visindigo 0.17.0 引入) void beginAssistantMessage()
(自 Visindigo 0.17.0 引入) Visindigo::Agent::Dialog &clearMessages()
(自 Visindigo 0.17.0 引入) bool copyTo(Visindigo::Agent::Dialog *target) const
(自 Visindigo 0.17.0 引入) void endAssistantMessage()
(自 Visindigo 0.17.0 引入) qint32 findLastAssistantMessage() const
(自 Visindigo 0.17.0 引入) bool fromJson(const Visindigo::Utility::JsonConfig &json)
(自 Visindigo 0.17.0 引入) QString getBranchFromID() const
(自 Visindigo 0.17.0 引入) Visindigo::Agent::Model::Capabilities getCapabilityRequirement() const
(自 Visindigo 0.17.0 引入) Visindigo::Agent::Function *getFunction(const QString &id) const
(自 Visindigo 0.17.0 引入) QStringList getFunctionIds() const
(自 Visindigo 0.17.0 引入) QString getId() const
(自 Visindigo 0.17.0 引入) Visindigo::Agent::Message getLastMessage() const
(自 Visindigo 0.17.0 引入) QList<Visindigo::Agent::MCP> getMCPs() const
(自 Visindigo 0.17.0 引入) qint32 getMessageCount() const
(自 Visindigo 0.17.0 引入) QList<Visindigo::Agent::Message> getMessages() const
(自 Visindigo 0.17.0 引入) QString getModelId() const
(自 Visindigo 0.17.0 引入) QList<Visindigo::Agent::Prompt> getPrompts() const
(自 Visindigo 0.17.0 引入) QString getProviderId() const
(自 Visindigo 0.17.0 引入) QString getReasoningContent() const
(自 Visindigo 0.17.0 引入) QList<Visindigo::Agent::Skill> getSkills() const
(自 Visindigo 0.17.0 引入) QString getStreamingContent() const
(自 Visindigo 0.17.0 引入) bool isStreaming() const
(自 Visindigo 0.17.0 引入) Visindigo::Agent::Dialog &removeFunction(const QString &id)
(自 Visindigo 0.17.0 引入) Visindigo::Agent::Dialog &removeMCP(const QString &name)
(自 Visindigo 0.17.0 引入) Visindigo::Agent::Dialog &removePrompt(const QString &name)
(自 Visindigo 0.17.0 引入) Visindigo::Agent::Dialog &removeSkill(const QString &name)
(自 Visindigo 0.17.0 引入) void run()
(自 Visindigo 0.17.0 引入) Visindigo::Agent::Dialog &setBranchFromID(const QString &id)
(自 Visindigo 0.17.0 引入) Visindigo::Agent::Dialog &setCapabilityRequirement(Visindigo::Agent::Model::Capabilities required)
(自 Visindigo 0.17.0 引入) Visindigo::Agent::Dialog &setModelId(const QString &id)
(自 Visindigo 0.17.0 引入) Visindigo::Agent::Dialog &setProviderId(const QString &id)
(自 Visindigo 0.17.0 引入) Visindigo::Utility::JsonConfig toJson() const
(自 Visindigo 0.17.0 引入) Visindigo::Agent::Dialog &truncateTo(qint32 messageCount)

信号

(自 Visindigo 0.17.0 引入) void messageAppended(qint32 index)
(自 Visindigo 0.17.0 引入) void runFailed(const QString &message)
(自 Visindigo 0.17.0 引入) void streamBegan()
(自 Visindigo 0.17.0 引入) void streamDelta(const QString &delta)
(自 Visindigo 0.17.0 引入) void streamEnded(const QString &fullContent)
(自 Visindigo 0.17.0 引入) void streamReasoning(const QString &delta)

详细说明

Dialog 持有消息列表、这次对话可用的 Skill / MCP / Function / Prompt, 以及要用哪个 Provider 的哪个模型。run() 会把当前消息发出去,把流式 返回的内容通过信号吐出,并在模型请求调用工具时自动执行工具、把结果 回灌后继续请求,直到模型给出最终答复。

每个 Dialog 在构造时获得一个 UUID,之后不再改变——它同时是 Center 里的 索引键和会话记录里的标识。setBranchFromID() 记录"本条对话是从哪条 分出来的",重新生成回答时新对话会指向被它取代的那条,于是分支关系自然而 然地留在数据里,不需要额外维护一棵树。

run() 上的配置优先级是:本 Dialog 上挂的 Skill / MCP / Function / Prompt 覆盖 Center 上的同名全局配置。这让人可以给某次特殊对话临时挂一个技能, 而不必先去全局配置里删掉同名项。

Note: Dialog 的所有权属于 Center。请通过 Center::removeDialog() 销毁, 直接 delete 会让 Center 的表里留下一个悬空指针。

成员函数文档

[since Visindigo 0.17.0] Dialog::Dialog()

构造一个空对话,并立即分配一个新的 UUID。

这个function 从 Visindigo 0.17.0 开始支持。

[virtual noexcept, since Visindigo 0.17.0] Dialog::~Dialog()

中止仍在进行的请求,并释放本对话独占的函数对象。

Warning: 这里不会把自己从 Center 的表中摘除。销毁对话请调用 Center::removeDialog()。

这个function 从 Visindigo 0.17.0 开始支持。

[since Visindigo 0.17.0] Visindigo::Agent::Dialog &Dialog::addFunction(Visindigo::Agent::Function *function)

给本对话挂一个函数,所有权随之转移给本对话。

同一个 id 重复添加会替换旧项,旧对象被释放。传入 nullptr 什么也不做。

function 要挂载的函数对象,所有权随之转移给本对话。

这个function 从 Visindigo 0.17.0 开始支持。

[since Visindigo 0.17.0] Visindigo::Agent::Dialog &Dialog::addMCP(const Visindigo::Agent::MCP &server)

给本对话挂一个工具服务器配置,同名会覆盖 Center 上的全局同名项。

server 要挂载的工具服务器配置。

这个function 从 Visindigo 0.17.0 开始支持。

[since Visindigo 0.17.0] Visindigo::Agent::Dialog &Dialog::addPrompt(const Visindigo::Agent::Prompt &prompt)

给本对话挂一个提示模板,同名会覆盖 Center 上的全局同名项。

prompt 要挂载的提示模板。

这个function 从 Visindigo 0.17.0 开始支持。

[since Visindigo 0.17.0] Visindigo::Agent::Dialog &Dialog::addSkill(const Visindigo::Agent::Skill &skill)

给本对话挂一个技能。同名技能会覆盖 Center 上的全局同名项。

skill 要挂载的技能。

这个function 从 Visindigo 0.17.0 开始支持。

[since Visindigo 0.17.0] void Dialog::appendDelta(const QString &delta)

追加一段流式增量,并发出 streamDelta()。

Note: 增量是模型输出的碎片,可能从多字节字符或 Markdown 语法的中途切开, 因此不要对单个增量做解析,只能对累积结果做。

delta 本次新增的正文片段。

这个function 从 Visindigo 0.17.0 开始支持。

[since Visindigo 0.17.0] Visindigo::Agent::Dialog &Dialog::appendMessage(const Visindigo::Agent::Message &message)

追加一条消息,并发出 messageAppended()。

message 要追加的消息。

这个function 从 Visindigo 0.17.0 开始支持。

[since Visindigo 0.17.0] Visindigo::Agent::Dialog &Dialog::appendMessage(Visindigo::Agent::Message::Role role, const QString &content)

以角色与内容追加一条消息的便捷重载。

这个function 从 Visindigo 0.17.0 开始支持。

[since Visindigo 0.17.0] Visindigo::Agent::Dialog &Dialog::appendPrompt(const QString &name, const QMap<QString, QString> &variables = {})

查找模板、渲染并追加为一条消息。模板名不存在时什么也不做。

查找顺序是先本对话后 Center,与 run() 的覆盖规则一致。

name 模板名称。 variables 模板变量表。

这个function 从 Visindigo 0.17.0 开始支持。

[since Visindigo 0.17.0] void Dialog::beginAssistantMessage()

开始接收一条助手消息:清空流式缓冲并发出 streamBegan()。

流式接收由 run() 自行驱动,手工调用它只适用于自己实现了传输、 想复用本对话渲染逻辑的场景。

这个function 从 Visindigo 0.17.0 开始支持。

[since Visindigo 0.17.0] Visindigo::Agent::Dialog &Dialog::clearMessages()

清空全部消息,但保留技能、工具与模型配置。

这个function 从 Visindigo 0.17.0 开始支持。

[since Visindigo 0.17.0] bool Dialog::copyTo(Visindigo::Agent::Dialog *target) const

把消息与配置复制到另一条对话。

复制的内容包括消息列表、Skill / MCP / Prompt、Provider 与模型选择、 能力要求。目标对话保留自己的 id,这样可以先看一份草稿再决定是否让它 取代原对话。

Note: 函数对象不会被复制。Function 是带有独占所有权的接口,无法深拷贝, 共享指针又会在两边析构时重复释放;需要跨对话复用的工具请注册到 Center 上, 那里本来就是通过 id 解析的。目标对话自己原有的函数保持不变。

target 复制目标对话。

return 复制是否成功;目标为空或就是自身时返回 false。

这个function 从 Visindigo 0.17.0 开始支持。

[since Visindigo 0.17.0] void Dialog::endAssistantMessage()

结束流式接收:把缓冲内容作为一条助手消息追加到对话末尾,发出 messageAppended() 与 streamEnded()。

缓冲为空时不追加消息,但仍会发出 streamEnded(),以便界面上把"正在 生成"的状态收回去。

思考内容会被一并写进这条消息(见 Message::setReasoning()),因此历史 记录里每一轮都能看到当时是怎么想的,而不只是最后说了什么。这一步必须在 清空缓冲之前完成:思考原本只活在缓冲区里,一旦漏掉,界面上那一段就会 随着流式状态一起消失,留下的答复看不出为什么是那个结论。

这个function 从 Visindigo 0.17.0 开始支持。

[since Visindigo 0.17.0] qint32 Dialog::findLastAssistantMessage() const

返回最后一条助手消息的下标;没有助手消息时返回 -1。

下标可以直接交给 truncateTo():保留到这个下标为止,就恰好丢掉了那次 回答以及之后的所有内容,这正是"重新生成"需要的前置状态。

这个function 从 Visindigo 0.17.0 开始支持。

[since Visindigo 0.17.0] bool Dialog::fromJson(const Visindigo::Utility::JsonConfig &json)

从 JSON 对象恢复。

存档里的 id 会被恢复,这是 Dialog 的 id 唯一的赋值入口。没有 id 字段时 保留当前(新生成的)id。

Warning: 函数对象不在存档里,恢复后需要重新用 addFunction() 挂上; 否则模型请求调用工具时会收到"未知工具"的答复。

json 已解析的 JSON 对象。

return 是否恢复了存档里的 id。

这个function 从 Visindigo 0.17.0 开始支持。

[since Visindigo 0.17.0] QString Dialog::getBranchFromID() const

返回分叉来源的 id;不是由其他对话派生而来时返回空串。

这个function 从 Visindigo 0.17.0 开始支持。

[since Visindigo 0.17.0] Visindigo::Agent::Model::Capabilities Dialog::getCapabilityRequirement() const

返回挑选模型时的最低能力要求。

这个function 从 Visindigo 0.17.0 开始支持。

[since Visindigo 0.17.0] Visindigo::Agent::Function *Dialog::getFunction(const QString &id) const

按 id 查找函数,先查本对话再查 Center。找不到时返回 nullptr。

id 函数 id。

这个function 从 Visindigo 0.17.0 开始支持。

[since Visindigo 0.17.0] QStringList Dialog::getFunctionIds() const

返回本对话独占的函数 id,不含 Center 上的全局函数。

这个function 从 Visindigo 0.17.0 开始支持。

[since Visindigo 0.17.0] QString Dialog::getId() const

返回对话的唯一标识。它在构造时生成,之后不再变化。

这个function 从 Visindigo 0.17.0 开始支持。

[since Visindigo 0.17.0] Visindigo::Agent::Message Dialog::getLastMessage() const

返回最后一条消息;没有任何消息时返回空消息。

这个function 从 Visindigo 0.17.0 开始支持。

[since Visindigo 0.17.0] QList<Visindigo::Agent::MCP> Dialog::getMCPs() const

返回本对话挂载的工具服务器配置。

这个function 从 Visindigo 0.17.0 开始支持。

[since Visindigo 0.17.0] qint32 Dialog::getMessageCount() const

返回消息条数。

这个function 从 Visindigo 0.17.0 开始支持。

[since Visindigo 0.17.0] QList<Visindigo::Agent::Message> Dialog::getMessages() const

返回全部消息,按时间顺序。

这个function 从 Visindigo 0.17.0 开始支持。

[since Visindigo 0.17.0] QString Dialog::getModelId() const

返回指定的模型 id;未指定时返回空串。

这个function 从 Visindigo 0.17.0 开始支持。

[since Visindigo 0.17.0] QList<Visindigo::Agent::Prompt> Dialog::getPrompts() const

返回本对话挂载的提示模板。

这个function 从 Visindigo 0.17.0 开始支持。

[since Visindigo 0.17.0] QString Dialog::getProviderId() const

返回指定的 Provider id;未指定时返回空串。

这个function 从 Visindigo 0.17.0 开始支持。

[since Visindigo 0.17.0] QString Dialog::getReasoningContent() const

返回最近一次生成中模型给出的思考内容,供界面在生成过程中实时展示。

推理模型的思考过程从 streamDelta() 之外的通道到达,它不属于回答, 因此不会在下一轮被重新发回服务端。生成结束后,这段内容会被写进对应的 助手消息(见 Message::getReasoning()),历史记录里仍能查到; 本函数只反映“当前这一次”的缓冲,在每次 beginAssistantMessage() 时清空。

这个function 从 Visindigo 0.17.0 开始支持。

[since Visindigo 0.17.0] QList<Visindigo::Agent::Skill> Dialog::getSkills() const

返回本对话挂载的技能,不含 Center 上的全局技能。

这个function 从 Visindigo 0.17.0 开始支持。

[since Visindigo 0.17.0] QString Dialog::getStreamingContent() const

返回当前已接收但尚未收尾的流式内容。

这个function 从 Visindigo 0.17.0 开始支持。

[since Visindigo 0.17.0] bool Dialog::isStreaming() const

判断本对话是否正在接收流式响应。

return 正在接收流式响应时返回 true。

这个function 从 Visindigo 0.17.0 开始支持。

[signal, since Visindigo 0.17.0] void Dialog::messageAppended(qint32 index)

新增了一条消息。index 是它在 getMessages() 中的下标。

Note: 只报下标不报内容,是为了让监听方自己去取:同一条消息在发出信号之后 仍可能被继续改写,传一份副本出去反而会造成"界面上的和实际存的不一样"。

这个function 从 Visindigo 0.17.0 开始支持。

[since Visindigo 0.17.0] Visindigo::Agent::Dialog &Dialog::removeFunction(const QString &id)

移除并释放本对话上的函数。移除之后,Center 上的全局同名函数会重新生效。

id 函数 id。

这个function 从 Visindigo 0.17.0 开始支持。

[since Visindigo 0.17.0] Visindigo::Agent::Dialog &Dialog::removeMCP(const QString &name)

移除本对话上的同名工具服务器配置。

name 工具服务器名称。

这个function 从 Visindigo 0.17.0 开始支持。

[since Visindigo 0.17.0] Visindigo::Agent::Dialog &Dialog::removePrompt(const QString &name)

移除本对话上的同名提示模板。

name 模板名称。

这个function 从 Visindigo 0.17.0 开始支持。

[since Visindigo 0.17.0] Visindigo::Agent::Dialog &Dialog::removeSkill(const QString &name)

移除本对话上的同名技能。移除之后,Center 上的全局同名技能会重新生效。

name 技能名称。

这个function 从 Visindigo 0.17.0 开始支持。

[since Visindigo 0.17.0] void Dialog::run()

执行本对话。

流程是:解析 Provider 与模型、拼装请求体(系统提示来自技能,消息来自 消息列表,工具声明来自函数表),随后发起流式请求。响应中的文本增量通过 streamDelta() 实时吐出;如果模型要求调用工具,则依次执行、把结果作为 Message::Role::Tool 消息追加,然后自动再发一轮,直到模型给出不含工具 调用的最终答复。

结果是异步的,本函数在请求发出后就返回。流程结束会发出 streamEnded(), 失败则发出 runFailed()。

Note: 同一时刻只允许一次执行。正在执行时再次调用会直接发出 runFailed(), 而不会排队——把两次生成叠在一起只会让会话记录变成一堆无法解释的片段。

这个function 从 Visindigo 0.17.0 开始支持。

[signal, since Visindigo 0.17.0] void Dialog::runFailed(const QString &message)

执行失败。message 是可以直接展示给用户的原因描述。

Note: 失败之后不会再有 streamEnded,因此界面上必须两个信号都接,否则 "正在生成"的状态会一直挂着消不掉。

这个function 从 Visindigo 0.17.0 开始支持。

[since Visindigo 0.17.0] Visindigo::Agent::Dialog &Dialog::setBranchFromID(const QString &id)

记录本对话从哪条对话分出来。全新对话留空。

它表达的是"这条对话取代了哪一条",因此重新生成回答时,新对话指向被它 取代的那条,分支关系就自然形成了,不需要额外的树结构。

id 被本条对话取代的对话 id;全新对话传空串。

这个function 从 Visindigo 0.17.0 开始支持。

[since Visindigo 0.17.0] Visindigo::Agent::Dialog &Dialog::setCapabilityRequirement(Visindigo::Agent::Model::Capabilities required)

设置挑选模型时的最低能力要求,默认要求文本能力。

当一次对话需要图片输入时把它设为文本与图片的按位或,模型挑选就会自动 跳过不支持图片的端点,而不是把图片发过去等一个 400 回来。

required 最低能力要求,多个能力按位或。

这个function 从 Visindigo 0.17.0 开始支持。

[since Visindigo 0.17.0] Visindigo::Agent::Dialog &Dialog::setModelId(const QString &id)

指定本次对话使用的模型。留空或指定的模型不可用时,由 Provider 按能力 要求自行挑选。

id 模型 id;留空表示由 Provider 挑选。

这个function 从 Visindigo 0.17.0 开始支持。

[since Visindigo 0.17.0] Visindigo::Agent::Dialog &Dialog::setProviderId(const QString &id)

指定本次对话使用的 Provider。留空时使用 Center::getDefaultProvider()。

id Provider 的 id;留空表示使用 Center 的默认 Provider。

这个function 从 Visindigo 0.17.0 开始支持。

[signal, since Visindigo 0.17.0] void Dialog::streamBegan()

开始一轮生成。这一轮的增量从此刻开始到达。

这个function 从 Visindigo 0.17.0 开始支持。

[signal, since Visindigo 0.17.0] void Dialog::streamDelta(const QString &delta)

回答正文的增量。

delta 本次新增的正文片段。

这个function 从 Visindigo 0.17.0 开始支持。

[signal, since Visindigo 0.17.0] void Dialog::streamEnded(const QString &fullContent)

这一轮生成结束。fullContent 是完整的回答正文。

出现工具调用时,一轮结束后会立刻开始下一轮,因此一次 run() 可能触发 多次 streamBegan 与 streamEnded。

这个function 从 Visindigo 0.17.0 开始支持。

[signal, since Visindigo 0.17.0] void Dialog::streamReasoning(const QString &delta)

思考内容的增量。仅推理模型会发出。

Note: 它与 streamDelta 是两条独立的通道:思考不属于回答,不会进入下一轮 请求,但会随 Message::setReasoning() 存进对应的助手消息。

delta 本次新增的思考片段。

这个function 从 Visindigo 0.17.0 开始支持。

[since Visindigo 0.17.0] Visindigo::Utility::JsonConfig Dialog::toJson() const

序列化为 JSON 对象,包含 id、分叉来源、模型选择、能力要求、消息列表, 以及本对话挂载的技能、工具服务器与模板。

Note: 函数对象无法序列化:它们承载的是可执行代码而不是数据。

这个function 从 Visindigo 0.17.0 开始支持。

[since Visindigo 0.17.0] Visindigo::Agent::Dialog &Dialog::truncateTo(qint32 messageCount)

只保留前 messageCount 条消息,删除其余部分。

messageCount 大于当前条数时什么也不做;为 0 时清空全部消息。

这个function 从 Visindigo 0.17.0 开始支持。