葫芦流 · 节点配置

工作流与节点配置

新手指南:什么是工作流、如何在控制台搭建,以及每类节点的重要设置。

若《入门》已让你完成第一次抓取,本页把全貌讲清楚。你可以全程在控制台操作;文中的 JSON 示例是给以后要用 API 的人看的。使用编辑器不必背字段名——列在这里是为了让每项设置都不神秘。编辑器右侧的 AI 聊天可提出改图建议,点保存后入库。

写给从未设计过数据流水线的人。术语第一次出现时都会解释。

约 25 分钟 能独立配置四类节点并连线

用白话说:什么是工作流?

工作流是一条处理网页数据的小流水线。你在画布上放方块(节点),用箭头连起来。流水线运行时,每个方块做一件事,再把结果交给下一个方块。

常见分工:生成许多分页 URL → 把每个页面读成行 → 把行存进表 → 有新行或价格变动时给你发邮件。葫芦流在云端托管这条线,因此可以在你离线时按调度运行。

你不是在写爬虫。你配置「读什么、放到哪里」。产品会从样例页发现列,由你选择保留哪些列。

配置节点之前

先准备好这些,发现与运行才容易一次成功:

  • 01一个你有权采集的公开样例 URL(尽量无登录、无验证码)。
  • 02明确目标:一次性采集进表,还是持续监控并邮件提醒。
  • 03本周期额度够用(按预期抓取行数估算)。
  • 04可选:站点的翻页规律(page=1,2,3…),若需要多个列表页。

迷你术语表

这些词会出现在编辑器、邮件和 API 响应里:

画布 / 图(graph)— 节点与箭头的画;底层存成 JSON。

上游 / 下游 — 上游先跑;箭头指向下游。

items — 节点之间传递的行对象数组(每行是一组字段)。

fields / schema — 发现后勾选的列定义(name、label、type)。

upsert — 键已存在则更新,不存在则插入。

额度 — 抓取节点每实际请求 1 个网页扣 1 额度(与输出行数无关)。

预设 — 可复用的抓取 / URL 生成 / 通知配置,可拖到其他工作流。

dry run — 通知测试模式:展示将发什么,但不真发邮件。

在控制台搭建(推荐路径)

不需要 API 时可以完全忽略 JSON。界面上这样做:

  1. 01 创建并命名工作流

    工作流 → 新建。用以后在邮件里也能认出来的名字。编辑期间保持 status=暂停。

  2. 02 从面板添加节点

    拖入抓取,之后再加存储 / 通知 / URL 生成。点击节点打开右侧配置。

  3. 03 先配好抓取

    粘贴 URL,选 list 或 detail,写需求,抓取字段,勾选列,应用。先运行一次检查 items,再加其他节点。

  4. 04 用箭头连线

    从输出端口拖到输入端口。方向很重要:数据从 from 流向 to。URL 生成只能连到抓取;抓取可连到抓取/存储/通知。

  5. 05 添加存储(与可选通知)

    设置数据集名与 key_fields(通常是 url)。通知可选 when=new 或 field_change。保存工作流。

  6. 06 就绪后再启用调度

    设置 interval_minutes,把状态改为启用,确认 next_run_at。样例运行正确之前请保持暂停。

工作流级设置

这些设置属于整条流水线,不属于单个节点。在工作流标题区或通过 API 创建/更新时设置。

运行需要剩余额度(保存画布不扣)。不足时 HTTP 402,请升级或等待下个周期。

字段含义
name可读名称。出现在控制台列表与默认通知主题里。
statusactive=到期可由调度器运行。paused=调度跳过,仍可手动运行。试验阶段请保持暂停。
interval_minutes启用工作流的运行间隔(分钟)。1440≈每天,60≈每小时(视套餐)。空/null=仅手动。有间隔时,一次运行尝试后 next_run_at 按间隔前进。

提示:按业务目的命名(「竞品 A 价格」),不要用难认的技术绰号。邮箱多起来以后会感谢现在的自己。

图是如何保存的

你看到的是方块和箭头。内部保存为 graph:节点列表 + 边列表。每个节点需要唯一 id 字符串(编辑器会生成)、type 与 config。

边使用 from 与 to(节点 id)。from 是上游。不要用 source/target——API 不认。运行器会排序,保证上游先完成。环会被拒绝。

{
  "nodes": [
    { "id": "s1", "type": "scrape", "config": { } },
    { "id": "st1", "type": "store", "config": { } }
  ],
  "edges": [
    { "from": "s1", "to": "st1" }
  ]
}

