@hasna/bridge 0.1.2 → 0.2.1

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
package/README.md CHANGED
@@ -12,10 +12,32 @@ bun install -g @hasna/bridge
12
12
 
13
13
  ## Commands
14
14
 
15
+ The `0.2.x` direction is session-first. A channel conversation attaches to a
16
+ bridge session, and normal messages go to that session. Agent adapters that do
17
+ not yet expose a stable create/send/resume API are marked `compatibility` in
18
+ session state.
19
+
20
+ Session surface:
21
+
22
+ ```sh
23
+ bridge sessions list
24
+ bridge sessions create --agent codewith --cwd /repo
25
+ bridge sessions attach SESSION_ID --channel telegram-main --conversation 123456789
26
+ bridge sessions use SESSION_ID --channel telegram-main --conversation 123456789
27
+ bridge sessions detach --channel telegram-main --conversation 123456789
28
+ bridge sessions pause SESSION_ID
29
+ bridge sessions resume SESSION_ID
30
+ bridge sessions close SESSION_ID
31
+ bridge sessions send SESSION_ID "status"
32
+ ```
33
+
34
+ Route compatibility surface:
35
+
15
36
  ```sh
16
37
  bridge init
17
38
  bridge doctor
18
39
  bridge channels add-telegram telegram-main --token-env TELEGRAM_BOT_TOKEN --allowed-chat-ids 123456789
40
+ bridge channels add-imessage imessage-main --allowed-handles +15555550100 --default-handle +15555550100
19
41
  bridge profiles add codewith-main --agent-kind codewith --auth-profile account001 --cwd /Users/hasna
20
42
  bridge agents add codewith --kind codewith --profile codewith-main
21
43
  bridge routes add telegram-codewith --from telegram-main --to codewith --chat-ids 123456789
@@ -23,6 +45,9 @@ bridge serve
23
45
  bridge daemon start
24
46
  ```
25
47
 
48
+ The session-backed multi-channel plan for the `0.2.x` release is tracked in
49
+ [`docs/session-bridge-plan.md`](docs/session-bridge-plan.md).
50
+
26
51
  Useful inspection commands:
27
52
 
28
53
  ```sh
@@ -38,8 +63,10 @@ Direct operations:
38
63
 
39
64
  ```sh
40
65
  bridge send telegram-main 123456789 "hello"
66
+ bridge send imessage-main +15555550100 "hello"
41
67
  bridge ask codewith "summarize this repo"
42
68
  bridge route-message --channel telegram-main --chat-id 123456789 --text "status" --json
