@cross-deck/node 1.0.0 → 1.1.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/CHANGELOG.md CHANGED
@@ -4,6 +4,29 @@ All notable changes to `@cross-deck/node` will be documented here. The
4
4
  format follows [Keep a Changelog](https://keepachangelog.com/en/1.1.0/)
5
5
  and this project adheres to [Semantic Versioning](https://semver.org/spec/v2.0.0.html).
6
6
 
7
+ ## [1.1.0] — 2026-05-13
8
+
9
+ ### Added
10
+
11
+ - **Auto-heartbeat on construction.** `new CrossdeckServer({...})` now
12
+ fires a heartbeat in the background the moment the SDK is
13
+ constructed, fire-and-forget. The dashboard's row flips LIVE within
14
+ ~200 ms of the customer's process boot — no explicit `.heartbeat()`
15
+ call required in the bootstrap. Solves the cold-start serverless
16
+ verification problem at its root (function boot triggers SDK
17
+ construction triggers heartbeat; the install-verifier's URL probe
18
+ doubles as a cold-start waker).
19
+ - New option `bootHeartbeat?: boolean` (default `true`). Set `false`
20
+ for latency-sensitive cold paths that want the prior v1.0.0
21
+ caller-controlled behaviour. Implicitly disabled in `testMode`.
22
+
23
+ ### Why this is non-breaking
24
+
25
+ The boot heartbeat is fire-and-forget and swallows its own errors —
26
+ the caller's code never blocks on it, never throws, and a failure
27
+ (bad key, network blip, firewall) has zero effect on subsequent
28
+ event flushes. Equivalent to Sentry's `Sentry.init()` boot session.
29
+
7
30
  ## [1.0.0] — 2026-05-13
8
31
 
9
32
  Full three-USP server SDK release. Version-aligned with `@cross-deck/web@1.0.0`. Bank-grade quality bar — Stripe + Apple + Google VP-level QA review across two passes. 6,796 LOC of source / 6,230 LOC of tests / 398 unit tests + 19 e2e todos passing / Gate 3 fixture verifying the snippet against the built bundle. Web-SDK parity at the capability level: every Web SDK guarantee that has a server-side analogue ships here.
@@ -1,4 +1,4 @@
1
- import { p as CrossdeckServer } from '../crossdeck-server-LvQwPKu5.mjs';
1
+ import { p as CrossdeckServer } from '../crossdeck-server-BXQaFjVx.mjs';
2
2
  import 'node:events';
3
3
 
4
4
  /**
@@ -1,4 +1,4 @@
1
- import { p as CrossdeckServer } from '../crossdeck-server-LvQwPKu5.js';
1
+ import { p as CrossdeckServer } from '../crossdeck-server-BXQaFjVx.js';
2
2
  import 'node:events';
3
3
 
4
4
  /**
@@ -236,7 +236,7 @@ interface RuntimeInfo {
236
236
  }
237
237
 
238
238
  declare const SDK_NAME = "@cross-deck/node";
239
- declare const SDK_VERSION = "1.0.0";
239
+ declare const SDK_VERSION = "1.1.0";
240
240
  declare const DEFAULT_BASE_URL = "https://api.cross-deck.com/v1";
241
241
  declare const DEFAULT_TIMEOUT_MS = 15000;
242
242
  /**
@@ -430,6 +430,27 @@ interface CrossdeckServerOptions {
430
430
  * platform's own SIGKILL (typically 5-10s after SIGTERM) preempts us.
431
431
  */
432
432
  flushOnExitTimeoutMs?: number;
433
+ /**
434
+ * Fire a heartbeat in the background the moment the SDK is
435
+ * constructed. Default `true`.
436
+ *
437
+ * This is what makes the dashboard's "Verify install" surface
438
+ * actually work in cold-start serverless: the moment the customer's
439
+ * process boots and runs `new CrossdeckServer({...})`, we phone
440
+ * home, the dashboard row flips LIVE, and the caller doesn't have
441
+ * to add an explicit `await server.heartbeat()` to their bootstrap.
442
+ *
443
+ * Fire-and-forget. Failures are swallowed (the SDK still works for
444
+ * events even if this boot ping can't reach the backend). The
445
+ * caller's process never blocks on this.
446
+ *
447
+ * Set `false` if you want the prior v1.0.0 behaviour where the
448
+ * caller controlled when (or whether) the first network ping fired
449
+ * — e.g., very latency-sensitive cold paths, or environments where
450
+ * the very first request must not race with an SDK-initiated call.
451
+ * `testMode: true` also disables this implicitly.
452
+ */
453
+ bootHeartbeat?: boolean;
433
454
  /**
434
455
  * TTL for the entitlement cache (ms). Default 60_000 (60s).
435
456
  *
@@ -236,7 +236,7 @@ interface RuntimeInfo {
236
236
  }
237
237
 
238
238
  declare const SDK_NAME = "@cross-deck/node";
239
- declare const SDK_VERSION = "1.0.0";
239
+ declare const SDK_VERSION = "1.1.0";
240
240
  declare const DEFAULT_BASE_URL = "https://api.cross-deck.com/v1";
241
241
  declare const DEFAULT_TIMEOUT_MS = 15000;
242
242
  /**
@@ -430,6 +430,27 @@ interface CrossdeckServerOptions {
430
430
  * platform's own SIGKILL (typically 5-10s after SIGTERM) preempts us.
431
431
  */
432
432
  flushOnExitTimeoutMs?: number;
433
+ /**
434
+ * Fire a heartbeat in the background the moment the SDK is
435
+ * constructed. Default `true`.
436
+ *
437
+ * This is what makes the dashboard's "Verify install" surface
438
+ * actually work in cold-start serverless: the moment the customer's
439
+ * process boots and runs `new CrossdeckServer({...})`, we phone
440
+ * home, the dashboard row flips LIVE, and the caller doesn't have
441
+ * to add an explicit `await server.heartbeat()` to their bootstrap.
442
+ *
443
+ * Fire-and-forget. Failures are swallowed (the SDK still works for
444
+ * events even if this boot ping can't reach the backend). The
445
+ * caller's process never blocks on this.
446
+ *
447
+ * Set `false` if you want the prior v1.0.0 behaviour where the
448
+ * caller controlled when (or whether) the first network ping fired
449
+ * — e.g., very latency-sensitive cold paths, or environments where
450
+ * the very first request must not race with an SDK-initiated call.
451
+ * `testMode: true` also disables this implicitly.
452
+ */
453
+ bootHeartbeat?: boolean;
433
454
  /**
434
455
  * TTL for the entitlement cache (ms). Default 60_000 (60s).
435
456
  *
package/dist/index.cjs CHANGED
@@ -365,7 +365,7 @@ function byteLength(s) {
365
365
 
366
366
  // src/http.ts
367
367
  var SDK_NAME = "@cross-deck/node";
368
- var SDK_VERSION = "1.0.0";
368
+ var SDK_VERSION = "1.1.0";
369
369
  var DEFAULT_BASE_URL = "https://api.cross-deck.com/v1";
370
370
  var DEFAULT_TIMEOUT_MS = 15e3;
371
371
  var CROSSDECK_API_VERSION = "2025-01-01";
@@ -2239,6 +2239,17 @@ var CrossdeckServer = class extends import_node_events.EventEmitter {
2239
2239
  });
2240
2240
  this.flushOnExit.install();
2241
2241
  }
2242
+ if (options.testMode !== true && options.bootHeartbeat !== false) {
2243
+ setImmediate(() => {
2244
+ void this.heartbeat().catch((err) => {
2245
+ this.debug.emit(
2246
+ "sdk.boot_heartbeat_failed",
2247
+ "Boot heartbeat failed (non-fatal \u2014 events will still flush).",
2248
+ { message: err instanceof Error ? err.message : String(err) }
2249
+ );
2250
+ });
2251
+ });
2252
+ }
2242
2253
  }
2243
2254
  // ============================================================
2244
2255
  // Identity — direct HTTP (transactional, not telemetry)