@agent-native/core 0.53.0 → 0.54.0

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.
Files changed (99) hide show
  1. package/dist/action.d.ts +40 -1
  2. package/dist/action.d.ts.map +1 -1
  3. package/dist/action.js +69 -2
  4. package/dist/action.js.map +1 -1
  5. package/dist/agent/index.d.ts +1 -0
  6. package/dist/agent/index.d.ts.map +1 -1
  7. package/dist/agent/index.js +1 -0
  8. package/dist/agent/index.js.map +1 -1
  9. package/dist/agent/observational-memory/index.d.ts +6 -6
  10. package/dist/agent/observational-memory/index.js +6 -6
  11. package/dist/agent/observational-memory/index.js.map +1 -1
  12. package/dist/agent/observational-memory/read.d.ts +7 -9
  13. package/dist/agent/observational-memory/read.d.ts.map +1 -1
  14. package/dist/agent/observational-memory/read.js +7 -9
  15. package/dist/agent/observational-memory/read.js.map +1 -1
  16. package/dist/agent/processors.d.ts +146 -0
  17. package/dist/agent/processors.d.ts.map +1 -0
  18. package/dist/agent/processors.js +122 -0
  19. package/dist/agent/processors.js.map +1 -0
  20. package/dist/agent/production-agent.d.ts +10 -0
  21. package/dist/agent/production-agent.d.ts.map +1 -1
  22. package/dist/agent/production-agent.js +101 -0
  23. package/dist/agent/production-agent.js.map +1 -1
  24. package/dist/agent/run-loop-with-resume.d.ts.map +1 -1
  25. package/dist/agent/run-loop-with-resume.js +4 -5
  26. package/dist/agent/run-loop-with-resume.js.map +1 -1
  27. package/dist/agent/tool-call-journal.d.ts +6 -8
  28. package/dist/agent/tool-call-journal.d.ts.map +1 -1
  29. package/dist/agent/tool-call-journal.js +6 -8
  30. package/dist/agent/tool-call-journal.js.map +1 -1
  31. package/dist/agent/types.d.ts +11 -0
  32. package/dist/agent/types.d.ts.map +1 -1
  33. package/dist/agent/types.js.map +1 -1
  34. package/dist/cli/plan-local.d.ts.map +1 -1
  35. package/dist/cli/plan-local.js +129 -4
  36. package/dist/cli/plan-local.js.map +1 -1
  37. package/dist/cli/skills.d.ts.map +1 -1
  38. package/dist/cli/skills.js +38 -3
  39. package/dist/cli/skills.js.map +1 -1
  40. package/dist/coding-tools/run-code.d.ts.map +1 -1
  41. package/dist/coding-tools/run-code.js +18 -2
  42. package/dist/coding-tools/run-code.js.map +1 -1
  43. package/dist/extensions/fetch-tool.d.ts.map +1 -1
  44. package/dist/extensions/fetch-tool.js +80 -15
  45. package/dist/extensions/fetch-tool.js.map +1 -1
  46. package/dist/extensions/web-content.d.ts +61 -0
  47. package/dist/extensions/web-content.d.ts.map +1 -0
  48. package/dist/extensions/web-content.js +468 -0
  49. package/dist/extensions/web-content.js.map +1 -0
  50. package/dist/extensions/web-search-tool.js +3 -3
  51. package/dist/extensions/web-search-tool.js.map +1 -1
  52. package/dist/mcp/build-server.d.ts.map +1 -1
  53. package/dist/mcp/build-server.js +4 -1
  54. package/dist/mcp/build-server.js.map +1 -1
  55. package/dist/provider-api/corpus-jobs.d.ts +80 -0
  56. package/dist/provider-api/corpus-jobs.d.ts.map +1 -1
  57. package/dist/provider-api/corpus-jobs.js +219 -22
  58. package/dist/provider-api/corpus-jobs.js.map +1 -1
  59. package/dist/provider-api/index.d.ts +24 -32
  60. package/dist/provider-api/index.d.ts.map +1 -1
  61. package/dist/provider-api/index.js +28 -1
  62. package/dist/provider-api/index.js.map +1 -1
  63. package/dist/server/agent-chat-plugin.js +1 -1
  64. package/dist/server/agent-chat-plugin.js.map +1 -1
  65. package/dist/server/better-auth-instance.d.ts +7 -0
  66. package/dist/server/better-auth-instance.d.ts.map +1 -1
  67. package/dist/server/better-auth-instance.js +90 -0
  68. package/dist/server/better-auth-instance.js.map +1 -1
  69. package/dist/server/deep-link.d.ts +7 -0
  70. package/dist/server/deep-link.d.ts.map +1 -1
  71. package/dist/server/deep-link.js +13 -2
  72. package/dist/server/deep-link.js.map +1 -1
  73. package/dist/server/index.d.ts +1 -1
  74. package/dist/server/index.d.ts.map +1 -1
  75. package/dist/server/index.js +1 -1
  76. package/dist/server/index.js.map +1 -1
  77. package/dist/templates/default/.agents/skills/actions/SKILL.md +52 -1
  78. package/dist/templates/default/.agents/skills/security/SKILL.md +22 -0
  79. package/dist/templates/workspace-core/.agents/skills/actions/SKILL.md +52 -1
  80. package/dist/templates/workspace-core/.agents/skills/external-agents/SKILL.md +6 -4
  81. package/dist/templates/workspace-core/.agents/skills/observability/SKILL.md +11 -0
  82. package/dist/templates/workspace-core/.agents/skills/security/SKILL.md +22 -0
  83. package/docs/content/actions.md +50 -0
  84. package/docs/content/durable-resume.md +49 -0
  85. package/docs/content/external-agents.md +2 -2
  86. package/docs/content/human-approval.md +101 -0
  87. package/docs/content/observability.md +21 -0
  88. package/docs/content/observational-memory.md +63 -0
  89. package/docs/content/plan-plugin.md +5 -0
  90. package/docs/content/pr-visual-recap.md +4 -3
  91. package/docs/content/processors.md +99 -0
  92. package/docs/content/template-plan.md +78 -14
  93. package/package.json +6 -1
  94. package/src/templates/default/.agents/skills/actions/SKILL.md +52 -1
  95. package/src/templates/default/.agents/skills/security/SKILL.md +22 -0
  96. package/src/templates/workspace-core/.agents/skills/actions/SKILL.md +52 -1
  97. package/src/templates/workspace-core/.agents/skills/external-agents/SKILL.md +6 -4
  98. package/src/templates/workspace-core/.agents/skills/observability/SKILL.md +11 -0
  99. package/src/templates/workspace-core/.agents/skills/security/SKILL.md +22 -0