69
+ bridge sessions route-message --channel telegram-main --chat-id 123456789 --text "status" --json
43
70
  ```
44
71
 
45
72
  Daemon operations:
@@ -116,8 +143,18 @@ bridge agents add aicopilot-main --kind aicopilot --profile aicopilot-main
116
143
 
117
144
  - `bridge_status`
118
145
  - `bridge_config`
146
+ - `bridge_session_list`
147
+ - `bridge_session_status`
148
+ - `bridge_session_create`
149
+ - `bridge_session_attach`
150
+ - `bridge_session_send`
151
+ - `bridge_session_route_message`
119
152
  - `bridge_route_message`
120
153
 
154
+ Use `bridge_session_route_message` for normal inbound channel behavior through
155
+ session bindings. `bridge_route_message` remains for compatibility with explicit
156
+ stateless routes.
157
+
121
158
  ## State
122
159
 
123
160
  Default config path:
@@ -134,9 +171,18 @@ var name, not the token value. Telegram channels fail closed unless
134
171
  `allowedChatIds` are set or `allowAllChats` is explicitly enabled.
135
172
  Disabled channels do not match or deliver routes. Channel-level `allowedChatIds`
136
173
  are enforced before route matching, and long-poll offsets are persisted in
137
- `~/.hasna/bridge/state.json` so restarts do not replay already-seen updates.
174
+ `~/.hasna/bridge/state.json` so restarts do not replay already-seen terminal
175
+ updates.
138
176
  MCP config inspection redacts profile and agent environment values.
139
177
 
178
+ Session state also lives in `~/.hasna/bridge/state.json`: `sessions`,
179
+ `bindings`, `messageLedger`, and `cursors`. The daemon records inbound messages
180
+ in the ledger and advances Telegram offsets only after a terminal state:
181
+ delivered, skipped, or unauthorized. Failed messages remain retryable and do
182
+ not advance the Telegram offset. If an agent succeeds but outbound delivery
183
+ fails, the response is stored as `agent_completed` so retry delivery does not
184
+ re-run the agent.
185
+
140
186
  Daemon metadata and logs are private as well. Logs can contain prompts and agent
141
187
  responses, so treat them as sensitive.
142
188
 
@@ -162,15 +208,59 @@ bridge init
162
208
  bridge channels add-telegram telegram-main --token-env TELEGRAM_BOT_TOKEN --allowed-chat-ids CHAT_ID --default-chat-id CHAT_ID
163
209
  bridge profiles add shell-echo --agent-kind shell --command printf --arg 'bridge ok: {prompt}'
164
210
  bridge agents add echo --kind shell --profile shell-echo
165
- bridge routes add telegram-echo --from telegram-main --to echo --chat-ids CHAT_ID
211
+ bridge sessions create --id test-session --agent echo
212
+ bridge sessions attach test-session --channel telegram-main --conversation CHAT_ID
166
213
  bridge doctor
167
214
  bridge daemon start
168
215
  bridge daemon status
169
216
  ```
170
217
 
171
- Send a Telegram message to the bot. It should reply with `bridge ok: ...`.
218
+ Send a plain Telegram message to the bot. It should reply with `bridge ok: ...`
219
+ without any prefix.
172
220
  Inspect logs with `bridge daemon logs`, then stop it with `bridge daemon stop`.
173
221
 
222
+ For Telegram forum topics, use `CHAT_ID:THREAD_ID` as the conversation value.
223
+
174
224
  For the first live test, use the default process supervisor above because it
175
225
  inherits `TELEGRAM_BOT_TOKEN` from your shell. Move to launchd/systemd after that
176
226
  works.
227
+
228
+ ## iMessage
229
+
230
+ iMessage is a local macOS channel. Sending uses the Messages app through
231
+ `osascript`, so macOS may ask for Automation permission for the terminal or
232
+ daemon host process.
233
+
234
+ Configure a send-only channel:
235
+
236
+ ```sh
237
+ bridge channels add-imessage imessage-main --allowed-handles +15555550100 --default-handle +15555550100
238
+ bridge send imessage-main "hello"
239
+ ```
240
+
241
+ If your Mac has more than one Messages account, add the account selector:
242
+
243
+ ```sh
244
+ bridge channels add-imessage imessage-main --allowed-handles +15555550100 --account you@example.com
245
+ ```
246
+
247
+ For receive mode, configured accounts are also used as a filter when Messages
248
+ stores account metadata in `chat.db`. If an account is configured but an inbound
249
+ row has no matching account metadata, the row is skipped rather than routed.
250
+
251
+ Enable local receive polling only when you are comfortable granting the daemon
252
+ host access to Messages data:
253
+
254
+ ```sh
255
+ bridge channels add-imessage imessage-main --allowed-handles +15555550100 --receive
256
+ bridge sessions attach SESSION_ID --channel imessage-main --conversation +15555550100
257
+ bridge daemon restart
258
+ ```
259
+
260
+ Receive mode reads `~/Library/Messages/chat.db`. If `bridge doctor` reports a
261
+ chat database permission failure, grant Full Disk Access to the terminal or
262
+ service host, or recreate the channel without `--receive`.
263
+
264
+ Inbound direct chats bind by handle. Group chats bind by local Messages chat id,
265
+ shown internally as `chat:<guid>`, and replies go back to that chat after the
266
+ sender handle passes the channel allowlist.