npm package discovery and stats viewer.

Discover Tips

  • General search

    [free text search, go nuts!]

  • Package details

    pkg:[package-name]

  • User packages

    @[username]

Sponsor

Optimize Toolset

I’ve always been into building performant and accessible sites, but lately I’ve been taking it extremely seriously. So much so that I’ve been building a tool to help me optimize and monitor the sites that I build to make sure that I’m making an attempt to offer the best experience to those who visit them. If you’re into performant, accessible and SEO friendly sites, you might like it too! You can check it out at Optimize Toolset.

About

Hi, 👋, I’m Ryan Hefner  and I built this site for me, and you! The goal of this site was to provide an easy way for me to check the stats on my npm packages, both for prioritizing issues and updates, and to give me a little kick in the pants to keep up on stuff.

As I was building it, I realized that I was actually using the tool to build the tool, and figured I might as well put this out there and hopefully others will find it to be a fast and useful way to search and browse npm packages as I have.

If you’re interested in other things I’m working on, follow me on Twitter or check out the open source projects I’ve been publishing on GitHub.

I am also working on a Twitter bot for this site to tweet the most popular, newest, random packages from npm. Please follow that account now and it will start sending out packages soon–ish.

Open Software & Tools

This site wouldn’t be possible without the immense generosity and tireless efforts from the people who make contributions to the world and share their work via open source initiatives. Thank you 🙏

© 2026 – Pkg Stats / Ryan Hefner

@roll-agent/octopus-agent

v0.4.1

Published

Octopus Agent:编排 Sponge MCP Server 的 NL2SQL 查询链路

Readme

Octopus Agent

Octopus Agent 是 Node.js 实现的轻量 NL2SQL(自然语言转 SQL)调用客户端。正常查询调用 query_sponge(查询 Sponge),SQL 修复由 Sponge 主流程内部完成;查询成功后根据 Sponge 返回的能力契约,可继续调用 analyze_query_result(分析查询结果)或 export_query_csv(导出全部数据)。丸子不负责图表生成。

询问能力、没有可识别的查询对象或查询动作、闲聊、无关问题或要求增删改业务数据时,由 LLM(大语言模型)调用 get_query_guidance(获取查询引导);程序不使用字符串或正则匹配用户原话。查询引导只是动态示例,不是能力白名单;明确业务查询即使重复提出、未出现在引导中或仅缺少筛选条件具体值,也必须调用 query,由 Sponge 判断是否追问。用户要求使用、启动或检查丸子 Agent 时,仅通过 GET /mcp/health 执行健康检查,不尝试简单业务查询。

上一轮 query 返回 clarifying(等待补充条件)或成功结果展示『猜你想查』后,用户选择编号或追加其他要求时,下一次 query.question(查询问题)仍逐字传入用户本轮原话,例如 2,并分析;禁止在 Octopus 中替换为选项正文,选项解析和历史继承由 Sponge 统一处理。

委托查询使用同一个 query,显式传入 delegation(委托信息)。输入、返回、失败及原行追溯见 只读委托契约。下文普通查询的逐字展示与结束规则不适用于委托。

本地运行

要求 Node.js 22.6 或更高版本。query 使用 @roll-agent/sdk 的 defineTool(定义工具)和 Zod(输入校验)声明入参;现有 MCP 响应适配层继续负责标准答案和结构化内容。

npm install
npm test
npm start

Roll Agent 接入

roll agent add .
roll run octopus-agent query --json \
  --input-json '{"question":"查询本月各门店销售额","isNewConversation":true}'

上层平台必须明确传递 isNewConversation(是否新建查询上下文)。当前聊天首次查询传 true;正常追问传 false,并从当前聊天已保存的工具结果中恢复上一次的 structuredContent.contextId(上下文编号)。确实无法恢复时,先提示用户重述完整问题;用户重述后,在同一聊天内传 true 新建查询上下文,再保存新返回的编号。仅补充条件时不得新建上下文,也不能从同一访问令牌的其他聊天推测当前聊天。

query(自然语言查询)入参:

| 字段 | 必填 | 中文说明 | |-|-|-| | question | 是 | 用户原始问题,不得改写 | | isNewConversation | 是 | 是否新建查询上下文;当前聊天首次查询或上下文丢失后重述完整问题传 true,正常追问传 false | | contextId | 条件必填 | 上一次返回的上下文 ID;普通查询且 isNewConversation=false 时必须传入 | | resultFormat | 否 | 结果格式,支持 text/json/yaml/md/markdown/html,默认 markdown(Markdown 格式) |

同一上层对话的后续调用示例:

roll run octopus-agent query --json \
  --input-json '{"question":"其中肯德基有多少个岗位","isNewConversation":false,"contextId":"ctx_a1b2"}'

isNewConversation=true 时禁止同时传入 contextId,避免新上下文误接旧查询。上下文丢失后重述完整问题的调用示例:

roll run octopus-agent query --json \
  --input-json '{"question":"查询本月上海门店销售额","isNewConversation":true}'

上层模型调用时使用 --json(完整 JSON),展示 content[0].text(最终文本),并随当前聊天保存 structuredContent.contextId(上下文编号)、最近一次成功查询的 queryId(查询编号)和 availableActions(可执行动作)。后续查询只回传当前聊天的 contextId;导出和专项分析只使用最近一次成功查询的 queryId 及对应动作。新建查询上下文后,用新结果覆盖当前聊天的默认续接目标。

export_query_csv(导出全部数据)接收必填的 queryId(查询编号)和可选的 analysisRequest(分析要求)。仅当上一条结果的 structuredContent.availableActions(可用动作)包含 export_query_csv 时,用户追问“导出 CSV”“导出全部”“把刚才结果导出”等纯导出诉求才直接沿用该查询编号。同一上层对话存在多次成功查询时,新查询覆盖此前的默认续接目标;用户未明确指定更早对象或查询编号时,只能使用时间上最后一次成功 query 返回的 queryId。用户要求“导出并分析”时只调用本工具,将本轮原话逐字传入 analysisRequest,禁止随后调用只分析页面快照的 analyze_query_result;只要求导出时省略。不再次调用 query,也不改写上一条问题。Sponge MCP Server 基于实际导出的最多 1000 条数据生成分析,并将同一份分析统一写入 answer(答案)和 CSV,octopus-agent 原样展示,不自行生成或补充分析。用户同时修改筛选条件时才发起新的 query。

纯图表要求不属于丸子能力,由独立 Chart Agent(图表智能体)处理。用户同时要求查询和生成图表时,Roll 先通过 Octopus 完成查询并导出 CSV,再将 CSV 临时地址和用户原始制图要求交给 Chart Agent;Octopus 不识别图型、不生成 HTML,也不为制图重新查询。

analyze_query_result(分析查询结果)接收必填的 queryId 和 analysisRequest(分析要求)。仅当上一条结果的 availableActions 包含 analyze_query_result,且用户只要求分析、没有同时要求导出时调用;查询当轮待分析时沿用 Sponge 返回的分析要求,用户后续追问分析时逐字传入本轮要求,不重新查询。

get_query_guidance(获取查询引导)接收必填的 showQueryOnlyNotice(是否展示仅支持查询提示)和可选的 systemType(系统类型),支持 sponge(2.0,默认)和 supplier(供应商),沿用调用方当前系统上下文。能力询问传 false;闲聊、无关问题、没有可识别的查询对象或查询动作、增删改请求传 true。仅缺少筛选条件具体值时调用 query。Tool(工具)从 Sponge 的 uiResult(界面结果)直接返回公开 structuredContent(结构化正文),只包含 title(标题,可省略)、datasets(数据集)、blocks(展示块)、actions(导出动作);旧快照、角色、机器委托和终止标记不混入公开对象。content[0].text(首段文字)由同一对象生成;showAll(展示全部)仅保留为兼容旧调用的布尔参数,无需填写;当前始终完整展示全部内容。

查询引导通过 outputSchema(输出结构定义)和 _meta["roll/appOutput"](应用输出声明)声明 hm.ui-result(通用界面结果)第一版,remoteReadable=true(愿意远程分享)。读取仍取决于 Runtime(执行服务)、Relay(中继)及 Companion(伴随服务)的版本与授权;本工程不会替部署环境修改授权。契约源及合成样例见 references(交付参考)。纯引导只使用原协议已有的 markdown(格式化文本)展示块,datasets(数据集)和 actions(导出动作)均为空。能力说明、推荐问句和沟通最佳实践完整展示,用户可复制示例后提问。缺失或非法 uiResult 时返回协议错误,不能把旧四字段伪装成新契约正文。

get_supplier_home(获取供应商首页卡片)供未来 Web(网页)端首屏调用,无入参。structuredContent.cards(结构化卡片列表)按 type=metric(数据卡片)或 type=question(问题卡片)区分;数据卡片带 value(统计值)和 unit(单位),两类卡片都带点击时交给 query 的完整 question(问题原文)。统计由 Sponge 按访问令牌唯一对应的供应商实时计算,跨供应商或管理员令牌会被拒绝。首版只展示有明确口径的“尚未产生上岗结果的工单”和“昨日实际上岗工单”,暂不展示无法可靠归属到单个供应商的人员缺口。四个快捷问题使用当前供应商名称,避免复用管理视角的动态引导问题。

