svoose 0.1.7 → 0.1.9

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 (74) hide show
  1. package/README.md +53 -17
  2. package/dist/index.d.ts +2 -2
  3. package/dist/index.d.ts.map +1 -1
  4. package/dist/index.js +1 -1
  5. package/dist/index.js.map +3 -3
  6. package/dist/machine/machine.svelte.d.ts.map +1 -1
  7. package/dist/machine/machine.svelte.js +1 -1
  8. package/dist/machine/machine.svelte.js.map +3 -3
  9. package/dist/machine/types.d.ts +2 -2
  10. package/dist/machine/types.d.ts.map +1 -1
  11. package/dist/metrics/index.d.ts +1 -1
  12. package/dist/metrics/index.d.ts.map +1 -1
  13. package/dist/metrics/index.js +1 -1
  14. package/dist/metrics/index.js.map +3 -3
  15. package/dist/metrics/metric.d.ts +1 -15
  16. package/dist/metrics/metric.d.ts.map +1 -1
  17. package/dist/metrics/metric.js +1 -1
  18. package/dist/metrics/metric.js.map +3 -3
  19. package/dist/metrics/typed.d.ts +1 -1
  20. package/dist/metrics/typed.d.ts.map +1 -1
  21. package/dist/metrics/typed.js.map +3 -3
  22. package/dist/observe/errors.d.ts.map +1 -1
  23. package/dist/observe/errors.js +1 -1
  24. package/dist/observe/errors.js.map +3 -3
  25. package/dist/observe/observe.svelte.d.ts.map +1 -1
  26. package/dist/observe/observe.svelte.js +1 -1
  27. package/dist/observe/observe.svelte.js.map +3 -3
  28. package/dist/observe/sampling.d.ts.map +1 -1
  29. package/dist/observe/sampling.js +1 -1
  30. package/dist/observe/sampling.js.map +2 -2
  31. package/dist/observe/session.d.ts +1 -1
  32. package/dist/observe/session.d.ts.map +1 -1
  33. package/dist/observe/session.js +1 -1
  34. package/dist/observe/session.js.map +3 -3
  35. package/dist/observe/vitals.d.ts.map +1 -1
  36. package/dist/observe/vitals.js +1 -1
  37. package/dist/observe/vitals.js.map +2 -2
  38. package/dist/svelte/index.svelte.d.ts +2 -2
  39. package/dist/svelte/index.svelte.d.ts.map +1 -1
  40. package/dist/svelte/index.svelte.js +1 -1
  41. package/dist/svelte/index.svelte.js.map +3 -3
  42. package/dist/transport/beacon.d.ts +14 -0
  43. package/dist/transport/beacon.d.ts.map +1 -0
  44. package/dist/transport/beacon.js +2 -0
  45. package/dist/transport/beacon.js.map +7 -0
  46. package/dist/transport/fetch.d.ts +2 -2
  47. package/dist/transport/fetch.d.ts.map +1 -1
  48. package/dist/transport/fetch.js +1 -1
  49. package/dist/transport/fetch.js.map +3 -3
  50. package/dist/transport/hybrid.d.ts +13 -0
  51. package/dist/transport/hybrid.d.ts.map +1 -0
  52. package/dist/transport/hybrid.js +2 -0
  53. package/dist/transport/hybrid.js.map +7 -0
  54. package/dist/transport/index.d.ts +3 -1
  55. package/dist/transport/index.d.ts.map +1 -1
  56. package/dist/transport/index.js +1 -1
  57. package/dist/transport/index.js.map +3 -3
  58. package/dist/transport/transport.d.ts +1 -1
  59. package/dist/transport/transport.d.ts.map +1 -1
  60. package/dist/types/index.d.ts +26 -8
  61. package/dist/types/index.d.ts.map +1 -1
  62. package/package.json +1 -1
  63. package/dist/upgrade/after.d.ts +0 -28
  64. package/dist/upgrade/after.d.ts.map +0 -1
  65. package/dist/upgrade/history.d.ts +0 -36
  66. package/dist/upgrade/history.d.ts.map +0 -1
  67. package/dist/upgrade/index.d.ts +0 -25
  68. package/dist/upgrade/index.d.ts.map +0 -1
  69. package/dist/upgrade/invoke.d.ts +0 -39
  70. package/dist/upgrade/invoke.d.ts.map +0 -1
  71. package/dist/upgrade/parallel.d.ts +0 -36
  72. package/dist/upgrade/parallel.d.ts.map +0 -1
  73. package/dist/upgrade/spawn.d.ts +0 -35
  74. package/dist/upgrade/spawn.d.ts.map +0 -1
package/README.md CHANGED
@@ -2,13 +2,14 @@
2
2
 
3
3
  > Svelte + Goose = **svoose** — the goose that sees everything
4
4
 
5
- Lightweight observability + state machines for Svelte 5. Zero dependencies. Tree-shakeable. **< 5KB gzipped** (core ~3.5KB).
5
+ Lightweight observability + state machines for Svelte 5. Zero dependencies. Tree-shakeable. **~5.5KB gzipped** (core ~3.8KB).
6
6
 
7
7
  ## Features
8
8
 
9
9
  - **Web Vitals** — CLS, LCP, FID, INP, FCP, TTFB (no external deps)
10
10
  - **Error Tracking** — global errors + unhandled rejections
11
11
  - **Custom Metrics** — `metric()`, `counter()`, `gauge()`, `histogram()` (v0.1.6+)
12
+ - **Beacon Transport** — reliable delivery on page close with auto-chunking (v0.1.8+)
12
13
  - **Session Tracking** — automatic sessionId with timeout (v0.1.5+)
13
14
  - **Sampling** — per-event-type rate limiting (v0.1.3+)
14
15
  - **State Machines** — minimal FSM with TypeScript inference
@@ -91,6 +92,9 @@ const cleanup = observe({
91
92
  // Sessions (v0.1.5+)
92
93
  session: true, // or { timeout: 30 * 60 * 1000, storage: 'sessionStorage' }
93
94
 
95
+ // Error callback (v0.1.9+) — handle transport failures
96
+ onError: (err) => console.error('Transport failed:', err),
97
+
94
98
  // Debug
95
99
  debug: false,
96
100
  });
@@ -124,8 +128,6 @@ observe({
124
128
  });
125
129
  ```
126
130
 
127
- > **Note**: `sampleRate` is deprecated. Use `sampling` instead.
128
-
129
131
  #### Sessions (v0.1.5+)
130
132
 
131
133
  Automatic session tracking with configurable timeout:
@@ -208,7 +210,7 @@ Track custom events for analytics:
208
210
  ```typescript
209
211
  import { metric } from 'svoose';
210
212
 
211
- // Basic usage
213
+ // Basic usage — metric(name, metadata?)
212
214
  metric('checkout_started', { step: 1, cartTotal: 99.99 });
213
215
  metric('button_clicked', { id: 'submit-btn' });
214
216
  metric('feature_used', { name: 'dark_mode', enabled: true });
@@ -234,11 +236,11 @@ histogram('response_time_ms', 123);
234
236
  histogram('payload_size', 4096, { route: '/api/data' });
235
237
  ```
236
238
 
237
- All helpers emit events with top-level `metricKind` and `value` fields for easy backend processing.
239
+ All helpers emit `CustomMetricEvent` with top-level `metricKind`, `value`, and optional `metadata` fields for easy backend processing.
238
240
 
239
241
  ##### Typed Metrics (v0.1.7+)
240
242
 
241
- Full TypeScript autocomplete for metric names and data shapes:
243
+ Full TypeScript autocomplete for metric names and metadata shapes:
242
244
 
243
245
  ```typescript
244
246
  import { createTypedMetric } from 'svoose';
@@ -298,6 +300,7 @@ machine.matchesAny('on', 'off'); // true
298
300
 
299
301
  // Check if event is valid
300
302
  machine.can('TOGGLE'); // true
303
+ machine.can({ type: 'SET', value: 42 }); // full event for payload-dependent guards
301
304
 
302
305
  // Send events
303
306
  machine.send('TOGGLE');
@@ -374,8 +377,8 @@ const auth = createMachine({
374
377
  },
375
378
  });
376
379
 
377
- // When an error occurs, it includes:
378
- // { machineId: 'auth', machineState: 'loading', ... }
380
+ // When an error occurs, it includes all active machines:
381
+ // { machineId: 'auth', machineState: 'loading', machines: [{ id: 'auth', state: 'loading' }], ... }
379
382
  ```
380
383
 
381
384
  ### Custom Transport
@@ -413,18 +416,46 @@ observe({
413
416
  });
414
417
  ```
415
418
 
419
+ #### Beacon & Hybrid Transport (v0.1.8+)
420
+
421
+ Prevent data loss on page close with `sendBeacon`:
422
+
423
+ ```typescript
424
+ import { createBeaconTransport, createHybridTransport } from 'svoose';
425
+
426
+ // Beacon only — guaranteed delivery on page close
427
+ observe({
428
+ transport: createBeaconTransport('/api/metrics', {
429
+ maxPayloadSize: 60000, // auto-chunks if exceeded (default: 60KB)
430
+ }),
431
+ });
432
+
433
+ // Hybrid (recommended for production)
434
+ // Uses fetch normally, switches to beacon on page close
435
+ const transport = createHybridTransport('/api/metrics', {
436
+ default: 'fetch', // normal operation
437
+ onUnload: 'beacon', // page close / tab switch
438
+ headers: { 'Authorization': 'Bearer xxx' },
439
+ });
440
+
441
+ observe({ transport });
442
+
443
+ // Cleanup when done (removes lifecycle listeners)
444
+ transport.destroy();
445
+ ```
446
+
416
447
  ## Bundle Size
417
448
 
418
449
  Tree-shakeable — pay only for what you use:
419
450
 
420
451
  | Import | Size (gzip) |
421
452
  |--------|-------------|
422
- | `observe()` + vitals + errors + metrics | ~3.6 KB |
423
- | `createMachine()` only | ~0.8 KB |
424
- | Full bundle (v0.1.x) | ~4.7 KB |
453
+ | `observe()` + vitals + errors + metrics | ~3.8 KB |
454
+ | `createMachine()` only | ~0.85 KB |
455
+ | Full bundle (v0.1.x) | ~5.5 KB |
425
456
  | Full production (v0.2.0+) | ~6 KB |
426
457
 
427
- > Most apps only need `observe()` core (~3.5 KB). Compare: Sentry ~20KB, PostHog ~40KB.
458
+ > Most apps only need `observe()` core (~3.8 KB). Compare: Sentry ~20KB, PostHog ~40KB.
428
459
 
429
460
  ## TypeScript
430
461
 
