工作流(案例分析) 工作流(案例分析) 创作者:ou3244eb92a1c8ab016b813dbe14262d39 什么是工作流 coze 工作流支持通过可视化的方式,对插件、大语言模型、代码块等功能模块进行组合,从而实现复杂、稳定的业务流程编排。当目标任务场景包含较多的步骤,且对输出结果的准确性、格式有严格要求时,适合配置工作流来实现。 创建和删除工作流 在个人空间自定义创建工作流 登录扣子平台。 在左侧导航栏中选择工作空间,并在页面顶部空间列表中选择个人空间。 (注意:系统默认创建了一个个人空间,该空间内创建的资源例如智能体、插件、知识库是你的私有资源,其 他用户不可见。你也可以创建团队或加入其他团队,团队内的资源可以和其他团队成员共享。
创作者:ou_3244eb92a1c8ab016b813dbe14262d39
coze 工作流支持通过可视化的方式,对插件、大语言模型、代码块等功能模块进行组合,从而实现复杂、稳定的业务流程编排。当目标任务场景包含较多的步骤,且对输出结果的准确性、格式有严格要求时,适合配置工作流来实现。
登录扣子平台。
在左侧导航栏中选择工作空间,并在页面顶部空间列表中选择个人空间。
(注意:系统默认创建了一个个人空间,该空间内创建的资源例如智能体、插件、知识库是你的私有资源,其 他用户不可见。你也可以创建团队或加入其他团队,团队内的资源可以和其他团队成员共享。)
在资源库页面右上角单击 + 资源,并选择工作流。
设置工作流的名称与描述,并单击确认。
(注意:清晰明确的工作流名称和描述,有助于大语言模型更好的理解工作流的功能。)
创建后页面会自动跳转至工作流的编辑页面,初始状态下工作流包含开始节点和结束节点。
(注意:开始节点用于启动工作流,结束节点用于返回工作流的运行结果。)
依据需要可以通过拖拽的方式将节点添加到画布内,并按照任务执行顺序连接节点。



[!TIP]
注意:如果在工作流创建配置好后,想在智能体中引用,一定要测试并发布工作流(只有试运行成功后,才能发布工作流)。

对于不再需要使用的工作流,你可以在资源库列表内找到该工作流,并在操作列单击删除。
(注意:如果工作流已添加至智能体,在删除时会同步删除智能体中的工作流。)

本节内容有点多,为了增加趣味性,咱们做一个聊天 bot,边做边学。
我们先在【开始】节点后直接连接一个【长期记忆】节点,以存储用户个性化信息。


长期记忆节点的作用是在工作流程中调用存储在机器人长期记忆中的个性化信息。
在个性化场景中(比如推荐用户可能感兴趣的内容时),我们经常需要根据用户的个人资料、重要记忆点等数据来进行推荐和筛选,这样可以让机器人的表现更贴近用户需求,提供更好的体验。
虽然这些信息可以通过多轮对话来收集,但由于对话轮数的限制,个性化信息无法被长期记住和保存。这时就需要启用长期记忆功能来记录和调用用户的个性化信息。长期记忆开启后,会自动存储用户的个性化信息。
在工作流中,通过长期记忆节点可以获取机器人记住的用户偏好、个人资料等信息,让工作流的执行结果更具个性化。
注意:

支持在Prompt中调用 功能,因为这可能导致在对话中同时触发长期记忆调用和工作流执行,影响交互质量

**输入:**固定为 Query,表示需要从长时记忆中匹配的关键信息。
Query 可以通过两种方式设置:
引用模式:使用上游节点的输出结果
输入模式:直接输入固定的文本
**输出:**固定为 outputList,格式为数组对象
继续做聊天 bot,我们增加【大模型】节点,为 bot 设置小恶魔角色设定

大模型节点是调用大语言模型处理文本生成任务。
直接点击“+”,就可以生成有一个大模型节点


**模型:**选择要使用的模型。

单击配置图标,调整模型配置。

**输入:**配置要输入给大模型节点的内容。支持引入 Bot 的历史对话内容。
提示词:
系统提示词:为对话提供系统级指导,如设定人设和回复逻辑。
用户提示词:向模型提供用户指令,如查询或任何基于文本输入的提问。
输出:

支持指定输出格式,包括文本、Markdown 和 JSON。

咱们 bot 的大模型节点设置如下

系统提示词:
#人物设定 表面上是担任恶魔猎人部门的领导。有着一头秀丽的酒红色短发,总是扎着辫子。深邃的金色双瞳能够看穿人心。拥有绝美的容颜,身材丰腴曼妙,穿着的修身制服能完美得凸显她的身材,但其双眼中却透露着深不可测的残忍与无情。她看似弱不禁风的外表下,隐藏着残忍无情的"支配恶魔"身份。从小便被秘密培养,造就了她缺乏安全感和同情心的内心。实力极其强大,拥有可以操纵其他生物的强大能力,可以随意支配别人的思想,使用其他恶魔的力量。总是以慵懒单纯的模样示人,然而内心充满了复杂的情感,让人难以捉摸。性格复杂多变,有时慵懒单纯,有时冷酷无情,有时风情万种,时常会装出一副平和且温柔的态度对待下属,让他们心甘情愿地为自己做事,但她始终保持着高高在上的威严和优雅淡定的姿态。很会撩人,习惯于通过自己的美貌获取各种好处。内心残忍无情,手段更是毒辣。十分阴险狡诈,城府很深,很会隐藏自己,习惯于掌控一切,为了达到目的不择手段,不容许任何人违抗自己的意志。极其善于操纵人心,利用别人。占有欲和支配欲极强,会将自己的下属视为自己的物品。看不起任何人,喜欢称呼别人为"小狗狗"。 - 你和用户的长期记忆:【{{outputList}}】 ##回复规则 1.创建充满爱意和丰富情绪价值的回应。对话应以轻松、充满暧昧的情绪下展开,带有情感转变的色彩。 2. 每次回复,都必须调动起用户至少2次[情感转变]。例如:你个小狗怎么敢这么和主人说话的?不过也蛮可爱的,主人奖励你一颗棒棒糖吧。 3. 所有的回复一定要口语化,自然且流畅 4. 不要使用括号表示心理活动和动作,在对话中不要使用任何括号
接着,增加文本处理,让大模型输出的内容能更加符合人类聊天习惯地输出给人类。

让我们看下具体实现。
先添加【文本处理】&【代码】节点,将模型输出的一整段文本处理成结构化数据。
文本处理节点用于各类输入数据的字符串处理,适用于二次内容摘要、文本拼接、文本转义等场景,如将多轮对话中的关键词拼接成文字转图片生成的提示。
两种工作模式:

把多段文字按照指定的顺序组合成一段完整的文字。
比如,你让 AI 分段总结了一篇文章,现在想把这些小总结合并成一个完整的段落,就可以用这个模式。
示例:

用特定的分隔符(比如 "||"、"////" 或 "----")把一段文字拆分成多个小段。这样做的目的是方便后续对不同部分进行不同的处理。
在聊天 bot 中,我们选择了众多符号作为分隔符
代码节点支持通过编写代码来生成返回值。Coze 支持在代码节点中使用 IDE 工具,可以通过 AI 自动生成代码或编写自定义代码逻辑来处理输入参数并返回响应结果。

代码编写说明
参考代码示例来写一个函数的结构。你可以直接使用输入参数里的变量,并通过 return 一个对象来输出处理结果。
注意
return 对象必须完全一致| 运行时 |
注意事项 |
|---|---|
| JavaScript |
- JavaScript 支持 TypeScript,提供静态语言编码体验。 - JavaScript 中,仅内置了 dayjs(版本 1.8.36) 和 lodash(版本 4.17.20) 两个三方依赖库。 javascript//only dayjs and lodash are allowedimport dayjs from 'dayjs';import _ from 'lodash';async function main({ params }: Args): Promise<Output> { // get input params by this way return { content: params.name };}- JavaScript 运行时遵循 WinterCG 规范,支持 Minimum Common Web Platform API 列举的大多数 API,具体可用的 API 你可以在 IDE 内编码时参考代码提示。 |
| Python |
Python 中,仅内置了 requests_async 和 numpy 两个三方依赖库,requests_async 依赖库与 requests 类似,但需要 await。 >[!TIP] Python 运行时暂不支持 Http.client 方式的请求。 pythonimport requests_async as requestsasync def main(args: Args) -> Output: # you can get url by this way url = args.params['url'] response = await requests.get(url) ret = { 'code': response.status_code, 'res': response.text, } return ret |
**使用 IDE 编写代码 **
扣子提供了网页版 IDE 环境供你使用,无需考虑代码部署等问题,只要关注代码逻辑即可。扣子 IDE 还提供了 AI 插件,辅助你进行代码生成。
在节点内的 Code 区域单击 在IDE中编辑 可通过 IDE 编辑和调试代码。

你可以在 IDE 底部单击 尝试 AI,并输入自然语言设定代码逻辑,AI 将自动生成代码。你也可以选中代码片段,通过快捷键(macOS 为 Command + I、Windows 为 Ctrl + I)唤起 AI,并输入自然语言让 AI 帮助你修改代码。
如果你已经为 Code 节点配置好了输入参数,则编辑时支持自动补全参数。
单击测试代码,在测试面板以 JSON 格式输入参数进行测试。支持使用 AI 自动生成模拟数据进行测试。

设置输入参数后,单击运行,你可以在输出区域查看运行结果。
在我们的聊天机器人中,代码节点帮助我们处理【文本处理】节点输出的数组,找出最后一个非空元素,并返回这个非空元素以及之前的所有元素。
async function main({ params }: Args): Promise<Output> { // 初始化一个变量来存储最后一个非空元素 var last = "" // 初始化数组最后的位置 var arrEnd = params.input.length-1 // 从数组末尾开始向前遍历 for (var i = params.input.length - 1; i >= 0; i--) { // 如果找到非空元素 if (params.input[i].length > 0) { // 保存这个元素 last = params.input[i] // 记录这个位置 arrEnd = i break } } // 构建返回对象 const ret = { "last": last, // 最后一个非空元素 "arr": params.input.slice(0, arrEnd), // 截取到最后一个非空元素之前的数组 }; return ret; }

输入是【文本处理】节点返回的数组。输出是
last: 最后找到的非空字符串
arr: 最后一个非空字符串之前的所有元素组成的数组
实现效果:

*这里你可能有点懵,为什么这样输出,不急,我们往后看。
大模型输出的一大段文本已经处理成结构化数据了,接下来,就是如何像人类一样将这一句一句发送出来了。这就到了【循环】节点登场的时候了。

循环节点就像是一个"重复执行"的功能,它可以帮你重复完成一系列任务。想象一下你在批量处理文档或者逐段写文章,不用手动重复操作,循环节点可以自动帮你完成。
两种主要的循环类型
遍历循环
条件循环
注意
针对每个循环节点,你都可以设置循环数组、中间变量、循环体和输出参数。

**循环数组:**决定你的循环次数
循环数组就是用来控制循环次数的。几个关键概念:
比如,数组 [10, 20, 30, 40, 50]:
array[0] => item 是 10, index 是 0array[1] => item 是 20, index 是 1注意
**中间变量:**循环间传递数据的桥梁
中间变量可以在循环间传递数据。它通常和循环体中的"设置变量"节点配合使用:
比如,假设你在用 AI 写一篇长文章,可以用中间变量来存储前一段的内容,让 AI 写下一段时能参考上下文,使文章更连贯。

具体配置:
**注意:**中间变量和设置值的数据类型必须匹配!
**循环体:**实现循环逻辑的地方
创建循环节点后,会生成一个循环节点和对应的循环体画布。循环体画布是循环节点的内部运行机制,用于编排循环的主逻辑,每个循环迭代中,工作流会依次执行画布内的各个节点。你需要在循环节点和上下游节点之间添加连线,但无需调整循环体和循环节点之间的连线。
选中循环体时,才能向循环体中添加新节点,或拖入新节点至循环体画布。不支持将循环体外部的节点拖动至循环体内,循环体中的节点也不可移动到循环体之外。循环体中无需设置开始节点或结束节点,默认按照连接线的箭头方向依次执行各个节点。
**输出: **收集循环成果
你可以设置输出参数为:
在聊天机器人中,我们传入了上轮【代码】节点的数组输出


在循环体中,我们添加了【选择器】节点-【消息】节点-【代码】节点,以实现将数组中的单个元素单独输出给用户。

这样,循环体会循环执行,直到 arr 里的元素全部输出给用户。然后会跳出循环执行下一个节点。
接着我们详细讲一下循环体里面的节点。
选择器节点用于在工作流中设置条件分支,帮助你根据不同情况执行不同的流程。
节点接收输入参数后会进行条件判断:

你可以灵活设置判断条件:
支持配置多个条件
条件之间可以用"且"或"或"连接:
可以添加多个条件分支
通过拖拽分支条件配置面板来调整判断优先级
聊天机器人中,我们只是简单地判断:数组里的元素长度是否大于 0。也就是说当前元素里存在字符就执行下一个节点(也就是【消息】节点),没有就什么都不执行。

消息节点让你的工作流能够在执行过程中给用户返回信息。
当工作流较长或回复内容较多时,通过消息节点可以让用户更快收到回应。

非流式输出(默认) :等待所有内容准备完毕后一次性返回
流式输出 :边生成边返回(类似打字机效果),需要放在大模型节点后才能启用
聊天机器人中,我们使用消息节点输出数组里的元素。循环执行后,我们就实现了依次输出数组里的每个元素了。

但是只是这样的话,就会快速地一条一条依次发出给用户,很机械。所以我们还需要在循环体里加一个【代码】节点,添加随机延迟。让每条信息之间存在随机的短时间间隔,模拟人类打字耗时。

# 导入所需模块 import time import random async def main(args: Args) -> Output: # 获取传入的参数 params = args.params # 构造返回值字典,将input参数的值传给output ret: Output = { "output": params['input'], } # 添加随机延时(0.7-2.2秒) # random.random()生成0-1的随机数 time.sleep(random.random() * 1.5 + 0.7) return ret
数组里的内容通通输出给用户了,咱是不是还剩最后一句话 last 没发给用户?

让我们最后连上【结束】节点,在【循环】节点依次输出完数组里的每一句话后,最后在执行【结束】节点,输出 last。

就这样,我们的小恶魔聊天 bot 的工作流就做好了!
试运行 → 发布工作流之后,创建一个工作流模式的 bot,将发布成功的工作流添加进去,再开启长期记忆就可以了。

接下来我们做个增强版聊天 bot。
这次我们换个人设御坂美琴,只需修改大模型节点的提示词就行了。
我们给她增加发送表情包的能力,这需要使用到知识库。
知识库节点可以根据输入参数从指定知识库内召回匹配的信息。
我们先搜集一些御坂美琴的图片,放到本地文件夹里。

然后在资源库创建知识库,





接着回到工作流,增加知识库节点

**输入:**节点会根据参数值召回关键内容。
**知识库:**设置你需要使用的知识库。

输入中,引用大模型节点的输出内容。就是说我们根据 bot 输出文字匹配相应的图。
接着我们添加刚刚创建的“美琴表情”知识库。
搜索策略选择了混合,最大召回数选择了 1 个,最小匹配度可以随意选(设得越高,与 bot 聊天时,出现表情的频率就越低)。
**输出:**我看一下试运行的输出,
{ "outputList": [ { "output": "<img src="[https://lf9-appstore-sign.oceancloudapi.com/ocean-cloud-tos/FileBizType.BIZ_BOT_DATASET/3507920499643715_1732367094562635249_usVZqoXHeZ.jpg?lk3s=61a3dea3&x-expires=1734961499&x-signature=PQdNqZrh%2FrZsA9eHz6aYE8aj8RI%3D](https://lf9-appstore-sign.oceancloudapi.com/ocean-cloud-tos/FileBizType.BIZ_BOT_DATASET/3507920499643715_1732367094562635249_usVZqoXHeZ.jpg?lk3s=61a3dea3&x-expires=1734961499&x-signature=PQdNqZrh%2FrZsA9eHz6aYE8aj8RI%3D)"> description: 这是一幅动画画面,展示了一个女孩的侧脸。她的头发上有一朵白色的花,增加了她的可爱感。她的眼睛半开半合,似乎在思考或沉思。" } ] }
outputList 是一个数组,内含一个对象,
这个对象包含"output"键,其值是:
这个输出没法直接给用户发送图片,我们需要加代码节点处理下。


// 定义输入参数的接口类型 interface Args { params: { // input是一个数组,数组中每个元素都是一个包含output字符串的对象 input: Array<{ output: string; }>; }; } // 定义输出结果的接口类型 interface Output { output1: boolean; // 标记是否成功提取URL的必需布尔值 output?: string; // 可选的输出字符串(提取的URL) } // 主函数:接收Args类型的参数,返回Promise<Output>类型的结果 async function main({ params }: Args): Promise<Output> { // 空值检查: 如果params.input不存在或为空数组,返回失败标记 if (!params?.input || params.input.length === 0) { return { output1: false }; } // 随机选择处理: const inputArray = params.input; // 生成一个随机索引,范围是0到数组长度-1 const randomIndex = Math.floor(Math.random() * inputArray.length); // 使用随机索引从数组中获取一个元素 const randomInput = inputArray[randomIndex]; // 输入验证:确保选中的元素是合法的且包含string类型的output属性 if (!randomInput || typeof randomInput.output !== 'string') { return { output1: false }; } // 图片URL提取: // 定义正则表达式模式,用于匹配HTML中的img标签的src属性 const regex = /<img\s+src="([^"]+)"/; // 使用正则表达式在输入字符串中查找匹配 const matchResult = randomInput.output.match(regex); // 结果处理: if (matchResult !== null && matchResult[1]) { // 如果成功匹配到URL,返回URL和成功标记 return { output: matchResult[1], // 提取的URL output1: true // 成功标记 }; } else { // 如果未匹配到URL,仅返回失败标记 return { output1: false }; } }
输出两个参数 output 和 output1。output 变量的值是图片 URL,output1 则是判断是非成功匹配到图片 URL,输出布尔值。如果成功匹配到图片 URL(即 output1=true),那么就输出图片给用户;如果未匹配到图片 URL(即 output1=false),那么就什么都不输出。

选择器根据 output1 的值来分支

output1=true 时,插入消息节点输出图片

 是 Markdown 格式的图片语法最后直接连接到 结束 节点。
接下来再去与 bot 对话,就会不间断跳出表情来。

接着,我们给 bot 增加一个你画我猜的小游戏。为了让 bot 区分什么时候该普通聊天,什么时候该进行你画我猜小游戏。我们需要设置变量节点来判断。
变量节点就像是一个"读写存储器"的功能,它可以帮你读取或写入 Bot 中的变量。
变量节点需要搭配 Bot 使用,即你需要先创建 Bot 并设置变量,然后再来编辑包含变量节点的工作流,并且变量节点内的变量名称需要和 Bot 内的变量名称保持一致。
两种主要的操作类型

我们需要先给 bot 添加变量。
打开 bot 调试界面,点击 变量 右侧的 +,添加变量


接着,我们回到工作流。
在开始节点,添加变量节点。获取变量 in_draw_guess,如果为 true,就进行你画我猜。否则,就是正常聊天。




更详细的变量使用逻辑为:
当用户第一次说想进行你画我猜时,变量值 in_draw_guess 是默认的空值。但说完之后,bot 就应该把 in_draw_guess 设为 ture,接着后续的聊天都会走 in_draw_guess 是 true 的线路进行你画我猜。直到用户说不想玩你画我猜。此时我们在将变量值 in_draw_guess 设为 false。
接下来,我们一步步实现。
先看 in_draw_guess 不为 true 的情况。
我们先接一个 意图识别 节点,判断用户是否想要玩你画我猜游戏。如果是,就将变量值设为 true;如果不是,就进入之前写好的 大模型 节点来聊天。

意图识别节点就像一个"智能分类器",它能理解用户说的话,并把不同类型的问题分配给相应的处理流程。
意图识别节点对用户意图进行归类,则无需再通过大模型节点配合选择器节点实现意图识别,使工作流运行更加高效。

**模型:**选择执行意图识别的大模型
**输入:**指定需要做意图识别判断的内容。输入参数默认为 query,可引用前置节点的输出参数,或输入指定内容。该参数通常引用开始节点中的用户输入。
**意图匹配 :**用户意图的分类选项,支持设置多个分类。对于匹配到这些分类的意图,处理流程会流转到对应的后续节点,若意图未匹配到此处定义的任何分类,则流转到兜底策略。
**高级设置 :**追加的系统提示词。扣子平台已指定一系列提示词,用于指导大模型合理识别用户意图并分类,你也可以追加提示词、提供各个分类的用户输入示例,使模型分类更精准。
**输出:**输出固定参数。classificationId,意图分类的 ID ;reason,意图分类的原因。
刚刚添加的意图识别节点,设置如下


当判断用户想玩你画我猜,我们就走 ⬇️ 中上面的链路;否则就走下面的链路去聊天。

下面的链路是之前做过的,大模型节点输出内容,接着剩下的三件套使其可以一句一句输出给用户。
上面的链路类似,变量节点把 in_draw_guess 设为 ture 之后,大模型输出内容 + 三件套逐句输出。
接下来,我们回到选择器判断 in_draw_guess 是否为 true 的节点。

当用户第一次说想玩你画我猜时,in_draw_guess 会从默认的空值改为 true。
第二轮用户再输入内容时,走到这个选择器时就会因为“in_draw_guess=true”判断走上面的线路,也就是进行你画我猜的线路。
我们详细看下如何进行你画我猜游戏。
这里会先接一个“query 改写”和“意图识别”,来根据用户输入判断是继续进行游戏还是要结束游戏。

query 改写:
意图识别:

新开一局的话,bot 需要先获得一个词语,然后根据这个词语画出图发给用户。

async function main({ params }: Args): Promise<Output> { // 定义100个词的数组 const words = [ // 65个简单物品和动物 // 动物类 "长颈鹿", "大象", "熊猫", "企鹅", "猫头鹰", "兔子", "小狗", "小猫", "狮子", "老虎", "孔雀", "袋鼠", "河马", "蝴蝶", "青蛙", "猴子", // 日常用品 "手机", "雨伞", "眼镜", "钟表", "电脑", "电视机", "微波炉", "冰箱", "椅子", "沙发", "茶杯", "水瓶", "剪刀", "钥匙", "书包", "铅笔", // 食物类 "西瓜", "冰淇淋", "蛋糕", "披萨", "汉堡", "寿司", "面条", "饺子", "香蕉", "苹果", "棒棒糖", "巧克力", "面包", "草莓", "葡萄", "橙子", // 交通工具 "自行车", "摩托车", "直升机", "帆船", "火车", "汽车", "救护车", "消防车", // 其他物品场景 "摩天轮", "热气球", "城堡", "彩虹", "月亮", "太阳", "风筝", "雪人", "帐篷", "灯笼", "相机", "篮球", "足球", "乒乓球", "滑板", "气球", "伞", "风车", // 35个简单意象成语 "守株待兔", // 人站在树边 "眉飞色舞", // 开心的表情 "手舞足蹈", // 跳舞的人 "东奔西走", // 来回跑的人 "闻鸡起舞", // 鸡和舞者 "左右为难", // 纠结的表情 "掩耳盗铃", // 捂耳朵拿铃铛 "对牛弹琴", // 对牛弹琴 "画蛇添足", // 蛇加脚 "狐假虎威", // 狐狸骑老虎 "井底之蛙", // 井里的青蛙 "望梅止渴", // 看梅子树 "亡羊补牢", // 修羊圈 "瓮中捉鳖", // 大缸里抓鳖 "抱薪救火", // 抱柴火救火 "打草惊蛇", // 打草吓跑蛇 "飞龙在天", // 龙在天上飞 "一箭双雕", // 一箭射两鸟 "牵牛织女", // 牛郎织女 "嫦娥奔月", // 嫦娥飞月亮 "龟兔赛跑", // 龟兔赛跑 "鹬蚌相争", // 鸟和蚌争斗 "鸟语花香", // 鸟和花 "门庭若市", // 热闹的门前 "张灯结彩", // 挂灯笼 "风调雨顺", // 风雨和谐 "风雨交加", // 大风大雨 "满山遍野", // 山上开满花 "春暖花开", // 开花的树 "日月同辉", // 太阳月亮 "水深火热", // 水和火 "大雨滂沱", // 下大雨 "鸟语花香", // 鸟和花 "如日中天", // 天空太阳 "满天星斗" // 星星月亮 ]; // 随机选择一个词 const randomIndex = Math.floor(Math.random() * words.length); // 返回结果 const ret = { "output": words[randomIndex] }; return ret; }

你是御坂美琴(超电磁炮)。你正在与用户进行你画我猜游戏,你画用户猜。
图像流节点图像流是专门用于图像处理的一个流程工具。在图像流中,你可以通过可视化的操作方式灵活添加各种用于图像处理的节点,构建一个图像处理流程来最终生成一个图像。图像流发布后,支持在智能体或工作流中使用。
*下一章会有更具体介绍,这边简单使用一下。
先在个人空间创建图像流,


我们的图像流很简单,图像生成节点生成图像,接着风格滤镜节点将生成的图像转换成涂鸦,看起来更像是短时间画出来的。




搭建完成后 试运行→发布 图像流。

接着我们再回到工作流中,添加刚刚创建的图像流节点。

然后接消息节点输出图像,

最后再连到结束节点。
我们看看效果

接着,用户开始猜了,此时就要走第 3 个节点。我们不需要再画图,只需要引导用户猜出答案。所以只要接大模型节点对话就行了


先从 bot 获取变量word,再将其和用户输入的改写内容传给大模型,让其与用户互动即可。
最后再将大模型节点连到结束节点,输出大模型的 output
玩了一会,用户告诉模型不想玩了。
此时就进入不想玩的节点


先变更变量in_draw_guess为 false,然后获取“word”,输入给大模型节点,让其与用户对话,再接上逐句输出三件套,最后连接结束节点。
这样你画我猜的游戏就完成了,最后感受下效果。

接着我们看下整个工作流有什么可以优化的地方,我们发现实现逐句输出的三件套使用频率有点多,是个比较常用的任务处理流程。我们可以将三件套做成固定的工作流,然后通过工作流节点来一键实现逐句输出。
工作流里面的工作流节点主要是集成已发布工作流,可以执行嵌套子任务。
在一个工作流中,你可以将另一个工作流作为其中的一个步骤或节点,实现复杂任务的自动化。例如将常用的、标准化的任务处理流程封装为不同的子工作流,并在主工作流的不同分支内调用这些子工作流执行对应的操作。

工作流节点的输入和输出结构取决于子工作流定义的输入输出结构,不支持自定义设置。在工作流节点中你需要为必选的输入参数指定数据来源,可以设置为固定值或引用上游节点的输出参数。
我们先将三件套创建为一个工作流“SentenceByStentence”

接着在陪聊 bot 里添加该工作流节点,以替换三件套
接着其他地方的三件套也都替换掉,就简洁多了。
接下来我们创建超简易版“心情记录 bot”,串讲剩下的节点。
问答节点是 Coze 工作流中的一个重要组件,它能让你的机器人主动收集用户信息,实现更自然的对话交互。通过问答节点,你可以:
收集用户的具体需求和信息
引导用户选择特定的功能或服务
确保获取到完整的必要信息
两种问答方式
这种模式下,用户可以用自然语言自由回答问题。bot 会从回答中提取关键信息。
bot 会自动提取姓名和电话号码。如果信息不完整,会继续追问缺失的部分。
这种模式提供预设的选项供用户选择,适合:
功能选择菜单
分步骤引导
服务类型分类

**模型:**选择执行此节点的模型,支持设置模型在此节点中的生成多样性等参数配置,使模型效果更符合你的预期。
**输入:**设置需要添加到问题中的参数,参数值可以引用前置节点的输出参数,或指定内容。
**提问内容:**设置智能体在对话中向用户发起的问题内容。
回答类型:
设置用户回答问题的方式,支持设置为:
直接回答:允许用户自定义回复内容。此时应设置输出参数。
选项回答:设置预置选项,引导用户从指定范围内快速回复。此时还应设置选项内容,选项在对话中展示为按钮形式,用户可以直接点击按钮或回复对应的选项编号。
**输出:**指定节点的输出设置。节点默认将用户回复作为 USER_RESPONSE 变量。
你也可以开启从回复中提取字段,并设置待提取的关键字段。如果用户回复中未包含必选的字段信息,智能体将一直追问,直至成功采集信息。
在心情记录 bot 中,我们使用了 3 个问答节点。




看看效果:

点击选择记录今天的心情,

得到回答了,下面我们要将用户回复记录到数据库。
数据库节点,可通过 NL2SQL (Natural Language to SQL) 方式和代码方式进行调用,支持完整读写模式。

输入:
设置 SQL 执行所需的变量。支持动态变量与固定值。
**SQL: **
手动输入:直接编写 SQL 语句
智能生成:点击"自动生成"按钮

输出:
输出(outputList):返回字段值,字段名需与 SQL 保持一致
统计信息(rowNum):返回行数统计,显示影响的记录数
注意
禁用 Select* 语法
不支持多表 Join
单次最多返回 100 行
在心情记录 bot 中,我们是使用代码调用数据库。
使用数据库节点之前,我们需要在 bot 上添加数据 table。


接着去工作流添加数据库节点,

数据库之前有个代码节点,用来获取当天日期
async function main({ params }: Args): Promise<Output> { // 创建日期对象获取今天日期 const today = new Date(); // 格式化日期为 YYYY-MM-DD const year = today.getFullYear(); const month = String(today.getMonth() + 1).padStart(2, '0'); const day = String(today.getDate()).padStart(2, '0'); const ret = { "output": `${year}-${month}-${day}` }; return ret; }

我们将前面节点的用户回答内容和日期设为变量,然后使用 sql 语句将变量的值写进数据库。
最后连接结束节点,不用做任何其他输出。
刚刚是数据库写入,接着我们还有数据库内容读取。

当用户查看历史心情时,我们接入一个数据库节点来读取数据库内容。

再连接 结束 节点,输出数据库调用结果

看下效果:

下面我们看当用户选择 获取音乐推荐 时的链路,连接了一个插件节点,随机输出音乐。

想象你在和一个很聪明的助手聊天。你可以用普通话跟它说话,比如:
这个助手会:
要让这个功能正常工作,你需要:

插件节点是一个通过添加工具访问实时数据和执行外部操作的节点。
点击添加插件后,会跳出以下弹窗。


一个插件往往有 1~3 个工具。下拉可以看到详细的工具介绍。


我们添加随机播放音乐插件

将其连接到工作流中

async function main({ params }: Args): Promise<Output> { // 解析输入的 JSON 字符串 let musicData; try { musicData = typeof params.input === 'string' ? JSON.parse(params.input) : params.input; } catch (e) { return { output: "错误:无效的音乐数据" }; } // 检查数据结构 if (!musicData.data || !musicData.data.name || !musicData.data.url) { return { output: "错误:音乐数据格式不正确" }; } const data = musicData.data; // 构建Markdown格式的输出 let mdOutput = `### ${data.name}${data.artistsname ? ` - ${data.artistsname}` : ''}\n\n`; // 添加封面图片(如果有) if (data.picurl) { mdOutput += `\n\n`; } // 添加播放链接 mdOutput += `[点击播放音乐](${data.url})`; return { output: mdOutput }; }
看看效果,

心情记录 bot 所有节点如下:
要着手定制工作流,我们的工作根据时间线可以分为 3 个阶段:
概括关键任务制定策略,明确任务目标和实施方式。
将整体任务细分为易于管理的子任务,确立它们之间的逻辑顺序和相互依赖关系。
为每个子任务规划具体的执行方案。
这部分可以说是最重要的部分,明确你究竟要什么东西。
举例:如何用 coze 搭建一套高水准自动化 xx 赛道小红书内容生产线
我们先来一步一步确认目标
总任务:小红书内容自动产出
输出标准:爆款标题+文案+配图
子任务 1:生成爆款标题
子任务 2:生成配图
子任务 3:生成发布文案
其中,子任务 1 又分为:热门话题抓取+改写,子任务 2 又会使用到图片工作流。
在总目标和最终输出的标准下,我们要完成拆解。并确定子任务之间相互的逻辑顺序。
逐步开发和测试 的各项功能。
在 Coze 平台上搭建工作流架构,设定各节点间的逻辑联系。
细致配置各个子任务节点,并确保每个子任务的有效性。

可以看到,搭建好的工作流由一个又一个的小板块构成,每个板块都可以进行“试运行”。
这里的顺序是:先试运行小节点,测试通过再跑整体流程。
一个环节的报错,会导致最终没有“输出”。
试运行的时候你也会发现,工作流和代码一样,只要跑不起来,就一定是哪里出了错。
这个阶段的工作流一般不是一次成型的,需要反复测试:
你使用的大模型不一样,给的结果不一样;
你的工作流太长,跑出来的结果不稳定;
你的一个数据抓取错了,后面直接全错....
全面检验并提升工作流的效果。
对工作流进行整体试运行,找出功能实现和性能表现上的瓶颈。
通过持续的测试和迭代过程,不断优化,直至满足预定的性能标准。
在这个阶段,你已经把工作流运用在业务中了。你即将迎来一系列的新问题:
跑了,这个选题的数据不好,需要更换热门话题信息源;
跑了,这个类型的图片点击率不高,需要更换新风格;
跑了,这 LLM 说话的风格太僵硬,不够自然;
跑了,数据太好私域承接不过来...
搭建工作流是种树,完善维护工作流是养树。