@buoy-gg/mcp 7.0.16 → 7.0.18

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/dist/cli.mjs CHANGED
@@ -3,7 +3,7 @@ import {
3
3
  SyncClient,
4
4
  createMcpServer,
5
5
  runInit
6
- } from "./chunk-P2OALRPK.mjs";
6
+ } from "./chunk-ZLTXVKRQ.mjs";
7
7
 
8
8
  // src/cli.ts
9
9
  import { StdioServerTransport } from "@modelcontextprotocol/sdk/server/stdio.js";
package/dist/index.d.mts CHANGED
@@ -47,7 +47,11 @@ declare class SyncClient {
47
47
  private devices;
48
48
  /** Latest snapshot payload per `${deviceId}::${toolId}`. */
49
49
  private snapshots;
50
- /** Tools we've asked the broker to keep streaming, as `${deviceId}::${toolId}`. */
50
+ /**
51
+ * Capture-mode watches this client holds, keyed by snapKey. Stored with
52
+ * their addressing because they have to be RE-SENT on every reconnect: the
53
+ * broker keys watch state by socket id, and a reconnect gets a new one.
54
+ */
51
55
  private watching;
52
56
  /** In-flight actions awaiting a result, keyed by requestId. */
53
57
  private pendingActions;
@@ -87,15 +91,47 @@ declare class SyncClient {
87
91
  * is blocked.
88
92
  */
89
93
  requireProDevice(deviceId?: string): string;
94
+ /**
95
+ * Keep the device RECORDING this tool, without asking it to stream.
96
+ *
97
+ * A dashboard watches for as long as its panel is open; this client is
98
+ * request/response, so it used to watch and unwatch around every single
99
+ * read. That works for a tool whose state just IS (the query cache, the env
100
+ * table) and is useless for one that records a timeline: the unwatch drops
101
+ * the device's subscriber count to zero, which stops capture, so nothing is
102
+ * ever recorded between two reads. The list comes back empty and reads as
103
+ * "the app made no requests" — a wrong conclusion that is very expensive to
104
+ * chase, because everything about the app looks fine.
105
+ *
106
+ * Capture-mode watches are held for the life of the connection and released
107
+ * on disconnect (the broker also drops them for us). They cost the device's
108
+ * ring buffer, not the socket: no snapshot is pushed, and reads still go
109
+ * through `request-devtool-state`.
110
+ */
90
111
  private ensureWatching;
112
+ private sendWatch;
113
+ /**
114
+ * Re-arm every held watch after a reconnect.
115
+ *
116
+ * The broker tracks watches per SOCKET, so a reconnect (broker restart, a
117
+ * dropped wifi link) silently discards all of ours while `watching` still
118
+ * says we hold them — `ensureWatching` would then short-circuit forever and
119
+ * the device would never record again. Silent and permanent: the exact
120
+ * failure this whole capture-mode change exists to remove.
121
+ */
122
+ private rearmWatches;
91
123
  /** Stop streaming a tool (releases the device-side backpressure). */
92
124
  unwatch(toolId: string, targetDeviceId: string): void;
93
125
  /** Last snapshot received for a tool/device, if any. */
94
126
  cachedSnapshot(toolId: string, deviceId: string): unknown;
95
127
  /**
96
- * Get a tool's current state. Starts watching (so the device begins emitting),
97
- * explicitly requests state, and resolves with the next snapshot. Falls back
98
- * to the last cached snapshot if the request times out.
128
+ * Get a tool's current state: arm capture (once, for the connection), ask
129
+ * for state explicitly, and resolve with the snapshot that comes back.
130
+ * Falls back to the last cached snapshot if the request times out.
131
+ *
132
+ * The capture watch is deliberately NOT released afterwards — see
133
+ * `ensureWatching`. It costs the device nothing on the socket, and dropping
134
+ * it is what made every timeline tool look permanently empty from here.
99
135
  */
100
136
  getSnapshot(toolId: string, deviceId?: string, opts?: {
101
137
  timeoutMs?: number;
package/dist/index.d.ts CHANGED
@@ -47,7 +47,11 @@ declare class SyncClient {
47
47
  private devices;
48
48
  /** Latest snapshot payload per `${deviceId}::${toolId}`. */
49
49
  private snapshots;
50
- /** Tools we've asked the broker to keep streaming, as `${deviceId}::${toolId}`. */
50
+ /**
51
+ * Capture-mode watches this client holds, keyed by snapKey. Stored with
52
+ * their addressing because they have to be RE-SENT on every reconnect: the
53
+ * broker keys watch state by socket id, and a reconnect gets a new one.
54
+ */
51
55
  private watching;
52
56
  /** In-flight actions awaiting a result, keyed by requestId. */
53
57
  private pendingActions;
@@ -87,15 +91,47 @@ declare class SyncClient {
87
91
  * is blocked.
88
92
  */
89
93
  requireProDevice(deviceId?: string): string;
94
+ /**
95
+ * Keep the device RECORDING this tool, without asking it to stream.
96
+ *
97
+ * A dashboard watches for as long as its panel is open; this client is
98
+ * request/response, so it used to watch and unwatch around every single
99
+ * read. That works for a tool whose state just IS (the query cache, the env
100
+ * table) and is useless for one that records a timeline: the unwatch drops
101
+ * the device's subscriber count to zero, which stops capture, so nothing is
102
+ * ever recorded between two reads. The list comes back empty and reads as
103
+ * "the app made no requests" — a wrong conclusion that is very expensive to
104
+ * chase, because everything about the app looks fine.
105
+ *
106
+ * Capture-mode watches are held for the life of the connection and released
107
+ * on disconnect (the broker also drops them for us). They cost the device's
108
+ * ring buffer, not the socket: no snapshot is pushed, and reads still go
109
+ * through `request-devtool-state`.
110
+ */
90
111
  private ensureWatching;
112
+ private sendWatch;
113
+ /**
114
+ * Re-arm every held watch after a reconnect.
115
+ *
116
+ * The broker tracks watches per SOCKET, so a reconnect (broker restart, a
117
+ * dropped wifi link) silently discards all of ours while `watching` still
118
+ * says we hold them — `ensureWatching` would then short-circuit forever and
119
+ * the device would never record again. Silent and permanent: the exact
120
+ * failure this whole capture-mode change exists to remove.
121
+ */
122
+ private rearmWatches;
91
123
  /** Stop streaming a tool (releases the device-side backpressure). */
92
124
  unwatch(toolId: string, targetDeviceId: string): void;
93
125
  /** Last snapshot received for a tool/device, if any. */
94
126
  cachedSnapshot(toolId: string, deviceId: string): unknown;
95
127
  /**
96
- * Get a tool's current state. Starts watching (so the device begins emitting),
97
- * explicitly requests state, and resolves with the next snapshot. Falls back
98
- * to the last cached snapshot if the request times out.
128
+ * Get a tool's current state: arm capture (once, for the connection), ask
129
+ * for state explicitly, and resolve with the snapshot that comes back.
130
+ * Falls back to the last cached snapshot if the request times out.
131
+ *
132
+ * The capture watch is deliberately NOT released afterwards — see
133
+ * `ensureWatching`. It costs the device nothing on the socket, and dropping
134
+ * it is what made every timeline tool look permanently empty from here.
99
135
  */
100
136
  getSnapshot(toolId: string, deviceId?: string, opts?: {
101
137
  timeoutMs?: number;