OpenCLI DuckDuckGo 适配器实战:浏览器搜索 + 补全建议双命令深度解析

OpenCLI DuckDuckGo 适配器实战:浏览器搜索 + 补全建议双命令深度解析 OpenCLI DuckDuckGo 适配器实战浏览器搜索 补全建议双命令深度解析【免费下载链接】OpenCLIMake Any Website into CLI Use your logged-in browser by AI agent.项目地址: https://gitcode.com/gh_mirrors/ope/OpenCLI本文以 OpenCLI 仓库中的 DuckDuckGo 适配器文档docs/adapters/browser/duckduckgo.md为主体结合其源码实现clis/duckduckgo/search.js、clis/duckduckgo/suggest.js与测试用例完整讲解opencli duckduckgo search与opencli duckduckgo suggest两条命令的参数语义、底层原理与使用边界。读完本文你将能够在终端中完成 DuckDuckGo 的区域化检索、时间过滤、跨页分页、结果提取与搜索词联想并理解浏览器模式与纯 HTTP API 两种适配器实现路线的差异。适配器总览DuckDuckGo 适配器属于 OpenCLI 的公开Public站点适配器工作模式为 公开访问覆盖两个域名域名用途html.duckduckgo.comsearch命令使用的 HTML 精简版搜索结果页duckduckgo.comsuggest命令使用的补全 API 所在域名适配器对外暴露两条命令CommandDescriptionopencli duckduckgo search keywordSearch DuckDuckGo and extract results from the pageopencli duckduckgo suggest keywordGet DuckDuckGo search suggestions从源码注册信息可以看到两条命令的元数据search为只读access: read、公开策略Strategy.PUBLIC、需要浏览器browser: truesuggest同样为只读公开策略但browser: false即完全不需要浏览器环境见 clis/duckduckgo/search.js 与 clis/duckduckgo/suggest.js。search命令浏览器模式下的结果提取参数语义search命令共支持 5 个参数其中keyword为必填位置参数其余均有默认值参数类型默认值说明keywordstring位置参数必填搜索关键词--limitint10单页结果数范围110HTML 版每页最多 10 条--offsetint0分页偏移量必须是10 的倍数0、10、20…内部走 XHR POST--regionstring全部区域区域代码如jp-jp、us-en、cn-zh--timestring无时间范围d天、w周、m月、y年这些参数并非文档建议而是在源码中被严格校验后才会发起网络请求--limit通过共享工具requireBoundedInteger校验越界直接抛出ArgumentError见 clis/duckduckgo/search.js--offset通过requireNonNegativeInteger校验后还会单独检查offset % 10 ! 0并抛出--offset must be a multiple of 10 for DuckDuckGo HTML pagination错误clis/duckduckgo/search.js--time必须匹配^(d|w|m|y)$正则否则报错clis/duckduckgo/search.js。输出列结构search的结果以表格/JSON 形式输出固定 7 个列源码columns定义于 clis/duckduckgo/search.js列名含义rank排名从 1 开始分页时等于index 1 offsettitle结果标题url解码后的真实目标 URL已处理uddg重定向snippet摘要文本取自.result__snippet节点displayUrl页面展示的 URL 文本icon站点图标地址取自.result__icon__imgresultType结果类型web/news/video/image输出格式与 OpenCLI 全局约定一致search同样支持-f json、-f yaml、-f csv、-f md等格式化输出便于管道传递给jq或 LLM 消费。使用示例# Basic search opencli duckduckgo search machine learning # Limit results opencli duckduckgo search machine learning --limit 5 # Region-specific search opencli duckduckgo search machine learning --region jp-jp # Time filter (past week) opencli duckduckgo search machine learning --time w # Pagination (second page) opencli duckduckgo search machine learning --offset 10 # JSON output opencli duckduckgo search machine learning -f json # Search suggestions opencli duckduckgo suggest machine --limit 5请求构造细节search的请求 URL 在源码中按如下规则拼装clis/duckduckgo/search.jshttps://html.duckduckgo.com/html/?q编码后的关键词[kl区域代码][df时间范围]其中kl是 DuckDuckGo 的区域region参数df是时间范围参数。区域代码遵循 DuckDuckGo 自己的格式如jp-jp、us-en、uk-en默认不传即表示全部区域。区域与时间过滤均以用户传入值为准直接透传未做白名单枚举因此传入有效区域代码即可生效。suggest命令免浏览器的公开 JSON API与search不同suggest走的是 DuckDuckGo 的公开补全接口duckduckgo.com/ac/全程使用 Node 内置fetch不依赖 Chrome 浏览器。参数与实现参数类型默认值说明keywordstring位置参数必填搜索词前缀--limitint8返回建议数量上限范围120实现要点见 clis/duckduckgo/suggest.js校验keyword非空、limit在 120 之间请求https://duckduckgo.com/ac/?q关键词typelist解析 JSON取数组第二个元素data[1]作为建议短语列表过滤空字符串按limit截断逐条映射为{ phrase }行输出输出列为[phrase]。fetch失败网络错误、非 2xx 状态码、畸形 JSON时分别被包装为带COMMAND_EXEC错误码的CommandExecutionError保证错误可被程序化捕获而非静默吞掉clis/duckduckgo/suggest.js。使用示例# 基本联想 opencli duckduckgo suggest machine # 指定建议数量 opencli duckduckgo suggest opencli --limit 5 # JSON 输出便于程序消费 opencli duckduckgo suggest machine -f json底层原理从源码看两条命令的工程实现1.uddg重定向解码DuckDuckGo 的搜索结果链接统一经过uddg参数跳转形如/l/?uddghttps%3A%2F%2Fexample.com%2F...适配器在decodeDdgUrl函数中解析该参数并还原出干净的最终 URL解码失败时退回原href并统一通过toHttpsUrl保证只输出http/https协议地址见 clis/duckduckgo/search.js 与共享工具 clis/_shared/search-adapter.js。测试用例 clis/duckduckgo/search.test.js 专门验证了/l/?uddg...到https://github.com/jackwener/OpenCLI的解码正确性。2. 浏览器内 DOM 提取脚本search之所以必须走浏览器模式是因为 DuckDuckGo 存在反爬保护普通 HTTP 请求难以稳定获取结果。适配器通过page.evaluate在页面上下文内执行一段注入脚本buildExtractFn其提取逻辑为clis/duckduckgo/search.js遍历.result节点通过 CSS 类名识别并跳过广告结果result--ad、result--ads、badge--ad分别抓取标题.result__a、摘要.result__snippet、展示 URL.result__url、图标.result__icon__img通过类名判定结果类型news-result→news、video-result→video、image-result→image否则为web以 href 为 key 去重按limit提前截断。测试用例使用JSDOM模拟了广告结果与自然结果的混合 DOM验证广告被过滤、自然结果被正确提取并映射为规范行结构clis/duckduckgo/search.test.js。3. 分页为何用 XHR POSTDuckDuckGo HTML 版的分页跳转依赖form.submit()行为在浏览器自动化场景下容易引发页面导航问题。适配器因此改用页面内 XHR POST实现翻页在首屏加载后通过XMLHttpRequest向/html/提交表单编码参数q、soffset、vl、ojson、可选kl再用DOMParser解析返回的 HTML 并复用同一套提取函数见buildPaginateJsclis/duckduckgo/search.js。这种方式避免了二次页面导航同时让--offset与结果rank精确对齐第 2 页首条即rank: 11测试见 clis/duckduckgo/search.test.js。代价是分页边界处结果可能与上一页存在少量重叠且--offset必须是 10 的倍数。4. 共享校验与错误封装两条命令复用clis/_shared/search-adapter.js中的一组工具函数这体现了 OpenCLI 搜索类适配器的通用工程约束clis/_shared/search-adapter.jsrequireSearchQuery关键词去空格后非空校验requireBoundedInteger/requireNonNegativeInteger整数区间校验requireRows/unwrapBrowserResult兼容浏览器会话信封{session, data}与纯数组两种载荷形态载荷形状异常时抛出带COMMAND_EXEC码的类型化错误runBrowserStep将浏览器步骤导航、提取的底层异常统一包装为类型化CommandExecutionErroremptySearchResults结果为空时抛出EmptyResultError。search测试中有一例专门验证当提取载荷形状不符合预期如{rows: []}时命令以COMMAND_EXEC错误失败而不是静默返回空数组clis/duckduckgo/search.test.js。suggest测试则验证了空关键词/超限 limit 在fetch之前就被拦截clis/duckduckgo/suggest.test.js。前置条件与运行环境suggest不需要 Chrome任何能运行 OpenCLI 的环境均可直接使用search需要 Chrome 处于运行状态Standalone 模式会自动启动或安装并启用 Browser Bridge 扩展详见 docs/guide/browser-bridge.md。Browser Bridge 是 OpenCLI 连接浏览器会话的轻量方案安装扩展后守护进程daemon会在首次执行浏览器命令时自动启动无需手工配置。可用opencli doctor检查扩展与守护进程的连通性。需要强调的是浏览器命令复用的是你 Chrome 中已登录的会话状态凭证不会离开浏览器DuckDuckGo 为公开站点无登录要求但浏览器模式本身仍是其反爬防护下最稳定的取数路径。已知限制与注意事项结合文档与源码使用本适配器时需注意以下边界search必须使用浏览器模式由于 DuckDuckGo 的反爬保护纯 HTTP 方式不可行单页最多 10 条结果HTML 版每页固定返回最多 10 条--limit只能在 110 之间取值需要更多结果请用--offset翻页分页结果可能重叠分页走 POST 导航页面边界处可能与前页结果重复摘要提取依赖 DOM 结构摘要取自 HTML 版的.result__snippet节点若 DuckDuckGo 调整前端结构提取逻辑clis/duckduckgo/search.js需同步跟进CJK 关键词联想为拼音近似ac/补全 API 对中文等 CJK 查询返回的是拼音音近建议phonetic suggestions可能与预期结果不完全一致区域代码格式遵循 DuckDuckGo 自身格式如jp-jp、us-en、uk-en默认全部区域。测试与质量保障本适配器带有完整的 Vitest 测试套件是理解其行为契约的最佳入口clis/duckduckgo/search.test.js覆盖命令注册元数据、参数校验前置拦截、uddg解码、广告过滤与 DOM 提取、分页信封解包、畸形载荷的类型化报错clis/duckduckgo/suggest.test.js覆盖命令注册、参数前置校验、公开 API 载荷解析与过滤、网络/JSON 异常映射为类型化错误。这些测试同时印证了本文所述的全部参数边界与错误语义——ARGUMENT类错误在发请求前抛出COMMAND_EXEC类错误统一封装底层异常空结果抛出EMPTY_RESULT。在 OpenCLI 中编写或审计新适配器时DuckDuckGo 适配器是一个兼具浏览器模式 纯 API 模式双路实现的参考范例。【免费下载链接】OpenCLIMake Any Website into CLI Use your logged-in browser by AI agent.项目地址: https://gitcode.com/gh_mirrors/ope/OpenCLI创作声明:本文部分内容由AI辅助生成(AIGC),仅供参考