docs: 联网搜索服务架构方案全套(plan-final/design-arch/选型决策/整合导览/MCP文档/部署预设/联调手册) bench: 5 方案 + 代理 + 站点矩阵本机实测工程(无密钥) 部署目标:primary mgr1 先行测试(待批准后执行)
10 KiB
| type | status | created | step |
|---|---|---|---|
| arch | active | 2026-09-01 | P2 / plan-20260901-02 |
onesvm-browser-server 设计与整合方式总览(入门导览)
读者:项目 owner 与后续接手工程师。本文是梳理与导读,回答四问——我们如何整合自部署服务?目前整合哪些?怎么整合的?提供什么样的服务?怎么做并发排队的? 权威关系:决策结论以
plan-final-20260901.md为准,机制细节以design-arch-20260901.md为准,选型理由见decision-candidates-20260901.md;本文只做组织与串联,数字全部引用自既有文档与 bench 产物(2026-09-01 本机实测)。
0. 一段式总览
onesvm-browser-server 是一个面向智能体消费者的自构建联网搜索服务:所有消费者(Vlepontas、EAI 等)在统一出口网关注册主体、拿 key,以 MCP(主)或 HTTP(兜底)调用两类意图(search / read);请求经认证、合规预检后进入零 Redis 的 SQLite WAL 队列(60 会话接纳上限),由单写者 scheduler 按能力标签路由给 Dock 适配器集群——目前整合了 5+1 个自部署组件(双 SearXNG、Trafilatura、Lightpanda、chrome-headless-shell、mihomo 代理数据面);适配器只产出原始结果,统一由**共享 worker 模版层(整合器)**做体积守卫、正文提纯、安全扫描后封装成 AI 原生信封返回。全栈常驻内存实测 ~380MB,承诺 ≤1GB 渐进扩容。
flowchart LR
C[智能体消费者<br/>Vlepontas / EAI / 注册主体] --> G[统一出口网关 ×N 无状态<br/>MCP 主 POST /mcp + HTTP 兜底 /v1/*<br/>X-Service-Token 认证 · 配额预扣]
G --> POL1[合规·请求侧<br/>SSRF / 域名策略]
POL1 -->|overlay POST /enqueue| S[scheduler 单副本<br/>SQLite WAL 单写者 · ADMIT_MAX=60]
S --> RT{能力路由<br/>region / render 标签}
subgraph DOCK[Dock worker 集群(共享模版层 = 整合器)]
subgraph WA[A 无浏览器]
AA1[适配器: searxng-cn<br/>searxng-global]
AA2[适配器: trafilatura-http]
end
subgraph WB[B 轻渲染]
AB[适配器: lightpanda]
end
subgraph WC[C 保真·按需槽]
AC[适配器: chrome-headless-shell]
end
TPL[共享模版层<br/>RawResult → Size guard → fit markdown<br/>→ 安全扫描/PII redact → 统一信封<br/>词表单源版本化]
WA & WB & WC --> TPL
end
RT --> WA & WB & WC
DOCK -.插拔预留 render=full+headful.-> HD[(有头档·默认不部署)]
WB & WC --> PM[ProxyManager 单副本<br/>mihomo vless 热池 · 域名路由]
AA1 -->|国内域| DI[国内直连]
AA1 -->|境外搜索| PM
TPL -->|Envelope ok/error| C
(机制细节拓扑见 design-arch §1;接入时序见 design-arch §3.5。)
1. 目前整合了哪些自部署服务
5 个消费组件 + 1 个代理数据面,全部经 2026-09-01 本机 Docker 实测(darwin arm64,cgroup 口径;原始数据 bench/*/results.json):
| 组件 | 镜像与版本 pin | 角色 | idle | 单会话峰 | 60 burst 峰 | 出处 |
|---|---|---|---|---|---|---|
| searxng-cn | searxng/searxng:2026.8.29-d226b78bc(digest b36af798) |
国内搜索(百度/搜狗/360/必应中国) | 98.9MB | 121.6MB | 170.5MB | S3b-summary §2 |
| trafilatura-http | 自构建 python:3.12-slim-bookworm + trafilatura==2.2.0 |
正文精读(纯 HTTP) | 33.0MB | 35.2MB | 40.6MB | S3b-summary §2 |
| searxng-global | 同 SearXNG 镜像第二实例(Google/Bing/DDG/Brave 等) | 国外搜索(实测 Bing-only,见 D2) | 121.6MB | 149.6MB | 181.3MB | S3c-summary §1 |
| lightpanda | lightpanda/browser:0.3.7(digest eae2c7f8) |
默认轻 JS 渲染核 | 3.6MB | 251.4MB(重 Shopify 页) | 143.4MB | S3c-summary §1 |
| chrome-headless-shell | chromedp/headless-shell:151.0.7922.109(digest 2d349b54) |
保真渲染单槽(L2 按需/L3 常驻) | 37.5MB | 394.0MB(同页) | 179.3MB | S3c-summary §1 |
| mihomo(ProxyManager 数据面) | metacubex/mihomo v1.19.24 |
代理出口(vless 热池 52 节点实测全活) | 小(未单独采样,估算·待校准) | — | — | proxy-probe.md |
为什么选它们(含排除与预留):见 decision-candidates-20260901.md §1–§3。
2. 怎么整合的(Dock Protocol)
设计全文:design-arch §3。核心四件套:
- 适配器契约(五方法):
init / health / execute / teardown / capabilities。health()强制上报rss_bytes / startup_ms / slots_free;capabilities()声明支持的意图、渲染分级(none|light|full)、出口需求(domestic|overseas)、自身并发上限、是否必须走代理。适配器负责把统一意图翻译成引擎原生调用(SearXNGformat=json、CDP navigate 等),只产出 RawResult,原生结构不出适配器。 - 共享 worker 模版层(= 整合器,S7 架构审查锁定归属):所有适配器共用同一层完成
RawResult → Size/Type guard → fit markdown → 安全扫描 + PII redact + 注入包裹 → 统一信封;词表/规则单源版本化(wordlist_version入审计),N 个适配器零合规代码,杜绝门闩漂移。 - 能力路由(标签制):
region=domestic直连、region=overseas经 ProxyManager、render=none/light/full分流到 A/B/C 类适配器;约 90% 流量(搜索 + 纯 HTTP 读)不进浏览器槽。 - 降级链:C 槽满 → B → A →
blocked/upstream,不静默降数据质量(打warnings);cloudflare/waf/captcha拦截不拿渲染空转,直接blocked(站点矩阵实测纪律,decision-candidates §6)。
接入第 6 个方案要做什么(示例:新增 RSSHub 适配器)
- 部署或接入 RSSHub 实例(自部署 Docker,内网端点),版本 pin 写入 stack;
- 在 worker 代码里新增
RsshubAdapter实现五方法:capabilities() = {intents:[search,read], render:none, regions:[domestic,overseas], proxy_required:false, formats:[markdown,links]};execute()把Search/Read意图译为 RSSHub 路由请求,返回 RawResult; - 在 scheduler 路由表注册标签(如
region=domestic, render=none, kind=rss),按需挂路由规则; - 不需要写任何合规/提纯代码——共享模版层自动生效;只需确认 RawResult 字段映射正确;
- 跑 bench 三档内存 + 模板断言(参照
bench/plan.md),数字回填档位表;超预算则开评审。
3. 提供什么样的服务
设计全文:design-arch §2/§3.3;决策摘要:plan-final §1/§3。
- 两类意图:
Search{query, max_results≤20, time_range?, lang?, region}→ 返回results[{title,url,content≤800字,score 0–1,engine}],不含全文;Read{url, formats=["markdown"], max_chars, extract?, region}→ 返回 fit markdown(实测提纯 420–500 倍:1.44MB Shopify 壳 → 2.9–3.4KB)+ 可选extract结构化抽取(默认零 LLM 路径:JSON-LD/OG/CSS)。browse(多步交互)协议预留,默认关闭。
- region 参数:
domestic/overseas由消费者按 MCP 文档自行选择(国内直连数据 vs 经代理的外域数据);网关仍按域名路由表强制合规兜底。 - 统一信封:
{ok, kind, request_id, took_ms, usage{credits,engine,tokens_estimate}, provenance{url,retrieved_at+08:00,adapter,proxy_exit,cached}, error{code,message,retry_after_s?}}。 - 错误码(MCP/HTTP 两面对齐):
blocked | denied | timeout | quota | rate_limited | extract_failed | upstream。 - 双形态:MCP Server 为主(
POST /mcp,Streamable HTTP,2026 无状态;2025 兼容腿挂 O9 待决)+ HTTP API 兜底(独立端口:8640+/bs-api前缀,D3 待确认);认证X-Service-Token,禁 Bearer 塞静态 key。 - 能力边界(20 站实测矩阵):纯 HTTP 够 7 站、须 JS 4 站、当前出口打不过 9 站(Amazon/Medium/Reddit/X/知乎/微博等)——逐场景结论见
decision-candidates-20260901.md§6,原始数据site-matrix.md。
4. 怎么做并发排队(零 Redis)
设计全文:design-arch §4;实测校准:plan-final §2。
为什么不要 Redis:60 深度远低于 SQLite WAL 舒适区;Redis 白占 30–80MB 直接威胁 1GB 预算;NATS Core 不可靠、JetStream 是另一个中间件;PG SKIP LOCKED 需要现成 PG(本集群没有为此单拉)。
入队路径:消费者 → gateway(无状态:认证/配额预扣/合规预检)→ overlay 内网 POST /enqueue → scheduler(SQLite 唯一写者)进程内快通道 + 立即落 WAL → 落盘成功才 ACK 排队位;scheduler 不可达 → 503 + Retry-After(fail-closed,gateway 本地不落盘)。
背压三层:ADMIT_MAX=60(running+queued 合计)→ 超限 429/503 只拒新不杀旧;CONCURRENT 浏览器槽 = 1 起步;HEALTH 内存阈 60–70%;渲染互斥规则 shell_active ⇒ lightpanda 停接新任务(入队侧执行,无需预知页面重量);租约 + reaper + 指数退避(attempts≤2)+ 死信表。
实测行为锚点(为什么这样设计):
| 实测现象(2026-09-01) | 对应设计 |
|---|---|
| chrome-headless-shell CONCURRENT=1:60 任务 FIFO 全入队、顺序执行、0 拒绝 0 OOM、墙钟 74.0s | 60 是队列深度不是浏览器并发;保真槽单实例排队复用 |
| lightpanda 4 槽:60/60 全过、28.2s(2.13 jobs/s) | 轻渲染多槽并行,承载 JS 流量主力 |
| searxng-cn 裸 60 并发:HTTP 全 200 但断言仅 4/60——百度/搜狗被 CAPTCHA 打灭,必应中国 60/60 | 网关对上游钳 4–8 并发 + 每 host 最小间隔 + 短缓存;多副本不能分散 CAPTCHA(反爬按出口 IP 计) |
| trafilatura 60/60、p50 0.115s、burst 仅 40.6MB | 纯 HTTP 读走高并发快通道,不占浏览器槽 |
负载结论:60 会话稳态占用率——搜索 ~21%、读取 ~3%、渲染 ~5%(换算见 plan-final §2.5);1GB 可维持 Vlepontas + EAI 日常负载,扩容触发条件与 L3 增量见 D1。
5. 延伸阅读
| 想深入了解 | 去读 |
|---|---|
| 决策点与档位表 | plan-final-20260901.md §2/§7 |
| 机制细节(队列字段/代理池策略/合规五道) | design-arch-20260901.md §4/§5 |
| 为什么选这 5 套、能力边界矩阵 | decision-candidates-20260901.md |
| 实测原始数据 | bench/*/results.json、.dsh/artifacts/run-20260901-browser-arch/ |