gobot-channel-bgos 0.3.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 (90) hide show
  1. package/README.md +121 -0
  2. package/dist/adapter.d.ts +125 -0
  3. package/dist/adapter.d.ts.map +1 -0
  4. package/dist/adapter.js +291 -0
  5. package/dist/adapter.js.map +1 -0
  6. package/dist/agent-hints.d.ts +26 -0
  7. package/dist/agent-hints.d.ts.map +1 -0
  8. package/dist/agent-hints.js +137 -0
  9. package/dist/agent-hints.js.map +1 -0
  10. package/dist/approval-handler.d.ts +52 -0
  11. package/dist/approval-handler.d.ts.map +1 -0
  12. package/dist/approval-handler.js +79 -0
  13. package/dist/approval-handler.js.map +1 -0
  14. package/dist/attachment-bridge.d.ts +58 -0
  15. package/dist/attachment-bridge.d.ts.map +1 -0
  16. package/dist/attachment-bridge.js +197 -0
  17. package/dist/attachment-bridge.js.map +1 -0
  18. package/dist/bgos-api.d.ts +97 -0
  19. package/dist/bgos-api.d.ts.map +1 -0
  20. package/dist/bgos-api.js +106 -0
  21. package/dist/bgos-api.js.map +1 -0
  22. package/dist/bgos-ws.d.ts +47 -0
  23. package/dist/bgos-ws.d.ts.map +1 -0
  24. package/dist/bgos-ws.js +135 -0
  25. package/dist/bgos-ws.js.map +1 -0
  26. package/dist/catalog-sync.d.ts +26 -0
  27. package/dist/catalog-sync.d.ts.map +1 -0
  28. package/dist/catalog-sync.js +24 -0
  29. package/dist/catalog-sync.js.map +1 -0
  30. package/dist/commands-sync.d.ts +24 -0
  31. package/dist/commands-sync.d.ts.map +1 -0
  32. package/dist/commands-sync.js +43 -0
  33. package/dist/commands-sync.js.map +1 -0
  34. package/dist/config.d.ts +4 -0
  35. package/dist/config.d.ts.map +1 -0
  36. package/dist/config.js +36 -0
  37. package/dist/config.js.map +1 -0
  38. package/dist/create-adapter.d.ts +37 -0
  39. package/dist/create-adapter.d.ts.map +1 -0
  40. package/dist/create-adapter.js +48 -0
  41. package/dist/create-adapter.js.map +1 -0
  42. package/dist/default-commands.d.ts +54 -0
  43. package/dist/default-commands.d.ts.map +1 -0
  44. package/dist/default-commands.js +93 -0
  45. package/dist/default-commands.js.map +1 -0
  46. package/dist/home-channel.d.ts +33 -0
  47. package/dist/home-channel.d.ts.map +1 -0
  48. package/dist/home-channel.js +43 -0
  49. package/dist/home-channel.js.map +1 -0
  50. package/dist/inbound-handler.d.ts +125 -0
  51. package/dist/inbound-handler.d.ts.map +1 -0
  52. package/dist/inbound-handler.js +196 -0
  53. package/dist/inbound-handler.js.map +1 -0
  54. package/dist/index.d.ts +37 -0
  55. package/dist/index.d.ts.map +1 -0
  56. package/dist/index.js +36 -0
  57. package/dist/index.js.map +1 -0
  58. package/dist/last-id-store.d.ts +26 -0
  59. package/dist/last-id-store.d.ts.map +1 -0
  60. package/dist/last-id-store.js +86 -0
  61. package/dist/last-id-store.js.map +1 -0
  62. package/dist/load-config.d.ts +15 -0
  63. package/dist/load-config.d.ts.map +1 -0
  64. package/dist/load-config.js +67 -0
  65. package/dist/load-config.js.map +1 -0
  66. package/dist/outbound.d.ts +143 -0
  67. package/dist/outbound.d.ts.map +1 -0
  68. package/dist/outbound.js +240 -0
  69. package/dist/outbound.js.map +1 -0
  70. package/dist/pair-cli.d.ts +30 -0
  71. package/dist/pair-cli.d.ts.map +1 -0
  72. package/dist/pair-cli.js +98 -0
  73. package/dist/pair-cli.js.map +1 -0
  74. package/dist/proactive.d.ts +81 -0
  75. package/dist/proactive.d.ts.map +1 -0
  76. package/dist/proactive.js +197 -0
  77. package/dist/proactive.js.map +1 -0
  78. package/dist/reseed-cli.d.ts +4 -0
  79. package/dist/reseed-cli.d.ts.map +1 -0
  80. package/dist/reseed-cli.js +157 -0
  81. package/dist/reseed-cli.js.map +1 -0
  82. package/dist/tool-progress.d.ts +103 -0
  83. package/dist/tool-progress.d.ts.map +1 -0
  84. package/dist/tool-progress.js +216 -0
  85. package/dist/tool-progress.js.map +1 -0
  86. package/dist/types.d.ts +205 -0
  87. package/dist/types.d.ts.map +1 -0
  88. package/dist/types.js +16 -0
  89. package/dist/types.js.map +1 -0
  90. package/package.json +43 -0