若把文档里的 JSON 拷进 API,请保持节点 id 稳定——通知会与同一 node id 的上次输出比较。

数据如何沿边流动

多数节点产出包含 items(行)以及常有的 fields(列定义)的对象。下一节点把它当作输入。若多个箭头指向同一节点,运行器会按规则合并上游输出——对新手而言,保持一条清晰主链最简单。

URL 生成忽略输入,只产出网址列表。存储与通知从相连上游读取数据行(或本次运行中首个可用的数据行)。它们不会再去抓网页。

列表→详情较特殊:详情抓取从每条上游行读取 URL(经 input_field 或 link/url/href),并把父列表字段合并进详情行,这样既保留列表上的标题价格,又有详情页的描述。

URL 生成

作用:不用手敲就生成许多列表页 URL。它从不下载页面,也不占额度。可以把它想成填 page=1…N 的表格公式。

输出始终是 items: [{url}, …],带简单的 url 字段。输出只应连到抓取。上限:每个生成器配置最多 500 条 URL。

什么时候用: 需要同一列表模式的第 1、2、3…页,或有一份固定的种子 URL 要粘贴。

字段含义
mode翻页范围=用数字填模板。URL 列表=每行粘贴一个网址。默认翻页范围。
template仅 range。必须包含花括号占位符,如 https://shop.example/list?page={page}。占位符名不对会校验失败。
param花括号内的名字。默认 page 表示模板须含 {page}。若站点用 {p},把 param 设为 p。
start仅 range。起始整数(含)。默认 1。
end仅 range。结束整数(含),须 ≥ start。(end−start)/step+1 不能超过 500。
step仅 range。正整数步长(默认 1)。只要奇数页可用 2 等。
urls_text仅 list。每行一个绝对 http(s) URL。空行忽略;非法 URL 校验失败。

配置示例

{
  "mode": "range",
  "template": "https://example.com/list?page={page}",
  "param": "page",
  "start": 1,
  "end": 10,
  "step": 1
}
{
  "mode": "list",
  "urls_text": "https://example.com/a\nhttps://example.com/b"
}

配置后先在界面预览/校验将生成多少条,再应用。若生成超过 20 条,请提高下游抓取的 limit。

抓取

作用:打开页面并抽取结构化行。工作流运行时,每实际请求 1 个网页扣 1 额度。没有可用的抓取,存储和通知就没有有用的数据。

两阶段心智模型:(1)发现——用白话写 requirement,引擎提出 fields 与 fetch_profile。(2)抽取——之后运行用你勾选的 fields(+ profile)反复拉这些列。正式依赖运行前务必先应用已选字段。

list 模式从列表页返回多条。detail 模式每个 URL 返回更丰富的一行,并可合并上游列表字段。默认每次运行最多 20 个 URL——生成器喂了更多页时请提高 limit。

什么时候用: 任何需要从网页取数的时候。先从一个抓取开始;只有需要详情页时再加第二个抓取。

字段含义
url没有上游提供链接时的种子 URL。若 URL 生成或其他抓取已喂入 URL,可省略。
mode列表=列表页多行。详情=每个网址一页(商品/档案)。模式选错是新手常见问题。
requirement发现用的日常语言列描述,如「标题、价格、货币、商品链接」。不是选择器语言。
fields你保留的列:[{name, label, type}, …]。抓取预设必填。发现后点应用写入。
limit本节点单次运行最多处理的 URL 数(默认 20)。与生成器 500 上限彼此独立,可能同时生效。
input_field列表→详情:上游中装下一跳 URL 的列名。为空则尝试 link、url、href。
fetch_profile发现返回的内部配置,使重复抽取更稳定。控制台在「抓取字段」后会替你保存——很少需要手改。

可能见到的高级项:scope_xpath、item_xpath(来自发现)、url_from(强制 URL 列表)。输入应来自「URL 生成」或「抓取」,不要来自「存储 / 通知」。

配置示例

{
  "url": "https://example.com/list",
  "mode": "list",
  "requirement": "title, price, url",
  "limit": 20,
  "fields": [
    { "name": "title", "label": "title", "type": "text" },
    { "name": "url", "label": "url", "type": "url" }
  ]
}
{
  "mode": "detail",
  "input_field": "url",
  "requirement": "description, sku",
  "limit": 20,
  "fields": [
    { "name": "description", "label": "description", "type": "text" }
  ]
}