问题反馈

拿到用户反馈原文后直接调用 submit_query_feedback(提交查询反馈),不询问是否提交,不要求用户确认内容、选择分类或补齐详情,也不重新执行查询。分类由模型按语义选择,不确定时使用 other(其他);问题描述逐字保留用户原文,反馈由后台人工审核。缺少可选查询编号或原始提问时直接省略,不追问、不编造。多人令牌仅使用当前上下文已知且已授权的用户编号,不猜测身份。传入 category(问题类型,支持 wrong_result/结果有误、query_failed/查询失败、unclear/结果难懂、slow/查询慢、other/其他)和 description(用户描述)。优先附被反馈查询的 queryId(查询编号);查询中断而没有编号时可附 question(原始提问)。服务端按访问令牌核对查询归属。成功后返回 feedbackId(反馈编号)和 pending(待处理)状态;失败时不得显示已受理。

用户询问进度时直接调用 get_query_feedback(查询反馈进度),不要求用户提供编号。无编号返回此人的全部反馈,按最近处理时间和提交时间倒序;需要看某一条时,Agent 从列表取内部 feedbackId 再查详情,逐条展示状态与各自的处理说明。本轮直接请求某条详情但还没有列表时,先向 Agent 工具传 detailRequested=true(本轮需要详情),由 Agent 列出候选并继续查询唯一匹配的历史;该标志不传给 Sponge。多人令牌由可信调用方传入已授权 userId(用户编号)。管理员在 Sponge 的 /mcp/admin/trace-view#feedback 页面查看并更新反馈。

query 的结构化结果包含 resultKind(结果类型)、availableActions、pendingActions(待执行动作)及可能存在的 exportResult(自动导出结果)。pendingActions 非空时 terminal=false(当前调用链未结束),上层按顺序调用对应工具;全部完成后再统一展示每次工具返回的 content[0].text。resultKind=report(报表)且动作列表为空时,不显示查询编号,也不允许套用普通查询的导出或分析动作。

health(健康检查)无入参,返回 Sponge MCP Server 及业务库、权限库、审计库的 UP(正常)或 DOWN(异常)状态。

环境变量

| 环境变量 | 必填 | 中文说明 | 默认值 | |-|-|-|-| | SPONGE_MCP_BASE_URL | 是 | Sponge MCP Server 地址 | https://sponge-mcp.duliday.com | | SPONGE_MCP_ACCESS_TOKEN | 是 | 身份透传 Token(令牌) | 无 |

Agent 内置单次请求超时 58 秒、query(查询)总超时 59 秒、网络重试 2 次,无需额外配置。每个新问题生成新的 requestId(请求编号),仅网络重试复用该编号。总超时低于当前 Roll 的 60 秒固定限制。

agentDurationSeconds(Agent 总耗时)保存在 structuredContent(结构化内容)供排查,不加入用户答案。计算范围为 octopus-agent 收到 query 请求到组装可交给平台渲染的答案,包含上下文处理、网络传输和服务端处理;不包含平台收到结果后的 UI(用户界面)绘制耗时。

isNewConversation=true 时 octopus-agent 直接生成全局唯一 contextId(上下文 ID),不读取历史。普通查询在 isNewConversation=false 时必须传入当前会话保存的 contextId;缺少时不查询其他会话,也不发起业务查询。MCP Server 在生成 SQL 时根据最终 ID 独立加载最近 5 轮;禁止 Server 自行切换 ID。requestId(请求编号)仍由 octopus-agent 每次请求重新生成。委托查询未提供 contextId 时使用独立新上下文。

Sponge Server 返回的 steps(阶段数据)仅用于内部审计,不再透传给上层 Agent;完整步骤通过现有 PostgreSQL 审计记录查看。

查询成功后,octopus-agent 直接使用 Sponge MCP Server 返回的 answer(答案),不校验是否包含数据分析,不调用 Roll Core Sampling(采样调用),也不使用程序重新生成分析。最终正文放在 result.content[0].text,不追加查询编号或耗时;queryId(查询编号)和 agentDurationSeconds 保存在 result.structuredContent 供后续动作和排查使用。result.content[1] 只要求上层 Agent 逐字复制并在需要时继续执行 pendingActions,不要求外层模型分析或重建表格。查询返回的 resultAnalysis(结果分析信息)和 steps(阶段数据)不再透传;contextId、contextAction(上下文动作)和 contextReason(判断原因)保留在结构化内容中。

