@rstreamlabs/tunnels 3.2.0 → 3.4.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.
package/README.md CHANGED
@@ -112,7 +112,7 @@ await watch.connect();
112
112
  ```
113
113
 
114
114
  URL-based watch authentication requires a short-lived token with bounded
115
- lifetime and watch-only tunnel list resources.
115
+ lifetime, explicit read-only watch permissions, and list-only tunnel resources.
116
116
 
117
117
  Browser integrations should provide `auth` as a function that calls a backend
118
118
  token route and returns a fresh watch token for each connection attempt. Do not
@@ -190,7 +190,8 @@ For a receiving backend, verify the signature before touching the JSON payload
190
190
  and use the event id as the idempotency key.
191
191
 
192
192
  ```ts
193
- import { RstreamWebhookResource, type WebhookEvent } from "@rstreamlabs/tunnels";
193
+ import { RstreamWebhookResource } from "@rstreamlabs/tunnels";
194
+ import { type WebhookEvent } from "@rstreamlabs/tunnels";
194
195
 
195
196
  const webhooks = new RstreamWebhookResource();
196
197
 
@@ -225,18 +226,71 @@ export async function receiveWebhook(request: Request) {
225
226
  const rawBody = Buffer.from(await request.arrayBuffer());
226
227
  const signature = request.headers.get("rstream-signature");
227
228
  if (!signature) throw new Error("Missing webhook signature.");
228
-
229
229
  const event = await webhooks.event(
230
230
  rawBody,
231
231
  signature,
232
232
  process.env.WEBHOOK_SECRET!,
233
233
  );
234
234
  if (!event.id) throw new Error("Missing webhook event id.");
235
-
236
235
  await handleLifecycleEvent(event);
237
236
  }
238
237
  ```
239
238
 
239
+ ## Project Log Events
240
+
241
+ Use `streamSummarySchema` for connection log entries returned by the Engine API.
242
+ The `request.entry.kind` field distinguishes published access from private
243
+ rstream dials; `formatStreamAccessPath` returns the dashboard-safe label for
244
+ that value.
245
+
246
+ ```ts
247
+ import { formatStreamAccessPath } from "@rstreamlabs/tunnels";
248
+ import { streamSummarySchema } from "@rstreamlabs/tunnels";
249
+
250
+ const summary = streamSummarySchema.parse(payload);
251
+
252
+ console.log(formatStreamAccessPath(summary.request.entry));
253
+ ```
254
+
255
+ For local receiver tests, the SDK exposes the same signing primitives used by
256
+ the CLI and Engine dispatcher:
257
+
258
+ ```ts
259
+ import { buildWebhookHeaders } from "@rstreamlabs/tunnels";
260
+ import { generateWebhookSigningSecret } from "@rstreamlabs/tunnels";
261
+ import { type WebhookEvent } from "@rstreamlabs/tunnels";
262
+
263
+ const secret = generateWebhookSigningSecret();
264
+ const event: WebhookEvent & { id: string } = {
265
+ id: "evt_test",
266
+ type: "tunnel.created",
267
+ created_at: new Date().toISOString(),
268
+ object: {
269
+ id: "tunnel_test",
270
+ labels: {
271
+ device: "device_123",
272
+ },
273
+ },
274
+ };
275
+ const body = JSON.stringify(event);
276
+ const headers = buildWebhookHeaders(body, event, secret, {
277
+ deliveryId: "del_test",
278
+ webhookId: "we_test",
279
+ });
280
+
281
+ await fetch("http://localhost:3000/api/rstream/webhook", {
282
+ body,
283
+ headers: {
284
+ "content-type": "application/json",
285
+ ...headers,
286
+ },
287
+ method: "POST",
288
+ });
289
+ ```
290
+
291
+ `rstream events --webhook` uses the same request body and header contract when
292
+ forwarding live local events to a receiver.
293
+
240
294
  ## WebTTY Helpers
241
295
 
242
296
  Use `parseWebTTYServers()` to derive WebTTY server metadata from tunnel