额度按实际请求网页次数计。先单独测列表抓取。数据行不对时,先修好发现再加存储。

存储

作用:把上游 items 写入可浏览、可导出、可用 API 查询的数据集(表)。存储不占配额。因为指向具体表,所以不做可复用预设。

每条入行按 key_fields 哈希 upsert。相同键→更新;新键→插入。这样每日监控能刷新价格而不复制商品。

什么时候用: 只要你需要可留存的历史或导出——认真的工作流几乎都以存储结尾。

字段含义
dataset_id你拥有的已有数据集数字 id。若设置,优先于 dataset_name。
dataset_name按该名称在账号下创建或复用表。默认回退为「{工作流名} data」。
key_fields标识一行的字段。默认 ["url","link"]。优先用稳定的商品/档案 URL。避免只用标题。
store_fields可选写入列白名单。别名 keep_fields。省略则写入行上全部投影列。

配置示例

{
  "dataset_name": "products",
  "key_fields": ["url"],
  "store_fields": ["title", "price", "url"]
}

第一次存储成功后,打开「数据集」确认列与几行样例。需要表格时从那里导出 CSV/JSON。

通知

作用:与同一通知节点上次运行比较,条件满足时发邮件。它不爬网页,只读取上游 items(通常来自抓取或存储)。

第一次运行往往没有可比较的基线——可能收到一批「新」行,或没有任何邮件,取决于 when。测试告警时建议连跑两次。节点测试支持 dry_run(不发信)。

什么时候用: 监控类任务:新上架、降价,或任意关注字段变化。纯一次性采集可跳过通知。

字段含义
when「有新数据时」= 仅上次没有的行(按链接/URL 等识别)。「关注字段变化时」= 同一行上任一监控字段变化。
email收件地址。默认当前账号邮箱。
watch_fields「关注字段变化时」要用的字段名,如 price。不填则该模式无效。
subject邮件主题。默认含工作流名称。

配置示例

{
  "email": "ops@example.com",
  "when": "field_change",
  "watch_fields": ["price"],
  "subject": "[HuluFlow] price change"
}

把通知接在你关心的那次抓取(或存储)之后。价格告警选「关注字段变化时」,监控字段填 price,并保证上游有稳定的网址键。

如何连线(可行模式)

编辑器会拦下许多错误连线(例如 URL 生成不能直接进存储)。优先用这些模式:

保持一条主链。旁支可以有,但对新手更难排查。

  • URL 生成 → 抓取(列表)— 生成的网址成为要打开的页面。
  • 抓取(列表)→ 抓取(详情)— 将「链接字段」设为列表里的链接/URL 列;详情会合并列表与详情字段。
  • 抓取 → 存储 — 行按去重键写入数据集。
  • 抓取或存储 → 通知 — 通知读取上游数据行;关心已有记录上的数值变化时,选「关注字段变化时」。

故事示例:生成目录第 1–5 页 → 列表抓取(标题、价格、网址)→ 详情抓取(描述)→ 按网址存储 → 对价格做字段变化通知。额度按实际请求网页次数计费。

限额、额度与导出

URL 生成:单节点最多 500 条。抓取:默认每次运行 20 个 URL(可用 limit 调整)。额度:本周期抓取节点实际请求网页次数——不是「每个抓取节点占一个名额」。额度不足 → 运行 HTTP 402。

数据集:浏览时有控制台分页与 API 页大小限制;导出支持 CSV/JSON,最多约 10 万行(更大则 413)。抓取失败会体现在运行里的节点 error——打开运行详情查看。

新手问答

我只想导出一次表格,需要通知和调度吗?

不需要。抓取 → 存储,运行一次,导出 CSV。保持暂停、间隔留空即可。

暂停会释放额度吗?

不会——额度在运行时消耗,不是因为保留暂停的工作流。未用额度保留到周期结束或你升级。

发现了很多我不想要的列,有问题吗?

没有。应用前只勾需要的。未勾选的发现列不会入库。

列表→详情后缺少列表字段。

确认 list→detail 连线、第二节点为 detail 模式,且 input_field 对应链接列。引擎能把详情 URL 匹配回父行时,才会合并父字段。

通知从不发信。

检查 email、when、watch_fields。连跑两次以建立基线。确认两次运行间 node id 没变。用 dry-run 测试看触发是否成立。

应该从 API 开始吗?

不应该。先在控制台搭好并验证。当别的系统必须自动创建工作流或拉行时,再看 API 优先指南。

接下来

继续场景指南,或回概念查词。