接口名称:export_query_csv(导出全部数据)

接口说明:重新校验并执行原查询 SQL,最多导出 1000 条;传入 analysisRequest 时基于实际导出数据生成分析,并把同一份分析写入页面答案和 CSV。

入参:

| 字段 | 必填 | 中文说明 | |-|-|-| | queryId | 是 | 原查询编号,必须来自上一条可导出的查询结果 | | analysisRequest | 否 | 用户本轮逐字提出的分析要求;只导出时省略 |

回参:

| 字段 | 中文说明 | |-|-| | queryId | 原查询编号 | | rowCount | 实际导出条数 | | url | CSV 下载地址 | | expiresAt | 下载地址过期时间 | | answer | 下载信息,以及按需生成的完整导出数据分析 | | resultAnalysis | 按需返回的分析文本、状态和导出统计摘要 |

curl -X POST 'http://localhost:3001/mcp/tools/export_query_csv' \
  -H 'Authorization: Bearer <访问令牌>' \
  -H 'Content-Type: application/json' \
  -d '{"queryId":"qry_a1b2","analysisRequest":"分析多次上岗人员和门店分布"}'
{
  "queryId": "qry_a1b2",
  "rowCount": 1000,
  "url": "http://localhost:3001/mcp/exports/example",
  "expiresAt": "2026-08-26T10:00:00.000Z",
  "answer": "## 导出结果\n已生成 CSV,共 1000 条。\n\n## 数据分析\n以下结论基于本次实际导出的 1000 条数据。",
  "resultAnalysis": {
    "status": "llm",
    "text": "以下结论基于本次实际导出的 1000 条数据。",
    "summary": {
      "rowCount": 1000,
      "exportLimit": 1000,
      "exportLimitReached": true
    }
  }
}

MCP Server 内部接口

接口名称:get_supplier_home(获取供应商首页卡片)

接口说明:按访问令牌对应的单一供应商返回初步数据统计和可点击问题;不接受前端传入供应商编号。统计时间使用 Asia/Shanghai(上海时区),昨日为当地自然日。

入参:无业务字段,请求体为 {}。

回参:

| 字段 | 中文说明 | |-|-| | generatedAt | 本次统计生成时间 | | cards[].type | 卡片类型:metric(数据)或 question(问题) | | cards[].title | 卡片标题 | | cards[].value | 数据卡片的统计值;问题卡片不返回 | | cards[].unit | 数据卡片的单位;问题卡片不返回 | | cards[].question | 点击卡片后提交给查询工具的完整问题原文 |

curl -X POST 'http://localhost:3001/mcp/tools/get_supplier_home' \
  -H 'Authorization: Bearer <供应商访问令牌>' \
  -H 'Content-Type: application/json' \
  -d '{}'
{
  "generatedAt": "2026-09-29T01:30:00.000Z",
  "cards": [
    {
      "type": "metric",
      "title": "昨日实际上岗工单",
      "value": 15,
      "unit": "单",
      "question": "查询甲供应商昨天实际开始上岗的工单明细"
    },
    {
      "type": "question",
      "title": "本月交付情况",
      "question": "查询甲供应商本月按报名时间统计的报名工单数、面试通过数和上岗成功数"
    }
  ]
}

示例数字仅演示格式,不代表真实业务数据。

接口名称:get_query_guidance(获取查询引导)

接口说明:读取 Sponge 当前系统的引导内容;“猜你想查”依次使用当前访问令牌专属配置、本系统公共配置、系统默认内容,在 trace-view(追踪管理页)的“文案配置 → 猜你想查”维护。每组一至三条,按配置顺序整组返回,不按业务用户编号或角色选择,也不补齐三条。访问令牌由现有鉴权识别,无需新增入参。HTTP(超文本传输协议)内部结果保留旧字段并增加界面投影,recommendedQuestions(推荐问题)与界面推荐同源。Agent(智能体)公开出口只使用 uiResult(界面结果)。

入参:

| 字段 | 必填 | 中文说明 | |-|-|-| | systemType | 否 | 系统类型:sponge(2.0,默认)、supplier(供应商) |

回参:

| 字段 | 中文说明 | |-|-| | snapshot | 快照时间范围、生成时间及下次刷新时间 | | weeklyHotQuestions | 本周热门问题 | | recommendedQuestions | 推荐问题 | | blueprintGroups | 可复用查询蓝图分组 | | uiResult | 严格契约的界面结果;Agent 对外直接作为结构化正文 |

