chainlesschain 0.165.6 → 0.165.8
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/package.json +2 -1
- package/src/assets/web-panel/assets/{AIOps-vfoDb6HZ.js → AIOps-B3gWmXjo.js} +1 -1
- package/src/assets/web-panel/assets/{ActionButton-Cm5f7p93.js → ActionButton-G9pdT-0e.js} +1 -1
- package/src/assets/web-panel/assets/{Analytics-yRuvgWxa.js → Analytics-Ca30J7m2.js} +3 -3
- package/src/assets/web-panel/assets/{AppLayout-BROsC4h1.js → AppLayout-BtVTm8PU.js} +5 -5
- package/src/assets/web-panel/assets/{Artifacts-CimHApb1.js → Artifacts-BhViNa6u.js} +1 -1
- package/src/assets/web-panel/assets/{Audit-DI8kr8zI.js → Audit-DhKq-FnY.js} +1 -1
- package/src/assets/web-panel/assets/{BackgroundAgents-DSLzKy-n.js → BackgroundAgents-BL0SVbnE.js} +1 -1
- package/src/assets/web-panel/assets/{Backup-DkH_n2r1.js → Backup-BWkblnFi.js} +1 -1
- package/src/assets/web-panel/assets/{BaseInput-CKSrUoRA.js → BaseInput-ClaRNrF8.js} +1 -1
- package/src/assets/web-panel/assets/{Chat-ClwfMXUS.js → Chat-sZE2Z77o.js} +4 -4
- package/src/assets/web-panel/assets/{ChatBubbleRenderer-CjMaqfL7.js → ChatBubbleRenderer-BAfKOnRe.js} +1 -1
- package/src/assets/web-panel/assets/{Checkbox-BYTehcQG.js → Checkbox-Cvhay5WM.js} +1 -1
- package/src/assets/web-panel/assets/{Codegen-B8AMcp6J.js → Codegen-BpejL-4N.js} +1 -1
- package/src/assets/web-panel/assets/{Col-BNSogPo3.js → Col-g2Ki6g_1.js} +1 -1
- package/src/assets/web-panel/assets/{Community-JxPvGb8O.js → Community-D2xKbNo9.js} +1 -1
- package/src/assets/web-panel/assets/{Compact-DF7bFAgE.js → Compact-DbL1Pds3.js} +1 -1
- package/src/assets/web-panel/assets/{Compliance-Bvhqnwrq.js → Compliance-DGtZCV4c.js} +1 -1
- package/src/assets/web-panel/assets/{Cowork-BDS0CJvM.js → Cowork-4kQpoNsI.js} +3 -3
- package/src/assets/web-panel/assets/{Cron-DqvRfxoQ.js → Cron-BxTYXXAN.js} +2 -2
- package/src/assets/web-panel/assets/{Crosschain-CDcIvnqS.js → Crosschain-k0J0LT2N.js} +1 -1
- package/src/assets/web-panel/assets/{DID-D7jaUxU3.js → DID-BaqhoPgN.js} +2 -2
- package/src/assets/web-panel/assets/{Dashboard-B5A18wEV.js → Dashboard-T4RVPIM1.js} +2 -2
- package/src/assets/web-panel/assets/{Dropdown-_6IVkGag.js → Dropdown-DszOToWq.js} +1 -1
- package/src/assets/web-panel/assets/{EmailListRenderer-C9PeiKCG.js → EmailListRenderer-C9KJU7HF.js} +1 -1
- package/src/assets/web-panel/assets/{FamilyGuardDashboard-DXjuEHrX.js → FamilyGuardDashboard-Cmr0JnsA.js} +1 -1
- package/src/assets/web-panel/assets/{Federation-B4IAR9zv.js → Federation-BI-_2xZX.js} +1 -1
- package/src/assets/web-panel/assets/{FormItemContext-CxQeSNx1.js → FormItemContext-DsnDEPsl.js} +1 -1
- package/src/assets/web-panel/assets/{GenericCardRenderer-B8GS-Y3N.js → GenericCardRenderer-BLncAKKK.js} +1 -1
- package/src/assets/web-panel/assets/{Git-BS8SouUX.js → Git-BPQhGXDn.js} +2 -2
- package/src/assets/web-panel/assets/{Governance-Dq9aYb5Q.js → Governance-CyElbUQW.js} +1 -1
- package/src/assets/web-panel/assets/{Inference-BrCEe9AJ.js → Inference-CcSntBQD.js} +1 -1
- package/src/assets/web-panel/assets/{KnowledgeGraph-DybOpiY2.js → KnowledgeGraph-p6e7HZ2r.js} +1 -1
- package/src/assets/web-panel/assets/{Logs-DBpzbRfx.js → Logs-CNEtr-wz.js} +2 -2
- package/src/assets/web-panel/assets/MarkdownRenderer-Bj9xI0YH.js +1 -0
- package/src/assets/web-panel/assets/{Marketplace-Cc7CCSCu.js → Marketplace-Dd2notAJ.js} +1 -1
- package/src/assets/web-panel/assets/{McpTools-DFaIhOfu.js → McpTools-BBsN2CSW.js} +4 -4
- package/src/assets/web-panel/assets/{Memory-KCqlp9ol.js → Memory-Dg2uTvwx.js} +2 -2
- package/src/assets/web-panel/assets/{MobileBridge-Bys84ySN.js → MobileBridge-r1YMRiJV.js} +1 -1
- package/src/assets/web-panel/assets/{MobileProjects-B-6qU-je.js → MobileProjects-C-89kSm4.js} +1 -1
- package/src/assets/web-panel/assets/{Mtc-BgY-fvCq.js → Mtc-CrPZcVgf.js} +5 -5
- package/src/assets/web-panel/assets/{MtcAudit-B8pCmqQJ.js → MtcAudit-sxi7hqJb.js} +4 -4
- package/src/assets/web-panel/assets/{Multisig-BbOmYutA.js → Multisig-CAgOMfF1.js} +3 -3
- package/src/assets/web-panel/assets/{NLProgramming-BocLQz_M.js → NLProgramming-DafaPts3.js} +1 -1
- package/src/assets/web-panel/assets/{Notes-CSwbxEop.js → Notes-CJM-xUW_.js} +3 -3
- package/src/assets/web-panel/assets/{NotificationSettings-CqFNSYG3.js → NotificationSettings-L0ZjfAh_.js} +1 -1
- package/src/assets/web-panel/assets/{OrderTableRenderer-C6gMfAk7.js → OrderTableRenderer-BB1CvCK0.js} +1 -1
- package/src/assets/web-panel/assets/{Organization-QrDXVdMJ.js → Organization-DeLtgAD8.js} +4 -4
- package/src/assets/web-panel/assets/{Overflow-Cxntotjt.js → Overflow-CKC2b10z.js} +1 -1
- package/src/assets/web-panel/assets/{P2P-CIdBOwNq.js → P2P-eyf2rzY1.js} +2 -2
- package/src/assets/web-panel/assets/{PdhVaultBrowser-CT5aP8rD.js → PdhVaultBrowser-5upNIOW8.js} +3 -3
- package/src/assets/web-panel/assets/{Permissions-DH7OM8XU.js → Permissions-B8p3W6JK.js} +4 -4
- package/src/assets/web-panel/assets/{PersonalDataHub-CnJqbWce.js → PersonalDataHub-BnRMxTq3.js} +5 -5
- package/src/assets/web-panel/assets/{Pipeline-5C3HG1kH.js → Pipeline-DjCNI1li.js} +1 -1
- package/src/assets/web-panel/assets/{Privacy-B4yIp7xK.js → Privacy-u6gXLbWT.js} +1 -1
- package/src/assets/web-panel/assets/{ProjectInit-BMvt-2M0.js → ProjectInit-BZAw4tkM.js} +2 -2
- package/src/assets/web-panel/assets/{ProjectSettings-CvSTEMRG.js → ProjectSettings-B1Tr72q7.js} +2 -2
- package/src/assets/web-panel/assets/{Projects-BKBJxEek.js → Projects-DO7HFuBQ.js} +1 -1
- package/src/assets/web-panel/assets/{Providers-BdwUqFWN.js → Providers-BjCztyhj.js} +1 -1
- package/src/assets/web-panel/assets/{QrScannerModal-DtnCKlTm.js → QrScannerModal-ZWyCUbR1.js} +1 -1
- package/src/assets/web-panel/assets/{QuickAsk-sTbgwyNr.js → QuickAsk-DhDjeW4G.js} +1 -1
- package/src/assets/web-panel/assets/{Recommend-Bzr14gSb.js → Recommend-R_CN2MuU.js} +1 -1
- package/src/assets/web-panel/assets/{RemoteSession-C_TF5IaJ.js → RemoteSession-uxFcujeu.js} +2 -2
- package/src/assets/web-panel/assets/{Reputation-GCAM4H2K.js → Reputation-DX8D7rks.js} +1 -1
- package/src/assets/web-panel/assets/{Row-Dir0r6OQ.js → Row-BYahQILD.js} +1 -1
- package/src/assets/web-panel/assets/{RssFeed-CpGnlecX.js → RssFeed-CUSQ2tm-.js} +3 -3
- package/src/assets/web-panel/assets/{Search-DMMamC6u.js → Search-CnN_S8Cs.js} +1 -1
- package/src/assets/web-panel/assets/{Security-yqay5yG-.js → Security-DcZlh-O4.js} +4 -4
- package/src/assets/web-panel/assets/{Services-C5i2wh9G.js → Services-ZhBOjzIX.js} +2 -2
- package/src/assets/web-panel/assets/{Skeleton-vUqk35yj.js → Skeleton-D5Qnq_lI.js} +1 -1
- package/src/assets/web-panel/assets/{Skills-DzcSkhot.js → Skills-BC9cZ3Be.js} +1 -1
- package/src/assets/web-panel/assets/{Sla-CB6qbYNr.js → Sla-DauJ3E8_.js} +1 -1
- package/src/assets/web-panel/assets/SpeechSettings-DbNeZ_fh.js +1 -0
- package/src/assets/web-panel/assets/{SyncSettings-D-RrsxTJ.js → SyncSettings-DUvJbSct.js} +2 -2
- package/src/assets/web-panel/assets/{Tasks-DFxdOJiq.js → Tasks-BXa-5noQ.js} +1 -1
- package/src/assets/web-panel/assets/{Templates-SKAob_Aq.js → Templates-JxaiUt_3.js} +1 -1
- package/src/assets/web-panel/assets/{Tenant-BPfsfHQ-.js → Tenant-BW4ERQN8.js} +1 -1
- package/src/assets/web-panel/assets/{Terminal-8iw7FpUf.js → Terminal-DltUbdtv.js} +2 -2
- package/src/assets/web-panel/assets/{TimelineRenderer-C4Gjj5Su.js → TimelineRenderer-CMoZz0Tc.js} +1 -1
- package/src/assets/web-panel/assets/{Tokens-COYhN18e.js → Tokens-D_VEV60K.js} +1 -1
- package/src/assets/web-panel/assets/{Trigger-B-JzXcf6.js → Trigger-CCXTCs0R.js} +1 -1
- package/src/assets/web-panel/assets/{Trust-BJ5bg0nI.js → Trust-lkGRIPcG.js} +1 -1
- package/src/assets/web-panel/assets/{UkeySign-BG_ByRMf.js → UkeySign-BfGeQ9HX.js} +1 -1
- package/src/assets/web-panel/assets/{VideoEditing-B3kOnSiU.js → VideoEditing-BEC7pYvc.js} +1 -1
- package/src/assets/web-panel/assets/{Wallet-CcoGFnK7.js → Wallet-BZdG24o0.js} +4 -4
- package/src/assets/web-panel/assets/{WebAuthn-DdT8vRC_.js → WebAuthn-yoEddedp.js} +4 -4
- package/src/assets/web-panel/assets/{WorkflowEditor-CZu3M9N8.js → WorkflowEditor-BXZEprOW.js} +1 -1
- package/src/assets/web-panel/assets/{chat-DxJt3Qba.js → chat-gg0bzZal.js} +1 -1
- package/src/assets/web-panel/assets/{colors-DdYfwJaB.js → colors-DjRVRuin.js} +1 -1
- package/src/assets/web-panel/assets/{compact-item-BG3SUzwj.js → compact-item-su-dieAc.js} +1 -1
- package/src/assets/web-panel/assets/{createContext-By51z2-1.js → createContext-Ci3S8oKF.js} +1 -1
- package/src/assets/web-panel/assets/devWarning-CxbFX9uH.js +1 -0
- package/src/assets/web-panel/assets/{hasIn-B0apZ3KJ.js → hasIn-D8F10heH.js} +1 -1
- package/src/assets/web-panel/assets/{index-DE76D-kA.js → index-11wtYQiF.js} +1 -1
- package/src/assets/web-panel/assets/{index-BkvcEo4p.js → index-1IgxgALJ.js} +1 -1
- package/src/assets/web-panel/assets/{index-Bos5_aMV.js → index-1agckWSq.js} +1 -1
- package/src/assets/web-panel/assets/{index-BfWYsB9t.js → index-5JqhujnR.js} +1 -1
- package/src/assets/web-panel/assets/{index-CAhHirVH.js → index-6Tniqk1s.js} +1 -1
- package/src/assets/web-panel/assets/{index-BYINoRLK.js → index-8Z-8BIlN.js} +1 -1
- package/src/assets/web-panel/assets/{index-B5rLiEo0.js → index-BCI5v0yB.js} +1 -1
- package/src/assets/web-panel/assets/{index-BZ_0qm4g.js → index-BDJntYmJ.js} +1 -1
- package/src/assets/web-panel/assets/{index-CWEuZWCK.js → index-BGzixOGZ.js} +1 -1
- package/src/assets/web-panel/assets/{index-BLIbGOLX.js → index-BMMOVoLD.js} +1 -1
- package/src/assets/web-panel/assets/{index-bP_VlDb4.js → index-BTFpdBtt.js} +1 -1
- package/src/assets/web-panel/assets/{index-B3rWuPMW.js → index-Ba_HyPnE.js} +1 -1
- package/src/assets/web-panel/assets/{index-Da_WBdLX.js → index-BbF1IHof.js} +1 -1
- package/src/assets/web-panel/assets/{index-RD6O-0C6.js → index-BgT9su_e.js} +1 -1
- package/src/assets/web-panel/assets/{index-CpjZhgNd.js → index-BzPB6kGZ.js} +1 -1
- package/src/assets/web-panel/assets/{index-Q2SCX-MI.js → index-C6ygzplr.js} +1 -1
- package/src/assets/web-panel/assets/{index-BIrJfqO4.js → index-CC3ZDjzY.js} +1 -1
- package/src/assets/web-panel/assets/{index-BBPf3TpM.js → index-CEmXRhAE.js} +1 -1
- package/src/assets/web-panel/assets/index-CJGOlduY.js +1 -0
- package/src/assets/web-panel/assets/{index-Cp6e-hGw.js → index-CMPqd5Cv.js} +1 -1
- package/src/assets/web-panel/assets/{index-kf57LJ93.js → index-COWd8uGx.js} +1 -1
- package/src/assets/web-panel/assets/{index-CW93tZDv.js → index-CPIYSp4H.js} +1 -1
- package/src/assets/web-panel/assets/{index-BewKYrX9.js → index-CR0h6seT.js} +1 -1
- package/src/assets/web-panel/assets/{index-p1_8SbI1.js → index-CUmDhC4j.js} +1 -1
- package/src/assets/web-panel/assets/index-CkBCN5yH.js +1 -0
- package/src/assets/web-panel/assets/{index-ZxtP8jG7.js → index-CusgZPtc.js} +1 -1
- package/src/assets/web-panel/assets/{index-BWF8_mkx.js → index-DBAETXft.js} +1 -1
- package/src/assets/web-panel/assets/{index-BP94CrBV.js → index-DIJ2qFOC.js} +1 -1
- package/src/assets/web-panel/assets/{index-CNIxXMmN.js → index-Dbq4NMET.js} +1 -1
- package/src/assets/web-panel/assets/{index-CzmQElZy.js → index-DkMEF5VT.js} +1 -1
- package/src/assets/web-panel/assets/{index-ZFbps9po.js → index-DkfQR3hM.js} +1 -1
- package/src/assets/web-panel/assets/{index-Dz49VOyQ.js → index-DnLucOn9.js} +1 -1
- package/src/assets/web-panel/assets/{index-oxRrmFO9.js → index-DugB_aKa.js} +1 -1
- package/src/assets/web-panel/assets/{index-Bissefox.js → index-DyLUarhZ.js} +3 -3
- package/src/assets/web-panel/assets/{index-DaIz0NAW.js → index-T6_6ygJZ.js} +1 -1
- package/src/assets/web-panel/assets/{index-SQqOlR3d.js → index-Tu8eWqh-.js} +1 -1
- package/src/assets/web-panel/assets/{index-DCn8IcxV.js → index-W7XUgdVL.js} +1 -1
- package/src/assets/web-panel/assets/{index-3jWkIu5j.js → index-dHZinfko.js} +1 -1
- package/src/assets/web-panel/assets/{index-C1C9i79A.js → index-jyNgp5FI.js} +1 -1
- package/src/assets/web-panel/assets/{initDefaultProps-BWJktcg8.js → initDefaultProps-Cv4p8e4w.js} +1 -1
- package/src/assets/web-panel/assets/{motion-BEXBzUFV.js → motion-B8EwmMOw.js} +1 -1
- package/src/assets/web-panel/assets/{move-BUKwn2sx.js → move-B8R9F8TK.js} +1 -1
- package/src/assets/web-panel/assets/{mtc-parser-FTI7btqQ.js → mtc-parser-DoFYz5Bp.js} +1 -1
- package/src/assets/web-panel/assets/{omit-CsLtSPH3.js → omit-CHWYLBjI.js} +1 -1
- package/src/assets/web-panel/assets/{pickAttrs-DWZxsT_S.js → pickAttrs-CXuPDO77.js} +1 -1
- package/src/assets/web-panel/assets/{placementArrow-Bcfs43CX.js → placementArrow-BaAtUUon.js} +1 -1
- package/src/assets/web-panel/assets/{responsiveObserve-a9bcC1p-.js → responsiveObserve-DCc4zcDD.js} +1 -1
- package/src/assets/web-panel/assets/{slide-BDTzgOXN.js → slide-B_lx89oZ.js} +1 -1
- package/src/assets/web-panel/assets/{statusUtils-Iq1j_HUg.js → statusUtils-DE8DPmR0.js} +1 -1
- package/src/assets/web-panel/assets/{styleChecker-DAZEYxeh.js → styleChecker-1ktXOsL_.js} +1 -1
- package/src/assets/web-panel/assets/{useFlexGapSupport-DVkjyDrh.js → useFlexGapSupport-xH89-wjh.js} +1 -1
- package/src/assets/web-panel/assets/{useFs-wXTpNTHt.js → useFs-DscvfW5p.js} +1 -1
- package/src/assets/web-panel/assets/{usePersonalDataHub-CtQM_aZr.js → usePersonalDataHub-RdMKQta7.js} +1 -1
- package/src/assets/web-panel/assets/{vnode-hjEoG85v.js → vnode-Z3wTni2T.js} +1 -1
- package/src/assets/web-panel/assets/{zoom-BHVpyKg_.js → zoom-B0iChCsm.js} +1 -1
- package/src/assets/web-panel/index.html +1 -1
- package/src/command-help-index.json +3 -3
- package/src/commands/agent.js +91 -60
- package/src/commands/git.js +39 -0
- package/src/commands/plugin.js +17 -2
- package/src/commands/session-group.js +131 -0
- package/src/commands/session-location.js +48 -0
- package/src/commands/session.js +11 -0
- package/src/commands/sync-providers.js +4 -1
- package/src/commands/update.js +1 -0
- package/src/data/changelog.json +27 -1
- package/src/gateways/ws/ws-agent-handler.js +20 -12
- package/src/harness/jsonl-session-store.js +279 -37
- package/src/harness/mcp-client.js +701 -91
- package/src/harness/session-index.js +15 -4
- package/src/lib/agent-worktree.js +8 -1
- package/src/lib/auto-mode-safety-classifier.js +3 -17
- package/src/lib/background-agent-keeper-protocol.js +26 -6
- package/src/lib/background-agent-supervisor.js +17 -1
- package/src/lib/browser-evidence.js +1405 -0
- package/src/lib/chrome-connector.js +465 -79
- package/src/lib/claude-project-auto-memory.js +481 -0
- package/src/lib/claude-project-storage-layout.js +104 -0
- package/src/lib/cloud/cloud-client.js +40 -0
- package/src/lib/execution-location-local-supervisor.mjs +226 -0
- package/src/lib/execution-location-runner-lifecycle.js +991 -0
- package/src/lib/execution-location-target-preflight.js +333 -0
- package/src/lib/execution-location-target.js +783 -13
- package/src/lib/file-lines.js +6 -1
- package/src/lib/gateway-client-resilience.js +571 -0
- package/src/lib/gitlab-mr-worktree.js +176 -0
- package/src/lib/hooks-v2-producers.js +119 -15
- package/src/lib/hooks-v2-workspace-context.js +44 -1
- package/src/lib/host-resource-budget.js +295 -0
- package/src/lib/ide-context.js +15 -2
- package/src/lib/llm-config-defaults.js +43 -0
- package/src/lib/mcp-lifecycle-authority.js +887 -0
- package/src/lib/mcp-oauth.js +101 -20
- package/src/lib/mcp-tls.js +103 -3
- package/src/lib/paths.js +260 -32
- package/src/lib/permission-request.js +48 -0
- package/src/lib/plugin-runtime/bin.js +3 -1
- package/src/lib/plugin-runtime/hooks.js +3 -1
- package/src/lib/plugin-runtime/install.js +117 -1
- package/src/lib/plugin-runtime/lsp.js +4 -4
- package/src/lib/plugin-runtime/marketplace-archive-source.js +40 -5
- package/src/lib/plugin-runtime/marketplace-catalog.js +13 -2
- package/src/lib/plugin-runtime/marketplace-command-descriptor.js +343 -0
- package/src/lib/plugin-runtime/marketplace-command-source.js +580 -0
- package/src/lib/plugin-runtime/marketplace-source-adapter.js +33 -8
- package/src/lib/plugin-runtime/mcp.js +3 -1
- package/src/lib/plugin-runtime/monitors.js +3 -1
- package/src/lib/plugin-runtime/remote-source.js +151 -6
- package/src/lib/plugin-runtime/settings.js +3 -1
- package/src/lib/plugin-runtime/trust.js +274 -13
- package/src/lib/process-execution-broker/credential-agent.js +210 -41
- package/src/lib/process-execution-broker/index.js +15 -1
- package/src/lib/process-execution-broker/linux-cgroup-v2.js +391 -0
- package/src/lib/process-execution-broker/platform-sandbox.js +50 -28
- package/src/lib/project-mcp-trust.js +165 -10
- package/src/lib/resume-session.js +9 -6
- package/src/lib/session-core-singletons.js +26 -11
- package/src/lib/session-host-lease.js +52 -16
- package/src/lib/session-lifecycle-scope.js +153 -0
- package/src/lib/session-message-fabric.js +168 -21
- package/src/lib/session-projection.js +244 -4
- package/src/lib/session-store-guard.js +3 -1
- package/src/lib/session-workbench-store.js +466 -0
- package/src/lib/spellcheck.js +211 -0
- package/src/lib/sub-agent-context.js +9 -9
- package/src/lib/sync-cli-db.js +485 -129
- package/src/lib/sync-credentials.js +31 -20
- package/src/lib/web-fetch.js +112 -40
- package/src/lib/web-search.js +127 -61
- package/src/lib/workspace-trust.js +793 -0
- package/src/repl/agent-repl.js +124 -5
- package/src/repl/permission-prompt.js +10 -12
- package/src/runtime/agent-core.js +311 -18
- package/src/runtime/bootstrap.js +37 -13
- package/src/runtime/coding-agent-contract-shared.cjs +11 -4
- package/src/runtime/headless-runner.js +234 -36
- package/src/runtime/headless-stream.js +181 -6
- package/src/runtime/mcp-config.js +298 -8
- package/src/runtime/policies/agent-policy.js +8 -0
- package/src/runtime/status-diagnostics-lite.js +9 -1
- package/src/assets/web-panel/assets/MarkdownRenderer-CFyt8iUd.js +0 -1
- package/src/assets/web-panel/assets/SpeechSettings-BHUI7cox.js +0 -1
- package/src/assets/web-panel/assets/devWarning-DorRZcI9.js +0 -1
- package/src/assets/web-panel/assets/index-BETiL0a3.js +0 -1
- package/src/assets/web-panel/assets/index-BhAVHuW8.js +0 -1
|
@@ -21,9 +21,9 @@
|
|
|
21
21
|
|
|
22
22
|
import fs from "node:fs";
|
|
23
23
|
import path from "node:path";
|
|
24
|
-
import os from "node:os";
|
|
25
24
|
import crypto from "node:crypto";
|
|
26
25
|
import { withFileLock } from "./with-file-lock.js";
|
|
26
|
+
import { ensureDir, getHomeDir } from "./paths.js";
|
|
27
27
|
|
|
28
28
|
const SENSITIVE_FIELDS = ["sync.webdav.password", "sync.oss.secretAccessKey"];
|
|
29
29
|
const ALLOWED_PROVIDER_IDS = ["webdav", "oss"];
|
|
@@ -37,10 +37,7 @@ let _ccDirOverride = null;
|
|
|
37
37
|
|
|
38
38
|
function _ccDir() {
|
|
39
39
|
if (_ccDirOverride) return _ccDirOverride;
|
|
40
|
-
return (
|
|
41
|
-
process.env.CHAINLESSCHAIN_HOME ||
|
|
42
|
-
path.join(os.homedir(), ".chainlesschain")
|
|
43
|
-
);
|
|
40
|
+
return getHomeDir();
|
|
44
41
|
}
|
|
45
42
|
|
|
46
43
|
function _keyPath() {
|
|
@@ -53,7 +50,13 @@ function _vaultPath() {
|
|
|
53
50
|
|
|
54
51
|
function _ensureDir() {
|
|
55
52
|
const dir = _ccDir();
|
|
56
|
-
|
|
53
|
+
// Explicit test-only override keeps the existing isolated fake-filesystem
|
|
54
|
+
// seam lightweight; production roots always go through owner-only setup.
|
|
55
|
+
if (_ccDirOverride) {
|
|
56
|
+
if (!fs.existsSync(dir)) fs.mkdirSync(dir, { recursive: true });
|
|
57
|
+
return;
|
|
58
|
+
}
|
|
59
|
+
ensureDir(dir);
|
|
57
60
|
}
|
|
58
61
|
|
|
59
62
|
/**
|
|
@@ -217,24 +220,32 @@ function setCredentials(providerId, creds) {
|
|
|
217
220
|
// Credential metadata is security-critical: never decrypt-modify-encrypt
|
|
218
221
|
// without exclusion, because a lost update can silently restore/revoke the
|
|
219
222
|
// wrong provider credentials.
|
|
220
|
-
return withFileLock(
|
|
221
|
-
|
|
222
|
-
|
|
223
|
-
|
|
224
|
-
|
|
225
|
-
|
|
223
|
+
return withFileLock(
|
|
224
|
+
_vaultPath(),
|
|
225
|
+
() => {
|
|
226
|
+
const all = loadAll();
|
|
227
|
+
if (!all.sync || typeof all.sync !== "object") all.sync = {};
|
|
228
|
+
all.sync[providerId] = { ...creds };
|
|
229
|
+
return saveAll(all);
|
|
230
|
+
},
|
|
231
|
+
{ failIfUnavailable: true },
|
|
232
|
+
);
|
|
226
233
|
}
|
|
227
234
|
|
|
228
235
|
function clearCredentials(providerId) {
|
|
229
236
|
assertProviderId(providerId);
|
|
230
|
-
return withFileLock(
|
|
231
|
-
|
|
232
|
-
|
|
233
|
-
|
|
234
|
-
|
|
235
|
-
|
|
236
|
-
|
|
237
|
-
|
|
237
|
+
return withFileLock(
|
|
238
|
+
_vaultPath(),
|
|
239
|
+
() => {
|
|
240
|
+
const all = loadAll();
|
|
241
|
+
if (all?.sync?.[providerId]) {
|
|
242
|
+
delete all.sync[providerId];
|
|
243
|
+
return saveAll(all);
|
|
244
|
+
}
|
|
245
|
+
return true;
|
|
246
|
+
},
|
|
247
|
+
{ failIfUnavailable: true },
|
|
248
|
+
);
|
|
238
249
|
}
|
|
239
250
|
|
|
240
251
|
/** Test seam: override the resolved chainlesschain dir without env leak. */
|
package/src/lib/web-fetch.js
CHANGED
|
@@ -9,6 +9,7 @@ import http from "node:http";
|
|
|
9
9
|
import https from "node:https";
|
|
10
10
|
import { lookup as dnsLookup } from "node:dns";
|
|
11
11
|
import { URL } from "node:url";
|
|
12
|
+
import { createHash } from "node:crypto";
|
|
12
13
|
|
|
13
14
|
const DEFAULT_MAX_BYTES = 2_000_000;
|
|
14
15
|
const DEFAULT_TIMEOUT_MS = 15_000;
|
|
@@ -140,6 +141,35 @@ function stripTags(html) {
|
|
|
140
141
|
return String(html).replace(/<[^>]+>/g, "");
|
|
141
142
|
}
|
|
142
143
|
|
|
144
|
+
function webFetchCacheKey(parsed, { format, maxBytes, maxRedirects, headers }) {
|
|
145
|
+
// A caller-provided header can carry credentials or change representation.
|
|
146
|
+
// Keep those requests out of the shared host cache entirely.
|
|
147
|
+
if (
|
|
148
|
+
(headers && Object.keys(headers).length > 0) ||
|
|
149
|
+
parsed.username ||
|
|
150
|
+
parsed.password
|
|
151
|
+
) {
|
|
152
|
+
return null;
|
|
153
|
+
}
|
|
154
|
+
const payload = JSON.stringify({
|
|
155
|
+
url: parsed.toString(),
|
|
156
|
+
format,
|
|
157
|
+
maxBytes,
|
|
158
|
+
maxRedirects,
|
|
159
|
+
});
|
|
160
|
+
// Do not retain a raw URL/query as a long-lived Map key in the host cache.
|
|
161
|
+
return `web-fetch:${createHash("sha256").update(payload).digest("hex")}`;
|
|
162
|
+
}
|
|
163
|
+
|
|
164
|
+
function hostBudgetUnavailable(tool, error) {
|
|
165
|
+
const reason = String(error?.budgetReason || "unavailable").slice(0, 128);
|
|
166
|
+
return {
|
|
167
|
+
error: `${tool} unavailable: host resource budget (${reason})`,
|
|
168
|
+
code: "ERR_HOST_RESOURCE_BUDGET",
|
|
169
|
+
reason,
|
|
170
|
+
};
|
|
171
|
+
}
|
|
172
|
+
|
|
143
173
|
/**
|
|
144
174
|
* A `lookup` for http(s).request that resolves the hostname and REJECTS the
|
|
145
175
|
* connection if any resolved IP is private/loopback/link-local. checkAllowed
|
|
@@ -243,6 +273,7 @@ export async function webFetch(url, options = {}) {
|
|
|
243
273
|
config = {},
|
|
244
274
|
headers = {},
|
|
245
275
|
maxRedirects = 3,
|
|
276
|
+
hostResourceBudget = null,
|
|
246
277
|
} = options;
|
|
247
278
|
|
|
248
279
|
const check = checkAllowed(url, config);
|
|
@@ -250,53 +281,94 @@ export async function webFetch(url, options = {}) {
|
|
|
250
281
|
return { error: `web_fetch blocked: ${check.reason}` };
|
|
251
282
|
}
|
|
252
283
|
|
|
253
|
-
|
|
254
|
-
|
|
255
|
-
|
|
256
|
-
|
|
257
|
-
|
|
258
|
-
|
|
259
|
-
|
|
260
|
-
|
|
261
|
-
|
|
262
|
-
|
|
263
|
-
|
|
264
|
-
|
|
265
|
-
return { error: "too many redirects" };
|
|
266
|
-
}
|
|
267
|
-
const next = new URL(response.redirect, parsed);
|
|
268
|
-
const nextCheck = checkAllowed(next.toString(), config);
|
|
269
|
-
if (!nextCheck.allowed) {
|
|
270
|
-
return { error: `redirect blocked: ${nextCheck.reason}` };
|
|
284
|
+
const cacheKey = webFetchCacheKey(check.url, {
|
|
285
|
+
format,
|
|
286
|
+
maxBytes,
|
|
287
|
+
maxRedirects,
|
|
288
|
+
headers,
|
|
289
|
+
});
|
|
290
|
+
if (cacheKey && hostResourceBudget?.getWebFetch) {
|
|
291
|
+
try {
|
|
292
|
+
const cached = hostResourceBudget.getWebFetch(cacheKey);
|
|
293
|
+
if (cached) return { ...cached, cached: true };
|
|
294
|
+
} catch (error) {
|
|
295
|
+
return hostBudgetUnavailable("web_fetch", error);
|
|
271
296
|
}
|
|
272
|
-
parsed = nextCheck.url;
|
|
273
297
|
}
|
|
274
298
|
|
|
275
|
-
|
|
276
|
-
|
|
277
|
-
|
|
278
|
-
let output = body;
|
|
279
|
-
let outputFormat = format;
|
|
280
|
-
if (format === "markdown") {
|
|
281
|
-
output = /html/i.test(contentType) ? htmlToMarkdown(body) : body;
|
|
282
|
-
} else if (format === "text") {
|
|
283
|
-
output = /html/i.test(contentType) ? stripTags(body) : body;
|
|
284
|
-
} else if (format === "json") {
|
|
299
|
+
let toolLease = null;
|
|
300
|
+
if (hostResourceBudget) {
|
|
285
301
|
try {
|
|
286
|
-
|
|
287
|
-
|
|
288
|
-
|
|
302
|
+
if (typeof hostResourceBudget.admitTool !== "function") {
|
|
303
|
+
throw new TypeError(
|
|
304
|
+
"host resource budget does not provide admitTool()",
|
|
305
|
+
);
|
|
306
|
+
}
|
|
307
|
+
toolLease = hostResourceBudget.admitTool({ kind: "web-fetch" });
|
|
308
|
+
} catch (error) {
|
|
309
|
+
return hostBudgetUnavailable("web_fetch", error);
|
|
289
310
|
}
|
|
290
311
|
}
|
|
291
312
|
|
|
292
|
-
|
|
293
|
-
|
|
294
|
-
|
|
295
|
-
|
|
296
|
-
|
|
297
|
-
|
|
298
|
-
|
|
299
|
-
|
|
313
|
+
try {
|
|
314
|
+
let parsed = check.url;
|
|
315
|
+
let redirects = 0;
|
|
316
|
+
let response;
|
|
317
|
+
while (true) {
|
|
318
|
+
response = await _doRequest(parsed, {
|
|
319
|
+
maxBytes,
|
|
320
|
+
timeout,
|
|
321
|
+
headers,
|
|
322
|
+
allowPrivateHosts: config.allowPrivateHosts,
|
|
323
|
+
});
|
|
324
|
+
if (!response.redirect) break;
|
|
325
|
+
if (++redirects > maxRedirects) {
|
|
326
|
+
return { error: "too many redirects" };
|
|
327
|
+
}
|
|
328
|
+
const next = new URL(response.redirect, parsed);
|
|
329
|
+
const nextCheck = checkAllowed(next.toString(), config);
|
|
330
|
+
if (!nextCheck.allowed) {
|
|
331
|
+
return { error: `redirect blocked: ${nextCheck.reason}` };
|
|
332
|
+
}
|
|
333
|
+
parsed = nextCheck.url;
|
|
334
|
+
}
|
|
335
|
+
|
|
336
|
+
const { statusCode, headers: respHeaders, body } = response;
|
|
337
|
+
const contentType = String(respHeaders["content-type"] || "");
|
|
338
|
+
|
|
339
|
+
let output = body;
|
|
340
|
+
let outputFormat = format;
|
|
341
|
+
if (format === "markdown") {
|
|
342
|
+
output = /html/i.test(contentType) ? htmlToMarkdown(body) : body;
|
|
343
|
+
} else if (format === "text") {
|
|
344
|
+
output = /html/i.test(contentType) ? stripTags(body) : body;
|
|
345
|
+
} else if (format === "json") {
|
|
346
|
+
try {
|
|
347
|
+
output = JSON.parse(body);
|
|
348
|
+
} catch {
|
|
349
|
+
return { error: "response is not valid JSON", statusCode, body };
|
|
350
|
+
}
|
|
351
|
+
}
|
|
352
|
+
|
|
353
|
+
const result = {
|
|
354
|
+
url: parsed.toString(),
|
|
355
|
+
statusCode,
|
|
356
|
+
contentType,
|
|
357
|
+
format: outputFormat,
|
|
358
|
+
bytes: Buffer.byteLength(body, "utf8"),
|
|
359
|
+
content: output,
|
|
360
|
+
};
|
|
361
|
+
if (cacheKey && hostResourceBudget?.putWebFetch) {
|
|
362
|
+
try {
|
|
363
|
+
hostResourceBudget.putWebFetch(cacheKey, result);
|
|
364
|
+
} catch {
|
|
365
|
+
// Cache failures never weaken the completed, bounded I/O result.
|
|
366
|
+
}
|
|
367
|
+
}
|
|
368
|
+
return result;
|
|
369
|
+
} finally {
|
|
370
|
+
toolLease?.release();
|
|
371
|
+
}
|
|
300
372
|
}
|
|
301
373
|
|
|
302
374
|
// `lookup` is injectable so tests can resolve a domain to a private IP without
|
package/src/lib/web-search.js
CHANGED
|
@@ -18,6 +18,7 @@ import { URL } from "url";
|
|
|
18
18
|
const DEFAULT_MAX_BYTES = 2_000_000;
|
|
19
19
|
const DEFAULT_TIMEOUT_MS = 15_000;
|
|
20
20
|
const DEFAULT_MAX_RESULTS = 8;
|
|
21
|
+
export const MAX_WEB_SEARCH_RESULTS = 20;
|
|
21
22
|
|
|
22
23
|
const KEYED_PROVIDERS = ["tavily", "brave", "bocha", "qianfan"];
|
|
23
24
|
const KEYLESS_PROVIDERS = ["duckduckgo", "searxng", "baidu"];
|
|
@@ -38,7 +39,11 @@ export function resolveApiKey(provider, options = {}, config = {}) {
|
|
|
38
39
|
switch (provider) {
|
|
39
40
|
case "tavily":
|
|
40
41
|
return (
|
|
41
|
-
options.apiKey ||
|
|
42
|
+
options.apiKey ||
|
|
43
|
+
config.tavilyApiKey ||
|
|
44
|
+
config.apiKey ||
|
|
45
|
+
env.TAVILY_API_KEY ||
|
|
46
|
+
""
|
|
42
47
|
);
|
|
43
48
|
case "brave":
|
|
44
49
|
return (
|
|
@@ -51,7 +56,11 @@ export function resolveApiKey(provider, options = {}, config = {}) {
|
|
|
51
56
|
);
|
|
52
57
|
case "bocha":
|
|
53
58
|
return (
|
|
54
|
-
options.apiKey ||
|
|
59
|
+
options.apiKey ||
|
|
60
|
+
config.bochaApiKey ||
|
|
61
|
+
config.apiKey ||
|
|
62
|
+
env.BOCHA_API_KEY ||
|
|
63
|
+
""
|
|
55
64
|
);
|
|
56
65
|
case "qianfan":
|
|
57
66
|
return (
|
|
@@ -82,7 +91,10 @@ export function resolveProvider(options = {}, config = {}) {
|
|
|
82
91
|
return "duckduckgo";
|
|
83
92
|
}
|
|
84
93
|
|
|
85
|
-
function _request(
|
|
94
|
+
function _request(
|
|
95
|
+
urlStr,
|
|
96
|
+
{ method = "GET", headers = {}, body = null, timeout, maxBytes },
|
|
97
|
+
) {
|
|
86
98
|
const parsed = new URL(urlStr);
|
|
87
99
|
const lib = parsed.protocol === "https:" ? _deps.https : _deps.http;
|
|
88
100
|
return new Promise((resolve, reject) => {
|
|
@@ -147,6 +159,22 @@ function _clean(s) {
|
|
|
147
159
|
return _decodeEntities(_stripTags(s)).replace(/\s+/g, " ").trim();
|
|
148
160
|
}
|
|
149
161
|
|
|
162
|
+
function normalizeMaxResults(value) {
|
|
163
|
+
const parsed = Number(value);
|
|
164
|
+
const requested =
|
|
165
|
+
Number.isSafeInteger(parsed) && parsed > 0 ? parsed : DEFAULT_MAX_RESULTS;
|
|
166
|
+
return Math.min(requested, MAX_WEB_SEARCH_RESULTS);
|
|
167
|
+
}
|
|
168
|
+
|
|
169
|
+
function hostBudgetUnavailable(error) {
|
|
170
|
+
const reason = String(error?.budgetReason || "unavailable").slice(0, 128);
|
|
171
|
+
return {
|
|
172
|
+
error: `web_search unavailable: host resource budget (${reason})`,
|
|
173
|
+
code: "ERR_HOST_RESOURCE_BUDGET",
|
|
174
|
+
reason,
|
|
175
|
+
};
|
|
176
|
+
}
|
|
177
|
+
|
|
150
178
|
// ---- Provider adapters: each returns { results: [{title,url,snippet}], answer } ----
|
|
151
179
|
|
|
152
180
|
async function _searchTavily(query, { apiKey, maxResults, timeout, maxBytes }) {
|
|
@@ -167,7 +195,9 @@ async function _searchTavily(query, { apiKey, maxResults, timeout, maxBytes }) {
|
|
|
167
195
|
maxBytes,
|
|
168
196
|
});
|
|
169
197
|
if (res.statusCode >= 400) {
|
|
170
|
-
return {
|
|
198
|
+
return {
|
|
199
|
+
error: `tavily HTTP ${res.statusCode}: ${res.body.slice(0, 200)}`,
|
|
200
|
+
};
|
|
171
201
|
}
|
|
172
202
|
let json;
|
|
173
203
|
try {
|
|
@@ -326,10 +356,7 @@ async function _searchQianfan(
|
|
|
326
356
|
url: r.url || "",
|
|
327
357
|
snippet: _clean(r.content || r.web_anchor || ""),
|
|
328
358
|
}));
|
|
329
|
-
const answer =
|
|
330
|
-
json.answer ||
|
|
331
|
-
json.choices?.[0]?.message?.content ||
|
|
332
|
-
"";
|
|
359
|
+
const answer = json.answer || json.choices?.[0]?.message?.content || "";
|
|
333
360
|
return { results, answer: typeof answer === "string" ? answer : "" };
|
|
334
361
|
}
|
|
335
362
|
|
|
@@ -362,7 +389,8 @@ async function _searchBaidu(query, { maxResults, timeout, maxBytes }) {
|
|
|
362
389
|
// Markup-agnostic: anchor each result on its <h3 class="t|c-title"> heading,
|
|
363
390
|
// pull the URL from the anchor inside it (a baidu.com/link?url= redirect that
|
|
364
391
|
// web_fetch resolves), and take the text up to the next heading as snippet.
|
|
365
|
-
const h3re =
|
|
392
|
+
const h3re =
|
|
393
|
+
/<h3[^>]*class="[^"]*\b(?:t|c-title)\b[^"]*"[^>]*>([\s\S]*?)<\/h3>/gi;
|
|
366
394
|
const marks = [];
|
|
367
395
|
let m;
|
|
368
396
|
while ((m = h3re.exec(html)) !== null) {
|
|
@@ -381,7 +409,10 @@ async function _searchBaidu(query, { maxResults, timeout, maxBytes }) {
|
|
|
381
409
|
return { results, answer: "" };
|
|
382
410
|
}
|
|
383
411
|
|
|
384
|
-
async function _searchSearxng(
|
|
412
|
+
async function _searchSearxng(
|
|
413
|
+
query,
|
|
414
|
+
{ instanceUrl, maxResults, timeout, maxBytes },
|
|
415
|
+
) {
|
|
385
416
|
if (!instanceUrl) return { error: "searxng: missing instanceUrl" };
|
|
386
417
|
const base = instanceUrl.replace(/\/+$/, "");
|
|
387
418
|
const url = `${base}/search?q=${encodeURIComponent(query)}&format=json`;
|
|
@@ -398,7 +429,9 @@ async function _searchSearxng(query, { instanceUrl, maxResults, timeout, maxByte
|
|
|
398
429
|
try {
|
|
399
430
|
json = JSON.parse(res.body);
|
|
400
431
|
} catch {
|
|
401
|
-
return {
|
|
432
|
+
return {
|
|
433
|
+
error: "searxng: invalid JSON response (is json format enabled?)",
|
|
434
|
+
};
|
|
402
435
|
}
|
|
403
436
|
const results = (json.results || []).slice(0, maxResults).map((r) => ({
|
|
404
437
|
title: _clean(r.title || ""),
|
|
@@ -419,10 +452,7 @@ export async function webSearch(query, options = {}) {
|
|
|
419
452
|
|
|
420
453
|
const config = options.config || {};
|
|
421
454
|
const provider = resolveProvider(options, config);
|
|
422
|
-
|
|
423
|
-
Number(options.maxResults) ||
|
|
424
|
-
Number(config.maxResults) ||
|
|
425
|
-
DEFAULT_MAX_RESULTS;
|
|
455
|
+
let maxResults = normalizeMaxResults(options.maxResults ?? config.maxResults);
|
|
426
456
|
const timeout = Number(options.timeout) || DEFAULT_TIMEOUT_MS;
|
|
427
457
|
const maxBytes = Number(options.maxBytes) || DEFAULT_MAX_BYTES;
|
|
428
458
|
|
|
@@ -432,56 +462,92 @@ export async function webSearch(query, options = {}) {
|
|
|
432
462
|
};
|
|
433
463
|
}
|
|
434
464
|
|
|
435
|
-
const
|
|
436
|
-
|
|
465
|
+
const hostResourceBudget = options.hostResourceBudget || null;
|
|
466
|
+
if (hostResourceBudget?.capWebSearchResults) {
|
|
467
|
+
try {
|
|
468
|
+
maxResults = normalizeMaxResults(
|
|
469
|
+
hostResourceBudget.capWebSearchResults(maxResults),
|
|
470
|
+
);
|
|
471
|
+
} catch (error) {
|
|
472
|
+
return hostBudgetUnavailable(error);
|
|
473
|
+
}
|
|
474
|
+
}
|
|
437
475
|
|
|
438
|
-
let
|
|
439
|
-
|
|
440
|
-
|
|
441
|
-
|
|
442
|
-
|
|
443
|
-
|
|
444
|
-
|
|
445
|
-
|
|
446
|
-
|
|
447
|
-
|
|
448
|
-
|
|
449
|
-
break;
|
|
450
|
-
case "qianfan":
|
|
451
|
-
out = await _searchQianfan(q, {
|
|
452
|
-
...common,
|
|
453
|
-
endpoint: options.qianfanUrl || config.qianfanUrl,
|
|
454
|
-
});
|
|
455
|
-
break;
|
|
456
|
-
case "searxng":
|
|
457
|
-
out = await _searchSearxng(q, {
|
|
458
|
-
instanceUrl: options.instanceUrl || config.instanceUrl,
|
|
459
|
-
maxResults,
|
|
460
|
-
timeout,
|
|
461
|
-
maxBytes,
|
|
462
|
-
});
|
|
463
|
-
break;
|
|
464
|
-
case "baidu":
|
|
465
|
-
out = await _searchBaidu(q, { maxResults, timeout, maxBytes });
|
|
466
|
-
break;
|
|
467
|
-
case "duckduckgo":
|
|
468
|
-
default:
|
|
469
|
-
out = await _searchDuckDuckGo(q, { maxResults, timeout, maxBytes });
|
|
470
|
-
break;
|
|
476
|
+
let toolLease = null;
|
|
477
|
+
if (hostResourceBudget) {
|
|
478
|
+
try {
|
|
479
|
+
if (typeof hostResourceBudget.admitTool !== "function") {
|
|
480
|
+
throw new TypeError(
|
|
481
|
+
"host resource budget does not provide admitTool()",
|
|
482
|
+
);
|
|
483
|
+
}
|
|
484
|
+
toolLease = hostResourceBudget.admitTool({ kind: "web-search" });
|
|
485
|
+
} catch (error) {
|
|
486
|
+
return hostBudgetUnavailable(error);
|
|
471
487
|
}
|
|
472
|
-
} catch (err) {
|
|
473
|
-
return { error: `web_search (${provider}) failed: ${err.message}`, provider };
|
|
474
488
|
}
|
|
475
489
|
|
|
476
|
-
|
|
477
|
-
|
|
478
|
-
|
|
479
|
-
|
|
480
|
-
|
|
481
|
-
|
|
482
|
-
|
|
483
|
-
|
|
484
|
-
|
|
490
|
+
try {
|
|
491
|
+
const apiKey = resolveApiKey(provider, options, config);
|
|
492
|
+
const common = { apiKey, maxResults, timeout, maxBytes };
|
|
493
|
+
|
|
494
|
+
let out;
|
|
495
|
+
try {
|
|
496
|
+
switch (provider) {
|
|
497
|
+
case "tavily":
|
|
498
|
+
out = await _searchTavily(q, common);
|
|
499
|
+
break;
|
|
500
|
+
case "brave":
|
|
501
|
+
out = await _searchBrave(q, common);
|
|
502
|
+
break;
|
|
503
|
+
case "bocha":
|
|
504
|
+
out = await _searchBocha(q, common);
|
|
505
|
+
break;
|
|
506
|
+
case "qianfan":
|
|
507
|
+
out = await _searchQianfan(q, {
|
|
508
|
+
...common,
|
|
509
|
+
endpoint: options.qianfanUrl || config.qianfanUrl,
|
|
510
|
+
});
|
|
511
|
+
break;
|
|
512
|
+
case "searxng":
|
|
513
|
+
out = await _searchSearxng(q, {
|
|
514
|
+
instanceUrl: options.instanceUrl || config.instanceUrl,
|
|
515
|
+
maxResults,
|
|
516
|
+
timeout,
|
|
517
|
+
maxBytes,
|
|
518
|
+
});
|
|
519
|
+
break;
|
|
520
|
+
case "baidu":
|
|
521
|
+
out = await _searchBaidu(q, { maxResults, timeout, maxBytes });
|
|
522
|
+
break;
|
|
523
|
+
case "duckduckgo":
|
|
524
|
+
default:
|
|
525
|
+
out = await _searchDuckDuckGo(q, {
|
|
526
|
+
maxResults,
|
|
527
|
+
timeout,
|
|
528
|
+
maxBytes,
|
|
529
|
+
});
|
|
530
|
+
break;
|
|
531
|
+
}
|
|
532
|
+
} catch (err) {
|
|
533
|
+
return {
|
|
534
|
+
error: `web_search (${provider}) failed: ${err.message}`,
|
|
535
|
+
provider,
|
|
536
|
+
};
|
|
537
|
+
}
|
|
538
|
+
|
|
539
|
+
if (out && out.error) return { ...out, provider };
|
|
540
|
+
const results = (out && out.results) || [];
|
|
541
|
+
return {
|
|
542
|
+
query: q,
|
|
543
|
+
provider,
|
|
544
|
+
count: results.length,
|
|
545
|
+
results,
|
|
546
|
+
answer: (out && out.answer) || "",
|
|
547
|
+
};
|
|
548
|
+
} finally {
|
|
549
|
+
toolLease?.release();
|
|
550
|
+
}
|
|
485
551
|
}
|
|
486
552
|
|
|
487
553
|
export const _deps = { http, https };
|