@@ -0,0 +1 @@
1
+ {"version":3,"file":"web-content.js","sourceRoot":"","sources":["../../src/extensions/web-content.ts"],"names":[],"mappings":"AAAA,OAAO,EAAE,WAAW,EAAE,MAAM,sBAAsB,CAAC;AACnD,OAAO,EAAE,SAAS,EAAE,MAAM,iBAAiB,CAAC;AAC5C,OAAO,SAAS,MAAM,aAAa,CAAC;AACpC,OAAO,eAAe,MAAM,UAAU,CAAC;AAsEvC,MAAM,yBAAyB,GAAG,MAAM,CAAC;AACzC,MAAM,uBAAuB,GAAG,OAAO,CAAC;AACxC,MAAM,mBAAmB,GAAG,EAAE,CAAC;AAC/B,MAAM,WAAW,GAAG,GAAG,CAAC;AACxB,MAAM,qBAAqB,GAAG,GAAG,CAAC;AAClC,MAAM,iBAAiB,GAAG,KAAK,CAAC;AAEhC,MAAM,QAAQ,GAAG,IAAI,eAAe,CAAC;IACnC,YAAY,EAAE,KAAK;IACnB,gBAAgB,EAAE,GAAG;IACrB,cAAc,EAAE,QAAQ;IACxB,SAAS,EAAE,SAAS;CACrB,CAAC,CAAC;AACH,QAAQ,CAAC,MAAM,CAAC,CAAC,QAAQ,EAAE,OAAO,EAAE,UAAU,CAAC,CAAC,CAAC;AAEjD,MAAM,UAAU,mBAAmB,CACjC,MAAkD;IAElD,IAAI,CAAC,MAAM;QAAE,OAAO,KAAK,CAAC;IAC1B,OAAO,OAAO,CACZ,mBAAmB,CAAC,MAAM,CAAC,KAAK,CAAC,CAAC,MAAM;QACxC,mBAAmB,CAAC,MAAM,CAAC,OAAO,CAAC,CAAC,MAAM;QAC1C,mBAAmB,CAAC,MAAM,CAAC,KAAK,CAAC,CAAC,MAAM;QACxC,MAAM,CAAC,MAAM,CAAC,KAAK,IAAI,EAAE,CAAC,CAAC,IAAI,EAAE,CAClC,CAAC;AACJ,CAAC;AAED,MAAM,UAAU,wBAAwB,CACtC,KAAc,EACd,WAA4B,MAAM;IAElC,MAAM,UAAU,GAAG,MAAM,CAAC,KAAK,IAAI,QAAQ,CAAC,CAAC,WAAW,EAAE,CAAC;IAC3D,IACE,UAAU,KAAK,MAAM;QACrB,UAAU,KAAK,KAAK;QACpB,UAAU,KAAK,MAAM;QACrB,UAAU,KAAK,UAAU;QACzB,UAAU,KAAK,OAAO;QACtB,UAAU,KAAK,UAAU;QACzB,UAAU,KAAK,SAAS,EACxB,CAAC;QACD,OAAO,UAAU,CAAC;IACpB,CAAC;IACD,MAAM,IAAI,KAAK,CACb,yBAAyB,MAAM,CAAC,KAAK,CAAC,qEAAqE,CAC5G,CAAC;AACJ,CAAC;AAED,MAAM,UAAU,uBAAuB,CACrC,KAAc,EACd,WAA2B,aAAa;IAExC,MAAM,UAAU,GAAG,MAAM,CAAC,KAAK,IAAI,QAAQ,CAAC,CAAC,WAAW,EAAE,CAAC;IAC3D,IACE,UAAU,KAAK,aAAa;QAC5B,UAAU,KAAK,aAAa;QAC5B,UAAU,KAAK,MAAM,EACrB,CAAC;QACD,OAAO,UAAU,CAAC;IACpB,CAAC;IACD,MAAM,IAAI,KAAK,CACb,oBAAoB,MAAM,CAAC,KAAK,CAAC,gDAAgD,CAClF,CAAC;AACJ,CAAC;AAED,MAAM,UAAU,4BAA4B,CAC1C,KAAc;IAEd,IAAI,CAAC,KAAK;QAAE,OAAO,IAAI,CAAC;IACxB,IAAI,OAAO,KAAK,KAAK,QAAQ,IAAI,CAAC,KAAK,CAAC,OAAO,CAAC,KAAK,CAAC,EAAE,CAAC;QACvD,OAAO,KAAgC,CAAC;IAC1C,CAAC;IACD,IAAI,OAAO,KAAK,KAAK,QAAQ;QAAE,OAAO,IAAI,CAAC;IAC3C,MAAM,OAAO,GAAG,KAAK,CAAC,IAAI,EAAE,CAAC;IAC7B,IAAI,CAAC,OAAO;QAAE,OAAO,IAAI,CAAC;IAC1B,IAAI,CAAC;QACH,MAAM,MAAM,GAAG,IAAI,CAAC,KAAK,CAAC,OAAO,CAAC,CAAC;QACnC,IAAI,MAAM,IAAI,OAAO,MAAM,KAAK,QAAQ,IAAI,CAAC,KAAK,CAAC,OAAO,CAAC,MAAM,CAAC,EAAE,CAAC;YACnE,OAAO,MAAiC,CAAC;QAC3C,CAAC;IACH,CAAC;IAAC,MAAM,CAAC;QACP,OAAO,EAAE,KAAK,EAAE,OAAO,EAAE,CAAC;IAC5B,CAAC;IACD,OAAO,IAAI,CAAC;AACd,CAAC;AAED,MAAM,UAAU,iBAAiB,CAC/B,OAAiC;IAEjC,MAAM,WAAW,GAAG,OAAO,CAAC,WAAW,EAAE,KAAK,CAAC,GAAG,CAAC,CAAC,CAAC,CAAC,EAAE,IAAI,EAAE,IAAI,IAAI,CAAC;IACvE,MAAM,OAAO,GAAG,uBAAuB,CAAC,OAAO,CAAC,OAAO,CAAC,CAAC;IACzD,MAAM,aAAa,GAAG,wBAAwB,CAAC,OAAO,CAAC,YAAY,CAAC,CAAC;IACrE,MAAM,MAAM,GAAG,OAAO,CAAC,MAAM,IAAI,IAAI,CAAC;IACtC,MAAM,IAAI,GAAG,cAAc,CAAC,WAAW,EAAE,OAAO,CAAC,IAAI,CAAC,CAAC;IACvD,MAAM,IAAI,GAAG,WAAW,CAAC,aAAa,EAAE,IAAI,EAAE,MAAM,CAAC,CAAC;IACtD,MAAM,QAAQ,GAAG,sBAAsB,CACrC,OAAO,CAAC,QAAQ,EAChB,yBAAyB,EACzB,CAAC,EACD,OAAO,CACR,CAAC;IAEF,MAAM,SAAS,GACb,IAAI,IAAI,CAAC,IAAI,KAAK,KAAK,IAAI,mBAAmB,CAAC,MAAM,CAAC,CAAC;QACrD,CAAC,CAAC,WAAW,CAAC,OAAO,CAAC,IAAI,EAAE,OAAO,CAAC,GAAG,EAAE,OAAO,CAAC;QACjD,CAAC,CAAC,IAAI,CAAC;IACX,MAAM,WAAW,GAAG,cAAc,CAAC,IAAI,EAAE,OAAO,CAAC,IAAI,EAAE,SAAS,CAAC,CAAC;IAClE,MAAM,MAAM,GAAqB;QAC/B,IAAI;QACJ,OAAO;QACP,WAAW;QACX,GAAG,sBAAsB,CAAC,SAAS,CAAC;KACrC,CAAC;IAEF,IAAI,IAAI,KAAK,OAAO,EAAE,CAAC;QACrB,MAAM,CAAC,KAAK,GAAG,SAAS,EAAE,KAAK,IAAI,EAAE,CAAC;QACtC,OAAO,MAAM,CAAC;IAChB,CAAC;IAED,IAAI,IAAI,KAAK,UAAU,EAAE,CAAC;QACxB,IAAI,OAAO,CAAC,YAAY;YAAE,MAAM,CAAC,KAAK,GAAG,SAAS,EAAE,KAAK,IAAI,EAAE,CAAC;QAChE,OAAO,MAAM,CAAC;IAChB,CAAC;IAED,IAAI,IAAI,KAAK,SAAS,EAAE,CAAC;QACvB,MAAM,WAAW,GAAG,qBAAqB,CAAC;YACxC,GAAG,EAAE,OAAO,CAAC,IAAI;YACjB,SAAS,EAAE,WAAW;YACtB,MAAM;YACN,oBAAoB,EAAE,IAAI,CAAC,CAAC,CAAC,WAAW,CAAC,CAAC,CAAC,KAAK;SACjD,CAAC,CAAC;QACH,MAAM,CAAC,MAAM,CAAC,MAAM,EAAE,WAAW,CAAC,CAAC;QACnC,IAAI,OAAO,CAAC,YAAY;YAAE,MAAM,CAAC,KAAK,GAAG,SAAS,EAAE,KAAK,IAAI,EAAE,CAAC;QAChE,OAAO,MAAM,CAAC;IAChB,CAAC;IAED,MAAM,SAAS,GAAG,WAAW,CAAC,MAAM,GAAG,QAAQ,CAAC;IAChD,MAAM,CAAC,OAAO,GAAG,SAAS;QACxB,CAAC,CAAC,GAAG,WAAW,CAAC,KAAK,CAAC,CAAC,EAAE,QAAQ,CAAC,mBAAmB;QACtD,CAAC,CAAC,WAAW,CAAC;IAChB,MAAM,CAAC,SAAS,GAAG,SAAS,CAAC;IAC7B,IAAI,OAAO,CAAC,YAAY;QAAE,MAAM,CAAC,KAAK,GAAG,SAAS,EAAE,KAAK,IAAI,EAAE,CAAC;IAEhE,IAAI,mBAAmB,CAAC,MAAM,CAAC,EAAE,CAAC;QAChC,MAAM,WAAW,GAAG,qBAAqB,CAAC;YACxC,GAAG,EAAE,OAAO,CAAC,IAAI;YACjB,SAAS,EAAE,WAAW;YACtB,MAAM;YACN,oBAAoB,EAAE,IAAI,CAAC,CAAC,CAAC,WAAW,CAAC,CAAC,CAAC,KAAK;SACjD,CAAC,CAAC;QACH,MAAM,CAAC,OAAO,GAAG,WAAW,CAAC,OAAO,CAAC;QACrC,MAAM,CAAC,YAAY,GAAG,WAAW,CAAC,YAAY,CAAC;QAC/C,MAAM,CAAC,cAAc,GAAG,WAAW,CAAC,cAAc,CAAC;QACnD,MAAM,CAAC,YAAY,GAAG,WAAW,CAAC,YAAY,CAAC;QAC/C,MAAM,CAAC,eAAe,GAAG,WAAW,CAAC,eAAe,CAAC;IACvD,CAAC;IAED,OAAO,MAAM,CAAC;AAChB,CAAC;AAED,MAAM,UAAU,sBAAsB,CAAC,MAAwB;IAC7D,IAAI,MAAM,CAAC,IAAI,KAAK,KAAK;QAAE,OAAO,MAAM,CAAC,OAAO,IAAI,EAAE,CAAC;IAEvD,MAAM,KAAK,GAAa,EAAE,CAAC;IAC3B,IAAI,MAAM,CAAC,KAAK;QAAE,KAAK,CAAC,IAAI,CAAC,KAAK,MAAM,CAAC,KAAK,EAAE,EAAE,EAAE,CAAC,CAAC;IACtD,IAAI,MAAM,CAAC,QAAQ;QAAE,KAAK,CAAC,IAAI,CAAC,SAAS,MAAM,CAAC,QAAQ,EAAE,CAAC,CAAC;IAC5D,IAAI,MAAM,CAAC,aAAa;QAAE,KAAK,CAAC,IAAI,CAAC,cAAc,MAAM,CAAC,aAAa,EAAE,CAAC,CAAC;IAC3E,IAAI,MAAM,CAAC,OAAO,IAAI,MAAM,CAAC,IAAI,KAAK,UAAU,EAAE,CAAC;QACjD,KAAK,CAAC,IAAI,CAAC,YAAY,MAAM,CAAC,OAAO,EAAE,CAAC,CAAC;IAC3C,CAAC;IACD,IAAI,KAAK,CAAC,MAAM,IAAI,KAAK,CAAC,KAAK,CAAC,MAAM,GAAG,CAAC,CAAC,KAAK,EAAE;QAAE,KAAK,CAAC,IAAI,CAAC,EAAE,CAAC,CAAC;IAEnE,IAAI,MAAM,CAAC,IAAI,KAAK,SAAS,EAAE,CAAC;QAC9B,KAAK,CAAC,IAAI,CAAC,aAAa,CAAC,MAAM,CAAC,CAAC,CAAC;IACpC,CAAC;SAAM,IAAI,MAAM,CAAC,IAAI,KAAK,OAAO,EAAE,CAAC;QACnC,KAAK,CAAC,IAAI,CAAC,WAAW,CAAC,MAAM,CAAC,KAAK,IAAI,EAAE,CAAC,CAAC,CAAC;IAC9C,CAAC;SAAM,IAAI,MAAM,CAAC,IAAI,KAAK,UAAU,EAAE,CAAC;QACtC,KAAK,CAAC,IAAI,CAAC,cAAc,CAAC,MAAM,CAAC,CAAC,CAAC;IACrC,CAAC;SAAM,IAAI,MAAM,CAAC,OAAO,EAAE,CAAC;QAC1B,KAAK,CAAC,IAAI,CAAC,MAAM,CAAC,OAAO,CAAC,CAAC;IAC7B,CAAC;IAED,IACE,MAAM,CAAC,IAAI,KAAK,OAAO;QACvB,MAAM,CAAC,IAAI,KAAK,SAAS;QACzB,MAAM,CAAC,KAAK,EAAE,MAAM,EACpB,CAAC;QACD,KAAK,CAAC,IAAI,CAAC,EAAE,EAAE,QAAQ,EAAE,WAAW,CAAC,MAAM,CAAC,KAAK,CAAC,CAAC,CAAC;IACtD,CAAC;IACD,IAAI,MAAM,CAAC,OAAO,EAAE,MAAM,IAAI,MAAM,CAAC,IAAI,KAAK,SAAS,EAAE,CAAC;QACxD,KAAK,CAAC,IAAI,CAAC,EAAE,EAAE,aAAa,CAAC,MAAM,CAAC,CAAC,CAAC;IACxC,CAAC;IAED,OAAO,KAAK,CAAC,IAAI,CAAC,IAAI,CAAC,CAAC,IAAI,EAAE,CAAC;AACjC,CAAC;AAED,SAAS,WAAW,CAClB,aAA8B,EAC9B,IAAa,EACb,MAAsC;IAEtC,IAAI,aAAa,KAAK,MAAM,EAAE,CAAC;QAC7B,IAAI,mBAAmB,CAAC,MAAM,CAAC;YAAE,OAAO,SAAS,CAAC;QAClD,OAAO,IAAI,CAAC,CAAC,CAAC,UAAU,CAAC,CAAC,CAAC,KAAK,CAAC;IACnC,CAAC;IACD,OAAO,aAAa,CAAC;AACvB,CAAC;AAED,SAAS,cAAc,CAAC,WAA0B,EAAE,IAAY;IAC9D,IAAI,WAAW,EAAE,CAAC;QAChB,OAAO,CACL,WAAW,KAAK,WAAW;YAC3B,WAAW,KAAK,uBAAuB;YACvC,WAAW,CAAC,QAAQ,CAAC,OAAO,CAAC,CAC9B,CAAC;IACJ,CAAC;IACD,OAAO,qDAAqD,CAAC,IAAI,CAC/D,IAAI,CAAC,KAAK,CAAC,CAAC,EAAE,KAAK,CAAC,CACrB,CAAC;AACJ,CAAC;AAED,SAAS,WAAW,CAClB,IAAY,EACZ,GAAW,EACX,OAAuB;IAavB,MAAM,QAAQ,GAAG,iBAAiB,CAAC,IAAI,CAAC,CAAC;IACzC,qBAAqB,CAAC,QAAQ,CAAC,CAAC;IAChC,MAAM,SAAS,GAAG,eAAe,CAAC,QAAQ,CAAC,KAAK,CAAC,CAAC;IAClD,MAAM,OAAO,GACX,OAAO,KAAK,aAAa;QACvB,CAAC,CAAC,IAAI,WAAW,CAAC,QAAQ,CAAC,SAAS,CAAC,IAAI,CAAa,CAAC,CAAC,KAAK,EAAE;QAC/D,CAAC,CAAC,IAAI,CAAC;IACX,MAAM,UAAU,GACd,OAAO,KAAK,MAAM;QAChB,CAAC,CAAC,IAAI;QACN,CAAC,CAAC,OAAO,EAAE,OAAO;YAChB,QAAQ,CAAC,IAAI,EAAE,SAAS;YACxB,QAAQ,CAAC,eAAe,CAAC,SAAS;YAClC,IAAI,CAAC;IACX,MAAM,YAAY,GAAG,kBAAkB,CAAC,UAAU,EAAE,GAAG,CAAC,CAAC;IACzD,MAAM,UAAU,GACd,OAAO,KAAK,MAAM;QAChB,CAAC,CAAC,eAAe,CAAC,IAAI,CAAC;QACvB,CAAC,CAAC,OAAO,EAAE,WAAW;YACpB,QAAQ,CAAC,IAAI,EAAE,WAAW;YAC1B,QAAQ,CAAC,eAAe,CAAC,WAAW;YACpC,EAAE,CAAC;IACT,MAAM,QAAQ,GAAG,cAAc,CAAC,YAAY,CAAC,CAAC;IAC9C,OAAO;QACL,IAAI,EAAE,YAAY;QAClB,IAAI,EAAE,mBAAmB,CAAC,UAAU,CAAC;QACrC,QAAQ;QACR,KAAK,EAAE,YAAY,CAAC,YAAY,EAAE,GAAG,CAAC;QACtC,KAAK,EAAE,eAAe,CAAC,OAAO,EAAE,KAAK,CAAC,IAAI,SAAS;QACnD,OAAO,EAAE,eAAe,CAAC,OAAO,EAAE,OAAO,CAAC;QAC1C,MAAM,EAAE,eAAe,CAAC,OAAO,EAAE,MAAM,CAAC;QACxC,QAAQ,EAAE,eAAe,CAAC,OAAO,EAAE,QAAQ,CAAC;QAC5C,IAAI,EAAE,eAAe,CAAC,OAAO,EAAE,IAAI,CAAC;QACpC,aAAa,EAAE,eAAe,CAAC,OAAO,EAAE,aAAa,CAAC;KACvD,CAAC;AACJ,CAAC;AAED,SAAS,eAAe,CAAC,IAAY;IACnC,MAAM,QAAQ,GAAG,iBAAiB,CAAC,IAAI,CAAC,CAAC;IACzC,qBAAqB,CAAC,QAAQ,CAAC,CAAC;IAChC,OAAO,mBAAmB,CAAC,QAAQ,CAAC,IAAI,EAAE,WAAW,IAAI,EAAE,CAAC,CAAC;AAC/D,CAAC;AAED,SAAS,cAAc,CAAC,IAAY;IAClC,OAAO,iBAAiB,CAAC,QAAQ,CAAC,QAAQ,CAAC,IAAI,CAAC,CAAC,CAAC;AACpD,CAAC;AAED,SAAS,qBAAqB,CAAC,QAAkB;IAC/C,KAAK,MAAM,QAAQ,IAAI;QACrB,QAAQ;QACR,OAAO;QACP,UAAU;QACV,KAAK;QACL,UAAU;QACV,QAAQ;KACT,EAAE,CAAC;QACF,KAAK,MAAM,IAAI,IAAI,CAAC,GAAG,QAAQ,CAAC,gBAAgB,CAAC,QAAQ,CAAC,CAAC,EAAE,CAAC;YAC5D,IAAI,CAAC,MAAM,EAAE,CAAC;QAChB,CAAC;IACH,CAAC;AACH,CAAC;AAED,SAAS,iBAAiB,CAAC,IAAY;IACrC,OAAO,SAAS,CAAC,IAAI,CAAC,CAAC,QAA+B,CAAC;AACzD,CAAC;AAED,SAAS,iBAAiB,CAAC,IAAY;IACrC,OAAO,SAAS,CACd,2CAA2C,IAAI,gBAAgB,CAChE,CAAC,QAA+B,CAAC;AACpC,CAAC;AAED,SAAS,kBAAkB,CAAC,IAAY,EAAE,GAAW;IACnD,MAAM,QAAQ,GAAG,iBAAiB,CAAC,IAAI,CAAC,CAAC;IACzC,KAAK,MAAM,MAAM,IAAI,CAAC,GAAG,QAAQ,CAAC,gBAAgB,CAAC,SAAS,CAAC,CAAC,EAAE,CAAC;QAC/D,MAAM,IAAI,GAAG,MAAM,CAAC,YAAY,CAAC,MAAM,CAAC,CAAC;QACzC,IAAI,CAAC,IAAI;YAAE,SAAS;QACpB,IAAI,CAAC;YACH,MAAM,CAAC,YAAY,CAAC,MAAM,EAAE,IAAI,GAAG,CAAC,IAAI,EAAE,GAAG,CAAC,CAAC,IAAI,CAAC,CAAC;QACvD,CAAC;QAAC,MAAM,CAAC,CAAA,CAAC;IACZ,CAAC;IACD,KAAK,MAAM,KAAK,IAAI,CAAC,GAAG,QAAQ,CAAC,gBAAgB,CAAC,UAAU,CAAC,CAAC,EAAE,CAAC;QAC/D,MAAM,GAAG,GAAG,KAAK,CAAC,YAAY,CAAC,KAAK,CAAC,CAAC;QACtC,IAAI,CAAC,GAAG;YAAE,SAAS;QACnB,IAAI,CAAC;YACH,KAAK,CAAC,YAAY,CAAC,KAAK,EAAE,IAAI,GAAG,CAAC,GAAG,EAAE,GAAG,CAAC,CAAC,IAAI,CAAC,CAAC;QACpD,CAAC;QAAC,MAAM,CAAC,CAAA,CAAC;IACZ,CAAC;IACD,OAAO,QAAQ,CAAC,IAAI,EAAE,SAAS,IAAI,IAAI,CAAC;AAC1C,CAAC;AAED,SAAS,YAAY,CAAC,IAAY,EAAE,GAAW;IAC7C,MAAM,QAAQ,GAAG,iBAAiB,CAAC,IAAI,CAAC,CAAC;IACzC,MAAM,KAAK,GAAqB,EAAE,CAAC;IACnC,MAAM,IAAI,GAAG,IAAI,GAAG,EAAU,CAAC;IAC/B,KAAK,MAAM,MAAM,IAAI,CAAC,GAAG,QAAQ,CAAC,gBAAgB,CAAC,SAAS,CAAC,CAAC,EAAE,CAAC;QAC/D,MAAM,IAAI,GAAG,MAAM,CAAC,YAAY,CAAC,MAAM,CAAC,CAAC;QACzC,IAAI,CAAC,IAAI;YAAE,SAAS;QACpB,IAAI,QAAgB,CAAC;QACrB,IAAI,CAAC;YACH,QAAQ,GAAG,IAAI,GAAG,CAAC,IAAI,EAAE,GAAG,CAAC,CAAC,IAAI,CAAC;QACrC,CAAC;QAAC,MAAM,CAAC;YACP,SAAS;QACX,CAAC;QACD,IAAI,IAAI,CAAC,GAAG,CAAC,QAAQ,CAAC;YAAE,SAAS;QACjC,IAAI,CAAC,GAAG,CAAC,QAAQ,CAAC,CAAC;QACnB,KAAK,CAAC,IAAI,CAAC;YACT,IAAI,EAAE,mBAAmB,CAAC,MAAM,CAAC,WAAW,IAAI,QAAQ,CAAC,CAAC,KAAK,CAAC,CAAC,EAAE,GAAG,CAAC;YACvE,GAAG,EAAE,QAAQ;SACd,CAAC,CAAC;QACH,IAAI,KAAK,CAAC,MAAM,IAAI,GAAG;YAAE,MAAM;IACjC,CAAC;IACD,OAAO,KAAK,CAAC;AACf,CAAC;AAED,SAAS,cAAc,CACrB,IAAsC,EACtC,GAAW,EACX,SAAgD;IAEhD,IAAI,IAAI,KAAK,KAAK;QAAE,OAAO,GAAG,CAAC;IAC/B,IAAI,IAAI,KAAK,MAAM;QAAE,OAAO,SAAS,EAAE,IAAI,IAAI,GAAG,CAAC;IACnD,IAAI,IAAI,KAAK,UAAU,IAAI,IAAI,KAAK,SAAS,EAAE,CAAC;QAC9C,OAAO,SAAS,EAAE,QAAQ,IAAI,SAAS,EAAE,IAAI,IAAI,GAAG,CAAC;IACvD,CAAC;IACD,OAAO,EAAE,CAAC;AACZ,CAAC;AAED,SAAS,sBAAsB,CAC7B,SAAgD;IAEhD,IAAI,CAAC,SAAS;QAAE,OAAO,EAAE,CAAC;IAC1B,OAAO;QACL,GAAG,CAAC,SAAS,CAAC,KAAK,CAAC,CAAC,CAAC,EAAE,KAAK,EAAE,SAAS,CAAC,KAAK,EAAE,CAAC,CAAC,CAAC,EAAE,CAAC;QACtD,GAAG,CAAC,SAAS,CAAC,OAAO,CAAC,CAAC,CAAC,EAAE,OAAO,EAAE,SAAS,CAAC,OAAO,EAAE,CAAC,CAAC,CAAC,EAAE,CAAC;QAC5D,GAAG,CAAC,SAAS,CAAC,MAAM,CAAC,CAAC,CAAC,EAAE,MAAM,EAAE,SAAS,CAAC,MAAM,EAAE,CAAC,CAAC,CAAC,EAAE,CAAC;QACzD,GAAG,CAAC,SAAS,CAAC,QAAQ,CAAC,CAAC,CAAC,EAAE,QAAQ,EAAE,SAAS,CAAC,QAAQ,EAAE,CAAC,CAAC,CAAC,EAAE,CAAC;QAC/D,GAAG,CAAC,SAAS,CAAC,IAAI,CAAC,CAAC,CAAC,EAAE,IAAI,EAAE,SAAS,CAAC,IAAI,EAAE,CAAC,CAAC,CAAC,EAAE,CAAC;QACnD,GAAG,CAAC,SAAS,CAAC,aAAa;YACzB,CAAC,CAAC,EAAE,aAAa,EAAE,SAAS,CAAC,aAAa,EAAE;YAC5C,CAAC,CAAC,EAAE,CAAC;KACR,CAAC;AACJ,CAAC;AAED,SAAS,qBAAqB,CAAC,OAK9B;IAQC,MAAM,MAAM,GAAG,OAAO,CAAC,MAAM,IAAI,EAAE,CAAC;IACpC,MAAM,UAAU,GAAG,MAAM,CAAC,MAAM,IAAI,OAAO,CAAC,oBAAoB,CAAC;IACjE,MAAM,MAAM,GAAG,UAAU,KAAK,KAAK,CAAC,CAAC,CAAC,OAAO,CAAC,GAAG,CAAC,CAAC,CAAC,OAAO,CAAC,SAAS,CAAC;IACtE,MAAM,eAAe,GAAG,MAAM,CAAC,MAAM,GAAG,uBAAuB,CAAC;IAChE,MAAM,UAAU,GAAG,eAAe;QAChC,CAAC,CAAC,MAAM,CAAC,KAAK,CAAC,CAAC,EAAE,uBAAuB,CAAC;QAC1C,CAAC,CAAC,MAAM,CAAC;IACX,MAAM,UAAU,GAAG,sBAAsB,CACvC,MAAM,CAAC,UAAU,EACjB,mBAAmB,EACnB,CAAC,EACD,WAAW,CACZ,CAAC;IACF,MAAM,YAAY,GAAG,sBAAsB,CACzC,MAAM,CAAC,YAAY,EACnB,qBAAqB,EACrB,CAAC,EACD,iBAAiB,CAClB,CAAC;IACF,MAAM,OAAO,GAAsB,EAAE,CAAC;IACtC,IAAI,YAAY,GAAG,CAAC,CAAC;IACrB,MAAM,aAAa,GAAG,OAAO,CAAC,MAAM,CAAC,aAAa,CAAC,CAAC;IAEpD,MAAM,QAAQ,GAAG,CAAC,KAAuC,EAAE,EAAE;QAC3D,YAAY,IAAI,CAAC,CAAC;QAClB,IAAI,OAAO,CAAC,MAAM,IAAI,UAAU;YAAE,OAAO;QACzC,OAAO,CAAC,IAAI,CAAC;YACX,GAAG,KAAK;YACR,OAAO,EAAE,WAAW,CAAC,UAAU,EAAE,KAAK,CAAC,KAAK,EAAE,YAAY,CAAC;SAC5D,CAAC,CAAC;IACL,CAAC,CAAC;IAEF,KAAK,MAAM,KAAK,IAAI;QAClB,GAAG,mBAAmB,CAAC,MAAM,CAAC,KAAK,CAAC;QACpC,GAAG,mBAAmB,CAAC,MAAM,CAAC,OAAO,CAAC;KACvC,EAAE,CAAC;QACF,kBAAkB,CAAC,UAAU,EAAE,KAAK,EAAE,aAAa,EAAE,CAAC,KAAK,EAAE,KAAK,EAAE,EAAE,CACpE,QAAQ,CAAC,EAAE,IAAI,EAAE,OAAO,EAAE,KAAK,EAAE,KAAK,EAAE,KAAK,EAAE,CAAC,CACjD,CAAC;IACJ,CAAC;IAED,KAAK,MAAM,IAAI,IAAI,mBAAmB,CAAC,MAAM,CAAC,KAAK,CAAC,EAAE,CAAC;QACrD,kBAAkB,CAAC,UAAU,EAAE,IAAI,EAAE,aAAa,EAAE,CAAC,KAAK,EAAE,KAAK,EAAE,EAAE,CACnE,QAAQ,CAAC,EAAE,IAAI,EAAE,MAAM,EAAE,KAAK,EAAE,IAAI,EAAE,KAAK,EAAE,KAAK,EAAE,CAAC,CACtD,CAAC;IACJ,CAAC;IAED,MAAM,YAAY,GAAG,MAAM,CAAC,MAAM,CAAC,KAAK,IAAI,EAAE,CAAC,CAAC,IAAI,EAAE,CAAC;IACvD,IAAI,YAAY,EAAE,CAAC;QACjB,IAAI,CAAC,SAAS,CAAC,YAAY,EAAE,EAAE,KAAK,EAAE,EAAE,EAAE,CAAC,EAAE,CAAC;YAC5C,MAAM,IAAI,KAAK,CACb,iGAAiG,CAClG,CAAC;QACJ,CAAC;QACD,MAAM,KAAK,GAAG,IAAI,MAAM,CACtB,YAAY,EACZ,mBAAmB,CAAC,MAAM,CAAC,UAAU,EAAE,aAAa,CAAC,CACtD,CAAC;QACF,IAAI,KAA6B,CAAC;QAClC,OACE,CAAC,KAAK,GAAG,KAAK,CAAC,IAAI,CAAC,UAAU,CAAC,CAAC;YAChC,OAAO,KAAK,CAAC,KAAK,KAAK,QAAQ,EAC/B,CAAC;YACD,QAAQ,CAAC;gBACP,IAAI,EAAE,OAAO;gBACb,KAAK,EAAE,YAAY;gBACnB,KAAK,EAAE,KAAK,CAAC,CAAC,CAAC;gBACf,KAAK,EAAE,KAAK,CAAC,KAAK;aACnB,CAAC,CAAC;YACH,IAAI,KAAK,CAAC,CAAC,CAAC,KAAK,EAAE;gBAAE,KAAK,CAAC,SAAS,IAAI,CAAC,CAAC;YAC1C,IAAI,YAAY,IAAI,WAAW,GAAG,EAAE;gBAAE,MAAM;QAC9C,CAAC;IACH,CAAC;IAED,OAAO,CAAC,IAAI,CAAC,CAAC,CAAC,EAAE,CAAC,EAAE,EAAE,CAAC,CAAC,CAAC,KAAK,GAAG,CAAC,CAAC,KAAK,CAAC,CAAC;IAC1C,OAAO;QACL,OAAO;QACP,YAAY;QACZ,cAAc,EAAE,IAAI,CAAC,GAAG,CAAC,CAAC,EAAE,YAAY,GAAG,OAAO,CAAC,MAAM,CAAC;QAC1D,YAAY,EAAE,UAAU;QACxB,eAAe;KAChB,CAAC;AACJ,CAAC;AAED,SAAS,kBAAkB,CACzB,MAAc,EACd,KAAa,EACb,aAAsB,EACtB,OAA+C;IAE/C,IAAI,CAAC,KAAK;QAAE,OAAO;IACnB,MAAM,QAAQ,GAAG,aAAa,CAAC,CAAC,CAAC,MAAM,CAAC,CAAC,CAAC,MAAM,CAAC,WAAW,EAAE,CAAC;IAC/D,MAAM,MAAM,GAAG,aAAa,CAAC,CAAC,CAAC,KAAK,CAAC,CAAC,CAAC,KAAK,CAAC,WAAW,EAAE,CAAC;IAC3D,IAAI,IAAI,GAAG,CAAC,CAAC;IACb,OAAO,IAAI,IAAI,QAAQ,CAAC,MAAM,EAAE,CAAC;QAC/B,MAAM,KAAK,GAAG,QAAQ,CAAC,OAAO,CAAC,MAAM,EAAE,IAAI,CAAC,CAAC;QAC7C,IAAI,KAAK,GAAG,CAAC;YAAE,MAAM;QACrB,OAAO,CAAC,KAAK,EAAE,MAAM,CAAC,KAAK,CAAC,KAAK,EAAE,KAAK,GAAG,KAAK,CAAC,MAAM,CAAC,CAAC,CAAC;QAC1D,IAAI,GAAG,KAAK,GAAG,IAAI,CAAC,GAAG,CAAC,CAAC,EAAE,MAAM,CAAC,MAAM,CAAC,CAAC;IAC5C,CAAC;AACH,CAAC;AAED,SAAS,mBAAmB,CAC1B,KAAyB,EACzB,aAAsB;IAEtB,MAAM,OAAO,GAAG,IAAI,GAAG,CAAC,CAAC,GAAG,EAAE,GAAG,EAAE,GAAG,EAAE,GAAG,EAAE,GAAG,EAAE,GAAG,EAAE,GAAG,EAAE,GAAG,CAAC,CAAC,CAAC;IAClE,MAAM,MAAM,GAAG,IAAI,GAAG,CAAS,CAAC,GAAG,CAAC,CAAC,CAAC;IACtC,IAAI,CAAC,aAAa;QAAE,MAAM,CAAC,GAAG,CAAC,GAAG,CAAC,CAAC;IACpC,KAAK,MAAM,IAAI,IAAI,MAAM,CAAC,KAAK,IAAI,EAAE,CAAC,EAAE,CAAC;QACvC,IAAI,OAAO,CAAC,GAAG,CAAC,IAAI,CAAC;YAAE,MAAM,CAAC,GAAG,CAAC,IAAI,CAAC,CAAC;IAC1C,CAAC;IACD,MAAM,CAAC,MAAM,CAAC,GAAG,CAAC,CAAC;IACnB,OAAO,CAAC,GAAG,MAAM,CAAC,CAAC,IAAI,CAAC,EAAE,CAAC,CAAC;AAC9B,CAAC;AAED,SAAS,mBAAmB,CAAC,KAAc;IACzC,IAAI,KAAK,KAAK,SAAS,IAAI,KAAK,KAAK,IAAI;QAAE,OAAO,EAAE,CAAC;IACrD,MAAM,MAAM,GAAG,KAAK,CAAC,OAAO,CAAC,KAAK,CAAC,CAAC,CAAC,CAAC,KAAK,CAAC,CAAC,CAAC,CAAC,KAAK,CAAC,CAAC;IACtD,OAAO,MAAM;SACV,GAAG,CAAC,CAAC,IAAI,EAAE,EAAE,CAAC,MAAM,CAAC,IAAI,CAAC,CAAC,IAAI,EAAE,CAAC;SAClC,MAAM,CAAC,CAAC,IAAI,EAAE,EAAE,CAAC,IAAI,CAAC,MAAM,GAAG,CAAC,CAAC,CAAC;AACvC,CAAC;AAED,SAAS,sBAAsB,CAC7B,KAAc,EACd,QAAgB,EAChB,GAAW,EACX,GAAW;IAEX,MAAM,OAAO,GAAG,MAAM,CAAC,KAAK,CAAC,CAAC;IAC9B,IAAI,CAAC,MAAM,CAAC,QAAQ,CAAC,OAAO,CAAC;QAAE,OAAO,QAAQ,CAAC;IAC/C,OAAO,IAAI,CAAC,GAAG,CAAC,GAAG,EAAE,IAAI,CAAC,GAAG,CAAC,IAAI,CAAC,KAAK,CAAC,OAAO,CAAC,EAAE,GAAG,CAAC,CAAC,CAAC;AAC3D,CAAC;AAED,SAAS,WAAW,CAAC,MAAc,EAAE,KAAa,EAAE,YAAoB;IACtE,MAAM,KAAK,GAAG,IAAI,CAAC,GAAG,CAAC,CAAC,EAAE,KAAK,GAAG,YAAY,CAAC,CAAC;IAChD,MAAM,GAAG,GAAG,IAAI,CAAC,GAAG,CAAC,MAAM,CAAC,MAAM,EAAE,KAAK,GAAG,YAAY,CAAC,CAAC;IAC1D,MAAM,MAAM,GAAG,KAAK,GAAG,CAAC,CAAC,CAAC,CAAC,KAAK,CAAC,CAAC,CAAC,EAAE,CAAC;IACtC,MAAM,MAAM,GAAG,GAAG,GAAG,MAAM,CAAC,MAAM,CAAC,CAAC,CAAC,KAAK,CAAC,CAAC,CAAC,EAAE,CAAC;IAChD,OAAO,GAAG,MAAM,GAAG,mBAAmB,CAAC,MAAM,CAAC,KAAK,CAAC,KAAK,EAAE,GAAG,CAAC,CAAC,GAAG,MAAM,EAAE,CAAC;AAC9E,CAAC;AAED,SAAS,iBAAiB,CAAC,KAAa;IACtC,OAAO,KAAK;SACT,OAAO,CAAC,SAAS,EAAE,MAAM,CAAC;SAC1B,OAAO,CAAC,WAAW,EAAE,IAAI,CAAC;SAC1B,IAAI,EAAE,CAAC;AACZ,CAAC;AAED,SAAS,mBAAmB,CAAC,KAAa;IACxC,OAAO,KAAK,CAAC,OAAO,CAAC,MAAM,EAAE,GAAG,CAAC,CAAC,IAAI,EAAE,CAAC;AAC3C,CAAC;AAED,SAAS,eAAe,CAAC,KAAgC;IACvD,MAAM,UAAU,GAAG,mBAAmB,CAAC,KAAK,IAAI,EAAE,CAAC,CAAC;IACpD,OAAO,UAAU,IAAI,SAAS,CAAC;AACjC,CAAC;AAED,SAAS,aAAa,CAAC,MAAwB;IAC7C,MAAM,OAAO,GAAG,MAAM,CAAC,OAAO,IAAI,EAAE,CAAC;IACrC,MAAM,MAAM,GAAG,YAAY,OAAO,CAAC,MAAM,GAAG,MAAM,CAAC,YAAY,KAAK,SAAS,CAAC,CAAC,CAAC,aAAa,MAAM,CAAC,YAAY,EAAE,CAAC,CAAC,CAAC,EAAE,GAAG,MAAM,CAAC,cAAc,CAAC,CAAC,CAAC,KAAK,MAAM,CAAC,cAAc,WAAW,CAAC,CAAC,CAAC,EAAE,EAAE,CAAC;IAC/L,IAAI,CAAC,OAAO,CAAC,MAAM;QAAE,OAAO,MAAM,CAAC;IACnC,OAAO;QACL,MAAM;QACN,GAAG,OAAO,CAAC,GAAG,CACZ,CAAC,KAAK,EAAE,KAAK,EAAE,EAAE,CACf,GAAG,KAAK,GAAG,CAAC,KAAK,KAAK,CAAC,IAAI,IAAI,IAAI,CAAC,SAAS,CAAC,KAAK,CAAC,KAAK,CAAC,OAAO,KAAK,CAAC,KAAK,KAAK,KAAK,CAAC,OAAO,EAAE,CACnG;KACF,CAAC,IAAI,CAAC,IAAI,CAAC,CAAC;AACf,CAAC;AAED,SAAS,WAAW,CAAC,KAAuB;IAC1C,IAAI,CAAC,KAAK,CAAC,MAAM;QAAE,OAAO,QAAQ,CAAC;IACnC,OAAO,KAAK;SACT,GAAG,CACF,CAAC,IAAI,EAAE,KAAK,EAAE,EAAE,CAAC,GAAG,KAAK,GAAG,CAAC,MAAM,IAAI,CAAC,IAAI,IAAI,IAAI,CAAC,GAAG,KAAK,IAAI,CAAC,GAAG,GAAG,CACzE;SACA,IAAI,CAAC,IAAI,CAAC,CAAC;AAChB,CAAC;AAED,SAAS,cAAc,CAAC,MAAwB;IAC9C,OAAO,IAAI,CAAC,SAAS,CACnB;QACE,KAAK,EAAE,MAAM,CAAC,KAAK;QACnB,OAAO,EAAE,MAAM,CAAC,OAAO;QACvB,MAAM,EAAE,MAAM,CAAC,MAAM;QACrB,QAAQ,EAAE,MAAM,CAAC,QAAQ;QACzB,IAAI,EAAE,MAAM,CAAC,IAAI;QACjB,aAAa,EAAE,MAAM,CAAC,aAAa;QACnC,WAAW,EAAE,MAAM,CAAC,WAAW;KAChC,EACD,IAAI,EACJ,CAAC,CACF,CAAC;AACJ,CAAC","sourcesContent":["import { Readability } from \"@mozilla/readability\";\nimport { parseHTML } from \"linkedom/worker\";\nimport safeRegex from \"safe-regex2\";\nimport TurndownService from \"turndown\";\n\nexport type WebResponseMode =\n | \"auto\"\n | \"raw\"\n | \"text\"\n | \"markdown\"\n | \"links\"\n | \"metadata\"\n | \"matches\";\n\nexport type WebExtractMode = \"readability\" | \"all-visible\" | \"none\";\nexport type WebSearchSource = \"extracted\" | \"raw\";\n\nexport interface WebContentSearchOptions {\n query?: string | string[];\n queries?: string[];\n terms?: string[];\n regex?: string;\n regexFlags?: string;\n caseSensitive?: boolean;\n source?: WebSearchSource;\n maxMatches?: number;\n contextChars?: number;\n}\n\nexport interface WebContentProcessOptions {\n url: string;\n body: string;\n contentType?: string | null;\n responseMode?: string;\n extract?: string;\n includeLinks?: boolean;\n search?: WebContentSearchOptions | null;\n maxChars?: number;\n}\n\nexport interface WebContentLink {\n text: string;\n url: string;\n}\n\nexport interface WebContentMatch {\n kind: \"query\" | \"term\" | \"regex\";\n query: string;\n match: string;\n index: number;\n snippet: string;\n}\n\nexport interface WebContentResult {\n mode: Exclude<WebResponseMode, \"auto\">;\n extract: WebExtractMode;\n contentType: string | null;\n title?: string;\n excerpt?: string;\n byline?: string;\n siteName?: string;\n lang?: string;\n publishedTime?: string;\n content?: string;\n links?: WebContentLink[];\n matches?: WebContentMatch[];\n totalMatches?: number;\n omittedMatches?: number;\n searchSource?: WebSearchSource;\n truncated?: boolean;\n searchTruncated?: boolean;\n}\n\nconst DEFAULT_MAX_CONTENT_CHARS = 32_000;\nconst MAX_SEARCH_SOURCE_CHARS = 500_000;\nconst DEFAULT_MAX_MATCHES = 50;\nconst MAX_MATCHES = 500;\nconst DEFAULT_CONTEXT_CHARS = 160;\nconst MAX_CONTEXT_CHARS = 1_000;\n\nconst turndown = new TurndownService({\n headingStyle: \"atx\",\n bulletListMarker: \"-\",\n codeBlockStyle: \"fenced\",\n linkStyle: \"inlined\",\n});\nturndown.remove([\"script\", \"style\", \"noscript\"]);\n\nexport function hasWebContentSearch(\n search: WebContentSearchOptions | null | undefined,\n): boolean {\n if (!search) return false;\n return Boolean(\n normalizeSearchList(search.query).length ||\n normalizeSearchList(search.queries).length ||\n normalizeSearchList(search.terms).length ||\n String(search.regex ?? \"\").trim(),\n );\n}\n\nexport function normalizeWebResponseMode(\n value: unknown,\n fallback: WebResponseMode = \"auto\",\n): WebResponseMode {\n const normalized = String(value || fallback).toLowerCase();\n if (\n normalized === \"auto\" ||\n normalized === \"raw\" ||\n normalized === \"text\" ||\n normalized === \"markdown\" ||\n normalized === \"links\" ||\n normalized === \"metadata\" ||\n normalized === \"matches\"\n ) {\n return normalized;\n }\n throw new Error(\n `Invalid responseMode \"${String(value)}\". Expected auto, raw, text, markdown, links, metadata, or matches.`,\n );\n}\n\nexport function normalizeWebExtractMode(\n value: unknown,\n fallback: WebExtractMode = \"readability\",\n): WebExtractMode {\n const normalized = String(value || fallback).toLowerCase();\n if (\n normalized === \"readability\" ||\n normalized === \"all-visible\" ||\n normalized === \"none\"\n ) {\n return normalized;\n }\n throw new Error(\n `Invalid extract \"${String(value)}\". Expected readability, all-visible, or none.`,\n );\n}\n\nexport function parseWebContentSearchOptions(\n value: unknown,\n): WebContentSearchOptions | null {\n if (!value) return null;\n if (typeof value === \"object\" && !Array.isArray(value)) {\n return value as WebContentSearchOptions;\n }\n if (typeof value !== \"string\") return null;\n const trimmed = value.trim();\n if (!trimmed) return null;\n try {\n const parsed = JSON.parse(trimmed);\n if (parsed && typeof parsed === \"object\" && !Array.isArray(parsed)) {\n return parsed as WebContentSearchOptions;\n }\n } catch {\n return { query: trimmed };\n }\n return null;\n}\n\nexport function processWebContent(\n options: WebContentProcessOptions,\n): WebContentResult {\n const contentType = options.contentType?.split(\";\")[0]?.trim() || null;\n const extract = normalizeWebExtractMode(options.extract);\n const requestedMode = normalizeWebResponseMode(options.responseMode);\n const search = options.search ?? null;\n const html = isHtmlResponse(contentType, options.body);\n const mode = resolveMode(requestedMode, html, search);\n const maxChars = normalizeBoundedNumber(\n options.maxChars,\n DEFAULT_MAX_CONTENT_CHARS,\n 1,\n 200_000,\n );\n\n const extracted =\n html && (mode !== \"raw\" || hasWebContentSearch(search))\n ? extractHtml(options.body, options.url, extract)\n : null;\n const baseContent = contentForMode(mode, options.body, extracted);\n const result: WebContentResult = {\n mode,\n extract,\n contentType,\n ...metadataFromExtraction(extracted),\n };\n\n if (mode === \"links\") {\n result.links = extracted?.links ?? [];\n return result;\n }\n\n if (mode === \"metadata\") {\n if (options.includeLinks) result.links = extracted?.links ?? [];\n return result;\n }\n\n if (mode === \"matches\") {\n const matchResult = findWebContentMatches({\n raw: options.body,\n extracted: baseContent,\n search,\n fallbackSearchSource: html ? \"extracted\" : \"raw\",\n });\n Object.assign(result, matchResult);\n if (options.includeLinks) result.links = extracted?.links ?? [];\n return result;\n }\n\n const truncated = baseContent.length > maxChars;\n result.content = truncated\n ? `${baseContent.slice(0, maxChars)}\\n... (truncated)`\n : baseContent;\n result.truncated = truncated;\n if (options.includeLinks) result.links = extracted?.links ?? [];\n\n if (hasWebContentSearch(search)) {\n const matchResult = findWebContentMatches({\n raw: options.body,\n extracted: baseContent,\n search,\n fallbackSearchSource: html ? \"extracted\" : \"raw\",\n });\n result.matches = matchResult.matches;\n result.totalMatches = matchResult.totalMatches;\n result.omittedMatches = matchResult.omittedMatches;\n result.searchSource = matchResult.searchSource;\n result.searchTruncated = matchResult.searchTruncated;\n }\n\n return result;\n}\n\nexport function formatWebContentResult(result: WebContentResult): string {\n if (result.mode === \"raw\") return result.content ?? \"\";\n\n const lines: string[] = [];\n if (result.title) lines.push(`# ${result.title}`, \"\");\n if (result.siteName) lines.push(`Site: ${result.siteName}`);\n if (result.publishedTime) lines.push(`Published: ${result.publishedTime}`);\n if (result.excerpt && result.mode !== \"metadata\") {\n lines.push(`Excerpt: ${result.excerpt}`);\n }\n if (lines.length && lines[lines.length - 1] !== \"\") lines.push(\"\");\n\n if (result.mode === \"matches\") {\n lines.push(formatMatches(result));\n } else if (result.mode === \"links\") {\n lines.push(formatLinks(result.links ?? []));\n } else if (result.mode === \"metadata\") {\n lines.push(formatMetadata(result));\n } else if (result.content) {\n lines.push(result.content);\n }\n\n if (\n result.mode !== \"links\" &&\n result.mode !== \"matches\" &&\n result.links?.length\n ) {\n lines.push(\"\", \"Links:\", formatLinks(result.links));\n }\n if (result.matches?.length && result.mode !== \"matches\") {\n lines.push(\"\", formatMatches(result));\n }\n\n return lines.join(\"\\n\").trim();\n}\n\nfunction resolveMode(\n requestedMode: WebResponseMode,\n html: boolean,\n search: WebContentSearchOptions | null,\n): Exclude<WebResponseMode, \"auto\"> {\n if (requestedMode === \"auto\") {\n if (hasWebContentSearch(search)) return \"matches\";\n return html ? \"markdown\" : \"raw\";\n }\n return requestedMode;\n}\n\nfunction isHtmlResponse(contentType: string | null, body: string): boolean {\n if (contentType) {\n return (\n contentType === \"text/html\" ||\n contentType === \"application/xhtml+xml\" ||\n contentType.endsWith(\"+html\")\n );\n }\n return /<!doctype html|<html[\\s>]|<body[\\s>]|<article[\\s>]/i.test(\n body.slice(0, 2_000),\n );\n}\n\nfunction extractHtml(\n body: string,\n url: string,\n extract: WebExtractMode,\n): {\n html: string;\n text: string;\n markdown: string;\n links: WebContentLink[];\n title?: string;\n excerpt?: string;\n byline?: string;\n siteName?: string;\n lang?: string;\n publishedTime?: string;\n} {\n const document = parseFullDocument(body);\n removeNonContentNodes(document);\n const pageTitle = textOrUndefined(document.title);\n const article =\n extract === \"readability\"\n ? new Readability(document.cloneNode(true) as Document).parse()\n : null;\n const sourceHtml =\n extract === \"none\"\n ? body\n : article?.content ||\n document.body?.innerHTML ||\n document.documentElement.innerHTML ||\n body;\n const absoluteHtml = absolutizeHtmlUrls(sourceHtml, url);\n const sourceText =\n extract === \"none\"\n ? htmlToPlainText(body)\n : article?.textContent ||\n document.body?.textContent ||\n document.documentElement.textContent ||\n \"\";\n const markdown = htmlToMarkdown(absoluteHtml);\n return {\n html: absoluteHtml,\n text: normalizeWhitespace(sourceText),\n markdown,\n links: collectLinks(absoluteHtml, url),\n title: textOrUndefined(article?.title) ?? pageTitle,\n excerpt: textOrUndefined(article?.excerpt),\n byline: textOrUndefined(article?.byline),\n siteName: textOrUndefined(article?.siteName),\n lang: textOrUndefined(article?.lang),\n publishedTime: textOrUndefined(article?.publishedTime),\n };\n}\n\nfunction htmlToPlainText(html: string): string {\n const document = parseFullDocument(html);\n removeNonContentNodes(document);\n return normalizeWhitespace(document.body?.textContent ?? \"\");\n}\n\nfunction htmlToMarkdown(html: string): string {\n return normalizeMarkdown(turndown.turndown(html));\n}\n\nfunction removeNonContentNodes(document: Document) {\n for (const selector of [\n \"script\",\n \"style\",\n \"noscript\",\n \"svg\",\n \"template\",\n \"iframe\",\n ]) {\n for (const node of [...document.querySelectorAll(selector)]) {\n node.remove();\n }\n }\n}\n\nfunction parseFullDocument(html: string): Document {\n return parseHTML(html).document as unknown as Document;\n}\n\nfunction parseHtmlFragment(html: string): Document {\n return parseHTML(\n `<!doctype html><html><head></head><body>${html}</body></html>`,\n ).document as unknown as Document;\n}\n\nfunction absolutizeHtmlUrls(html: string, url: string): string {\n const document = parseHtmlFragment(html);\n for (const anchor of [...document.querySelectorAll(\"a[href]\")]) {\n const href = anchor.getAttribute(\"href\");\n if (!href) continue;\n try {\n anchor.setAttribute(\"href\", new URL(href, url).href);\n } catch {}\n }\n for (const image of [...document.querySelectorAll(\"img[src]\")]) {\n const src = image.getAttribute(\"src\");\n if (!src) continue;\n try {\n image.setAttribute(\"src\", new URL(src, url).href);\n } catch {}\n }\n return document.body?.innerHTML || html;\n}\n\nfunction collectLinks(html: string, url: string): WebContentLink[] {\n const document = parseHtmlFragment(html);\n const links: WebContentLink[] = [];\n const seen = new Set<string>();\n for (const anchor of [...document.querySelectorAll(\"a[href]\")]) {\n const href = anchor.getAttribute(\"href\");\n if (!href) continue;\n let absolute: string;\n try {\n absolute = new URL(href, url).href;\n } catch {\n continue;\n }\n if (seen.has(absolute)) continue;\n seen.add(absolute);\n links.push({\n text: normalizeWhitespace(anchor.textContent || absolute).slice(0, 200),\n url: absolute,\n });\n if (links.length >= 200) break;\n }\n return links;\n}\n\nfunction contentForMode(\n mode: Exclude<WebResponseMode, \"auto\">,\n raw: string,\n extracted: ReturnType<typeof extractHtml> | null,\n): string {\n if (mode === \"raw\") return raw;\n if (mode === \"text\") return extracted?.text ?? raw;\n if (mode === \"markdown\" || mode === \"matches\") {\n return extracted?.markdown || extracted?.text || raw;\n }\n return \"\";\n}\n\nfunction metadataFromExtraction(\n extracted: ReturnType<typeof extractHtml> | null,\n) {\n if (!extracted) return {};\n return {\n ...(extracted.title ? { title: extracted.title } : {}),\n ...(extracted.excerpt ? { excerpt: extracted.excerpt } : {}),\n ...(extracted.byline ? { byline: extracted.byline } : {}),\n ...(extracted.siteName ? { siteName: extracted.siteName } : {}),\n ...(extracted.lang ? { lang: extracted.lang } : {}),\n ...(extracted.publishedTime\n ? { publishedTime: extracted.publishedTime }\n : {}),\n };\n}\n\nfunction findWebContentMatches(options: {\n raw: string;\n extracted: string;\n search: WebContentSearchOptions | null;\n fallbackSearchSource: WebSearchSource;\n}): Pick<\n WebContentResult,\n | \"matches\"\n | \"totalMatches\"\n | \"omittedMatches\"\n | \"searchSource\"\n | \"searchTruncated\"\n> {\n const search = options.search ?? {};\n const sourceMode = search.source ?? options.fallbackSearchSource;\n const source = sourceMode === \"raw\" ? options.raw : options.extracted;\n const searchTruncated = source.length > MAX_SEARCH_SOURCE_CHARS;\n const searchable = searchTruncated\n ? source.slice(0, MAX_SEARCH_SOURCE_CHARS)\n : source;\n const maxMatches = normalizeBoundedNumber(\n search.maxMatches,\n DEFAULT_MAX_MATCHES,\n 1,\n MAX_MATCHES,\n );\n const contextChars = normalizeBoundedNumber(\n search.contextChars,\n DEFAULT_CONTEXT_CHARS,\n 0,\n MAX_CONTEXT_CHARS,\n );\n const matches: WebContentMatch[] = [];\n let totalMatches = 0;\n const caseSensitive = Boolean(search.caseSensitive);\n\n const addMatch = (match: Omit<WebContentMatch, \"snippet\">) => {\n totalMatches += 1;\n if (matches.length >= maxMatches) return;\n matches.push({\n ...match,\n snippet: makeSnippet(searchable, match.index, contextChars),\n });\n };\n\n for (const query of [\n ...normalizeSearchList(search.query),\n ...normalizeSearchList(search.queries),\n ]) {\n findLiteralMatches(searchable, query, caseSensitive, (index, match) =>\n addMatch({ kind: \"query\", query, match, index }),\n );\n }\n\n for (const term of normalizeSearchList(search.terms)) {\n findLiteralMatches(searchable, term, caseSensitive, (index, match) =>\n addMatch({ kind: \"term\", query: term, match, index }),\n );\n }\n\n const regexPattern = String(search.regex ?? \"\").trim();\n if (regexPattern) {\n if (!safeRegex(regexPattern, { limit: 25 })) {\n throw new Error(\n \"Unsafe regex rejected. Use a simpler literal query/terms search or a bounded run-code workflow.\",\n );\n }\n const regex = new RegExp(\n regexPattern,\n normalizeRegexFlags(search.regexFlags, caseSensitive),\n );\n let match: RegExpExecArray | null;\n while (\n (match = regex.exec(searchable)) &&\n typeof match.index === \"number\"\n ) {\n addMatch({\n kind: \"regex\",\n query: regexPattern,\n match: match[0],\n index: match.index,\n });\n if (match[0] === \"\") regex.lastIndex += 1;\n if (totalMatches >= MAX_MATCHES * 10) break;\n }\n }\n\n matches.sort((a, b) => a.index - b.index);\n return {\n matches,\n totalMatches,\n omittedMatches: Math.max(0, totalMatches - matches.length),\n searchSource: sourceMode,\n searchTruncated,\n };\n}\n\nfunction findLiteralMatches(\n source: string,\n query: string,\n caseSensitive: boolean,\n onMatch: (index: number, match: string) => void,\n) {\n if (!query) return;\n const haystack = caseSensitive ? source : source.toLowerCase();\n const needle = caseSensitive ? query : query.toLowerCase();\n let from = 0;\n while (from <= haystack.length) {\n const index = haystack.indexOf(needle, from);\n if (index < 0) break;\n onMatch(index, source.slice(index, index + query.length));\n from = index + Math.max(1, needle.length);\n }\n}\n\nfunction normalizeRegexFlags(\n flags: string | undefined,\n caseSensitive: boolean,\n): string {\n const allowed = new Set([\"d\", \"g\", \"i\", \"m\", \"s\", \"u\", \"v\", \"y\"]);\n const result = new Set<string>([\"g\"]);\n if (!caseSensitive) result.add(\"i\");\n for (const flag of String(flags ?? \"\")) {\n if (allowed.has(flag)) result.add(flag);\n }\n result.delete(\"y\");\n return [...result].join(\"\");\n}\n\nfunction normalizeSearchList(value: unknown): string[] {\n if (value === undefined || value === null) return [];\n const values = Array.isArray(value) ? value : [value];\n return values\n .map((item) => String(item).trim())\n .filter((item) => item.length > 0);\n}\n\nfunction normalizeBoundedNumber(\n value: unknown,\n fallback: number,\n min: number,\n max: number,\n): number {\n const numeric = Number(value);\n if (!Number.isFinite(numeric)) return fallback;\n return Math.max(min, Math.min(Math.floor(numeric), max));\n}\n\nfunction makeSnippet(source: string, index: number, contextChars: number) {\n const start = Math.max(0, index - contextChars);\n const end = Math.min(source.length, index + contextChars);\n const prefix = start > 0 ? \"...\" : \"\";\n const suffix = end < source.length ? \"...\" : \"\";\n return `${prefix}${normalizeWhitespace(source.slice(start, end))}${suffix}`;\n}\n\nfunction normalizeMarkdown(value: string): string {\n return value\n .replace(/\\n{3,}/g, \"\\n\\n\")\n .replace(/[ \\t]+\\n/g, \"\\n\")\n .trim();\n}\n\nfunction normalizeWhitespace(value: string): string {\n return value.replace(/\\s+/g, \" \").trim();\n}\n\nfunction textOrUndefined(value: string | null | undefined): string | undefined {\n const normalized = normalizeWhitespace(value ?? \"\");\n return normalized || undefined;\n}\n\nfunction formatMatches(result: WebContentResult): string {\n const matches = result.matches ?? [];\n const header = `Matches: ${matches.length}${result.totalMatches !== undefined ? ` shown of ${result.totalMatches}` : \"\"}${result.omittedMatches ? ` (${result.omittedMatches} omitted)` : \"\"}`;\n if (!matches.length) return header;\n return [\n header,\n ...matches.map(\n (match, index) =>\n `${index + 1}. ${match.kind} ${JSON.stringify(match.query)} at ${match.index}: ${match.snippet}`,\n ),\n ].join(\"\\n\");\n}\n\nfunction formatLinks(links: WebContentLink[]): string {\n if (!links.length) return \"(none)\";\n return links\n .map(\n (link, index) => `${index + 1}. [${link.text || link.url}](${link.url})`,\n )\n .join(\"\\n\");\n}\n\nfunction formatMetadata(result: WebContentResult): string {\n return JSON.stringify(\n {\n title: result.title,\n excerpt: result.excerpt,\n byline: result.byline,\n siteName: result.siteName,\n lang: result.lang,\n publishedTime: result.publishedTime,\n contentType: result.contentType,\n },\n null,\n 2,\n );\n}\n"]}
@@ -183,7 +183,7 @@ export function createWebSearchToolEntry(opts = {}) {
183
183
  return {
184
184
  "web-search": {
185
185
  tool: {
186
- description: "Search the public web. Use to find API documentation, endpoints, current information, or any topic. Returns ranked results from BYOK providers or a grounded Builder-managed summary. Follow up with web-request or provider-api-docs to fetch the full content of promising URLs. Requires either Connect Builder.io or one of: BRAVE_SEARCH_API_KEY, TAVILY_API_KEY, or EXA_API_KEY.",
186
+ description: "Search the public web. Use to find API documentation, endpoints, current information, or any topic. Returns ranked results from BYOK providers or a grounded Builder-managed summary. Follow up with web-request or provider-api-docs using responseMode:'markdown' or responseMode:'matches' to fetch clean text, links, or compact snippets from promising URLs. Requires either Connect Builder.io or one of: BRAVE_SEARCH_API_KEY, TAVILY_API_KEY, or EXA_API_KEY.",
187
187
  parameters: {
188
188
  type: "object",
189
189
  properties: {
@@ -253,7 +253,7 @@ export function createWebSearchToolEntry(opts = {}) {
253
253
  "",
254
254
  managedText,
255
255
  "",
256
- "Use web-request or provider-api-docs to fetch full content from cited or promising URLs.",
256
+ "Use web-request or provider-api-docs with responseMode:'markdown' for readable docs or responseMode:'matches' plus search for compact snippets.",
257
257
  ].join("\n");
258
258
  }
259
259
  if (results.length === 0) {
@@ -273,7 +273,7 @@ export function createWebSearchToolEntry(opts = {}) {
273
273
  }
274
274
  lines.push("");
275
275
  }
276
- lines.push("Use web-request or provider-api-docs to fetch full content from promising URLs.");
276
+ lines.push("Use web-request or provider-api-docs with responseMode:'markdown' for readable docs or responseMode:'matches' plus search for compact snippets.");
277
277
  return lines.join("\n");
278
278
  },
279
279
  readOnly: true,
@@ -1 +1 @@
1
- {"version":3,"file":"web-search-tool.js","sourceRoot":"","sources":["../../src/extensions/web-search-tool.ts"],"names":[],"mappings":"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","sourcesContent":["/**\n * Web-search tool — agent tool for searching the public web.\n *\n * Pluggable backends resolved at call time based on which API key is\n * configured (env var or secrets/credentials store):\n *\n * 1. Brave Search API (BRAVE_SEARCH_API_KEY)\n * 2. Tavily (TAVILY_API_KEY)\n * 3. Exa (EXA_API_KEY)\n * 4. Builder.io (connected Builder credentials)\n *\n * The first configured backend wins. If none is configured, the tool\n * returns a helpful message telling the user which keys to add.\n *\n * Connect Builder.io or register BRAVE_SEARCH_API_KEY, TAVILY_API_KEY, or\n * EXA_API_KEY via app secrets settings or environment variables.\n */\n\nimport type { ActionEntry } from \"../agent/production-agent.js\";\nimport type { CredentialContext } from \"../credentials/index.js\";\n\nexport interface WebSearchResult {\n title: string;\n url: string;\n snippet: string;\n}\n\nexport interface WebSearchToolOptions {\n /**\n * Resolve a request-scoped secret by key. When not provided the tool falls\n * back to env-var lookup only.\n */\n resolveSecret?: (key: string) => Promise<string | null>;\n /**\n * Legacy credential resolver retained for older callers.\n */\n resolveCredential?: (\n key: string,\n ctx: CredentialContext,\n ) => Promise<string | undefined>;\n /**\n * Legacy credential context callback retained for older callers.\n */\n getCredentialContext?: () => CredentialContext | null;\n /**\n * Resolve connected Builder credentials for managed web search.\n */\n resolveBuilderCredentials?: () => Promise<BuilderWebSearchCredentials>;\n /**\n * Base URL for Builder-managed web search.\n */\n getBuilderWebSearchBaseUrl?: () => string;\n /**\n * Stable attribution headers for Builder-managed API calls.\n */\n getBuilderRequestHeaders?: () => Record<string, string>;\n}\n\nconst DEFAULT_COUNT = 5;\nconst MAX_COUNT = 10;\n\ninterface BuilderWebSearchCredentials {\n privateKey: string | null;\n publicKey: string | null;\n userId?: string | null;\n}\n\nasync function resolveSearchKey(\n key: string,\n opts: WebSearchToolOptions,\n): Promise<string | undefined> {\n let usedRequestScopedResolver = false;\n // 1. Try request-scoped app secrets (user/org/workspace stored key).\n if (opts.resolveSecret) {\n usedRequestScopedResolver = true;\n try {\n const value = await opts.resolveSecret(key);\n if (value) return value;\n } catch {\n // Secret lookup failures are non-fatal; fall through to legacy/env.\n }\n }\n\n // 2. Try legacy per-request credential context.\n if (opts.resolveCredential && opts.getCredentialContext) {\n const ctx = opts.getCredentialContext();\n if (ctx) {\n try {\n const value = await opts.resolveCredential(key, ctx);\n if (value) return value;\n } catch {\n // Credential lookup failures are non-fatal; fall through to env.\n }\n }\n }\n\n if (usedRequestScopedResolver) return undefined;\n\n // 3. Fall back to env var.\n return process.env[key] || undefined;\n}\n\nasync function resolveBuilderSearchCredentials(\n opts: WebSearchToolOptions,\n): Promise<BuilderWebSearchCredentials | null> {\n if (!opts.resolveBuilderCredentials) return null;\n try {\n const creds = await opts.resolveBuilderCredentials();\n if (creds.privateKey && creds.publicKey) return creds;\n } catch {\n // Builder credential lookup failures are non-fatal; BYOK backends or the\n // setup hint below can still handle the tool call.\n }\n return null;\n}\n\n// ---------------------------------------------------------------------------\n// Backend implementations\n// ---------------------------------------------------------------------------\n\nasync function searchBrave(\n query: string,\n count: number,\n apiKey: string,\n): Promise<WebSearchResult[]> {\n const url = `https://api.search.brave.com/res/v1/web/search?q=${encodeURIComponent(query)}&count=${count}`;\n const res = await fetch(url, {\n headers: {\n Accept: \"application/json\",\n \"Accept-Encoding\": \"gzip\",\n \"X-Subscription-Token\": apiKey,\n },\n signal: AbortSignal.timeout(15_000),\n });\n if (!res.ok) {\n throw new Error(`Brave Search error ${res.status}: ${await res.text()}`);\n }\n const data = (await res.json()) as {\n web?: {\n results?: Array<{\n title?: string;\n url?: string;\n description?: string;\n }>;\n };\n };\n return (data.web?.results ?? []).map((r) => ({\n title: r.title ?? \"\",\n url: r.url ?? \"\",\n snippet: r.description ?? \"\",\n }));\n}\n\nasync function searchTavily(\n query: string,\n count: number,\n apiKey: string,\n): Promise<WebSearchResult[]> {\n const res = await fetch(\"https://api.tavily.com/search\", {\n method: \"POST\",\n headers: {\n \"Content-Type\": \"application/json\",\n },\n body: JSON.stringify({\n api_key: apiKey,\n query,\n max_results: count,\n search_depth: \"basic\",\n }),\n signal: AbortSignal.timeout(15_000),\n });\n if (!res.ok) {\n throw new Error(`Tavily error ${res.status}: ${await res.text()}`);\n }\n const data = (await res.json()) as {\n results?: Array<{\n title?: string;\n url?: string;\n content?: string;\n }>;\n };\n return (data.results ?? []).map((r) => ({\n title: r.title ?? \"\",\n url: r.url ?? \"\",\n snippet: r.content ?? \"\",\n }));\n}\n\nasync function searchExa(\n query: string,\n count: number,\n apiKey: string,\n): Promise<WebSearchResult[]> {\n const res = await fetch(\"https://api.exa.ai/search\", {\n method: \"POST\",\n headers: {\n \"Content-Type\": \"application/json\",\n \"x-api-key\": apiKey,\n },\n body: JSON.stringify({\n query,\n numResults: count,\n type: \"auto\",\n contents: { text: { maxCharacters: 400 } },\n }),\n signal: AbortSignal.timeout(15_000),\n });\n if (!res.ok) {\n throw new Error(`Exa error ${res.status}: ${await res.text()}`);\n }\n const data = (await res.json()) as {\n results?: Array<{\n title?: string;\n url?: string;\n text?: string;\n }>;\n };\n return (data.results ?? []).map((r) => ({\n title: r.title ?? \"\",\n url: r.url ?? \"\",\n snippet: r.text ?? \"\",\n }));\n}\n\nasync function searchBuilderManaged(\n query: string,\n count: number,\n credentials: BuilderWebSearchCredentials,\n opts: WebSearchToolOptions,\n): Promise<string> {\n const baseUrl =\n opts.getBuilderWebSearchBaseUrl?.() ??\n process.env.BUILDER_WEB_SEARCH_BASE_URL ??\n \"https://api.builder.io/agent-native/web-search/v1\";\n const url = new URL(\n \"search\",\n baseUrl.endsWith(\"/\") ? baseUrl : `${baseUrl}/`,\n );\n const res = await fetch(url.toString(), {\n method: \"POST\",\n headers: {\n \"Content-Type\": \"application/json\",\n Authorization: `Bearer ${credentials.privateKey}`,\n \"x-builder-api-key\": credentials.publicKey ?? \"\",\n ...(credentials.userId\n ? { \"x-builder-user-id\": credentials.userId }\n : {}),\n ...(opts.getBuilderRequestHeaders?.() ?? {}),\n },\n body: JSON.stringify({\n query,\n count,\n source: {\n appId: \"agent-native\",\n feature: \"web-search-tool\",\n },\n }),\n signal: AbortSignal.timeout(45_000),\n });\n if (!res.ok) {\n const text = await res.text().catch(() => \"\");\n throw new Error(\n `Builder web search error ${res.status}${text ? `: ${text.slice(0, 300)}` : \"\"}`,\n );\n }\n const data = (await res.json()) as {\n text?: string;\n };\n const text = data.text?.trim();\n if (!text) {\n throw new Error(\"Builder web search returned no text.\");\n }\n return text;\n}\n\n// ---------------------------------------------------------------------------\n// Tool entry factory\n// ---------------------------------------------------------------------------\n\n/**\n * Create the web-search tool entry for the agent tool registry.\n */\nexport function createWebSearchToolEntry(\n opts: WebSearchToolOptions = {},\n): Record<string, ActionEntry> {\n return {\n \"web-search\": {\n tool: {\n description:\n \"Search the public web. Use to find API documentation, endpoints, current information, or any topic. Returns ranked results from BYOK providers or a grounded Builder-managed summary. Follow up with web-request or provider-api-docs to fetch the full content of promising URLs. Requires either Connect Builder.io or one of: BRAVE_SEARCH_API_KEY, TAVILY_API_KEY, or EXA_API_KEY.\",\n parameters: {\n type: \"object\" as const,\n properties: {\n query: {\n type: \"string\",\n description:\n \"Search query. Be specific — include API name, version, and what you need (e.g. 'Stripe API list subscriptions endpoint').\",\n },\n count: {\n type: \"number\",\n description: `Number of results to return. Default ${DEFAULT_COUNT}, max ${MAX_COUNT}.`,\n },\n },\n required: [\"query\"],\n },\n },\n run: async (args: Record<string, string>) => {\n const query = (args.query ?? \"\").trim();\n if (!query) return \"query is required.\";\n\n const rawCount = Number(args.count);\n const count =\n Number.isFinite(rawCount) && rawCount > 0\n ? Math.min(Math.floor(rawCount), MAX_COUNT)\n : DEFAULT_COUNT;\n\n // Backend selection — first configured wins.\n const braveKey = await resolveSearchKey(\"BRAVE_SEARCH_API_KEY\", opts);\n const tavilyKey = await resolveSearchKey(\"TAVILY_API_KEY\", opts);\n const exaKey = await resolveSearchKey(\"EXA_API_KEY\", opts);\n const builderCredentials = await resolveBuilderSearchCredentials(opts);\n\n let results: WebSearchResult[];\n let backend: string;\n let managedText: string | null = null;\n\n try {\n if (braveKey) {\n results = await searchBrave(query, count, braveKey);\n backend = \"Brave Search\";\n } else if (tavilyKey) {\n results = await searchTavily(query, count, tavilyKey);\n backend = \"Tavily\";\n } else if (exaKey) {\n results = await searchExa(query, count, exaKey);\n backend = \"Exa\";\n } else if (builderCredentials) {\n managedText = await searchBuilderManaged(\n query,\n count,\n builderCredentials,\n opts,\n );\n results = [];\n backend = \"Builder.io\";\n } else {\n return [\n \"No web-search backend configured.\",\n \"Connect Builder.io in Settings, or add one of the following keys via app settings or environment variables:\",\n \" • BRAVE_SEARCH_API_KEY — https://brave.com/search/api/\",\n \" • TAVILY_API_KEY — https://tavily.com/\",\n \" • EXA_API_KEY — https://exa.ai/\",\n ].join(\"\\n\");\n }\n } catch (err: unknown) {\n const msg = err instanceof Error ? err.message : String(err);\n return `Web search failed (${msg}). Try web-request to fetch a specific URL directly.`;\n }\n\n if (managedText) {\n return [\n `Web search results for \"${query}\" (backend: ${backend}):`,\n \"\",\n managedText,\n \"\",\n \"Use web-request or provider-api-docs to fetch full content from cited or promising URLs.\",\n ].join(\"\\n\");\n }\n\n if (results.length === 0) {\n return `No results found for \"${query}\" (backend: ${backend}).`;\n }\n\n const lines: string[] = [\n `Web search results for \"${query}\" (backend: ${backend}):`,\n \"\",\n ];\n for (let i = 0; i < results.length; i++) {\n const r = results[i];\n lines.push(`${i + 1}. ${r.title}`);\n lines.push(` URL: ${r.url}`);\n if (r.snippet) {\n const snippet = r.snippet.slice(0, 300).replace(/\\n+/g, \" \");\n lines.push(` ${snippet}`);\n }\n lines.push(\"\");\n }\n lines.push(\n \"Use web-request or provider-api-docs to fetch full content from promising URLs.\",\n );\n return lines.join(\"\\n\");\n },\n readOnly: true,\n },\n };\n}\n"]}
1
+ {"version":3,"file":"web-search-tool.js","sourceRoot":"","sources":["../../src/extensions/web-search-tool.ts"],"names":[],"mappings":"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","sourcesContent":["/**\n * Web-search tool — agent tool for searching the public web.\n *\n * Pluggable backends resolved at call time based on which API key is\n * configured (env var or secrets/credentials store):\n *\n * 1. Brave Search API (BRAVE_SEARCH_API_KEY)\n * 2. Tavily (TAVILY_API_KEY)\n * 3. Exa (EXA_API_KEY)\n * 4. Builder.io (connected Builder credentials)\n *\n * The first configured backend wins. If none is configured, the tool\n * returns a helpful message telling the user which keys to add.\n *\n * Connect Builder.io or register BRAVE_SEARCH_API_KEY, TAVILY_API_KEY, or\n * EXA_API_KEY via app secrets settings or environment variables.\n */\n\nimport type { ActionEntry } from \"../agent/production-agent.js\";\nimport type { CredentialContext } from \"../credentials/index.js\";\n\nexport interface WebSearchResult {\n title: string;\n url: string;\n snippet: string;\n}\n\nexport interface WebSearchToolOptions {\n /**\n * Resolve a request-scoped secret by key. When not provided the tool falls\n * back to env-var lookup only.\n */\n resolveSecret?: (key: string) => Promise<string | null>;\n /**\n * Legacy credential resolver retained for older callers.\n */\n resolveCredential?: (\n key: string,\n ctx: CredentialContext,\n ) => Promise<string | undefined>;\n /**\n * Legacy credential context callback retained for older callers.\n */\n getCredentialContext?: () => CredentialContext | null;\n /**\n * Resolve connected Builder credentials for managed web search.\n */\n resolveBuilderCredentials?: () => Promise<BuilderWebSearchCredentials>;\n /**\n * Base URL for Builder-managed web search.\n */\n getBuilderWebSearchBaseUrl?: () => string;\n /**\n * Stable attribution headers for Builder-managed API calls.\n */\n getBuilderRequestHeaders?: () => Record<string, string>;\n}\n\nconst DEFAULT_COUNT = 5;\nconst MAX_COUNT = 10;\n\ninterface BuilderWebSearchCredentials {\n privateKey: string | null;\n publicKey: string | null;\n userId?: string | null;\n}\n\nasync function resolveSearchKey(\n key: string,\n opts: WebSearchToolOptions,\n): Promise<string | undefined> {\n let usedRequestScopedResolver = false;\n // 1. Try request-scoped app secrets (user/org/workspace stored key).\n if (opts.resolveSecret) {\n usedRequestScopedResolver = true;\n try {\n const value = await opts.resolveSecret(key);\n if (value) return value;\n } catch {\n // Secret lookup failures are non-fatal; fall through to legacy/env.\n }\n }\n\n // 2. Try legacy per-request credential context.\n if (opts.resolveCredential && opts.getCredentialContext) {\n const ctx = opts.getCredentialContext();\n if (ctx) {\n try {\n const value = await opts.resolveCredential(key, ctx);\n if (value) return value;\n } catch {\n // Credential lookup failures are non-fatal; fall through to env.\n }\n }\n }\n\n if (usedRequestScopedResolver) return undefined;\n\n // 3. Fall back to env var.\n return process.env[key] || undefined;\n}\n\nasync function resolveBuilderSearchCredentials(\n opts: WebSearchToolOptions,\n): Promise<BuilderWebSearchCredentials | null> {\n if (!opts.resolveBuilderCredentials) return null;\n try {\n const creds = await opts.resolveBuilderCredentials();\n if (creds.privateKey && creds.publicKey) return creds;\n } catch {\n // Builder credential lookup failures are non-fatal; BYOK backends or the\n // setup hint below can still handle the tool call.\n }\n return null;\n}\n\n// ---------------------------------------------------------------------------\n// Backend implementations\n// ---------------------------------------------------------------------------\n\nasync function searchBrave(\n query: string,\n count: number,\n apiKey: string,\n): Promise<WebSearchResult[]> {\n const url = `https://api.search.brave.com/res/v1/web/search?q=${encodeURIComponent(query)}&count=${count}`;\n const res = await fetch(url, {\n headers: {\n Accept: \"application/json\",\n \"Accept-Encoding\": \"gzip\",\n \"X-Subscription-Token\": apiKey,\n },\n signal: AbortSignal.timeout(15_000),\n });\n if (!res.ok) {\n throw new Error(`Brave Search error ${res.status}: ${await res.text()}`);\n }\n const data = (await res.json()) as {\n web?: {\n results?: Array<{\n title?: string;\n url?: string;\n description?: string;\n }>;\n };\n };\n return (data.web?.results ?? []).map((r) => ({\n title: r.title ?? \"\",\n url: r.url ?? \"\",\n snippet: r.description ?? \"\",\n }));\n}\n\nasync function searchTavily(\n query: string,\n count: number,\n apiKey: string,\n): Promise<WebSearchResult[]> {\n const res = await fetch(\"https://api.tavily.com/search\", {\n method: \"POST\",\n headers: {\n \"Content-Type\": \"application/json\",\n },\n body: JSON.stringify({\n api_key: apiKey,\n query,\n max_results: count,\n search_depth: \"basic\",\n }),\n signal: AbortSignal.timeout(15_000),\n });\n if (!res.ok) {\n throw new Error(`Tavily error ${res.status}: ${await res.text()}`);\n }\n const data = (await res.json()) as {\n results?: Array<{\n title?: string;\n url?: string;\n content?: string;\n }>;\n };\n return (data.results ?? []).map((r) => ({\n title: r.title ?? \"\",\n url: r.url ?? \"\",\n snippet: r.content ?? \"\",\n }));\n}\n\nasync function searchExa(\n query: string,\n count: number,\n apiKey: string,\n): Promise<WebSearchResult[]> {\n const res = await fetch(\"https://api.exa.ai/search\", {\n method: \"POST\",\n headers: {\n \"Content-Type\": \"application/json\",\n \"x-api-key\": apiKey,\n },\n body: JSON.stringify({\n query,\n numResults: count,\n type: \"auto\",\n contents: { text: { maxCharacters: 400 } },\n }),\n signal: AbortSignal.timeout(15_000),\n });\n if (!res.ok) {\n throw new Error(`Exa error ${res.status}: ${await res.text()}`);\n }\n const data = (await res.json()) as {\n results?: Array<{\n title?: string;\n url?: string;\n text?: string;\n }>;\n };\n return (data.results ?? []).map((r) => ({\n title: r.title ?? \"\",\n url: r.url ?? \"\",\n snippet: r.text ?? \"\",\n }));\n}\n\nasync function searchBuilderManaged(\n query: string,\n count: number,\n credentials: BuilderWebSearchCredentials,\n opts: WebSearchToolOptions,\n): Promise<string> {\n const baseUrl =\n opts.getBuilderWebSearchBaseUrl?.() ??\n process.env.BUILDER_WEB_SEARCH_BASE_URL ??\n \"https://api.builder.io/agent-native/web-search/v1\";\n const url = new URL(\n \"search\",\n baseUrl.endsWith(\"/\") ? baseUrl : `${baseUrl}/`,\n );\n const res = await fetch(url.toString(), {\n method: \"POST\",\n headers: {\n \"Content-Type\": \"application/json\",\n Authorization: `Bearer ${credentials.privateKey}`,\n \"x-builder-api-key\": credentials.publicKey ?? \"\",\n ...(credentials.userId\n ? { \"x-builder-user-id\": credentials.userId }\n : {}),\n ...(opts.getBuilderRequestHeaders?.() ?? {}),\n },\n body: JSON.stringify({\n query,\n count,\n source: {\n appId: \"agent-native\",\n feature: \"web-search-tool\",\n },\n }),\n signal: AbortSignal.timeout(45_000),\n });\n if (!res.ok) {\n const text = await res.text().catch(() => \"\");\n throw new Error(\n `Builder web search error ${res.status}${text ? `: ${text.slice(0, 300)}` : \"\"}`,\n );\n }\n const data = (await res.json()) as {\n text?: string;\n };\n const text = data.text?.trim();\n if (!text) {\n throw new Error(\"Builder web search returned no text.\");\n }\n return text;\n}\n\n// ---------------------------------------------------------------------------\n// Tool entry factory\n// ---------------------------------------------------------------------------\n\n/**\n * Create the web-search tool entry for the agent tool registry.\n */\nexport function createWebSearchToolEntry(\n opts: WebSearchToolOptions = {},\n): Record<string, ActionEntry> {\n return {\n \"web-search\": {\n tool: {\n description:\n \"Search the public web. Use to find API documentation, endpoints, current information, or any topic. Returns ranked results from BYOK providers or a grounded Builder-managed summary. Follow up with web-request or provider-api-docs using responseMode:'markdown' or responseMode:'matches' to fetch clean text, links, or compact snippets from promising URLs. Requires either Connect Builder.io or one of: BRAVE_SEARCH_API_KEY, TAVILY_API_KEY, or EXA_API_KEY.\",\n parameters: {\n type: \"object\" as const,\n properties: {\n query: {\n type: \"string\",\n description:\n \"Search query. Be specific — include API name, version, and what you need (e.g. 'Stripe API list subscriptions endpoint').\",\n },\n count: {\n type: \"number\",\n description: `Number of results to return. Default ${DEFAULT_COUNT}, max ${MAX_COUNT}.`,\n },\n },\n required: [\"query\"],\n },\n },\n run: async (args: Record<string, string>) => {\n const query = (args.query ?? \"\").trim();\n if (!query) return \"query is required.\";\n\n const rawCount = Number(args.count);\n const count =\n Number.isFinite(rawCount) && rawCount > 0\n ? Math.min(Math.floor(rawCount), MAX_COUNT)\n : DEFAULT_COUNT;\n\n // Backend selection — first configured wins.\n const braveKey = await resolveSearchKey(\"BRAVE_SEARCH_API_KEY\", opts);\n const tavilyKey = await resolveSearchKey(\"TAVILY_API_KEY\", opts);\n const exaKey = await resolveSearchKey(\"EXA_API_KEY\", opts);\n const builderCredentials = await resolveBuilderSearchCredentials(opts);\n\n let results: WebSearchResult[];\n let backend: string;\n let managedText: string | null = null;\n\n try {\n if (braveKey) {\n results = await searchBrave(query, count, braveKey);\n backend = \"Brave Search\";\n } else if (tavilyKey) {\n results = await searchTavily(query, count, tavilyKey);\n backend = \"Tavily\";\n } else if (exaKey) {\n results = await searchExa(query, count, exaKey);\n backend = \"Exa\";\n } else if (builderCredentials) {\n managedText = await searchBuilderManaged(\n query,\n count,\n builderCredentials,\n opts,\n );\n results = [];\n backend = \"Builder.io\";\n } else {\n return [\n \"No web-search backend configured.\",\n \"Connect Builder.io in Settings, or add one of the following keys via app settings or environment variables:\",\n \" • BRAVE_SEARCH_API_KEY — https://brave.com/search/api/\",\n \" • TAVILY_API_KEY — https://tavily.com/\",\n \" • EXA_API_KEY — https://exa.ai/\",\n ].join(\"\\n\");\n }\n } catch (err: unknown) {\n const msg = err instanceof Error ? err.message : String(err);\n return `Web search failed (${msg}). Try web-request to fetch a specific URL directly.`;\n }\n\n if (managedText) {\n return [\n `Web search results for \"${query}\" (backend: ${backend}):`,\n \"\",\n managedText,\n \"\",\n \"Use web-request or provider-api-docs with responseMode:'markdown' for readable docs or responseMode:'matches' plus search for compact snippets.\",\n ].join(\"\\n\");\n }\n\n if (results.length === 0) {\n return `No results found for \"${query}\" (backend: ${backend}).`;\n }\n\n const lines: string[] = [\n `Web search results for \"${query}\" (backend: ${backend}):`,\n \"\",\n ];\n for (let i = 0; i < results.length; i++) {\n const r = results[i];\n lines.push(`${i + 1}. ${r.title}`);\n lines.push(` URL: ${r.url}`);\n if (r.snippet) {\n const snippet = r.snippet.slice(0, 300).replace(/\\n+/g, \" \");\n lines.push(` ${snippet}`);\n }\n lines.push(\"\");\n }\n lines.push(\n \"Use web-request or provider-api-docs with responseMode:'markdown' for readable docs or responseMode:'matches' plus search for compact snippets.\",\n );\n return lines.join(\"\\n\");\n },\n readOnly: true,\n },\n };\n}\n"]}
@@ -1 +1 @@
1
- {"version":3,"file":"build-server.d.ts","sourceRoot":"","sources":["../../src/mcp/build-server.ts"],"names":[],"mappings":"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"}
1
+ {"version":3,"file":"build-server.d.ts","sourceRoot":"","sources":["../../src/mcp/build-server.ts"],"names":[],"mappings":"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"}
@@ -21,7 +21,7 @@ import { isMcpActionResult } from "../mcp-client/app-result.js";
21
21
  import { MCP_APP_EXTENSION_ID, MCP_APP_MIME_TYPE, MCP_APP_RESOURCE_URI_META_KEY, } from "../action.js";
22
22
  import { MCP_APP_REQUEST_ORIGIN_CSP_SOURCE } from "./embed-app.js";
23
23
  import { getRequestContext, getRequestOrgId, getRequestUserEmail, runWithRequestContext, } from "../server/request-context.js";
24
- import { buildDeepLink, toAbsoluteOpenUrl, toDesktopOpenUrl, } from "../server/deep-link.js";
24
+ import { buildDeepLink, toAbsoluteOpenUrl, toDesktopOpenUrl, toVsCodeOpenUrl, } from "../server/deep-link.js";
25
25
  import { isAgentNativeOpenDeepLink, withCollapsedAgentSidebarParam, } from "../shared/agent-sidebar-url.js";
26
26
  import { MCP_APP_CHAT_BRIDGE_QUERY_PARAM } from "../shared/embed-auth.js";
27
27
  import { getBuiltinCrossAppTools } from "./builtin-tools.js";
@@ -298,6 +298,7 @@ function mcpAppEmbedOpenLinkMeta(result, resource, meta) {
298
298
  ...(view ? { view } : {}),
299
299
  webUrl: safeOpenUrl,
300
300
  desktopUrl: desktopDeepLinkUrl ?? safeOpenUrl,
301
+ vscodeUrl: toVsCodeOpenUrl(safeOpenUrl),
301
302
  },
302
303
  }
303
304
  : {}),
@@ -371,6 +372,7 @@ export function buildLinkArtifacts(entry, args, result, meta) {
371
372
  : lk.url;
372
373
  const webUrl = toAbsoluteOpenUrl(linkUrl, meta?.origin);
373
374
  const desktopUrl = toDesktopOpenUrl(linkUrl);
375
+ const vscodeUrl = toVsCodeOpenUrl(webUrl);
374
376
  const markdownUrl = meta?.target === "desktop" ? desktopUrl : webUrl;
375
377
  return {
376
378
  block: { type: "text", text: `\n\n[${lk.label} →](${markdownUrl})` },
@@ -380,6 +382,7 @@ export function buildLinkArtifacts(entry, args, result, meta) {
380
382
  view: lk.view,
381
383
  webUrl,
382
384
  desktopUrl,
385
+ vscodeUrl,
383
386
  },
384
387
  },
385
388
  };