curl -X POST 'http://localhost:3001/mcp/tools/get_query_guidance' \
  -H 'Authorization: Bearer <访问令牌>' \
  -H 'Content-Type: application/json' \
  -d '{"systemType":"supplier"}'
{
  "snapshot": {
    "timezone": "Asia/Shanghai",
    "weekStart": "2026-08-24T00:00:00+08:00",
    "weekEndExclusive": "2026-08-31T00:00:00+08:00",
    "generatedAt": "2026-08-25T09:00:00+08:00",
    "nextRefreshAt": "2026-08-25T12:30:00+08:00"
  },
  "weeklyHotQuestions": [],
  "recommendedQuestions": [],
  "blueprintGroups": [],
  "uiResult": {
    "title": "丸子 · 供应商使用引导",
    "datasets": [],
    "blocks": [{
      "id": "intro",
      "type": "markdown",
      "content": "我可以帮你查询供应商业务数据,并分析已查询的结果。"
    }],
    "actions": []
  }
}

接口名称:analyze_query_result(分析查询结果)

接口说明:基于已成功查询的服务端留存结果执行专项分析,不重新生成或执行 SQL。

入参:

| 字段 | 必填 | 中文说明 | |-|-|-| | queryId | 是 | 原查询编号,必须来自上一条结果 | | analysisRequest | 否 | 分析要求;不传时复用原查询已保存的明确要求,但最终必须存在非空要求 |

回参:

| 字段 | 中文说明 | |-|-| | queryId | 原查询编号 | | status | 分析状态 | | analysisRequest | 本次分析要求 | | answer | 已渲染的分析正文 | | analysis | 分析内容 | | analysisStatus | 模型分析状态 | | cached | 是否复用已有分析 |

curl -X POST 'http://localhost:3001/mcp/tools/analyze_query_result' \
  -H 'Authorization: Bearer <访问令牌>' \
  -H 'Content-Type: application/json' \
  -d '{"queryId":"qry_a1b2","analysisRequest":"比较供应商高低"}'
{
  "queryId": "qry_a1b2",
  "status": "succeeded",
  "analysisRequest": "比较供应商高低",
  "answer": "## 数据分析\n甲供应商高于乙供应商。",
  "analysis": "甲供应商高于乙供应商。",
  "analysisStatus": "llm",
  "cached": false
}

安全边界

  • 正常查询只调用一次 query_sponge;SQL 生成、校验和最多两次自动修复都由 Sponge 主流程完成。
  • 上一条查询的 availableActions 包含 export_query_csv 时,纯导出追问才沿用 queryId 调用该工具;禁止重新调用 query_sponge。导出仍由 Sponge MCP Server 去掉展示上限、应用导出上限并重新执行安全与权限校验。
  • 上一条查询的 availableActions 包含 analyze_query_result 时,才可沿用 queryId 做专项分析;查询当轮待分析时沿用服务端要求,后续追问时逐字传入用户本轮要求,禁止自行改写或重跑查询。
  • 查询已自动导出全部数据时,保留 Sponge 返回的 exportResult,直接展示下载与分析正文。
  • 导出成功时,Sponge MCP Server 返回的 answer 已包含 CSV 下载信息和完整导出数据分析;octopus-agent 与上层 Agent 只能原样展示。
  • 查询返回 failed(失败)时原样展示服务端错误并结束,禁止追问或自行补充查询条件。
  • 查询返回 clarifying(等待补充条件)时原样展示服务端追问;用户下一轮补充条件后使用原 contextId 继续调用 query。
  • 查询成功或失败都使用 renderMode=verbatim_markdown(原样 Markdown)或 renderMode=verbatim(原样文本)。octopus-agent 不校验或补充 Sponge MCP Server 返回的 answer;上层 Agent 只能逐字展示 content[0].text。terminal=false 时按 pendingActions 顺序继续调用,不重新查询;terminal=true 且 nextAction=stop 时结束调用链。
  • 使用或检查 Agent 时只调用 health,禁止通过 query 做连接测试。
  • 非明确查询场景调用 get_query_guidance;能力询问直接展示动态引导,其他场景先说明目前只支持查询。
  • 未经用户明确确认,不调用 export_query_csv。
  • Agent 不接收或传入任意 SQL。
  • Agent 不读取 Schema,不生成 SQL,也不生成数据分析;用户语义路由由上层 LLM 负责,不使用正则或硬编码业务判断。
  • 认证 Token 仅用于身份透传,数据权限由 Sponge MCP Server 校验。
  • 不新建数据库。MCP Server 使用现有 mcp_query_run 持久化完整问答;当前会话的 contextId 由上层平台随会话记录保存并在续问时回传。