package/README.md ADDED
@@ -0,0 +1,121 @@
1
+ # gobot-channel-bgos
2
+
3
+ BGOS channel adapter for [Gobot](https://github.com/autonomee/gobot) — Socket.IO + REST client, full outbound modality coverage (text, inline buttons, approvals, ask-user-input pop-under, files/images/videos, typing), and a pair-CLI for first-time setup.
4
+
5
+ The fork ([`BrandGrowthOS/gobot-bgos-fork`](https://github.com/BrandGrowthOS/gobot-bgos-fork) — private) wires this package into Gobot's existing message pipeline. Telegram and BGOS run side-by-side; replies always return to whichever channel the user wrote in.
6
+
7
+ ## Install
8
+
9
+ ```bash
10
+ npm i -g gobot-channel-bgos
11
+ ```
12
+
13
+ The package is published to npm as `gobot-channel-bgos`. The fork lists it under `optionalDependencies`, so a stock Gobot install still runs without it (BGOS support stays inert until the package is present).
14
+
15
+ ## Pair
16
+
17
+ After standing up Gobot on your host (Mac mini, VPS, whatever), generate a pair code in BGOS (Integrations screen → "Pair Gobot") and run:
18
+
19
+ ```bash
20
+ gobot-pair-bgos BGOS-XXXX-YY --device-label mac-mini
21
+ ```
22
+
23
+ This:
24
+
25
+ 1. POSTs `/integrations/pair-exchange` with the code + your device label.
26
+ 2. Writes the pairing token to `~/.gobot/secrets/bgos.json` (mode 0600).
27
+ 3. Exits 0 on success, non-zero with a diagnostic on failure.
28
+
29
+ ## Environment variables
30
+
31
+ The adapter resolves config in order: explicit constructor arg → env var → `~/.gobot/secrets/bgos.json`.
32
+
33
+ | Var | Default | Purpose |
34
+ |---|---|---|
35
+ | `BGOS_PAIRING_TOKEN` | _from secrets file_ | The token written by `gobot-pair-bgos`. |
36
+ | `BGOS_BASE_URL` | `https://api.brandgrowthos.ai` | BGOS backend root. |
37
+ | `GOBOT_HOME` | `~/.gobot` | Where the adapter persists state (`bgos_last_id` cursor + secrets dir). |
38
+ | `GOBOT_HOME_CHANNEL` | `both` | Destination for proactive (no-origin) messages: `telegram` \| `bgos` \| `both`. |
39
+ | `GOBOT_POLL_INTERVAL` | `5` (seconds) | REST backfill interval. Set to `0` to disable polling once the server-side WS push gap is fixed. |
40
+
41
+ ## Prerequisites
42
+
43
+ - The fork (`BrandGrowthOS/gobot-bgos-fork`) must be checked out and running on the host. The fork's loader auto-discovers `gobot-channel-bgos` and wires the adapter into Gobot's bootstrap.
44
+ - Bun 1.x (Gobot's runtime) — npm-installed packages work fine.
45
+ - A reachable BGOS backend (production by default; point `BGOS_BASE_URL` elsewhere for testing).
46
+
47
+ ## Architecture in one diagram
48
+
49
+ ```
50
+ ┌────────────────── Gobot host process (Bun) ───────────────────┐
51
+ │ │
52
+ │ grammY Telegram handler ──┐ │
53
+ │ ▼ │
54
+ │ ┌──────────────────────────────────────────────────────────┐ │
55
+ │ │ processMessageForAgent({ origin, agentRoute, text, │ │
56
+ │ │ attachments, replyHandle, ... })│ │
57
+ │ │ — fork-exported wrapper around Gobot's Claude pipeline │ │
58
+ │ └──────────────────────────────────────────────────────────┘ │
59
+ │ ▲ │
60
+ │ │ │
61
+ │ ┌──────────────────── BGOSAdapter ───────────────────────┐ │
62
+ │ │ bgos-ws.ts (Socket.IO) ◀── REST backfill cursor ◀──── │ │
63
+ │ │ bgos-api.ts (REST) │ │
64
+ │ │ outbound.ts: sendText / sendButtons / sendApproval ... │ │
65
+ │ │ inbound-handler.ts: builds replyHandle, calls dispatch │ │
66
+ │ └────────────────────────────────────────────────────────┘ │
67
+ └───────────────────────────────────────────────────────────────┘
68
+
69
+
70
+ BGOS backend (api.brandgrowthos.ai)
71
+ ```
72
+
73
+ ## Troubleshooting
74
+
75
+ **No replies in BGOS, but Telegram works:**
76
+ - Tail `~/.gobot/logs/bgos-daemon.log` (the fork's loader writes here). Look for `whoami OK`, `connected`, `catalog pushed`.
77
+ - Confirm `~/.gobot/secrets/bgos.json` exists and is readable: `cat ~/.gobot/secrets/bgos.json | jq .pairingId`.
78
+ - Re-pair via the BGOS Integrations card if the pairing was revoked — adapter logs `PAIRING_REVOKED` on 401.
79
+
80
+ **Replies are duplicated after every restart:**
81
+ - The persisted cursor at `$GOBOT_HOME/bgos_last_id` failed to update. This file MUST advance with every processed message — if it stays at 0, every restart replays history.
82
+ - Reset cursor manually: `echo <max-message-id> > ~/.gobot/bgos_last_id`. Or `rm` it to start fresh (will replay everything once).
83
+
84
+ **Logs:** the fork pipes adapter output through Gobot's logger. On a default Mac install, look in `~/.gobot/logs/`.
85
+
86
+ **Reset everything:**
87
+ ```bash
88
+ rm -rf ~/.gobot/secrets ~/.gobot/bgos_last_id
89
+ gobot-pair-bgos <NEW-CODE>
90
+ # restart Gobot
91
+ ```
92
+
93
+ ## What lives in this package
94
+
95
+ | Module | Role |
96
+ |---|---|
97
+ | `BGOSAdapter` (`src/adapter.ts`) | Lifecycle, route map, dispatch injection, poll loop |
98
+ | `BgosOutbound` (`src/outbound.ts`) | All outbound modalities |
99
+ | `inbound-handler.ts` | WS event → Gobot dispatch translator |
100
+ | `attachment-bridge.ts` | BGOS files ⇄ local file paths (S3 + base64) |
101
+ | `agent-hints.ts` | System-prompt addendum injected at dispatch |
102
+ | `default-commands.ts` | 7 seeded slash commands |
103
+ | `last-id-store.ts` | Persistent inbound cursor (CRITICAL — see source) |
104
+ | `pair-cli.ts` | `gobot-pair-bgos` CLI |
105
+ | `home-channel.ts` | Resolves `GOBOT_HOME_CHANNEL` for proactive messages |
106
+
107
+ ## Development
108
+
109
+ ```bash
110
+ git clone https://github.com/BrandGrowthOS/gobot-channel-bgos
111
+ cd gobot-channel-bgos
112
+ npm install
113
+ npm test # vitest
114
+ npm run build # tsc + finalize-daemon
115
+ ```
116
+
117
+ The package is also mirrored inside the BGOS monorepo at `gobot-channel-bgos/` — the public repo is the source of truth (matching the Hermes pattern).
118
+
119
+ ## License
120
+
121
+ MIT.
@@ -0,0 +1,125 @@
1
+ /**
2
+ * Main adapter for the Gobot ↔ BGOS channel.
3
+ *
4
+ * Lifecycle:
5
+ * 1. Fork instantiates `new BGOSAdapter(config)`. Optionally calls
6
+ * `setDispatch(fn)` immediately afterwards if dispatch is ready.
7
+ * 2. Fork calls `await adapter.start()`. Adapter:
8
+ * - GET /integrations/me to populate the assistant→agent_route map
9
+ * - opens the Socket.IO connection
10
+ * - pushes the agent catalog (see `setCatalog()` for source)
11
+ * - seeds default slash-commands for empty manifests
12
+ * - replays missed messages via REST backfill from the persisted
13
+ * cursor (CRITICAL — see last-id-store)
14
+ * - starts a poll loop fallback for the server-side WS push gap
15
+ * (mirrors the Hermes adapter; toggle via GOBOT_POLL_INTERVAL)
16
+ * 3. Inbound events flow through `inbound-handler.ts` which calls the
17
+ * registered dispatch function.
18
+ * 4. Fork calls `await adapter.stop()` on shutdown.
19
+ *
20
+ * Reference: `hermes-channel-bgos/src/hermes_channel_bgos/bgos_adapter.py`
21
+ * — same shape, ported to TypeScript with Node-idiomatic event handling.
22
+ */
23
+ import { BgosApi } from "./bgos-api.js";
24
+ import { BgosOutbound } from "./outbound.js";
25
+ import { ApprovalHandler } from "./approval-handler.js";
26
+ import { CommandsSync } from "./commands-sync.js";
27
+ import { ToolProgressOrchestrator } from "./tool-progress.js";
28
+ import { type CatalogAgent } from "./catalog-sync.js";
29
+ import { type CommandSeedMode } from "./default-commands.js";
30
+ import { type DispatchFn } from "./inbound-handler.js";
31
+ /** Public configuration the fork passes in. Mirrors `PluginConfig` plus
32
+ * optional Gobot-specific knobs. */
33
+ export interface BgosConfig {
34
+ /** Backend base URL (e.g. https://api.brandgrowthos.ai). */
35
+ baseUrl?: string;
36
+ /** Pairing token from `~/.gobot/secrets/bgos.json`. */
37
+ pairingToken?: string;
38
+ /** Reconnect tuning. Defaults: 1s initial, 30s max. */
39
+ reconnect?: {
40
+ initialDelayMs?: number;
41
+ maxDelayMs?: number;
42
+ };
43
+ /** Optional agent catalog to push on connect. If omitted, the fork
44
+ * can call `setCatalog([...])` later or the catalog stays whatever
45
+ * was registered at pair time. */
46
+ agents?: CatalogAgent[];
47
+ /** Optional system-prompt prefix per agent_route. Adapter appends
48
+ * `BGOS_AGENT_HINTS` to whatever this returns at dispatch time. */
49
+ getSystemPrompt?: (agentRoute: string) => string;
50
+ /**
51
+ * Override the default-commands seed strategy. Defaults to whatever
52
+ * `GOBOT_BGOS_RESEED_COMMANDS` resolves to (which itself defaults to
53
+ * `"auto"`).
54
+ *
55
+ * Use `"safe"` to also seed when the backend's `whoami` doesn't return
56
+ * `command_count` (older deploys), or `"always"` to force a reseed
57
+ * after fixing a stuck manifest.
58
+ */
59
+ commandSeedMode?: CommandSeedMode;
60
+ }
61
+ export declare class BGOSAdapter {
62
+ /** REST client — public so the fork can use it for ad-hoc operations
63
+ * (e.g. renaming chats, fetching history). */
64
+ readonly api: BgosApi;
65
+ /** Outbound modalities — public so proactive (no-origin) cron paths in
66
+ * the fork can push messages directly without an inbound trigger. */
67
+ readonly outbound: BgosOutbound;
68
+ /** Approval bridge — public so the fork's task-queue can register +
69
+ * resolve approvals without re-routing through `_handle_callback`. */
70
+ readonly approvals: ApprovalHandler;
71
+ /** Slash-command manifest sync — public so the fork can call
72
+ * `commandsSync.schedule(assistantId, commands)` whenever Gobot's
73
+ * user-defined commands change. */
74
+ readonly commandsSync: CommandsSync;
75
+ /** Tool-progress card orchestrator — wired into `ReplyHandle`
76
+ * (sendToolStart + finalizeTurn). The fork's BGOS dispatch should
77
+ * call replyHandle.sendToolStart(toolName) per LIVE tool_use event
78
+ * (via callClaudeStreaming's onToolStart hook) and finalizeTurn()
79
+ * after the agent's text reply lands. Public so proactive paths can
80
+ * also emit cards if they ever run tools server-side. */
81
+ readonly toolProgress: ToolProgressOrchestrator;
82
+ private readonly cfg;
83
+ private readonly ws;
84
+ private readonly assistantToRoute;
85
+ private dispatch;
86
+ private catalog;
87
+ private getSystemPrompt;
88
+ private commandSeedModeOverride;
89
+ private pairingId;
90
+ private pollTimer;
91
+ private started;
92
+ constructor(input?: BgosConfig | unknown);
93
+ /** Resolve the effective seed mode — explicit override wins over env. */
94
+ private getCommandSeedMode;
95
+ /** The fork calls this at boot to install Gobot's dispatch function.
96
+ * Safe to call multiple times — last call wins. */
97
+ setDispatch(fn: DispatchFn): void;
98
+ /** Replace the agent catalog (the next `start()` or call to
99
+ * `pushCatalog()` will use it). */
100
+ setCatalog(agents: CatalogAgent[]): void;
101
+ /** Look up the bound agent_route for an assistant id. Returns null
102
+ * for unbound or unknown assistants. Also exposed publicly so the
103
+ * fork's reply-side code can correlate. */
104
+ getRouteForAssistant(assistantId: number): string | null;
105
+ /** Snapshot of the assistant→agent_route map. Defensive copy. */
106
+ get routeMap(): ReadonlyMap<number, string>;
107
+ start(): Promise<void>;
108
+ stop(): Promise<void>;
109
+ /**
110
+ * Force-replace the slash-command manifest with `DEFAULT_COMMANDS` for
111
+ * every bound assistant (or just the ones in `assistantIds`). Useful
112
+ * when the BGOS slash picker is missing commands and you need to reset
113
+ * without re-pairing.
114
+ *
115
+ * Idempotent — safe to call repeatedly. Returns the per-assistant
116
+ * outcome so callers can log / surface failures.
117
+ */
118
+ reseedAllCommands(assistantIds?: ReadonlyArray<number>): Promise<Array<{
119
+ assistantId: number;
120
+ ok: boolean;
121
+ error?: string;
122
+ }>>;
123
+ private seedDefaultCommands;
124
+ }
125
+ //# sourceMappingURL=adapter.d.ts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"adapter.d.ts","sourceRoot":"","sources":["../src/adapter.ts"],"names":[],"mappings":"AAAA;;;;;;;;;;;;;;;;;;;;;GAqBG;AACH,OAAO,EAAE,OAAO,EAAE,MAAM,eAAe,CAAC;AAExC,OAAO,EAAE,YAAY,EAAE,MAAM,eAAe,CAAC;AAC7C,OAAO,EAAE,eAAe,EAAE,MAAM,uBAAuB,CAAC;AACxD,OAAO,EAAE,YAAY,EAAE,MAAM,oBAAoB,CAAC;AAClD,OAAO,EAAE,wBAAwB,EAAE,MAAM,oBAAoB,CAAC;AAC9D,OAAO,EAAe,KAAK,YAAY,EAAE,MAAM,mBAAmB,CAAC;AACnE,OAAO,EAIL,KAAK,eAAe,EACrB,MAAM,uBAAuB,CAAC;AAC/B,OAAO,EAEL,KAAK,UAAU,EAChB,MAAM,sBAAsB,CAAC;AAa9B;qCACqC;AACrC,MAAM,WAAW,UAAU;IACzB,4DAA4D;IAC5D,OAAO,CAAC,EAAE,MAAM,CAAC;IACjB,uDAAuD;IACvD,YAAY,CAAC,EAAE,MAAM,CAAC;IACtB,uDAAuD;IACvD,SAAS,CAAC,EAAE;QACV,cAAc,CAAC,EAAE,MAAM,CAAC;QACxB,UAAU,CAAC,EAAE,MAAM,CAAC;KACrB,CAAC;IACF;;uCAEmC;IACnC,MAAM,CAAC,EAAE,YAAY,EAAE,CAAC;IACxB;wEACoE;IACpE,eAAe,CAAC,EAAE,CAAC,UAAU,EAAE,MAAM,KAAK,MAAM,CAAC;IACjD;;;;;;;;OAQG;IACH,eAAe,CAAC,EAAE,eAAe,CAAC;CACnC;AAED,qBAAa,WAAW;IACtB;mDAC+C;IAC/C,QAAQ,CAAC,GAAG,EAAE,OAAO,CAAC;IACtB;0EACsE;IACtE,QAAQ,CAAC,QAAQ,EAAE,YAAY,CAAC;IAChC;2EACuE;IACvE,QAAQ,CAAC,SAAS,EAAE,eAAe,CAAC;IACpC;;wCAEoC;IACpC,QAAQ,CAAC,YAAY,EAAE,YAAY,CAAC;IACpC;;;;;8DAK0D;IAC1D,QAAQ,CAAC,YAAY,EAAE,wBAAwB,CAAC;IAEhD,OAAO,CAAC,QAAQ,CAAC,GAAG,CAAe;IACnC,OAAO,CAAC,QAAQ,CAAC,EAAE,CAAS;IAC5B,OAAO,CAAC,QAAQ,CAAC,gBAAgB,CAA6B;IAC9D,OAAO,CAAC,QAAQ,CAA2B;IAC3C,OAAO,CAAC,OAAO,CAAiB;IAChC,OAAO,CAAC,eAAe,CAA4B;IACnD,OAAO,CAAC,uBAAuB,CAAgC;IAC/D,OAAO,CAAC,SAAS,CAAuB;IACxC,OAAO,CAAC,SAAS,CAA+B;IAChD,OAAO,CAAC,OAAO,CAAS;gBAEZ,KAAK,GAAE,UAAU,GAAG,OAAmB;IAkBnD,yEAAyE;IACzE,OAAO,CAAC,kBAAkB;IAI1B;wDACoD;IACpD,WAAW,CAAC,EAAE,EAAE,UAAU,GAAG,IAAI;IAIjC;wCACoC;IACpC,UAAU,CAAC,MAAM,EAAE,YAAY,EAAE,GAAG,IAAI;IAIxC;;gDAE4C;IAC5C,oBAAoB,CAAC,WAAW,EAAE,MAAM,GAAG,MAAM,GAAG,IAAI;IAIxD,iEAAiE;IACjE,IAAI,QAAQ,IAAI,WAAW,CAAC,MAAM,EAAE,MAAM,CAAC,CAE1C;IAMK,KAAK,IAAI,OAAO,CAAC,IAAI,CAAC;IAyHtB,IAAI,IAAI,OAAO,CAAC,IAAI,CAAC;IAiB3B;;;;;;;;OAQG;IACG,iBAAiB,CACrB,YAAY,CAAC,EAAE,aAAa,CAAC,MAAM,CAAC,GACnC,OAAO,CAAC,KAAK,CAAC;QAAE,WAAW,EAAE,MAAM,CAAC;QAAC,EAAE,EAAE,OAAO,CAAC;QAAC,KAAK,CAAC,EAAE,MAAM,CAAA;KAAE,CAAC,CAAC;YA2CzD,mBAAmB;CAuBlC"}
@@ -0,0 +1,291 @@
1
+ /**
2
+ * Main adapter for the Gobot ↔ BGOS channel.
3
+ *
4
+ * Lifecycle:
5
+ * 1. Fork instantiates `new BGOSAdapter(config)`. Optionally calls
6
+ * `setDispatch(fn)` immediately afterwards if dispatch is ready.
7
+ * 2. Fork calls `await adapter.start()`. Adapter:
8
+ * - GET /integrations/me to populate the assistant→agent_route map
9
+ * - opens the Socket.IO connection
10
+ * - pushes the agent catalog (see `setCatalog()` for source)
11
+ * - seeds default slash-commands for empty manifests
12
+ * - replays missed messages via REST backfill from the persisted
13
+ * cursor (CRITICAL — see last-id-store)
14
+ * - starts a poll loop fallback for the server-side WS push gap
15
+ * (mirrors the Hermes adapter; toggle via GOBOT_POLL_INTERVAL)
16
+ * 3. Inbound events flow through `inbound-handler.ts` which calls the
17
+ * registered dispatch function.
18
+ * 4. Fork calls `await adapter.stop()` on shutdown.
19
+ *
20
+ * Reference: `hermes-channel-bgos/src/hermes_channel_bgos/bgos_adapter.py`
21
+ * — same shape, ported to TypeScript with Node-idiomatic event handling.
22
+ */
23
+ import { BgosApi } from "./bgos-api.js";
24
+ import { BgosWs } from "./bgos-ws.js";
25
+ import { BgosOutbound } from "./outbound.js";
26
+ import { ApprovalHandler } from "./approval-handler.js";
27
+ import { CommandsSync } from "./commands-sync.js";
28
+ import { ToolProgressOrchestrator } from "./tool-progress.js";
29
+ import { syncCatalog } from "./catalog-sync.js";
30
+ import { DEFAULT_COMMANDS, resolveCommandSeedMode, shouldSeedDefaults, } from "./default-commands.js";
31
+ import { createInboundHandler, } from "./inbound-handler.js";
32
+ import { loadLastId } from "./last-id-store.js";
33
+ import { loadConfigFromEnv, loadConfigFromPluginCfg, } from "./config.js";
34
+ export class BGOSAdapter {
35
+ /** REST client — public so the fork can use it for ad-hoc operations
36
+ * (e.g. renaming chats, fetching history). */
37
+ api;
38
+ /** Outbound modalities — public so proactive (no-origin) cron paths in
39
+ * the fork can push messages directly without an inbound trigger. */
40
+ outbound;
41
+ /** Approval bridge — public so the fork's task-queue can register +
42
+ * resolve approvals without re-routing through `_handle_callback`. */
43
+ approvals;
44
+ /** Slash-command manifest sync — public so the fork can call
45
+ * `commandsSync.schedule(assistantId, commands)` whenever Gobot's
46
+ * user-defined commands change. */
47
+ commandsSync;
48
+ /** Tool-progress card orchestrator — wired into `ReplyHandle`
49
+ * (sendToolStart + finalizeTurn). The fork's BGOS dispatch should
50
+ * call replyHandle.sendToolStart(toolName) per LIVE tool_use event
51
+ * (via callClaudeStreaming's onToolStart hook) and finalizeTurn()
52
+ * after the agent's text reply lands. Public so proactive paths can
53
+ * also emit cards if they ever run tools server-side. */
54
+ toolProgress;
55
+ cfg;
56
+ ws;
57
+ assistantToRoute = new Map();
58
+ dispatch = null;
59
+ catalog;
60
+ getSystemPrompt;
61
+ commandSeedModeOverride = null;
62
+ pairingId = null;
63
+ pollTimer = null;
64
+ started = false;
65
+ constructor(input = undefined) {
66
+ this.cfg =
67
+ input !== undefined
68
+ ? loadConfigFromPluginCfg(input)
69
+ : loadConfigFromEnv();
70
+ this.api = new BgosApi(this.cfg);
71
+ this.ws = new BgosWs(this.cfg, this.api);
72
+ this.outbound = new BgosOutbound(this.api);
73
+ this.approvals = new ApprovalHandler(this.outbound);
74
+ this.commandsSync = new CommandsSync(this.api);
75
+ this.toolProgress = new ToolProgressOrchestrator(this.api);
76
+ const inputCfg = input ?? {};
77
+ this.catalog = inputCfg.agents ?? [];
78
+ this.getSystemPrompt = inputCfg.getSystemPrompt ?? (() => "");
79
+ this.commandSeedModeOverride = inputCfg.commandSeedMode ?? null;
80
+ }
81
+ /** Resolve the effective seed mode — explicit override wins over env. */
82
+ getCommandSeedMode() {
83
+ return this.commandSeedModeOverride ?? resolveCommandSeedMode();
84
+ }
85
+ /** The fork calls this at boot to install Gobot's dispatch function.
86
+ * Safe to call multiple times — last call wins. */
87
+ setDispatch(fn) {
88
+ this.dispatch = fn;
89
+ }
90
+ /** Replace the agent catalog (the next `start()` or call to
91
+ * `pushCatalog()` will use it). */
92
+ setCatalog(agents) {
93
+ this.catalog = agents;
94
+ }
95
+ /** Look up the bound agent_route for an assistant id. Returns null
96
+ * for unbound or unknown assistants. Also exposed publicly so the
97
+ * fork's reply-side code can correlate. */
98
+ getRouteForAssistant(assistantId) {
99
+ return this.assistantToRoute.get(assistantId) ?? null;
100
+ }
101
+ /** Snapshot of the assistant→agent_route map. Defensive copy. */
102
+ get routeMap() {
103
+ return new Map(this.assistantToRoute);
104
+ }
105
+ // -------------------------------------------------------------------
106
+ // Lifecycle
107
+ // -------------------------------------------------------------------
108
+ async start() {
109
+ if (this.started)
110
+ return;
111
+ this.started = true;
112
+ // 1. whoami — populate route map + capture pairing id
113
+ const seedMode = this.getCommandSeedMode();
114
+ const emptyManifestAssistantIds = [];
115
+ try {
116
+ const me = await this.api.whoami();
117
+ this.pairingId = me.pairing_id;
118
+ for (const a of me.assistants ?? []) {
119
+ if (a.agent_route) {
120
+ this.assistantToRoute.set(a.assistant_id, a.agent_route);
121
+ }
122
+ if (shouldSeedDefaults(a.command_count, seedMode)) {
123
+ emptyManifestAssistantIds.push(a.assistant_id);
124
+ }
125
+ }
126
+ // eslint-disable-next-line no-console
127
+ console.log("[gobot-channel-bgos] whoami complete", {
128
+ assistantCount: me.assistants?.length ?? 0,
129
+ seedMode,
130
+ willSeed: emptyManifestAssistantIds.length,
131
+ assistants: (me.assistants ?? []).map((a) => ({
132
+ id: a.assistant_id,
133
+ route: a.agent_route,
134
+ commandCount: a.command_count,
135
+ })),
136
+ });
137
+ }
138
+ catch (err) {
139
+ // eslint-disable-next-line no-console
140
+ console.warn("[gobot-channel-bgos] whoami failed (non-fatal):", err instanceof Error ? err.message : String(err));
141
+ }
142
+ // 2. Wire WS event handlers BEFORE connecting so we don't miss
143
+ // anything the server emits in the window between connect + handler
144
+ // registration.
145
+ const inboundHandler = createInboundHandler({
146
+ outbound: this.outbound,
147
+ getRouteForAssistant: (id) => this.getRouteForAssistant(id),
148
+ getDispatch: () => this.dispatch,
149
+ getSystemPrompt: (route) => this.getSystemPrompt(route),
150
+ toolProgress: this.toolProgress,
151
+ });
152
+ this.ws.on("inbound_message", (msg) => {
153
+ void inboundHandler(msg);
154
+ });
155
+ this.ws.on("callback_result", (p) => {
156
+ // Approval clicks (`__approval__:*`) are absorbed by the approvals
157
+ // bridge; non-approval clicks fall through (the agent will see the
158
+ // resulting `inbound_message` if the backend synthesizes one).
159
+ this.approvals.handleCallbackResult(p);
160
+ });
161
+ this.ws.on("assistant_bound", (p) => {
162
+ this.assistantToRoute.set(p.assistantId, p.agentRoute);
163
+ // Newly-bound assistants always start with zero commands, so we
164
+ // can safely seed the defaults.
165
+ void this.seedDefaultCommands(p.assistantId, "bind");
166
+ });
167
+ this.ws.on("assistant_unbound", (p) => {
168
+ this.assistantToRoute.delete(p.assistantId);
169
+ });
170
+ this.ws.on("commands_updated", (_p) => {
171
+ // No-op — the user changed commands via the BGOS UI; nothing for
172
+ // the adapter to do. Hook is reserved so the fork can subscribe
173
+ // later if it needs to re-render a local picker.
174
+ });
175
+ this.ws.on("error", (err) => {
176
+ // eslint-disable-next-line no-console
177
+ console.warn("[gobot-channel-bgos] WS error:", err instanceof Error ? err.message : String(err));
178
+ });
179
+ // 3. Seed last-seen cursor + connect WS
180
+ this.ws.setLastSeen(loadLastId());
181
+ await this.ws.connect();
182
+ // 4. Push the agent catalog if we have one + a pairing id
183
+ if (this.pairingId !== null && this.catalog.length > 0) {
184
+ await syncCatalog(this.api, this.pairingId, this.catalog);
185
+ }
186
+ // 5. Seed defaults for any assistant whose manifest is empty
187
+ for (const id of emptyManifestAssistantIds) {
188
+ await this.seedDefaultCommands(id, "startup");
189
+ }
190
+ // 6. Run the initial backfill — this is the load-bearing step that
191
+ // replays messages that arrived while the daemon was down. Cursor
192
+ // came from disk via setLastSeen above.
193
+ await this.ws.triggerBackfill();
194
+ // 7. Start poll-loop fallback. Server currently doesn't deliver
195
+ // `inbound_message` to integration sockets (Hermes-shipped workaround;
196
+ // see `hermes_integration_shipped.md`). Until that's fixed, we poll
197
+ // REST every GOBOT_POLL_INTERVAL seconds.
198
+ const intervalRaw = process.env.GOBOT_POLL_INTERVAL;
199
+ const interval = intervalRaw !== undefined && intervalRaw !== ""
200
+ ? Number(intervalRaw)
201
+ : 5;
202
+ if (Number.isFinite(interval) && interval > 0) {
203
+ this.pollTimer = setInterval(() => {
204
+ void this.ws.triggerBackfill();
205
+ }, interval * 1000);
206
+ // Don't keep Node alive just for this timer.
207
+ this.pollTimer.unref?.();
208
+ }
209
+ }
210
+ async stop() {
211
+ if (!this.started)
212
+ return;
213
+ this.started = false;
214
+ if (this.pollTimer !== null) {
215
+ clearInterval(this.pollTimer);
216
+ this.pollTimer = null;
217
+ }
218
+ this.approvals.shutdown();
219
+ this.ws.disconnect();
220
+ this.toolProgress.dispose();
221
+ try {
222
+ await this.commandsSync.flushAll();
223
+ }
224
+ catch {
225
+ /* swallow on shutdown — best effort */
226
+ }
227
+ }
228
+ /**
229
+ * Force-replace the slash-command manifest with `DEFAULT_COMMANDS` for
230
+ * every bound assistant (or just the ones in `assistantIds`). Useful
231
+ * when the BGOS slash picker is missing commands and you need to reset
232
+ * without re-pairing.
233
+ *
234
+ * Idempotent — safe to call repeatedly. Returns the per-assistant
235
+ * outcome so callers can log / surface failures.
236
+ */
237
+ async reseedAllCommands(assistantIds) {
238
+ let ids = assistantIds ? [...assistantIds] : [];
239
+ if (ids.length === 0) {
240
+ try {
241
+ const me = await this.api.whoami();
242
+ for (const a of me.assistants ?? []) {
243
+ ids.push(a.assistant_id);
244
+ }
245
+ }
246
+ catch (err) {
247
+ return [
248
+ {
249
+ assistantId: -1,
250
+ ok: false,
251
+ error: err instanceof Error ? err.message : String(err),
252
+ },
253
+ ];
254
+ }
255
+ }
256
+ const results = [];
257
+ for (const id of ids) {
258
+ try {
259
+ await this.api.putCommands(id, [...DEFAULT_COMMANDS]);
260
+ results.push({ assistantId: id, ok: true });
261
+ }
262
+ catch (err) {
263
+ results.push({
264
+ assistantId: id,
265
+ ok: false,
266
+ error: err instanceof Error ? err.message : String(err),
267
+ });
268
+ }
269
+ }
270
+ return results;
271
+ }
272
+ // -------------------------------------------------------------------
273
+ // Helpers
274
+ // -------------------------------------------------------------------
275
+ async seedDefaultCommands(assistantId, origin) {
276
+ try {
277
+ await this.api.putCommands(assistantId, [...DEFAULT_COMMANDS]);
278
+ // eslint-disable-next-line no-console
279
+ console.log("[gobot-channel-bgos] seeded default commands", { assistantId, origin, count: DEFAULT_COMMANDS.length });
280
+ }
281
+ catch (err) {
282
+ // eslint-disable-next-line no-console
283
+ console.warn("[gobot-channel-bgos] default command seed failed (non-fatal):", {
284
+ assistantId,
285
+ origin,
286
+ error: err instanceof Error ? err.message : String(err),
287
+ });
288
+ }
289
+ }
290
+ }
291
+ //# sourceMappingURL=adapter.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"adapter.js","sourceRoot":"","sources":["../src/adapter.ts"],"names":[],"mappings":"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"}
@@ -0,0 +1,26 @@
1
+ /**
2
+ * BGOS system-prompt addendum for Gobot agents.
3
+ *
4
+ * This block is appended to every Gobot agent's system prompt when the
5
+ * agent is dispatched via the BGOS origin. Mirrors Hermes's
6
+ * `PLATFORM_HINTS["bgos"]` content (see hermes-fork-patch) so agents
7
+ * speaking to BGOS through Gobot get the same capability surface.
8
+ *
9
+ * Source of truth for what BGOS exposes: `hermes-channel-bgos/docs/
10
+ * bgos-agent-capabilities.md`. When that doc changes, this string MUST
11
+ * change too — the `bgos-plugin-capability-sync` skill enforces this.
12
+ */
13
+ /**
14
+ * The complete addendum, including its leading separator. Append to a
15
+ * system prompt verbatim.
16
+ */
17
+ export declare const BGOS_AGENT_HINTS: string;
18
+ /**
19
+ * Append BGOS_AGENT_HINTS to a base system prompt.
20
+ *
21
+ * Idempotent — calling twice on the same input yields the same output.
22
+ * The check uses the addendum's first line so trailing whitespace
23
+ * differences don't trigger duplication.
24
+ */
25
+ export declare function buildSystemPromptWithHints(originalPrompt: string): string;
26
+ //# sourceMappingURL=agent-hints.d.ts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"agent-hints.d.ts","sourceRoot":"","sources":["../src/agent-hints.ts"],"names":[],"mappings":"AAAA;;;;;;;;;;;GAWG;AA6GH;;;GAGG;AACH,eAAO,MAAM,gBAAgB,EAAE,MAA0C,CAAC;AAE1E;;;;;;GAMG;AACH,wBAAgB,0BAA0B,CAAC,cAAc,EAAE,MAAM,GAAG,MAAM,CAOzE"}