@@ -574,11 +605,16 @@ const machine = createMachine({
574
605
  - **v0.1.5** ✅ — Session Tracking + CLS Session Windows fix
575
606
  - **v0.1.6** ✅ — Custom metrics (`metric()` API)
576
607
  - **v0.1.7** ✅ — Extended Metrics (counter/gauge/histogram + typed API)
577
- - **v0.1.8** — Beacon + Hybrid Transport
578
- - **v0.1.9** — Retry Logic
579
- - **v0.1.10** — Privacy Utilities
580
- - **v0.2.0** — Production-Ready Observability + Bundle Restructure (modular entry points)
581
- - **v0.3.0** — SvelteKit Integration (Vite plugin, hooks, route tracking)
608
+ - **v0.1.8** — Beacon + Hybrid Transport
609
+ - **v0.1.9** API Cleanup: `data`→`metadata`, `can()` accepts full events, `onError` callback, multi-machine error context, validation
610
+ - **v0.1.10** — Retry Logic
611
+ - **v0.1.11** — Privacy Utilities
612
+ - **v0.2.0** — Production-Ready Observability (User ID, Offline, flush API, Rate Limiter)
613
+ - **v0.2.1** — Breadcrumbs
614
+ - **v0.2.2** — Navigation Events + Soft Navigation
615
+ - **v0.2.3** — Request Correlation
616
+ - **v0.3.0** — SvelteKit Core Integration
617
+ - **v0.3.1** — SvelteKit Vite Plugin
582
618
  - **v1.0.0** — Stable Release (Q1 2027)
583
619
 
584
620
  > **Note**: FSM is a lightweight bonus feature, not an XState competitor. For complex state machines, use XState.
package/dist/index.d.ts CHANGED
@@ -11,8 +11,8 @@ export { observeErrors, registerMachineContext, unregisterMachineContext, } from
11
11
  export type { ObserveErrorEvent, ErrorEvent, UnhandledRejectionEvent, } from './observe/index.js';
12
12
  export { observeCLS, observeLCP, observeFID, observeINP, observeFCP, observeTTFB, vitalObservers, } from './observe/index.js';
13
13
  export type { Metric, MetricName, MetricRating } from './observe/index.js';
14
- export { createFetchTransport, createConsoleTransport } from './transport/index.js';
15
- export type { Transport, TransportOptions } from './transport/index.js';
14
+ export { createFetchTransport, createConsoleTransport, createBeaconTransport, createHybridTransport } from './transport/index.js';
15
+ export type { Transport, TransportOptions, BeaconTransportOptions, HybridTransportOptions, HybridTransport } from './transport/index.js';
16
16
  export { createMachine, createEvent } from './machine/index.js';
17
17
  export type { MachineConfig, Machine, EventObject, StateNode, TransitionConfig, InferStates, InferEvents, InferContext, } from './machine/index.js';
18
18
  export { metric, counter, gauge, histogram, createTypedMetric } from './metrics/index.js';
@@ -1 +1 @@
1
- {"version":3,"file":"index.d.ts","sourceRoot":"","sources":["../src/index.ts"],"names":[],"mappings":"AAAA;;;;GAIG;AAKH,OAAO,EAAE,OAAO,EAAE,MAAM,oBAAoB,CAAC;AAC7C,YAAY,EAAE,cAAc,EAAE,MAAM,oBAAoB,CAAC;AAKzD,OAAO,EAAE,aAAa,EAAE,uBAAuB,EAAE,MAAM,oBAAoB,CAAC;AAC5E,YAAY,EAAE,cAAc,EAAE,cAAc,EAAE,iBAAiB,EAAE,OAAO,EAAE,MAAM,oBAAoB,CAAC;AAKrG,OAAO,EACL,aAAa,EACb,sBAAsB,EACtB,wBAAwB,GACzB,MAAM,oBAAoB,CAAC;AAC5B,YAAY,EACV,iBAAiB,EACjB,UAAU,EACV,uBAAuB,GACxB,MAAM,oBAAoB,CAAC;AAK5B,OAAO,EACL,UAAU,EACV,UAAU,EACV,UAAU,EACV,UAAU,EACV,UAAU,EACV,WAAW,EACX,cAAc,GACf,MAAM,oBAAoB,CAAC;AAC5B,YAAY,EAAE,MAAM,EAAE,UAAU,EAAE,YAAY,EAAE,MAAM,oBAAoB,CAAC;AAK3E,OAAO,EAAE,oBAAoB,EAAE,sBAAsB,EAAE,MAAM,sBAAsB,CAAC;AACpF,YAAY,EAAE,SAAS,EAAE,gBAAgB,EAAE,MAAM,sBAAsB,CAAC;AAKxE,OAAO,EAAE,aAAa,EAAE,WAAW,EAAE,MAAM,oBAAoB,CAAC;AAChE,YAAY,EACV,aAAa,EACb,OAAO,EACP,WAAW,EACX,SAAS,EACT,gBAAgB,EAChB,WAAW,EACX,WAAW,EACX,YAAY,GACb,MAAM,oBAAoB,CAAC;AAK5B,OAAO,EAAE,MAAM,EAAE,OAAO,EAAE,KAAK,EAAE,SAAS,EAAE,iBAAiB,EAAE,MAAM,oBAAoB,CAAC;AAK1F,YAAY,EACV,UAAU,EACV,eAAe,EACf,iBAAiB,EACjB,YAAY,GACb,MAAM,kBAAkB,CAAC"}
1
+ {"version":3,"file":"index.d.ts","sourceRoot":"","sources":["../src/index.ts"],"names":[],"mappings":"AAAA;;;;GAIG;AAKH,OAAO,EAAE,OAAO,EAAE,MAAM,oBAAoB,CAAC;AAC7C,YAAY,EAAE,cAAc,EAAE,MAAM,oBAAoB,CAAC;AAKzD,OAAO,EAAE,aAAa,EAAE,uBAAuB,EAAE,MAAM,oBAAoB,CAAC;AAC5E,YAAY,EAAE,cAAc,EAAE,cAAc,EAAE,iBAAiB,EAAE,OAAO,EAAE,MAAM,oBAAoB,CAAC;AAKrG,OAAO,EACL,aAAa,EACb,sBAAsB,EACtB,wBAAwB,GACzB,MAAM,oBAAoB,CAAC;AAC5B,YAAY,EACV,iBAAiB,EACjB,UAAU,EACV,uBAAuB,GACxB,MAAM,oBAAoB,CAAC;AAK5B,OAAO,EACL,UAAU,EACV,UAAU,EACV,UAAU,EACV,UAAU,EACV,UAAU,EACV,WAAW,EACX,cAAc,GACf,MAAM,oBAAoB,CAAC;AAC5B,YAAY,EAAE,MAAM,EAAE,UAAU,EAAE,YAAY,EAAE,MAAM,oBAAoB,CAAC;AAK3E,OAAO,EAAE,oBAAoB,EAAE,sBAAsB,EAAE,qBAAqB,EAAE,qBAAqB,EAAE,MAAM,sBAAsB,CAAC;AAClI,YAAY,EAAE,SAAS,EAAE,gBAAgB,EAAE,sBAAsB,EAAE,sBAAsB,EAAE,eAAe,EAAE,MAAM,sBAAsB,CAAC;AAKzI,OAAO,EAAE,aAAa,EAAE,WAAW,EAAE,MAAM,oBAAoB,CAAC;AAChE,YAAY,EACV,aAAa,EACb,OAAO,EACP,WAAW,EACX,SAAS,EACT,gBAAgB,EAChB,WAAW,EACX,WAAW,EACX,YAAY,GACb,MAAM,oBAAoB,CAAC;AAK5B,OAAO,EAAE,MAAM,EAAE,OAAO,EAAE,KAAK,EAAE,SAAS,EAAE,iBAAiB,EAAE,MAAM,oBAAoB,CAAC;AAK1F,YAAY,EACV,UAAU,EACV,eAAe,EACf,iBAAiB,EACjB,YAAY,GACb,MAAM,kBAAkB,CAAC"}
package/dist/index.js CHANGED
@@ -1,2 +1,2 @@
1
- import{observe as t}from"./observe/index.js";import{createSampler as n,eventTypeToSamplingType as s}from"./observe/index.js";import{observeErrors as p,registerMachineContext as a,unregisterMachineContext as v}from"./observe/index.js";import{observeCLS as x,observeLCP as c,observeFID as f,observeINP as b,observeFCP as E,observeTTFB as g,vitalObservers as T}from"./observe/index.js";import{createFetchTransport as d,createConsoleTransport as C}from"./transport/index.js";import{createMachine as M,createEvent as h}from"./machine/index.js";import{metric as S,counter as O,gauge as I,histogram as u,createTypedMetric as F}from"./metrics/index.js";export{O as counter,C as createConsoleTransport,h as createEvent,d as createFetchTransport,M as createMachine,n as createSampler,F as createTypedMetric,s as eventTypeToSamplingType,I as gauge,u as histogram,S as metric,t as observe,x as observeCLS,p as observeErrors,E as observeFCP,f as observeFID,b as observeINP,c as observeLCP,g as observeTTFB,a as registerMachineContext,v as unregisterMachineContext,T as vitalObservers};
1
+ import{observe as t}from"./observe/index.js";import{createSampler as n,eventTypeToSamplingType as s}from"./observe/index.js";import{observeErrors as i,registerMachineContext as a,unregisterMachineContext as v}from"./observe/index.js";import{observeCLS as m,observeLCP as x,observeFID as b,observeINP as f,observeFCP as T,observeTTFB as y,vitalObservers as d}from"./observe/index.js";import{createFetchTransport as g,createConsoleTransport as C,createBeaconTransport as l,createHybridTransport as M}from"./transport/index.js";import{createMachine as h,createEvent as j}from"./machine/index.js";import{metric as I,counter as u,gauge as F,histogram as B,createTypedMetric as H}from"./metrics/index.js";export{u as counter,l as createBeaconTransport,C as createConsoleTransport,j as createEvent,g as createFetchTransport,M as createHybridTransport,h as createMachine,n as createSampler,H as createTypedMetric,s as eventTypeToSamplingType,F as gauge,B as histogram,I as metric,t as observe,m as observeCLS,i as observeErrors,T as observeFCP,b as observeFID,f as observeINP,x as observeLCP,y as observeTTFB,a as registerMachineContext,v as unregisterMachineContext,d as vitalObservers};
2
2
  //# sourceMappingURL=index.js.map
package/dist/index.js.map CHANGED
@@ -1,7 +1,7 @@
1
1
  {
2
2
  "version": 3,
3
3
  "sources": ["../src/index.ts"],
4
- "sourcesContent": ["/**\n * \uD83E\uDEBF svoose - Observability + State Machines for Svelte 5\n *\n * @packageDocumentation\n */\n\n// ============================================\n// Core Observability\n// ============================================\nexport { observe } from './observe/index.js';\nexport type { ObserveOptions } from './observe/index.js';\n\n// ============================================\n// Sampling\n// ============================================\nexport { createSampler, eventTypeToSamplingType } from './observe/index.js';\nexport type { SamplingConfig, SamplingOption, SamplingEventType, Sampler } from './observe/index.js';\n\n// ============================================\n// Error Tracking\n// ============================================\nexport {\n observeErrors,\n registerMachineContext,\n unregisterMachineContext,\n} from './observe/index.js';\nexport type {\n ObserveErrorEvent,\n ErrorEvent,\n UnhandledRejectionEvent,\n} from './observe/index.js';\n\n// ============================================\n// Web Vitals\n// ============================================\nexport {\n observeCLS,\n observeLCP,\n observeFID,\n observeINP,\n observeFCP,\n observeTTFB,\n vitalObservers,\n} from './observe/index.js';\nexport type { Metric, MetricName, MetricRating } from './observe/index.js';\n\n// ============================================\n// Transport\n// ============================================\nexport { createFetchTransport, createConsoleTransport } from './transport/index.js';\nexport type { Transport, TransportOptions } from './transport/index.js';\n\n// ============================================\n// State Machines\n// ============================================\nexport { createMachine, createEvent } from './machine/index.js';\nexport type {\n MachineConfig,\n Machine,\n EventObject,\n StateNode,\n TransitionConfig,\n InferStates,\n InferEvents,\n InferContext,\n} from './machine/index.js';\n\n// ============================================\n// Custom Metrics\n// ============================================\nexport { metric, counter, gauge, histogram, createTypedMetric } from './metrics/index.js';\n\n// ============================================\n// Shared Types\n// ============================================\nexport type {\n VitalEvent,\n TransitionEvent,\n CustomMetricEvent,\n ObserveEvent,\n} from './types/index.js';\n"],
5
- "mappings": "AASA,OAAS,WAAAA,MAAe,qBAMxB,OAAS,iBAAAC,EAAe,2BAAAC,MAA+B,qBAMvD,OACE,iBAAAC,EACA,0BAAAC,EACA,4BAAAC,MACK,qBAUP,OACE,cAAAC,EACA,cAAAC,EACA,cAAAC,EACA,cAAAC,EACA,cAAAC,EACA,eAAAC,EACA,kBAAAC,MACK,qBAMP,OAAS,wBAAAC,EAAsB,0BAAAC,MAA8B,uBAM7D,OAAS,iBAAAC,EAAe,eAAAC,MAAmB,qBAe3C,OAAS,UAAAC,EAAQ,WAAAC,EAAS,SAAAC,EAAO,aAAAC,EAAW,qBAAAC,MAAyB",
6
- "names": ["observe", "createSampler", "eventTypeToSamplingType", "observeErrors", "registerMachineContext", "unregisterMachineContext", "observeCLS", "observeLCP", "observeFID", "observeINP", "observeFCP", "observeTTFB", "vitalObservers", "createFetchTransport", "createConsoleTransport", "createMachine", "createEvent", "metric", "counter", "gauge", "histogram", "createTypedMetric"]
4
+ "sourcesContent": ["/**\n * \uD83E\uDEBF svoose - Observability + State Machines for Svelte 5\n *\n * @packageDocumentation\n */\n\n// ============================================\n// Core Observability\n// ============================================\nexport { observe } from './observe/index.js';\nexport type { ObserveOptions } from './observe/index.js';\n\n// ============================================\n// Sampling\n// ============================================\nexport { createSampler, eventTypeToSamplingType } from './observe/index.js';\nexport type { SamplingConfig, SamplingOption, SamplingEventType, Sampler } from './observe/index.js';\n\n// ============================================\n// Error Tracking\n// ============================================\nexport {\n observeErrors,\n registerMachineContext,\n unregisterMachineContext,\n} from './observe/index.js';\nexport type {\n ObserveErrorEvent,\n ErrorEvent,\n UnhandledRejectionEvent,\n} from './observe/index.js';\n\n// ============================================\n// Web Vitals\n// ============================================\nexport {\n observeCLS,\n observeLCP,\n observeFID,\n observeINP,\n observeFCP,\n observeTTFB,\n vitalObservers,\n} from './observe/index.js';\nexport type { Metric, MetricName, MetricRating } from './observe/index.js';\n\n// ============================================\n// Transport\n// ============================================\nexport { createFetchTransport, createConsoleTransport, createBeaconTransport, createHybridTransport } from './transport/index.js';\nexport type { Transport, TransportOptions, BeaconTransportOptions, HybridTransportOptions, HybridTransport } from './transport/index.js';\n\n// ============================================\n// State Machines\n// ============================================\nexport { createMachine, createEvent } from './machine/index.js';\nexport type {\n MachineConfig,\n Machine,\n EventObject,\n StateNode,\n TransitionConfig,\n InferStates,\n InferEvents,\n InferContext,\n} from './machine/index.js';\n\n// ============================================\n// Custom Metrics\n// ============================================\nexport { metric, counter, gauge, histogram, createTypedMetric } from './metrics/index.js';\n\n// ============================================\n// Shared Types\n// ============================================\nexport type {\n VitalEvent,\n TransitionEvent,\n CustomMetricEvent,\n ObserveEvent,\n} from './types/index.js';\n"],
5
+ "mappings": "AASA,OAAS,WAAAA,MAAe,qBAMxB,OAAS,iBAAAC,EAAe,2BAAAC,MAA+B,qBAMvD,OACE,iBAAAC,EACA,0BAAAC,EACA,4BAAAC,MACK,qBAUP,OACE,cAAAC,EACA,cAAAC,EACA,cAAAC,EACA,cAAAC,EACA,cAAAC,EACA,eAAAC,EACA,kBAAAC,MACK,qBAMP,OAAS,wBAAAC,EAAsB,0BAAAC,EAAwB,yBAAAC,EAAuB,yBAAAC,MAA6B,uBAM3G,OAAS,iBAAAC,EAAe,eAAAC,MAAmB,qBAe3C,OAAS,UAAAC,EAAQ,WAAAC,EAAS,SAAAC,EAAO,aAAAC,EAAW,qBAAAC,MAAyB",
6
+ "names": ["observe", "createSampler", "eventTypeToSamplingType", "observeErrors", "registerMachineContext", "unregisterMachineContext", "observeCLS", "observeLCP", "observeFID", "observeINP", "observeFCP", "observeTTFB", "vitalObservers", "createFetchTransport", "createConsoleTransport", "createBeaconTransport", "createHybridTransport", "createMachine", "createEvent", "metric", "counter", "gauge", "histogram", "createTypedMetric"]
7
7
  }
@@ -1 +1 @@
1
- {"version":3,"file":"machine.svelte.d.ts","sourceRoot":"","sources":["../../src/machine/machine.svelte.ts"],"names":[],"mappings":"AAAA;;;;;GAKG;AAIH,OAAO,KAAK,EACV,WAAW,EACX,aAAa,EACb,OAAO,EAGR,MAAM,YAAY,CAAC;AAGpB;;;;;;;;;;;;;;;GAeG;AACH,wBAAgB,aAAa,CAC3B,QAAQ,SAAS,MAAM,EACvB,MAAM,SAAS,MAAM,EACrB,MAAM,SAAS,WAAW,EAC1B,MAAM,EAAE,aAAa,CAAC,QAAQ,EAAE,MAAM,EAAE,MAAM,CAAC,GAAG,OAAO,CAAC,QAAQ,EAAE,MAAM,EAAE,MAAM,CAAC,CAqMpF;AAGD,YAAY,EAAE,aAAa,EAAE,OAAO,EAAE,WAAW,EAAE,SAAS,EAAE,gBAAgB,EAAE,MAAM,YAAY,CAAC"}
1
+ {"version":3,"file":"machine.svelte.d.ts","sourceRoot":"","sources":["../../src/machine/machine.svelte.ts"],"names":[],"mappings":"AAAA;;;;;GAKG;AAIH,OAAO,KAAK,EACV,WAAW,EACX,aAAa,EACb,OAAO,EAGR,MAAM,YAAY,CAAC;AAGpB;;;;;;;;;;;;;;;GAeG;AACH,wBAAgB,aAAa,CAC3B,QAAQ,SAAS,MAAM,EACvB,MAAM,SAAS,MAAM,EACrB,MAAM,SAAS,WAAW,EAC1B,MAAM,EAAE,aAAa,CAAC,QAAQ,EAAE,MAAM,EAAE,MAAM,CAAC,GAAG,OAAO,CAAC,QAAQ,EAAE,MAAM,EAAE,MAAM,CAAC,CA4MpF;AAGD,YAAY,EAAE,aAAa,EAAE,OAAO,EAAE,WAAW,EAAE,SAAS,EAAE,gBAAgB,EAAE,MAAM,YAAY,CAAC"}
@@ -1,2 +1,2 @@
1
- import{registerMachineContext as E,unregisterMachineContext as b}from"../observe/errors.js";import{getGlobalObserver as C}from"../observe/observe.svelte.js";function m(t){if(!(t.initial in t.states))throw new Error(`[svoose] Invalid initial state "${t.initial}" for machine "${t.id}". Available states: ${Object.keys(t.states).join(", ")}`);let o=t.initial,r=t.context?{...t.context}:{};const c=t.observe===!0?{transitions:!0,context:!1}:t.observe===!1||t.observe===void 0?{transitions:!1,context:!1}:t.observe;E(t.id,()=>o);const f=t.states[t.initial];if(f?.entry)try{const e=f.entry(r);e&&(r={...r,...e})}catch(e){console.error(`[svoose] Error in entry action for initial state "${t.initial}":`,e)}function y(e,a){return e.on?.[a]}function v(e){const a=t.states[o];if(!a?.on)return!1;const s=y(a,e);return s?typeof s=="string"?!0:s.guard?s.guard(r,{type:e}):!0:!1}function p(e){const a=typeof e=="string"?{type:e}:e,s=t.states[o];if(!s?.on)return;const i=y(s,a.type);if(!i)return;const d=typeof i=="string"?i:i.target;if(typeof i=="object"&&i.guard)try{if(!i.guard(r,a))return}catch(n){console.error(`[svoose] Error in guard for event "${a.type}":`,n);return}const l=o;if(s.exit)try{s.exit(r)}catch(n){console.error(`[svoose] Error in exit action for state "${o}":`,n)}if(typeof i=="object"&&i.action)try{const n=i.action(r,a);n&&(r={...r,...n})}catch(n){console.error(`[svoose] Error in action for event "${a.type}":`,n)}o=d;const T=t.states[o];if(T?.entry)try{const n=T.entry(r);n&&(r={...r,...n})}catch(n){console.error(`[svoose] Error in entry action for state "${o}":`,n)}if(c.transitions){const n=C();if(n){const x={type:"transition",machineId:t.id,from:l,to:o,event:a.type,timestamp:Date.now(),...c.context?{context:{...r}}:{}};n(x)}}}function u(){b(t.id)}return{get state(){return o},get context(){return r},matches(e){return o===e},matchesAny(...e){return e.includes(o)},can(e){return v(e)},send:p,destroy:u}}export{m as createMachine};
1
+ import{registerMachineContext,unregisterMachineContext}from"../observe/errors.js";import{getGlobalObserver}from"../observe/observe.svelte.js";function createMachine(config){if(!(config.initial in config.states))throw new Error(`[svoose] Invalid initial state "${config.initial}" for machine "${config.id}". Available states: ${Object.keys(config.states).join(", ")}`);let _state=config.initial,_context=config.context?{...config.context}:{};const observeConfig=config.observe===!0?{transitions:!0,context:!1}:config.observe===!1||config.observe===void 0?{transitions:!1,context:!1}:config.observe;registerMachineContext(config.id,()=>_state);const initialState=config.states[config.initial];if(initialState?.entry)try{const update=initialState.entry(_context);update&&(_context={..._context,...update})}catch(err){console.error(`[svoose] Error in entry action for initial state "${config.initial}":`,err)}function getTransition(stateConfig,eventType){return stateConfig.on?.[eventType]}function canTransition(event){const eventType=typeof event=="string"?event:event.type,eventObj=typeof event=="string"?{type:event}:event,stateConfig=config.states[_state];if(!stateConfig?.on)return!1;const transition=getTransition(stateConfig,eventType);if(!transition)return!1;if(typeof transition=="string")return!0;if(transition.guard)try{return transition.guard(_context,eventObj)}catch{return!1}return!0}function send(event){const eventObj=typeof event=="string"?{type:event}:event,stateConfig=config.states[_state];if(!stateConfig?.on)return;const transition=getTransition(stateConfig,eventObj.type);if(!transition)return;const targetState=typeof transition=="string"?transition:transition.target;if(typeof transition=="object"&&transition.guard)try{if(!transition.guard(_context,eventObj))return}catch(err){console.error(`[svoose] Error in guard for event "${eventObj.type}":`,err);return}const prevState=_state;if(stateConfig.exit)try{stateConfig.exit(_context)}catch(err){console.error(`[svoose] Error in exit action for state "${_state}":`,err)}if(typeof transition=="object"&&transition.action)try{const update=transition.action(_context,eventObj);update&&(_context={..._context,...update})}catch(err){console.error(`[svoose] Error in action for event "${eventObj.type}":`,err)}_state=targetState;const newStateConfig=config.states[_state];if(newStateConfig?.entry)try{const update=newStateConfig.entry(_context);update&&(_context={..._context,...update})}catch(err){console.error(`[svoose] Error in entry action for state "${_state}":`,err)}if(observeConfig.transitions){const observer=getGlobalObserver();if(observer){const transitionEvent={type:"transition",machineId:config.id,from:prevState,to:_state,event:eventObj.type,timestamp:Date.now(),...observeConfig.context?{context:{..._context}}:{}};observer(transitionEvent)}}}function destroy(){unregisterMachineContext(config.id)}return{get state(){return _state},get context(){return _context},matches(state){return _state===state},matchesAny(...states){return states.includes(_state)},can(event){return canTransition(event)},send,destroy}}export{createMachine};
2
2
  //# sourceMappingURL=machine.svelte.js.map
@@ -1,7 +1,7 @@
1
1
  {
2
2
  "version": 3,
3
3
  "sources": ["../../src/machine/machine.svelte.ts"],
4
- "sourcesContent": ["/**\n * Minimal FSM with Svelte 5 Runes support\n *\n * Note: When used with Svelte 5, state and context are reactive via $state.\n * When used outside Svelte, they work as regular properties.\n */\n\nimport { registerMachineContext, unregisterMachineContext } from '../observe/errors.js';\nimport { getGlobalObserver } from '../observe/observe.svelte.js';\nimport type {\n EventObject,\n MachineConfig,\n Machine,\n StateNode,\n TransitionConfig,\n} from './types.js';\nimport type { TransitionEvent } from '../types/index.js';\n\n/**\n * Create a state machine\n *\n * @example\n * const toggle = createMachine({\n * id: 'toggle',\n * initial: 'off',\n * states: {\n * off: { on: { TOGGLE: 'on' } },\n * on: { on: { TOGGLE: 'off' } },\n * },\n * });\n *\n * toggle.send('TOGGLE');\n * console.log(toggle.state); // 'on'\n */\nexport function createMachine<\n TContext extends object,\n TState extends string,\n TEvent extends EventObject\n>(config: MachineConfig<TContext, TState, TEvent>): Machine<TContext, TState, TEvent> {\n // Validate initial state exists\n if (!(config.initial in config.states)) {\n throw new Error(\n `[svoose] Invalid initial state \"${config.initial}\" for machine \"${config.id}\". ` +\n `Available states: ${Object.keys(config.states).join(', ')}`\n );\n }\n\n // Internal state\n // For Svelte 5 reactivity, use useMachine() from 'svoose/svelte'\n let _state: TState = config.initial;\n let _context: TContext = config.context ? { ...config.context } : ({} as TContext);\n\n // Parse observe config\n const observeConfig =\n config.observe === true\n ? { transitions: true, context: false }\n : config.observe === false || config.observe === undefined\n ? { transitions: false, context: false }\n : config.observe;\n\n // Register for error context tracking\n registerMachineContext(config.id, () => _state);\n\n // Run entry action for initial state (with error handling)\n const initialState = config.states[config.initial];\n if (initialState?.entry) {\n try {\n const update = initialState.entry(_context);\n if (update) {\n _context = { ..._context, ...update };\n }\n } catch (err) {\n console.error(`[svoose] Error in entry action for initial state \"${config.initial}\":`, err);\n }\n }\n\n /**\n * Get transition config for an event\n */\n function getTransition(\n stateConfig: StateNode<TContext, TState, TEvent>,\n eventType: TEvent['type']\n ): TransitionConfig<TContext, TState, TEvent> | TState | undefined {\n return stateConfig.on?.[eventType as keyof typeof stateConfig.on] as\n | TransitionConfig<TContext, TState, TEvent>\n | TState\n | undefined;\n }\n\n /**\n * Check if a transition is valid (exists and guard passes)\n */\n function canTransition(eventType: TEvent['type']): boolean {\n const stateConfig = config.states[_state];\n if (!stateConfig?.on) return false;\n\n const transition = getTransition(stateConfig, eventType);\n if (!transition) return false;\n\n // If it's just a target state string, it's always valid\n if (typeof transition === 'string') return true;\n\n // If there's a guard, check it (with empty event for can() check)\n if (transition.guard) {\n return transition.guard(_context, { type: eventType } as Extract<\n TEvent,\n { type: typeof eventType }\n >);\n }\n\n return true;\n }\n\n /**\n * Send an event to the machine\n */\n function send(event: TEvent | TEvent['type']): void {\n const eventObj: TEvent =\n typeof event === 'string' ? ({ type: event } as TEvent) : event;\n\n const stateConfig = config.states[_state];\n if (!stateConfig?.on) return;\n\n const transition = getTransition(stateConfig, eventObj.type);\n if (!transition) return;\n\n const targetState: TState =\n typeof transition === 'string' ? transition : transition.target;\n\n // Check guard (with error handling)\n if (typeof transition === 'object' && transition.guard) {\n try {\n if (\n !transition.guard(\n _context,\n eventObj as Extract<TEvent, { type: (typeof eventObj)['type'] }>\n )\n ) {\n return;\n }\n } catch (err) {\n console.error(`[svoose] Error in guard for event \"${eventObj.type}\":`, err);\n return; // Don't transition if guard throws\n }\n }\n\n const prevState = _state;\n\n // Run exit action (with error handling)\n if (stateConfig.exit) {\n try {\n stateConfig.exit(_context);\n } catch (err) {\n console.error(`[svoose] Error in exit action for state \"${_state}\":`, err);\n }\n }\n\n // Run transition action (with error handling)\n if (typeof transition === 'object' && transition.action) {\n try {\n const update = transition.action(\n _context,\n eventObj as Extract<TEvent, { type: (typeof eventObj)['type'] }>\n );\n if (update) {\n _context = { ..._context, ...update };\n }\n } catch (err) {\n console.error(`[svoose] Error in action for event \"${eventObj.type}\":`, err);\n }\n }\n\n // Update state\n _state = targetState;\n\n // Run entry action for new state (with error handling)\n const newStateConfig = config.states[_state];\n if (newStateConfig?.entry) {\n try {\n const update = newStateConfig.entry(_context);\n if (update) {\n _context = { ..._context, ...update };\n }\n } catch (err) {\n console.error(`[svoose] Error in entry action for state \"${_state}\":`, err);\n }\n }\n\n // Emit observation event\n if (observeConfig.transitions) {\n const observer = getGlobalObserver();\n if (observer) {\n const transitionEvent: TransitionEvent = {\n type: 'transition',\n machineId: config.id,\n from: prevState,\n to: _state,\n event: eventObj.type,\n timestamp: Date.now(),\n ...(observeConfig.context\n ? { context: { ..._context } as Record<string, unknown> }\n : {}),\n };\n observer(transitionEvent);\n }\n }\n }\n\n /**\n * Cleanup machine\n */\n function destroy(): void {\n unregisterMachineContext(config.id);\n }\n\n // Return machine instance\n return {\n get state(): TState {\n return _state;\n },\n get context(): TContext {\n return _context;\n },\n matches(state: TState): boolean {\n return _state === state;\n },\n matchesAny(...states: TState[]): boolean {\n return states.includes(_state);\n },\n can(eventType: TEvent['type']): boolean {\n return canTransition(eventType);\n },\n send,\n destroy,\n };\n}\n\n// Re-export types\nexport type { MachineConfig, Machine, EventObject, StateNode, TransitionConfig } from './types.js';\n"],
5
- "mappings": "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",
6
- "names": ["registerMachineContext", "unregisterMachineContext", "getGlobalObserver", "createMachine", "config", "_state", "_context", "observeConfig", "initialState", "update", "err", "getTransition", "stateConfig", "eventType", "canTransition", "transition", "send", "event", "eventObj", "targetState", "prevState", "newStateConfig", "observer", "transitionEvent", "destroy", "state", "states"]
4
+ "sourcesContent": ["/**\n * Minimal FSM with Svelte 5 Runes support\n *\n * Note: When used with Svelte 5, state and context are reactive via $state.\n * When used outside Svelte, they work as regular properties.\n */\n\nimport { registerMachineContext, unregisterMachineContext } from '../observe/errors.js';\nimport { getGlobalObserver } from '../observe/observe.svelte.js';\nimport type {\n EventObject,\n MachineConfig,\n Machine,\n StateNode,\n TransitionConfig,\n} from './types.js';\nimport type { TransitionEvent } from '../types/index.js';\n\n/**\n * Create a state machine\n *\n * @example\n * const toggle = createMachine({\n * id: 'toggle',\n * initial: 'off',\n * states: {\n * off: { on: { TOGGLE: 'on' } },\n * on: { on: { TOGGLE: 'off' } },\n * },\n * });\n *\n * toggle.send('TOGGLE');\n * console.log(toggle.state); // 'on'\n */\nexport function createMachine<\n TContext extends object,\n TState extends string,\n TEvent extends EventObject\n>(config: MachineConfig<TContext, TState, TEvent>): Machine<TContext, TState, TEvent> {\n // Validate initial state exists\n if (!(config.initial in config.states)) {\n throw new Error(\n `[svoose] Invalid initial state \"${config.initial}\" for machine \"${config.id}\". ` +\n `Available states: ${Object.keys(config.states).join(', ')}`\n );\n }\n\n // Internal state\n // For Svelte 5 reactivity, use useMachine() from 'svoose/svelte'\n let _state: TState = config.initial;\n let _context: TContext = config.context ? { ...config.context } : ({} as TContext);\n\n // Parse observe config\n const observeConfig =\n config.observe === true\n ? { transitions: true, context: false }\n : config.observe === false || config.observe === undefined\n ? { transitions: false, context: false }\n : config.observe;\n\n // Register for error context tracking\n registerMachineContext(config.id, () => _state);\n\n // Run entry action for initial state (with error handling)\n const initialState = config.states[config.initial];\n if (initialState?.entry) {\n try {\n const update = initialState.entry(_context);\n if (update) {\n _context = { ..._context, ...update };\n }\n } catch (err) {\n console.error(`[svoose] Error in entry action for initial state \"${config.initial}\":`, err);\n }\n }\n\n /**\n * Get transition config for an event\n */\n function getTransition(\n stateConfig: StateNode<TContext, TState, TEvent>,\n eventType: TEvent['type']\n ): TransitionConfig<TContext, TState, TEvent> | TState | undefined {\n return stateConfig.on?.[eventType as keyof typeof stateConfig.on] as\n | TransitionConfig<TContext, TState, TEvent>\n | TState\n | undefined;\n }\n\n /**\n * Check if a transition is valid (exists and guard passes)\n */\n function canTransition(event: TEvent['type'] | TEvent): boolean {\n const eventType = typeof event === 'string' ? event : event.type;\n const eventObj = typeof event === 'string' ? { type: event } as TEvent : event;\n\n const stateConfig = config.states[_state];\n if (!stateConfig?.on) return false;\n\n const transition = getTransition(stateConfig, eventType);\n if (!transition) return false;\n\n // If it's just a target state string, it's always valid\n if (typeof transition === 'string') return true;\n\n // If there's a guard, check it\n if (transition.guard) {\n try {\n return transition.guard(_context, eventObj as Extract<\n TEvent,\n { type: typeof eventType }\n >);\n } catch {\n return false; // guard threw = can't transition\n }\n }\n\n return true;\n }\n\n /**\n * Send an event to the machine\n */\n function send(event: TEvent | TEvent['type']): void {\n const eventObj: TEvent =\n typeof event === 'string' ? ({ type: event } as TEvent) : event;\n\n const stateConfig = config.states[_state];\n if (!stateConfig?.on) return;\n\n const transition = getTransition(stateConfig, eventObj.type);\n if (!transition) return;\n\n const targetState: TState =\n typeof transition === 'string' ? transition : transition.target;\n\n // Check guard (with error handling)\n if (typeof transition === 'object' && transition.guard) {\n try {\n if (\n !transition.guard(\n _context,\n eventObj as Extract<TEvent, { type: (typeof eventObj)['type'] }>\n )\n ) {\n return;\n }\n } catch (err) {\n console.error(`[svoose] Error in guard for event \"${eventObj.type}\":`, err);\n return; // Don't transition if guard throws\n }\n }\n\n const prevState = _state;\n\n // Run exit action (with error handling)\n if (stateConfig.exit) {\n try {\n stateConfig.exit(_context);\n } catch (err) {\n console.error(`[svoose] Error in exit action for state \"${_state}\":`, err);\n }\n }\n\n // Run transition action (with error handling)\n if (typeof transition === 'object' && transition.action) {\n try {\n const update = transition.action(\n _context,\n eventObj as Extract<TEvent, { type: (typeof eventObj)['type'] }>\n );\n if (update) {\n _context = { ..._context, ...update };\n }\n } catch (err) {\n console.error(`[svoose] Error in action for event \"${eventObj.type}\":`, err);\n }\n }\n\n // Update state\n _state = targetState;\n\n // Run entry action for new state (with error handling)\n const newStateConfig = config.states[_state];\n if (newStateConfig?.entry) {\n try {\n const update = newStateConfig.entry(_context);\n if (update) {\n _context = { ..._context, ...update };\n }\n } catch (err) {\n console.error(`[svoose] Error in entry action for state \"${_state}\":`, err);\n }\n }\n\n // Emit observation event\n if (observeConfig.transitions) {\n const observer = getGlobalObserver();\n if (observer) {\n const transitionEvent: TransitionEvent = {\n type: 'transition',\n machineId: config.id,\n from: prevState,\n to: _state,\n event: eventObj.type,\n timestamp: Date.now(),\n ...(observeConfig.context\n ? { context: { ..._context } as Record<string, unknown> }\n : {}),\n };\n observer(transitionEvent);\n }\n }\n }\n\n /**\n * Cleanup machine\n */\n function destroy(): void {\n unregisterMachineContext(config.id);\n }\n\n // Return machine instance\n return {\n get state(): TState {\n return _state;\n },\n get context(): TContext {\n return _context;\n },\n matches(state: TState): boolean {\n return _state === state;\n },\n matchesAny(...states: TState[]): boolean {\n return states.includes(_state);\n },\n can(event: TEvent['type'] | TEvent): boolean {\n return canTransition(event);\n },\n send,\n destroy,\n };\n}\n\n// Re-export types\nexport type { MachineConfig, Machine, EventObject, StateNode, TransitionConfig } from './types.js';\n"],
5
+ "mappings": "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",
6
+ "names": []
7
7
  }
@@ -55,8 +55,8 @@ export interface Machine<TContext extends object, TState extends string, TEvent
55
55
  matches(state: TState): boolean;
56
56
  /** Check if machine is in any of given states */
57
57
  matchesAny(...states: TState[]): boolean;
58
- /** Check if event can be sent (has valid transition) */
59
- can(eventType: TEvent['type']): boolean;
58
+ /** Check if event can be sent (has valid transition). Accepts string or full event object for payload-dependent guards. */
59
+ can(event: TEvent['type'] | TEvent): boolean;
60
60
  /** Send event to machine */
61
61
  send(event: TEvent | TEvent['type']): void;
62
62
  /** Cleanup machine (unregister from error tracking) */
@@ -1 +1 @@
1
- {"version":3,"file":"types.d.ts","sourceRoot":"","sources":["../../src/machine/types.ts"],"names":[],"mappings":"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"}
1
+ {"version":3,"file":"types.d.ts","sourceRoot":"","sources":["../../src/machine/types.ts"],"names":[],"mappings":"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"}
@@ -1,6 +1,6 @@
1
1
  /**
2
2
  * Metrics module exports
3
3
  */
4
- export { metric, counter, gauge, histogram, setMetricEmitter, getMetricEmitter, _getPendingEventsCount, _clearPendingEvents, } from './metric.js';
4
+ export { metric, counter, gauge, histogram, setMetricEmitter, getMetricEmitter, } from './metric.js';
5
5
  export { createTypedMetric } from './typed.js';
6
6
  //# sourceMappingURL=index.d.ts.map
@@ -1 +1 @@
1
- {"version":3,"file":"index.d.ts","sourceRoot":"","sources":["../../src/metrics/index.ts"],"names":[],"mappings":"AAAA;;GAEG;AAEH,OAAO,EACL,MAAM,EACN,OAAO,EACP,KAAK,EACL,SAAS,EACT,gBAAgB,EAChB,gBAAgB,EAChB,sBAAsB,EACtB,mBAAmB,GACpB,MAAM,aAAa,CAAC;AAErB,OAAO,EAAE,iBAAiB,EAAE,MAAM,YAAY,CAAC"}
1
+ {"version":3,"file":"index.d.ts","sourceRoot":"","sources":["../../src/metrics/index.ts"],"names":[],"mappings":"AAAA;;GAEG;AAEH,OAAO,EACL,MAAM,EACN,OAAO,EACP,KAAK,EACL,SAAS,EACT,gBAAgB,EAChB,gBAAgB,GACjB,MAAM,aAAa,CAAC;AAErB,OAAO,EAAE,iBAAiB,EAAE,MAAM,YAAY,CAAC"}
@@ -1,2 +1,2 @@
1
- import{metric as r,counter as i,gauge as n,histogram as c,setMetricEmitter as g,getMetricEmitter as o,_getPendingEventsCount as m,_clearPendingEvents as a}from"./metric.js";import{createTypedMetric as E}from"./typed.js";export{a as _clearPendingEvents,m as _getPendingEventsCount,i as counter,E as createTypedMetric,n as gauge,o as getMetricEmitter,c as histogram,r as metric,g as setMetricEmitter};
1
+ import{metric as r,counter as i,gauge as c,histogram as m,setMetricEmitter as o,getMetricEmitter as g}from"./metric.js";import{createTypedMetric as p}from"./typed.js";export{i as counter,p as createTypedMetric,c as gauge,g as getMetricEmitter,m as histogram,r as metric,o as setMetricEmitter};
2
2
  //# sourceMappingURL=index.js.map
@@ -1,7 +1,7 @@
1
1
  {
2
2
  "version": 3,
3
3
  "sources": ["../../src/metrics/index.ts"],
4
- "sourcesContent": ["/**\n * Metrics module exports\n */\n\nexport {\n metric,\n counter,\n gauge,\n histogram,\n setMetricEmitter,\n getMetricEmitter,\n _getPendingEventsCount,\n _clearPendingEvents,\n} from './metric.js';\n\nexport { createTypedMetric } from './typed.js';\n"],
5
- "mappings": "AAIA,OACE,UAAAA,EACA,WAAAC,EACA,SAAAC,EACA,aAAAC,EACA,oBAAAC,EACA,oBAAAC,EACA,0BAAAC,EACA,uBAAAC,MACK,cAEP,OAAS,qBAAAC,MAAyB",
6
- "names": ["metric", "counter", "gauge", "histogram", "setMetricEmitter", "getMetricEmitter", "_getPendingEventsCount", "_clearPendingEvents", "createTypedMetric"]
4
+ "sourcesContent": ["/**\n * Metrics module exports\n */\n\nexport {\n metric,\n counter,\n gauge,\n histogram,\n setMetricEmitter,\n getMetricEmitter,\n} from './metric.js';\n\nexport { createTypedMetric } from './typed.js';\n"],
5
+ "mappings": "AAIA,OACE,UAAAA,EACA,WAAAC,EACA,SAAAC,EACA,aAAAC,EACA,oBAAAC,EACA,oBAAAC,MACK,cAEP,OAAS,qBAAAC,MAAyB",
6
+ "names": ["metric", "counter", "gauge", "histogram", "setMetricEmitter", "getMetricEmitter", "createTypedMetric"]
7
7
  }
@@ -11,26 +11,12 @@ import type { ObserveEvent } from '../types/index.js';
11
11
  * @param emit - The emit function from observe(), or null to disconnect
12
12
  */
13
13
  export declare function setMetricEmitter(emit: ((event: ObserveEvent) => void) | null): void;
14
- /**
15
- * Send a custom metric event
16
- *
17
- * Events are automatically batched with other metrics and sent to your backend.
18
- * If called before observe() is initialized, events are buffered (max 100).
19
- *
20
- * @param name - Metric name (e.g., 'checkout_started', 'button_clicked')
21
- * @param data - Optional data payload
22
- *
23
- * @example
24
- * metric('checkout_started', { step: 1, cartTotal: 99.99 });
25
- * metric('button_clicked', { id: 'submit-btn' });
26
- * metric('feature_used', { name: 'dark_mode', enabled: true });
27
- */
28
14
  /**
29
15
  * Get the current metric emitter function (for internal use)
30
16
  * @internal
31
17
  */
32
18
  export declare function getMetricEmitter(): ((event: ObserveEvent) => void) | null;
33
- export declare function metric(name: string, data?: Record<string, unknown>): void;
19
+ export declare function metric(name: string, metadata?: Record<string, unknown>): void;
34
20
  /**
35
21
  * Increment a counter metric
36
22
  *
@@ -1 +1 @@
1
- {"version":3,"file":"metric.d.ts","sourceRoot":"","sources":["../../src/metrics/metric.ts"],"names":[],"mappings":"AAAA;;;;GAIG;AAEH,OAAO,KAAK,EAAqB,YAAY,EAAE,MAAM,mBAAmB,CAAC;AAWzE;;;;;GAKG;AACH,wBAAgB,gBAAgB,CAAC,IAAI,EAAE,CAAC,CAAC,KAAK,EAAE,YAAY,KAAK,IAAI,CAAC,GAAG,IAAI,GAAG,IAAI,CAUnF;AAED;;;;;;;;;;;;;GAaG;AACH;;;GAGG;AACH,wBAAgB,gBAAgB,IAAI,CAAC,CAAC,KAAK,EAAE,YAAY,KAAK,IAAI,CAAC,GAAG,IAAI,CAEzE;AAkBD,wBAAgB,MAAM,CAAC,IAAI,EAAE,MAAM,EAAE,IAAI,GAAE,MAAM,CAAC,MAAM,EAAE,OAAO,CAAM,GAAG,IAAI,CAE7E;AAkCD;;;;;;;;;;;GAWG;AACH,wBAAgB,OAAO,CAAC,IAAI,EAAE,MAAM,EAAE,KAAK,GAAE,MAAU,EAAE,QAAQ,CAAC,EAAE,MAAM,CAAC,MAAM,EAAE,OAAO,CAAC,GAAG,IAAI,CAEjG;AAED;;;;;;;;;;GAUG;AACH,wBAAgB,KAAK,CAAC,IAAI,EAAE,MAAM,EAAE,KAAK,EAAE,MAAM,EAAE,QAAQ,CAAC,EAAE,MAAM,CAAC,MAAM,EAAE,OAAO,CAAC,GAAG,IAAI,CAE3F;AAED;;;;;;;;;;GAUG;AACH,wBAAgB,SAAS,CAAC,IAAI,EAAE,MAAM,EAAE,KAAK,EAAE,MAAM,EAAE,QAAQ,CAAC,EAAE,MAAM,CAAC,MAAM,EAAE,OAAO,CAAC,GAAG,IAAI,CAE/F;AAMD;;;GAGG;AACH,wBAAgB,sBAAsB,IAAI,MAAM,CAE/C;AAED;;;GAGG;AACH,wBAAgB,mBAAmB,IAAI,IAAI,CAE1C"}
1
+ {"version":3,"file":"metric.d.ts","sourceRoot":"","sources":["../../src/metrics/metric.ts"],"names":[],"mappings":"AAAA;;;;GAIG;AAEH,OAAO,KAAK,EAAqB,YAAY,EAAE,MAAM,mBAAmB,CAAC;AAWzE;;;;;GAKG;AACH,wBAAgB,gBAAgB,CAAC,IAAI,EAAE,CAAC,CAAC,KAAK,EAAE,YAAY,KAAK,IAAI,CAAC,GAAG,IAAI,GAAG,IAAI,CAUnF;AAED;;;GAGG;AACH,wBAAgB,gBAAgB,IAAI,CAAC,CAAC,KAAK,EAAE,YAAY,KAAK,IAAI,CAAC,GAAG,IAAI,CAEzE;AAkBD,wBAAgB,MAAM,CAAC,IAAI,EAAE,MAAM,EAAE,QAAQ,GAAE,MAAM,CAAC,MAAM,EAAE,OAAO,CAAM,GAAG,IAAI,CAEjF;AAkCD;;;;;;;;;;;GAWG;AACH,wBAAgB,OAAO,CAAC,IAAI,EAAE,MAAM,EAAE,KAAK,GAAE,MAAU,EAAE,QAAQ,CAAC,EAAE,MAAM,CAAC,MAAM,EAAE,OAAO,CAAC,GAAG,IAAI,CAEjG;AAED;;;;;;;;;;GAUG;AACH,wBAAgB,KAAK,CAAC,IAAI,EAAE,MAAM,EAAE,KAAK,EAAE,MAAM,EAAE,QAAQ,CAAC,EAAE,MAAM,CAAC,MAAM,EAAE,OAAO,CAAC,GAAG,IAAI,CAE3F;AAED;;;;;;;;;;GAUG;AACH,wBAAgB,SAAS,CAAC,IAAI,EAAE,MAAM,EAAE,KAAK,EAAE,MAAM,EAAE,QAAQ,CAAC,EAAE,MAAM,CAAC,MAAM,EAAE,OAAO,CAAC,GAAG,IAAI,CAE/F;AAMD;;;GAGG;AACH,wBAAgB,sBAAsB,IAAI,MAAM,CAE/C;AAED;;;GAGG;AACH,wBAAgB,mBAAmB,IAAI,IAAI,CAE1C"}
@@ -1,2 +1,2 @@
1
- let o=null;const r=[];function v(e){if(o=e,o&&r.length>0){const n=r.splice(0,r.length);for(const t of n)o(t)}}function d(){return o}function c(){try{return typeof process<"u",import.meta.env?.DEV===!0}catch{return!1}}function g(e,n={}){s({type:"custom",name:e,data:n,timestamp:Date.now()})}function s(e){if(o)o(e);else{if(r.length>=100){c()&&console.warn("[svoose] metric() buffer full (100 events). Call observe() to start sending events. New events are being dropped.");return}r.push(e)}}function i(e,n,t,u={}){s({type:"custom",name:e,metricKind:n,value:t,data:u,timestamp:Date.now()})}function f(e,n=1,t){i(e,"counter",n,t)}function m(e,n,t){i(e,"gauge",n,t)}function l(e,n,t){i(e,"histogram",n,t)}function p(){return r.length}function a(){r.length=0}export{a as _clearPendingEvents,p as _getPendingEventsCount,f as counter,m as gauge,d as getMetricEmitter,l as histogram,g as metric,v as setMetricEmitter};
1
+ let o=null;const r=[];function v(e){if(o=e,o&&r.length>0){const n=r.splice(0,r.length);for(const t of n)o(t)}}function g(){return o}function c(){try{return typeof process<"u",import.meta.env?.DEV===!0}catch{return!1}}function d(e,n={}){s({type:"custom",name:e,metadata:n,timestamp:Date.now()})}function s(e){if(o)o(e);else{if(r.length>=100){c()&&console.warn("[svoose] metric() buffer full (100 events). Call observe() to start sending events. New events are being dropped.");return}r.push(e)}}function i(e,n,t,u={}){s({type:"custom",name:e,metricKind:n,value:t,metadata:u,timestamp:Date.now()})}function f(e,n=1,t){i(e,"counter",n,t)}function m(e,n,t){i(e,"gauge",n,t)}function l(e,n,t){i(e,"histogram",n,t)}function p(){return r.length}function E(){r.length=0}export{E as _clearPendingEvents,p as _getPendingEventsCount,f as counter,m as gauge,g as getMetricEmitter,l as histogram,d as metric,v as setMetricEmitter};
2
2
  //# sourceMappingURL=metric.js.map
@@ -1,7 +1,7 @@
1
1
  {
2
2
  "version": 3,
3
3
  "sources": ["../../src/metrics/metric.ts"],
4
- "sourcesContent": ["/**\n * Custom metrics module\n *\n * Provides metric() function for sending custom events with pending buffer support.\n */\n\nimport type { CustomMetricEvent, ObserveEvent } from '../types/index.js';\n\n// Maximum pending events before dropping (with warning in dev)\nconst MAX_PENDING_EVENTS = 100;\n\n// Emitter function set by observe()\nlet emitter: ((event: ObserveEvent) => void) | null = null;\n\n// Pending events buffer for events sent before observe() is initialized\nconst pendingEvents: CustomMetricEvent[] = [];\n\n/**\n * Set the metric emitter function\n * Called by observe() to wire up the metric system\n *\n * @param emit - The emit function from observe(), or null to disconnect\n */\nexport function setMetricEmitter(emit: ((event: ObserveEvent) => void) | null): void {\n emitter = emit;\n\n // Flush pending events when emitter is set\n if (emitter && pendingEvents.length > 0) {\n const events = pendingEvents.splice(0, pendingEvents.length);\n for (const event of events) {\n emitter(event);\n }\n }\n}\n\n/**\n * Send a custom metric event\n *\n * Events are automatically batched with other metrics and sent to your backend.\n * If called before observe() is initialized, events are buffered (max 100).\n *\n * @param name - Metric name (e.g., 'checkout_started', 'button_clicked')\n * @param data - Optional data payload\n *\n * @example\n * metric('checkout_started', { step: 1, cartTotal: 99.99 });\n * metric('button_clicked', { id: 'submit-btn' });\n * metric('feature_used', { name: 'dark_mode', enabled: true });\n */\n/**\n * Get the current metric emitter function (for internal use)\n * @internal\n */\nexport function getMetricEmitter(): ((event: ObserveEvent) => void) | null {\n return emitter;\n}\n\ndeclare const process: { env: Record<string, string | undefined> } | undefined;\n\nfunction isDev(): boolean {\n try {\n if (typeof process !== 'undefined' && process?.env?.NODE_ENV === 'development') {\n return true;\n }\n if ((import.meta as any).env?.DEV === true) {\n return true;\n }\n return false;\n } catch {\n return false;\n }\n}\n\nexport function metric(name: string, data: Record<string, unknown> = {}): void {\n emitEvent({ type: 'custom', name, data, timestamp: Date.now() });\n}\n\n/**\n * Internal helper to emit or buffer a CustomMetricEvent\n */\nfunction emitEvent(event: CustomMetricEvent): void {\n if (emitter) {\n emitter(event);\n } else {\n if (pendingEvents.length >= MAX_PENDING_EVENTS) {\n if (isDev()) {\n console.warn(\n `[svoose] metric() buffer full (${MAX_PENDING_EVENTS} events). ` +\n `Call observe() to start sending events. New events are being dropped.`\n );\n }\n return;\n }\n pendingEvents.push(event);\n }\n}\n\n/**\n * Internal helper for typed metric helpers (counter, gauge, histogram)\n */\nfunction emitMetric(\n name: string,\n metricKind: 'counter' | 'gauge' | 'histogram',\n value: number,\n metadata: Record<string, unknown> = {},\n): void {\n emitEvent({ type: 'custom', name, metricKind, value, data: metadata, timestamp: Date.now() });\n}\n\n/**\n * Increment a counter metric\n *\n * @param name - Counter name\n * @param value - Increment amount (default: 1)\n * @param metadata - Optional metadata\n *\n * @example\n * counter('page_views');\n * counter('items_purchased', 3);\n * counter('api_calls', 1, { endpoint: '/users' });\n */\nexport function counter(name: string, value: number = 1, metadata?: Record<string, unknown>): void {\n emitMetric(name, 'counter', value, metadata);\n}\n\n/**\n * Set a gauge metric (point-in-time value)\n *\n * @param name - Gauge name\n * @param value - Current value\n * @param metadata - Optional metadata\n *\n * @example\n * gauge('active_users', 42);\n * gauge('memory_usage_mb', 256, { heap: 'old' });\n */\nexport function gauge(name: string, value: number, metadata?: Record<string, unknown>): void {\n emitMetric(name, 'gauge', value, metadata);\n}\n\n/**\n * Record a histogram metric (distribution value)\n *\n * @param name - Histogram name\n * @param value - Observed value\n * @param metadata - Optional metadata\n *\n * @example\n * histogram('response_time_ms', 123);\n * histogram('payload_size', 4096, { route: '/api/data' });\n */\nexport function histogram(name: string, value: number, metadata?: Record<string, unknown>): void {\n emitMetric(name, 'histogram', value, metadata);\n}\n\n// ============================================\n// Test helpers (not exported in production builds)\n// ============================================\n\n/**\n * Get number of pending events (for testing)\n * @internal\n */\nexport function _getPendingEventsCount(): number {\n return pendingEvents.length;\n}\n\n/**\n * Clear pending events (for testing)\n * @internal\n */\nexport function _clearPendingEvents(): void {\n pendingEvents.length = 0;\n}\n"],
5
- "mappings": "AAYA,IAAIA,EAAkD,KAGtD,MAAMC,EAAqC,CAAC,EAQrC,SAASC,EAAiBC,EAAoD,CAInF,GAHAH,EAAUG,EAGNH,GAAWC,EAAc,OAAS,EAAG,CACvC,MAAMG,EAASH,EAAc,OAAO,EAAGA,EAAc,MAAM,EAC3D,UAAWI,KAASD,EAClBJ,EAAQK,CAAK,CAEjB,CACF,CAoBO,SAASC,GAA2D,CACzE,OAAON,CACT,CAIA,SAASO,GAAiB,CACxB,GAAI,CAIF,OAHI,OAAO,QAAY,IAGlB,YAAoB,KAAK,MAAQ,EAIxC,MAAQ,CACN,MAAO,EACT,CACF,CAEO,SAASC,EAAOC,EAAcC,EAAgC,CAAC,EAAS,CAC7EC,EAAU,CAAE,KAAM,SAAU,KAAAF,EAAM,KAAAC,EAAM,UAAW,KAAK,IAAI,CAAE,CAAC,CACjE,CAKA,SAASC,EAAUN,EAAgC,CACjD,GAAIL,EACFA,EAAQK,CAAK,MACR,CACL,GAAIJ,EAAc,QAAU,IAAoB,CAC1CM,EAAM,GACR,QAAQ,KACN,mHAEF,EAEF,MACF,CACAN,EAAc,KAAKI,CAAK,CAC1B,CACF,CAKA,SAASO,EACPH,EACAI,EACAC,EACAC,EAAoC,CAAC,EAC/B,CACNJ,EAAU,CAAE,KAAM,SAAU,KAAAF,EAAM,WAAAI,EAAY,MAAAC,EAAO,KAAMC,EAAU,UAAW,KAAK,IAAI,CAAE,CAAC,CAC9F,CAcO,SAASC,EAAQP,EAAcK,EAAgB,EAAGC,EAA0C,CACjGH,EAAWH,EAAM,UAAWK,EAAOC,CAAQ,CAC7C,CAaO,SAASE,EAAMR,EAAcK,EAAeC,EAA0C,CAC3FH,EAAWH,EAAM,QAASK,EAAOC,CAAQ,CAC3C,CAaO,SAASG,EAAUT,EAAcK,EAAeC,EAA0C,CAC/FH,EAAWH,EAAM,YAAaK,EAAOC,CAAQ,CAC/C,CAUO,SAASI,GAAiC,CAC/C,OAAOlB,EAAc,MACvB,CAMO,SAASmB,GAA4B,CAC1CnB,EAAc,OAAS,CACzB",
6
- "names": ["emitter", "pendingEvents", "setMetricEmitter", "emit", "events", "event", "getMetricEmitter", "isDev", "metric", "name", "data", "emitEvent", "emitMetric", "metricKind", "value", "metadata", "counter", "gauge", "histogram", "_getPendingEventsCount", "_clearPendingEvents"]
4
+ "sourcesContent": ["/**\n * Custom metrics module\n *\n * Provides metric() function for sending custom events with pending buffer support.\n */\n\nimport type { CustomMetricEvent, ObserveEvent } from '../types/index.js';\n\n// Maximum pending events before dropping (with warning in dev)\nconst MAX_PENDING_EVENTS = 100;\n\n// Emitter function set by observe()\nlet emitter: ((event: ObserveEvent) => void) | null = null;\n\n// Pending events buffer for events sent before observe() is initialized\nconst pendingEvents: CustomMetricEvent[] = [];\n\n/**\n * Set the metric emitter function\n * Called by observe() to wire up the metric system\n *\n * @param emit - The emit function from observe(), or null to disconnect\n */\nexport function setMetricEmitter(emit: ((event: ObserveEvent) => void) | null): void {\n emitter = emit;\n\n // Flush pending events when emitter is set\n if (emitter && pendingEvents.length > 0) {\n const events = pendingEvents.splice(0, pendingEvents.length);\n for (const event of events) {\n emitter(event);\n }\n }\n}\n\n/**\n * Get the current metric emitter function (for internal use)\n * @internal\n */\nexport function getMetricEmitter(): ((event: ObserveEvent) => void) | null {\n return emitter;\n}\n\ndeclare const process: { env: Record<string, string | undefined> } | undefined;\n\nfunction isDev(): boolean {\n try {\n if (typeof process !== 'undefined' && process?.env?.NODE_ENV === 'development') {\n return true;\n }\n if ((import.meta as any).env?.DEV === true) {\n return true;\n }\n return false;\n } catch {\n return false;\n }\n}\n\nexport function metric(name: string, metadata: Record<string, unknown> = {}): void {\n emitEvent({ type: 'custom', name, metadata, timestamp: Date.now() });\n}\n\n/**\n * Internal helper to emit or buffer a CustomMetricEvent\n */\nfunction emitEvent(event: CustomMetricEvent): void {\n if (emitter) {\n emitter(event);\n } else {\n if (pendingEvents.length >= MAX_PENDING_EVENTS) {\n if (isDev()) {\n console.warn(\n `[svoose] metric() buffer full (${MAX_PENDING_EVENTS} events). ` +\n `Call observe() to start sending events. New events are being dropped.`\n );\n }\n return;\n }\n pendingEvents.push(event);\n }\n}\n\n/**\n * Internal helper for typed metric helpers (counter, gauge, histogram)\n */\nfunction emitMetric(\n name: string,\n metricKind: 'counter' | 'gauge' | 'histogram',\n value: number,\n metadata: Record<string, unknown> = {},\n): void {\n emitEvent({ type: 'custom', name, metricKind, value, metadata, timestamp: Date.now() });\n}\n\n/**\n * Increment a counter metric\n *\n * @param name - Counter name\n * @param value - Increment amount (default: 1)\n * @param metadata - Optional metadata\n *\n * @example\n * counter('page_views');\n * counter('items_purchased', 3);\n * counter('api_calls', 1, { endpoint: '/users' });\n */\nexport function counter(name: string, value: number = 1, metadata?: Record<string, unknown>): void {\n emitMetric(name, 'counter', value, metadata);\n}\n\n/**\n * Set a gauge metric (point-in-time value)\n *\n * @param name - Gauge name\n * @param value - Current value\n * @param metadata - Optional metadata\n *\n * @example\n * gauge('active_users', 42);\n * gauge('memory_usage_mb', 256, { heap: 'old' });\n */\nexport function gauge(name: string, value: number, metadata?: Record<string, unknown>): void {\n emitMetric(name, 'gauge', value, metadata);\n}\n\n/**\n * Record a histogram metric (distribution value)\n *\n * @param name - Histogram name\n * @param value - Observed value\n * @param metadata - Optional metadata\n *\n * @example\n * histogram('response_time_ms', 123);\n * histogram('payload_size', 4096, { route: '/api/data' });\n */\nexport function histogram(name: string, value: number, metadata?: Record<string, unknown>): void {\n emitMetric(name, 'histogram', value, metadata);\n}\n\n// ============================================\n// Test helpers (not exported in production builds)\n// ============================================\n\n/**\n * Get number of pending events (for testing)\n * @internal\n */\nexport function _getPendingEventsCount(): number {\n return pendingEvents.length;\n}\n\n/**\n * Clear pending events (for testing)\n * @internal\n */\nexport function _clearPendingEvents(): void {\n pendingEvents.length = 0;\n}\n"],
5
+ "mappings": "AAYA,IAAIA,EAAkD,KAGtD,MAAMC,EAAqC,CAAC,EAQrC,SAASC,EAAiBC,EAAoD,CAInF,GAHAH,EAAUG,EAGNH,GAAWC,EAAc,OAAS,EAAG,CACvC,MAAMG,EAASH,EAAc,OAAO,EAAGA,EAAc,MAAM,EAC3D,UAAWI,KAASD,EAClBJ,EAAQK,CAAK,CAEjB,CACF,CAMO,SAASC,GAA2D,CACzE,OAAON,CACT,CAIA,SAASO,GAAiB,CACxB,GAAI,CAIF,OAHI,OAAO,QAAY,IAGlB,YAAoB,KAAK,MAAQ,EAIxC,MAAQ,CACN,MAAO,EACT,CACF,CAEO,SAASC,EAAOC,EAAcC,EAAoC,CAAC,EAAS,CACjFC,EAAU,CAAE,KAAM,SAAU,KAAAF,EAAM,SAAAC,EAAU,UAAW,KAAK,IAAI,CAAE,CAAC,CACrE,CAKA,SAASC,EAAUN,EAAgC,CACjD,GAAIL,EACFA,EAAQK,CAAK,MACR,CACL,GAAIJ,EAAc,QAAU,IAAoB,CAC1CM,EAAM,GACR,QAAQ,KACN,mHAEF,EAEF,MACF,CACAN,EAAc,KAAKI,CAAK,CAC1B,CACF,CAKA,SAASO,EACPH,EACAI,EACAC,EACAJ,EAAoC,CAAC,EAC/B,CACNC,EAAU,CAAE,KAAM,SAAU,KAAAF,EAAM,WAAAI,EAAY,MAAAC,EAAO,SAAAJ,EAAU,UAAW,KAAK,IAAI,CAAE,CAAC,CACxF,CAcO,SAASK,EAAQN,EAAcK,EAAgB,EAAGJ,EAA0C,CACjGE,EAAWH,EAAM,UAAWK,EAAOJ,CAAQ,CAC7C,CAaO,SAASM,EAAMP,EAAcK,EAAeJ,EAA0C,CAC3FE,EAAWH,EAAM,QAASK,EAAOJ,CAAQ,CAC3C,CAaO,SAASO,EAAUR,EAAcK,EAAeJ,EAA0C,CAC/FE,EAAWH,EAAM,YAAaK,EAAOJ,CAAQ,CAC/C,CAUO,SAASQ,GAAiC,CAC/C,OAAOjB,EAAc,MACvB,CAMO,SAASkB,GAA4B,CAC1ClB,EAAc,OAAS,CACzB",
6
+ "names": ["emitter", "pendingEvents", "setMetricEmitter", "emit", "events", "event", "getMetricEmitter", "isDev", "metric", "name", "metadata", "emitEvent", "emitMetric", "metricKind", "value", "counter", "gauge", "histogram", "_getPendingEventsCount", "_clearPendingEvents"]
7
7
  }
@@ -14,5 +14,5 @@
14
14
  * m('button_clicked', { id: 'submit' }); // ✅
15
15
  * m('unknown_event', {}); // ❌ TypeScript error
16
16
  */
17
- export declare function createTypedMetric<T extends Record<string, Record<string, unknown>>>(): <K extends keyof T & string>(name: K, data: T[K]) => void;
17
+ export declare function createTypedMetric<T extends Record<string, Record<string, unknown>>>(): <K extends keyof T & string>(name: K, metadata: T[K]) => void;
18
18
  //# sourceMappingURL=typed.d.ts.map
@@ -1 +1 @@
1
- {"version":3,"file":"typed.d.ts","sourceRoot":"","sources":["../../src/metrics/typed.ts"],"names":[],"mappings":"AAAA;;GAEG;AAIH;;;;;;;;;;;;GAYG;AACH,wBAAgB,iBAAiB,CAAC,CAAC,SAAS,MAAM,CAAC,MAAM,EAAE,MAAM,CAAC,MAAM,EAAE,OAAO,CAAC,CAAC,MAChE,CAAC,SAAS,MAAM,CAAC,GAAG,MAAM,EAAE,MAAM,CAAC,EAAE,MAAM,CAAC,CAAC,CAAC,CAAC,KAAG,IAAI,CAGxE"}
1
+ {"version":3,"file":"typed.d.ts","sourceRoot":"","sources":["../../src/metrics/typed.ts"],"names":[],"mappings":"AAAA;;GAEG;AAIH;;;;;;;;;;;;GAYG;AACH,wBAAgB,iBAAiB,CAAC,CAAC,SAAS,MAAM,CAAC,MAAM,EAAE,MAAM,CAAC,MAAM,EAAE,OAAO,CAAC,CAAC,MAChE,CAAC,SAAS,MAAM,CAAC,GAAG,MAAM,EAAE,MAAM,CAAC,EAAE,UAAU,CAAC,CAAC,CAAC,CAAC,KAAG,IAAI,CAG5E"}
@@ -1,7 +1,7 @@
1
1
  {
2
2
  "version": 3,
3
3
  "sources": ["../../src/metrics/typed.ts"],
4
- "sourcesContent": ["/**\n * Typed metric factory for TypeScript autocomplete\n */\n\nimport { metric } from './metric.js';\n\n/**\n * Create a typed metric function with autocomplete for metric names and data shapes\n *\n * @example\n * const m = createTypedMetric<{\n * checkout_started: { step: number; cartTotal: number };\n * button_clicked: { id: string };\n * }>();\n *\n * m('checkout_started', { step: 1, cartTotal: 99.99 }); // \u2705 autocomplete works\n * m('button_clicked', { id: 'submit' }); // \u2705\n * m('unknown_event', {}); // \u274C TypeScript error\n */\nexport function createTypedMetric<T extends Record<string, Record<string, unknown>>>() {\n return function <K extends keyof T & string>(name: K, data: T[K]): void {\n metric(name, data);\n };\n}\n"],
5
- "mappings": "AAIA,OAAS,UAAAA,MAAc,cAehB,SAASC,GAAuE,CACrF,OAAO,SAAsCC,EAASC,EAAkB,CACtEH,EAAOE,EAAMC,CAAI,CACnB,CACF",
6
- "names": ["metric", "createTypedMetric", "name", "data"]
4
+ "sourcesContent": ["/**\n * Typed metric factory for TypeScript autocomplete\n */\n\nimport { metric } from './metric.js';\n\n/**\n * Create a typed metric function with autocomplete for metric names and data shapes\n *\n * @example\n * const m = createTypedMetric<{\n * checkout_started: { step: number; cartTotal: number };\n * button_clicked: { id: string };\n * }>();\n *\n * m('checkout_started', { step: 1, cartTotal: 99.99 }); // \u2705 autocomplete works\n * m('button_clicked', { id: 'submit' }); // \u2705\n * m('unknown_event', {}); // \u274C TypeScript error\n */\nexport function createTypedMetric<T extends Record<string, Record<string, unknown>>>() {\n return function <K extends keyof T & string>(name: K, metadata: T[K]): void {\n metric(name, metadata);\n };\n}\n"],
5
+ "mappings": "AAIA,OAAS,UAAAA,MAAc,cAehB,SAASC,GAAuE,CACrF,OAAO,SAAsCC,EAASC,EAAsB,CAC1EH,EAAOE,EAAMC,CAAQ,CACvB,CACF",
6
+ "names": ["metric", "createTypedMetric", "name", "metadata"]
7
7
  }
@@ -1 +1 @@
1
- {"version":3,"file":"errors.d.ts","sourceRoot":"","sources":["../../src/observe/errors.ts"],"names":[],"mappings":"AAAA;;;GAGG;AAEH,OAAO,KAAK,EAAE,UAAU,EAAE,uBAAuB,EAAE,iBAAiB,EAAE,MAAM,mBAAmB,CAAC;AAKhG;;;GAGG;AACH,wBAAgB,sBAAsB,CAAC,EAAE,EAAE,MAAM,EAAE,QAAQ,EAAE,MAAM,MAAM,GAAG,IAAI,CAE/E;AAED;;;GAGG;AACH,wBAAgB,wBAAwB,CAAC,EAAE,EAAE,MAAM,GAAG,IAAI,CAEzD;AA4BD;;;;GAIG;AACH,wBAAgB,aAAa,CAC3B,QAAQ,EAAE,CAAC,KAAK,EAAE,iBAAiB,KAAK,IAAI,GAC3C,MAAM,IAAI,CAsDZ;AAED,YAAY,EAAE,UAAU,EAAE,uBAAuB,EAAE,iBAAiB,EAAE,CAAC"}
1
+ {"version":3,"file":"errors.d.ts","sourceRoot":"","sources":["../../src/observe/errors.ts"],"names":[],"mappings":"AAAA;;;GAGG;AAEH,OAAO,KAAK,EAAE,UAAU,EAAE,uBAAuB,EAAE,iBAAiB,EAAE,MAAM,mBAAmB,CAAC;AAKhG;;;GAGG;AACH,wBAAgB,sBAAsB,CAAC,EAAE,EAAE,MAAM,EAAE,QAAQ,EAAE,MAAM,MAAM,GAAG,IAAI,CAE/E;AAED;;;GAGG;AACH,wBAAgB,wBAAwB,CAAC,EAAE,EAAE,MAAM,GAAG,IAAI,CAEzD;AA6CD;;;;GAIG;AACH,wBAAgB,aAAa,CAC3B,QAAQ,EAAE,CAAC,KAAK,EAAE,iBAAiB,KAAK,IAAI,GAC3C,MAAM,IAAI,CAsDZ;AAED,YAAY,EAAE,UAAU,EAAE,uBAAuB,EAAE,iBAAiB,EAAE,CAAC"}
@@ -1,2 +1,2 @@
1
- const i=new Map;function E(e,r){i.set(e,{getState:r})}function v(e){i.delete(e)}function a(){for(const[e,r]of i)try{return{machineId:e,machineState:r.getState()}}catch{}return{}}function c(){try{return typeof location<"u"?location.href:""}catch{return""}}function g(e){if(typeof window>"u")return()=>{};const r=t=>{const n={type:"error",message:t.message||"Unknown error",stack:t.error?.stack,filename:t.filename,lineno:t.lineno,colno:t.colno,timestamp:Date.now(),url:c(),...a()};e(n)},s=t=>{const n=t.reason;let o;if(n instanceof Error)o=n.message;else if(typeof n=="string")o=n;else try{o=JSON.stringify(n)}catch{o=String(n)}const d={type:"unhandled-rejection",reason:o,timestamp:Date.now(),url:c(),...a()};e(d)};return window.addEventListener("error",r),window.addEventListener("unhandledrejection",s),()=>{window.removeEventListener("error",r),window.removeEventListener("unhandledrejection",s)}}export{g as observeErrors,E as registerMachineContext,v as unregisterMachineContext};
1
+ const s=new Map;function E(e,r){s.set(e,{getState:r})}function l(e){s.delete(e)}const g=10;function a(){if(s.size===0)return{};const e=[];for(const[r,i]of s){if(e.length>=g)break;try{e.push({id:r,state:i.getState()})}catch{}}return e.length===0?{}:{machineId:e[0].id,machineState:e[0].state,machines:e}}function c(){try{return typeof location<"u"?location.href:""}catch{return""}}function f(e){if(typeof window>"u")return()=>{};const r=t=>{const n={type:"error",message:t.message||"Unknown error",stack:t.error?.stack,filename:t.filename,lineno:t.lineno,colno:t.colno,timestamp:Date.now(),url:c(),...a()};e(n)},i=t=>{const n=t.reason;let o;if(n instanceof Error)o=n.message;else if(typeof n=="string")o=n;else try{o=JSON.stringify(n)}catch{o=String(n)}const d={type:"unhandled-rejection",reason:o,timestamp:Date.now(),url:c(),...a()};e(d)};return window.addEventListener("error",r),window.addEventListener("unhandledrejection",i),()=>{window.removeEventListener("error",r),window.removeEventListener("unhandledrejection",i)}}export{f as observeErrors,E as registerMachineContext,l as unregisterMachineContext};
2
2
  //# sourceMappingURL=errors.js.map
@@ -1,7 +1,7 @@
1
1
  {
2
2
  "version": 3,
3
3
  "sources": ["../../src/observe/errors.ts"],
4
- "sourcesContent": ["/**\n * Error tracking - captures errors and unhandled promise rejections\n * Integrates with state machines to include machine context in error reports\n */\n\nimport type { ErrorEvent, UnhandledRejectionEvent, ObserveErrorEvent } from '../types/index.js';\n\n// Global machine context registry (populated by createMachine)\nconst machineContexts = new Map<string, { getState: () => string }>();\n\n/**\n * Register a machine's context for error tracking\n * Called internally by createMachine()\n */\nexport function registerMachineContext(id: string, getState: () => string): void {\n machineContexts.set(id, { getState });\n}\n\n/**\n * Unregister a machine's context\n * Called internally when machine is destroyed\n */\nexport function unregisterMachineContext(id: string): void {\n machineContexts.delete(id);\n}\n\n/**\n * Get current machine context for error reports\n * Returns first active machine (could be enhanced for multiple)\n */\nfunction getMachineContext(): { machineId?: string; machineState?: string } {\n for (const [id, ctx] of machineContexts) {\n try {\n return { machineId: id, machineState: ctx.getState() };\n } catch {\n // Machine might be in invalid state, skip it\n }\n }\n return {};\n}\n\n/**\n * Get current URL safely\n */\nfunction getCurrentUrl(): string {\n try {\n return typeof location !== 'undefined' ? location.href : '';\n } catch {\n return '';\n }\n}\n\n/**\n * Observe global errors and unhandled promise rejections\n * @param callback - Called for each error event\n * @returns Cleanup function\n */\nexport function observeErrors(\n callback: (event: ObserveErrorEvent) => void\n): () => void {\n // Check if we're in a browser environment\n if (typeof window === 'undefined') {\n return () => {};\n }\n\n const errorHandler = (event: globalThis.ErrorEvent) => {\n const errorEvent: ErrorEvent = {\n type: 'error',\n message: event.message || 'Unknown error',\n stack: event.error?.stack,\n filename: event.filename,\n lineno: event.lineno,\n colno: event.colno,\n timestamp: Date.now(),\n url: getCurrentUrl(),\n ...getMachineContext(),\n };\n callback(errorEvent);\n };\n\n const rejectionHandler = (event: PromiseRejectionEvent) => {\n const reason = event.reason;\n let message: string;\n\n if (reason instanceof Error) {\n message = reason.message;\n } else if (typeof reason === 'string') {\n message = reason;\n } else {\n try {\n message = JSON.stringify(reason);\n } catch {\n message = String(reason);\n }\n }\n\n const rejectionEvent: UnhandledRejectionEvent = {\n type: 'unhandled-rejection',\n reason: message,\n timestamp: Date.now(),\n url: getCurrentUrl(),\n ...getMachineContext(),\n };\n callback(rejectionEvent);\n };\n\n window.addEventListener('error', errorHandler);\n window.addEventListener('unhandledrejection', rejectionHandler);\n\n return () => {\n window.removeEventListener('error', errorHandler);\n window.removeEventListener('unhandledrejection', rejectionHandler);\n };\n}\n\nexport type { ErrorEvent, UnhandledRejectionEvent, ObserveErrorEvent };\n"],
5
- "mappings": "AAQA,MAAMA,EAAkB,IAAI,IAMrB,SAASC,EAAuBC,EAAYC,EAA8B,CAC/EH,EAAgB,IAAIE,EAAI,CAAE,SAAAC,CAAS,CAAC,CACtC,CAMO,SAASC,EAAyBF,EAAkB,CACzDF,EAAgB,OAAOE,CAAE,CAC3B,CAMA,SAASG,GAAmE,CAC1E,SAAW,CAACH,EAAII,CAAG,IAAKN,EACtB,GAAI,CACF,MAAO,CAAE,UAAWE,EAAI,aAAcI,EAAI,SAAS,CAAE,CACvD,MAAQ,CAER,CAEF,MAAO,CAAC,CACV,CAKA,SAASC,GAAwB,CAC/B,GAAI,CACF,OAAO,OAAO,SAAa,IAAc,SAAS,KAAO,EAC3D,MAAQ,CACN,MAAO,EACT,CACF,CAOO,SAASC,EACdC,EACY,CAEZ,GAAI,OAAO,OAAW,IACpB,MAAO,IAAM,CAAC,EAGhB,MAAMC,EAAgBC,GAAiC,CACrD,MAAMC,EAAyB,CAC7B,KAAM,QACN,QAASD,EAAM,SAAW,gBAC1B,MAAOA,EAAM,OAAO,MACpB,SAAUA,EAAM,SAChB,OAAQA,EAAM,OACd,MAAOA,EAAM,MACb,UAAW,KAAK,IAAI,EACpB,IAAKJ,EAAc,EACnB,GAAGF,EAAkB,CACvB,EACAI,EAASG,CAAU,CACrB,EAEMC,EAAoBF,GAAiC,CACzD,MAAMG,EAASH,EAAM,OACrB,IAAII,EAEJ,GAAID,aAAkB,MACpBC,EAAUD,EAAO,gBACR,OAAOA,GAAW,SAC3BC,EAAUD,MAEV,IAAI,CACFC,EAAU,KAAK,UAAUD,CAAM,CACjC,MAAQ,CACNC,EAAU,OAAOD,CAAM,CACzB,CAGF,MAAME,EAA0C,CAC9C,KAAM,sBACN,OAAQD,EACR,UAAW,KAAK,IAAI,EACpB,IAAKR,EAAc,EACnB,GAAGF,EAAkB,CACvB,EACAI,EAASO,CAAc,CACzB,EAEA,cAAO,iBAAiB,QAASN,CAAY,EAC7C,OAAO,iBAAiB,qBAAsBG,CAAgB,EAEvD,IAAM,CACX,OAAO,oBAAoB,QAASH,CAAY,EAChD,OAAO,oBAAoB,qBAAsBG,CAAgB,CACnE,CACF",
6
- "names": ["machineContexts", "registerMachineContext", "id", "getState", "unregisterMachineContext", "getMachineContext", "ctx", "getCurrentUrl", "observeErrors", "callback", "errorHandler", "event", "errorEvent", "rejectionHandler", "reason", "message", "rejectionEvent"]
4
+ "sourcesContent": ["/**\n * Error tracking - captures errors and unhandled promise rejections\n * Integrates with state machines to include machine context in error reports\n */\n\nimport type { ErrorEvent, UnhandledRejectionEvent, ObserveErrorEvent } from '../types/index.js';\n\n// Global machine context registry (populated by createMachine)\nconst machineContexts = new Map<string, { getState: () => string }>();\n\n/**\n * Register a machine's context for error tracking\n * Called internally by createMachine()\n */\nexport function registerMachineContext(id: string, getState: () => string): void {\n machineContexts.set(id, { getState });\n}\n\n/**\n * Unregister a machine's context\n * Called internally when machine is destroyed\n */\nexport function unregisterMachineContext(id: string): void {\n machineContexts.delete(id);\n}\n\nconst MAX_MACHINES_IN_ERROR = 10;\n\n/**\n * Get current machine context for error reports\n * Returns all active machines (max 10) + backward compat fields from first\n */\nfunction getMachineContext(): {\n machineId?: string;\n machineState?: string;\n machines?: Array<{ id: string; state: string }>;\n} {\n if (machineContexts.size === 0) return {};\n\n const machines: Array<{ id: string; state: string }> = [];\n for (const [id, ctx] of machineContexts) {\n if (machines.length >= MAX_MACHINES_IN_ERROR) break;\n try {\n machines.push({ id, state: ctx.getState() });\n } catch {\n // Machine might be in invalid state, skip it\n }\n }\n\n if (machines.length === 0) return {};\n\n return {\n machineId: machines[0].id,\n machineState: machines[0].state,\n machines,\n };\n}\n\n/**\n * Get current URL safely\n */\nfunction getCurrentUrl(): string {\n try {\n return typeof location !== 'undefined' ? location.href : '';\n } catch {\n return '';\n }\n}\n\n/**\n * Observe global errors and unhandled promise rejections\n * @param callback - Called for each error event\n * @returns Cleanup function\n */\nexport function observeErrors(\n callback: (event: ObserveErrorEvent) => void\n): () => void {\n // Check if we're in a browser environment\n if (typeof window === 'undefined') {\n return () => {};\n }\n\n const errorHandler = (event: globalThis.ErrorEvent) => {\n const errorEvent: ErrorEvent = {\n type: 'error',\n message: event.message || 'Unknown error',\n stack: event.error?.stack,\n filename: event.filename,\n lineno: event.lineno,\n colno: event.colno,\n timestamp: Date.now(),\n url: getCurrentUrl(),\n ...getMachineContext(),\n };\n callback(errorEvent);\n };\n\n const rejectionHandler = (event: PromiseRejectionEvent) => {\n const reason = event.reason;\n let message: string;\n\n if (reason instanceof Error) {\n message = reason.message;\n } else if (typeof reason === 'string') {\n message = reason;\n } else {\n try {\n message = JSON.stringify(reason);\n } catch {\n message = String(reason);\n }\n }\n\n const rejectionEvent: UnhandledRejectionEvent = {\n type: 'unhandled-rejection',\n reason: message,\n timestamp: Date.now(),\n url: getCurrentUrl(),\n ...getMachineContext(),\n };\n callback(rejectionEvent);\n };\n\n window.addEventListener('error', errorHandler);\n window.addEventListener('unhandledrejection', rejectionHandler);\n\n return () => {\n window.removeEventListener('error', errorHandler);\n window.removeEventListener('unhandledrejection', rejectionHandler);\n };\n}\n\nexport type { ErrorEvent, UnhandledRejectionEvent, ObserveErrorEvent };\n"],
5
+ "mappings": "AAQA,MAAMA,EAAkB,IAAI,IAMrB,SAASC,EAAuBC,EAAYC,EAA8B,CAC/EH,EAAgB,IAAIE,EAAI,CAAE,SAAAC,CAAS,CAAC,CACtC,CAMO,SAASC,EAAyBF,EAAkB,CACzDF,EAAgB,OAAOE,CAAE,CAC3B,CAEA,MAAMG,EAAwB,GAM9B,SAASC,GAIP,CACA,GAAIN,EAAgB,OAAS,EAAG,MAAO,CAAC,EAExC,MAAMO,EAAiD,CAAC,EACxD,SAAW,CAACL,EAAIM,CAAG,IAAKR,EAAiB,CACvC,GAAIO,EAAS,QAAUF,EAAuB,MAC9C,GAAI,CACFE,EAAS,KAAK,CAAE,GAAAL,EAAI,MAAOM,EAAI,SAAS,CAAE,CAAC,CAC7C,MAAQ,CAER,CACF,CAEA,OAAID,EAAS,SAAW,EAAU,CAAC,EAE5B,CACL,UAAWA,EAAS,CAAC,EAAE,GACvB,aAAcA,EAAS,CAAC,EAAE,MAC1B,SAAAA,CACF,CACF,CAKA,SAASE,GAAwB,CAC/B,GAAI,CACF,OAAO,OAAO,SAAa,IAAc,SAAS,KAAO,EAC3D,MAAQ,CACN,MAAO,EACT,CACF,CAOO,SAASC,EACdC,EACY,CAEZ,GAAI,OAAO,OAAW,IACpB,MAAO,IAAM,CAAC,EAGhB,MAAMC,EAAgBC,GAAiC,CACrD,MAAMC,EAAyB,CAC7B,KAAM,QACN,QAASD,EAAM,SAAW,gBAC1B,MAAOA,EAAM,OAAO,MACpB,SAAUA,EAAM,SAChB,OAAQA,EAAM,OACd,MAAOA,EAAM,MACb,UAAW,KAAK,IAAI,EACpB,IAAKJ,EAAc,EACnB,GAAGH,EAAkB,CACvB,EACAK,EAASG,CAAU,CACrB,EAEMC,EAAoBF,GAAiC,CACzD,MAAMG,EAASH,EAAM,OACrB,IAAII,EAEJ,GAAID,aAAkB,MACpBC,EAAUD,EAAO,gBACR,OAAOA,GAAW,SAC3BC,EAAUD,MAEV,IAAI,CACFC,EAAU,KAAK,UAAUD,CAAM,CACjC,MAAQ,CACNC,EAAU,OAAOD,CAAM,CACzB,CAGF,MAAME,EAA0C,CAC9C,KAAM,sBACN,OAAQD,EACR,UAAW,KAAK,IAAI,EACpB,IAAKR,EAAc,EACnB,GAAGH,EAAkB,CACvB,EACAK,EAASO,CAAc,CACzB,EAEA,cAAO,iBAAiB,QAASN,CAAY,EAC7C,OAAO,iBAAiB,qBAAsBG,CAAgB,EAEvD,IAAM,CACX,OAAO,oBAAoB,QAASH,CAAY,EAChD,OAAO,oBAAoB,qBAAsBG,CAAgB,CACnE,CACF",
6
+ "names": ["machineContexts", "registerMachineContext", "id", "getState", "unregisterMachineContext", "MAX_MACHINES_IN_ERROR", "getMachineContext", "machines", "ctx", "getCurrentUrl", "observeErrors", "callback", "errorHandler", "event", "errorEvent", "rejectionHandler", "reason", "message", "rejectionEvent"]
7
7
  }
@@ -1 +1 @@
1
- {"version":3,"file":"observe.svelte.d.ts","sourceRoot":"","sources":["../../src/observe/observe.svelte.ts"],"names":[],"mappings":"AAAA;;GAEG;AAYH,OAAO,KAAK,EAAE,cAAc,EAAc,YAAY,EAAa,MAAM,mBAAmB,CAAC;AAc7F,QAAA,IAAI,sBAAsB,EAAE,CAAC,CAAC,KAAK,EAAE,YAAY,KAAK,IAAI,CAAC,GAAG,IAAW,CAAC;AAE1E;;;GAGG;AACH,wBAAgB,iBAAiB,CAAC,QAAQ,EAAE,OAAO,sBAAsB,GAAG,IAAI,CAE/E;AAED;;;GAGG;AACH,wBAAgB,iBAAiB,IAAI,OAAO,sBAAsB,CAEjE;AAED;;;;;;;;;;;;;;;;;;GAkBG;AACH,wBAAgB,OAAO,CAAC,OAAO,GAAE,cAAmB,GAAG,MAAM,IAAI,CA+KhE;AAED,YAAY,EAAE,cAAc,EAAE,CAAC"}
1
+ {"version":3,"file":"observe.svelte.d.ts","sourceRoot":"","sources":["../../src/observe/observe.svelte.ts"],"names":[],"mappings":"AAAA;;GAEG;AAYH,OAAO,KAAK,EAAE,cAAc,EAAc,YAAY,EAAa,MAAM,mBAAmB,CAAC;AA4B7F,QAAA,IAAI,sBAAsB,EAAE,CAAC,CAAC,KAAK,EAAE,YAAY,KAAK,IAAI,CAAC,GAAG,IAAW,CAAC;AAE1E;;;GAGG;AACH,wBAAgB,iBAAiB,CAAC,QAAQ,EAAE,OAAO,sBAAsB,GAAG,IAAI,CAE/E;AAED;;;GAGG;AACH,wBAAgB,iBAAiB,IAAI,OAAO,sBAAsB,CAEjE;AAED;;;;;;;;;;;;;;;;;;GAkBG;AACH,wBAAgB,OAAO,CAAC,OAAO,GAAE,cAAmB,GAAG,MAAM,IAAI,CAyLhE;AAED,YAAY,EAAE,cAAc,EAAE,CAAC"}
@@ -1,2 +1,2 @@
1
- import{vitalObservers as y}from"./vitals.js";import{observeErrors as O}from"./errors.js";import{createFetchTransport as E}from"../transport/fetch.js";import{createSampler as S,eventTypeToSamplingType as M}from"./sampling.js";import{createSessionManager as T}from"./session.js";import{setMetricEmitter as f,getMetricEmitter as I}from"../metrics/index.js";const c={endpoint:"/api/metrics",vitals:!0,errors:!0,batchSize:10,flushInterval:5e3,sampleRate:1,debug:!1};let m=null;function d(l){m=l}function w(){return m}function N(l={}){if(Math.random()>(l.sampleRate??c.sampleRate))return()=>{};const t={...c,...l},b=t.transport??E(t.endpoint),u=t.sampling!=null?S(t.sampling):null,a=t.session!=null?T(t.session):null,n=[];a&&n.push(()=>a.destroy());const o=[];let v=null;const g=()=>{try{return typeof location<"u"?location.href:""}catch{return""}},s=e=>{if(!(t.filter&&!t.filter(e))){if(u){const r=M(e.type);if(r&&!u.shouldSample(r))return}a&&(e.sessionId=a.getSessionId()),t.debug&&console.log("[svoose]",e),o.push(e),o.length>=t.batchSize&&i()}},i=()=>{if(o.length===0)return;const e=o.splice(0,o.length),r=b.send(e);r&&typeof r.catch=="function"&&r.catch(p=>{t.debug&&console.error("[svoose] transport error:",p)})},h=e=>{const r={type:"vital",name:e.name,value:e.value,rating:e.rating,delta:e.delta,timestamp:e.timestamp,url:g()};s(r)};if(t.vitals){const e=t.vitals===!0?["CLS","LCP","FID","INP","FCP","TTFB"]:t.vitals;for(const r of e){const p=y[r];p&&n.push(p(h))}}if(t.errors&&n.push(O(e=>{s(e)})),d(s),n.push(()=>{w()===s&&d(null)}),f(s),n.push(()=>{I()===s&&f(null)}),v=setInterval(i,t.flushInterval),n.push(()=>{v&&clearInterval(v)}),typeof document<"u"){const e=()=>{document.visibilityState==="hidden"&&i()};document.addEventListener("visibilitychange",e),n.push(()=>{document.removeEventListener("visibilitychange",e)})}if(typeof window<"u"){const e=()=>{i()};window.addEventListener("beforeunload",e),n.push(()=>{window.removeEventListener("beforeunload",e)})}return()=>{i(),n.forEach(e=>e())}}export{w as getGlobalObserver,N as observe,d as setGlobalObserver};
1
+ import{vitalObservers}from"./vitals.js";import{observeErrors}from"./errors.js";import{createFetchTransport}from"../transport/fetch.js";import{createSampler,eventTypeToSamplingType}from"./sampling.js";import{createSessionManager}from"./session.js";import{setMetricEmitter,getMetricEmitter}from"../metrics/index.js";const defaults={endpoint:"/api/metrics",vitals:!0,errors:!0,batchSize:10,flushInterval:5e3,debug:!1};function validateOptions(options){if(options.batchSize!==void 0&&(options.batchSize<1||!Number.isFinite(options.batchSize)))throw new Error(`[svoose] batchSize must be >= 1, got ${options.batchSize}`);if(options.flushInterval!==void 0&&(options.flushInterval<100||!Number.isFinite(options.flushInterval)))throw new Error(`[svoose] flushInterval must be >= 100ms, got ${options.flushInterval}`);if(typeof options.sampling=="number"&&(options.sampling<0||options.sampling>1))throw new Error(`[svoose] sampling rate must be between 0 and 1, got ${options.sampling}`)}let globalObserverCallback=null;function setGlobalObserver(callback){globalObserverCallback=callback}function getGlobalObserver(){return globalObserverCallback}function observe(options={}){validateOptions(options);const config={...defaults,...options},transport=config.transport??createFetchTransport(config.endpoint),sampler=config.sampling!=null?createSampler(config.sampling):null,sessionManager=config.session!=null?createSessionManager(config.session,config.debug):null,cleanups=[];sessionManager&&cleanups.push(()=>sessionManager.destroy());const buffer=[];let flushTimer=null;const getUrl=()=>{try{return typeof location<"u"?location.href:""}catch{return""}},bufferEvent=event=>{if(!(config.filter&&!config.filter(event))){if(sampler){const samplingType=eventTypeToSamplingType(event.type);if(samplingType&&!sampler.shouldSample(samplingType))return}sessionManager&&(event.sessionId=sessionManager.getSessionId()),config.debug&&console.log("[svoose]",event),buffer.push(event),buffer.length>=config.batchSize&&flush()}},handleError=err=>{const error=err instanceof Error?err:new Error(String(err));config.onError&&config.onError(error),config.debug&&console.error("[svoose] transport error:",error)},flush=()=>{if(buffer.length===0)return;const events=buffer.splice(0,buffer.length);try{const result=transport.send(events);result&&typeof result.catch=="function"&&result.catch(handleError)}catch(err){handleError(err)}},handleMetric=metric=>{const vitalEvent={type:"vital",name:metric.name,value:metric.value,rating:metric.rating,delta:metric.delta,timestamp:metric.timestamp,url:getUrl()};bufferEvent(vitalEvent)};if(config.vitals){const vitalsToObserve=config.vitals===!0?["CLS","LCP","FID","INP","FCP","TTFB"]:config.vitals;for(const name of vitalsToObserve){const observer=vitalObservers[name];observer&&cleanups.push(observer(handleMetric))}}if(config.errors&&cleanups.push(observeErrors(event=>{bufferEvent(event)})),setGlobalObserver(bufferEvent),cleanups.push(()=>{getGlobalObserver()===bufferEvent&&setGlobalObserver(null)}),setMetricEmitter(bufferEvent),cleanups.push(()=>{getMetricEmitter()===bufferEvent&&setMetricEmitter(null)}),flushTimer=setInterval(flush,config.flushInterval),cleanups.push(()=>{flushTimer&&clearInterval(flushTimer)}),typeof document<"u"){const visibilityHandler=()=>{document.visibilityState==="hidden"&&flush()};document.addEventListener("visibilitychange",visibilityHandler),cleanups.push(()=>{document.removeEventListener("visibilitychange",visibilityHandler)})}if(typeof window<"u"){const unloadHandler=()=>{flush()};window.addEventListener("beforeunload",unloadHandler),cleanups.push(()=>{window.removeEventListener("beforeunload",unloadHandler)})}return()=>{flush(),cleanups.forEach(fn=>fn()),transport.destroy?.()}}export{getGlobalObserver,observe,setGlobalObserver};
2
2
  //# sourceMappingURL=observe.svelte.js.map