nusm 0.1.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.
Files changed (98) hide show
  1. package/README.md +66 -7
  2. package/dist/adapters/indexDbAdapter.d.ts.map +1 -1
  3. package/dist/adapters/localStorageAdapter.d.ts.map +1 -1
  4. package/dist/adapters/sessionStorageAdapter.d.ts.map +1 -1
  5. package/dist/adapters/storageAdapter.d.ts.map +1 -1
  6. package/dist/devtools/client.d.ts +12 -10
  7. package/dist/devtools/client.d.ts.map +1 -1
  8. package/dist/devtools/client.js +50 -10
  9. package/dist/devtools/client.js.map +1 -1
  10. package/dist/devtools/core.d.ts +9 -0
  11. package/dist/devtools/core.d.ts.map +1 -0
  12. package/dist/devtools/core.js +38 -0
  13. package/dist/devtools/core.js.map +1 -0
  14. package/dist/devtools/flatten.d.ts +4 -0
  15. package/dist/devtools/flatten.d.ts.map +1 -0
  16. package/dist/devtools/flatten.js +145 -0
  17. package/dist/devtools/flatten.js.map +1 -0
  18. package/dist/devtools/index.d.ts +4 -0
  19. package/dist/devtools/index.d.ts.map +1 -0
  20. package/dist/devtools/index.js +3 -0
  21. package/dist/devtools/index.js.map +1 -0
  22. package/dist/devtools/nusm-logo.d.ts +4 -0
  23. package/dist/devtools/nusm-logo.d.ts.map +1 -0
  24. package/dist/devtools/nusm-logo.js +5 -0
  25. package/dist/devtools/nusm-logo.js.map +1 -0
  26. package/dist/devtools/panel-controls.d.ts +13 -0
  27. package/dist/devtools/panel-controls.d.ts.map +1 -0
  28. package/dist/devtools/panel-controls.js +32 -0
  29. package/dist/devtools/panel-controls.js.map +1 -0
  30. package/dist/devtools/panel-detail.d.ts +15 -0
  31. package/dist/devtools/panel-detail.d.ts.map +1 -0
  32. package/dist/devtools/panel-detail.js +114 -0
  33. package/dist/devtools/panel-detail.js.map +1 -0
  34. package/dist/devtools/panel-helpers.d.ts +16 -0
  35. package/dist/devtools/panel-helpers.d.ts.map +1 -0
  36. package/dist/devtools/panel-helpers.js +40 -0
  37. package/dist/devtools/panel-helpers.js.map +1 -0
  38. package/dist/devtools/panel-list.d.ts +13 -0
  39. package/dist/devtools/panel-list.d.ts.map +1 -0
  40. package/dist/devtools/panel-list.js +28 -0
  41. package/dist/devtools/panel-list.js.map +1 -0
  42. package/dist/devtools/panel-model.d.ts +19 -0
  43. package/dist/devtools/panel-model.d.ts.map +1 -0
  44. package/dist/devtools/panel-model.js +53 -0
  45. package/dist/devtools/panel-model.js.map +1 -0
  46. package/dist/devtools/panel.d.ts +3 -0
  47. package/dist/devtools/panel.d.ts.map +1 -0
  48. package/dist/devtools/panel.js +429 -0
  49. package/dist/devtools/panel.js.map +1 -0
  50. package/dist/devtools/path.d.ts +5 -0
  51. package/dist/devtools/path.d.ts.map +1 -0
  52. package/dist/devtools/path.js +142 -0
  53. package/dist/devtools/path.js.map +1 -0
  54. package/dist/devtools/plugin.d.ts +14 -2
  55. package/dist/devtools/plugin.d.ts.map +1 -1
  56. package/dist/devtools/plugin.js +10 -56
  57. package/dist/devtools/plugin.js.map +1 -1
  58. package/dist/devtools/projection.d.ts +8 -0
  59. package/dist/devtools/projection.d.ts.map +1 -0
  60. package/dist/devtools/projection.js +72 -0
  61. package/dist/devtools/projection.js.map +1 -0
  62. package/dist/devtools/protocol.d.ts +4 -0
  63. package/dist/devtools/protocol.d.ts.map +1 -0
  64. package/dist/devtools/protocol.js +58 -0
  65. package/dist/devtools/protocol.js.map +1 -0
  66. package/dist/devtools/serialize.d.ts +3 -0
  67. package/dist/devtools/serialize.d.ts.map +1 -0
  68. package/dist/devtools/serialize.js +71 -0
  69. package/dist/devtools/serialize.js.map +1 -0
  70. package/dist/devtools/types.d.ts +60 -0
  71. package/dist/devtools/types.d.ts.map +1 -0
  72. package/dist/devtools/types.js +2 -0
  73. package/dist/devtools/types.js.map +1 -0
  74. package/dist/index.d.ts +2 -3
  75. package/dist/index.d.ts.map +1 -1
  76. package/dist/index.js +1 -2
  77. package/dist/index.js.map +1 -1
  78. package/dist/nusm.d.ts +5 -0
  79. package/dist/nusm.d.ts.map +1 -0
  80. package/dist/nusm.js +1026 -0
  81. package/dist/nusm.js.map +1 -0
  82. package/dist/react/index.d.ts +6 -8
  83. package/dist/react/index.d.ts.map +1 -1
  84. package/dist/react/index.js +16 -28
  85. package/dist/react/index.js.map +1 -1
  86. package/dist/types.d.ts +29 -15
  87. package/dist/types.d.ts.map +1 -1
  88. package/docs/UPGRADING.md +53 -0
  89. package/docs/devtools.md +139 -0
  90. package/package.json +61 -24
  91. package/dist/core/createNusmStore.d.ts +0 -3
  92. package/dist/core/createNusmStore.d.ts.map +0 -1
  93. package/dist/core/createNusmStore.js +0 -491
  94. package/dist/core/createNusmStore.js.map +0 -1
  95. package/dist/utils.d.ts +0 -5
  96. package/dist/utils.d.ts.map +0 -1
  97. package/dist/utils.js +0 -30
  98. package/dist/utils.js.map +0 -1
package/README.md CHANGED
@@ -1,9 +1,9 @@
1
1
  <p align="center">
2
- <img src="./logo.svg" alt="nusm" height="100" />
2
+ <img src="https://raw.githubusercontent.com/mwillbanks/nusm/refs/heads/main/logo.svg" alt="nusm" height="100" />
3
3
  </p>
4
4
 
5
5
  # nusm
6
- Non Uniform State Manager (nusm) > Pronounced **noose em** (nuːs əm/)
6
+ Non Uniform State Manager (nusm) > Pronounced **noose em** (`/ˈnuːs əm/`)
7
7
  is a persistence-ready wrapper around
8
8
  [@tanstack/store](https://github.com/TanStack/store) with adapter-based storage
9
9
 
@@ -16,12 +16,12 @@ is a persistence-ready wrapper around
16
16
  - Debounced persistence via @tanstack/pacer
17
17
  - Adapter events for cross-tab or external updates
18
18
  - React hooks (via `nusm/react`)
19
- - @tanstack/devtools event support (panel coming soon)
19
+ - Optional TanStack Devtools store inspector (`nusm/devtools`)
20
20
 
21
21
  ## Install
22
22
 
23
23
  ```bash
24
- bun install `nusm`
24
+ bun add nusm
25
25
  ```
26
26
 
27
27
  ## Quick Start
@@ -62,7 +62,16 @@ const nusm = createNusmStore(initialState, {
62
62
 
63
63
  Return value:
64
64
 
65
- - A @tanstack/store instance extended with `ready` (resolves when hydration completes).
65
+ - A @tanstack/store instance extended with `ready`, readonly `isReady`, and an immutable `hydration` snapshot. `hydration.overall` and each `hydration.byKey` entry report `pending`, `hydrated`, `discarded`, `error`, or `not_configured`; read a fresh snapshot after lifecycle events rather than mutating it.
66
+
67
+ ## Breaking changes and upgrades
68
+
69
+ nusm now targets the current `@tanstack/store` API directly. The legacy
70
+ `Derived` and `Effect` compatibility exports have been removed, and
71
+ `useStore` accepts only stores returned by `createNusmStore`.
72
+
73
+ See the [upgrade guide](docs/UPGRADING.md) before upgrading an existing
74
+ integration.
66
75
 
67
76
  ### Persistence strategies
68
77
 
@@ -89,6 +98,8 @@ persist: {
89
98
 
90
99
  ### Hydration configuration
91
100
 
101
+ When a configured persistence unit is missing, nusm writes the corresponding initial entire-store value or selected slice before `ready` resolves. A successfully hydrated store therefore has a real adapter baseline; zero pending keys means those initial writes have completed, not that persistence was skipped. Existing, discarded, and failed adapter values retain their normal hydration policy.
102
+
92
103
  ```ts
93
104
  persist: {
94
105
  strategy: 'entire',
@@ -123,7 +134,8 @@ type NusmAdapter = {
123
134
 
124
135
  Notes:
125
136
 
126
- - `getAllKeys` enables more complete persisted snapshots.
137
+ - `getAllKeys` is optional adapter-wide enumeration for callers that need it;
138
+ devtools snapshots read configured persistence units through `resolveKey`.
127
139
  - `resolveKey` lets you control key layout. When omitted, nusm uses
128
140
  `nusm:<storeId>:entire` and `nusm:<storeId>:slice:<sliceKey>`.
129
141
  - `subscribe` should emit adapter events for cross-tab or external updates.
@@ -177,7 +189,7 @@ Options:
177
189
  - `deserialize`: custom deserializer (default: `superjson.parse`).
178
190
  - `pacer`: persistence debouncer configuration.
179
191
 
180
- ### IndexDB
192
+ ### IndexedDB
181
193
 
182
194
  ```ts
183
195
  import { createIndexDbAdapter } from 'nusm'
@@ -238,3 +250,50 @@ bun run build
238
250
  ## License
239
251
 
240
252
  MIT. See [LICENSE](LICENSE).
253
+
254
+ ## TanStack Devtools inspector
255
+
256
+ nusm ships a framework-neutral event bridge plus an optional React panel built with
257
+ TanStack `devtools-utils`. The root `nusm` entry never imports React or the
258
+ Devtools shell.
259
+
260
+ ```bash
261
+ bun add -d @tanstack/devtools @tanstack/devtools-utils \
262
+ @tanstack/react-devtools lucide-react react react-dom
263
+ ```
264
+
265
+ ```tsx
266
+ import { TanStackDevtools } from "@tanstack/react-devtools"
267
+ import { createNusmDevtoolsPlugin } from "nusm/devtools"
268
+
269
+ const nusmPlugin = createNusmDevtoolsPlugin()
270
+
271
+ export function DevelopmentTools() {
272
+ return <TanStackDevtools plugins={[nusmPlugin]} />
273
+ }
274
+ ```
275
+
276
+ Instrument individual stores with `devtools: true` or a named configuration.
277
+ The panel provides a compact icon rail, searchable store sidebar, memory and
278
+ adapter tabs, path/value filtering, timeline history, copy, add, edit, remove,
279
+ raw JSON, reset, and refresh controls. Every mutation is sent through the typed
280
+ TanStack event bus and acknowledged by the target store.
281
+
282
+ Use `createNoOpNusmDevtoolsPlugin()` when a framework integration needs a stable
283
+ plugin shape without mounting the inspector. Never enable state inspection in
284
+ an untrusted production environment.
285
+
286
+ See [the full Devtools guide](docs/devtools.md) and the [example walkthrough](example/README.md), then run the standalone showcase from the repository root:
287
+
288
+ ```bash
289
+ bun run example:devtools # Bun server with hot reload
290
+ bun run example:test # React and multi-adapter tests
291
+ bun run example:build # production HTML/CSS/JS bundle
292
+ bun run example:serve # serve the production bundle
293
+ ```
294
+
295
+ The [`example` walkthrough](example/README.md) covers a Bun-native React application—no Vite or
296
+ similar build system—and exercises memory, localStorage, sessionStorage, and
297
+ IndexedDB stores. Its Command center, Stores, and Signals controls select real
298
+ visible views, and the canonical nusm mark identifies both the application and
299
+ the custom inspector panel. Open `http://127.0.0.1:4173/` during hot-reload development. Production serving keeps the inspector disabled unless `?devtools` is present, so use `http://127.0.0.1:4173/?devtools` only in a trusted environment. See the [browser runtime QA receipt](example/browser-qa.md) for the rebuilt panel, real adapter inspection, live mutation, responsive layout, and console checks.
@@ -1 +1 @@
1
- {"version":3,"file":"indexDbAdapter.d.ts","sourceRoot":"","sources":["../../src/adapters/indexDbAdapter.ts"],"names":[],"mappings":"AACA,OAAO,KAAK,EAAE,qBAAqB,EAAE,WAAW,EAAE,MAAM,UAAU,CAAC;AA+CnE,eAAO,MAAM,oBAAoB,GAC/B,UAAU,qBAAqB,KAC9B,WAsCF,CAAC"}
1
+ {"version":3,"file":"indexDbAdapter.d.ts","sourceRoot":"","sources":["../../src/adapters/indexDbAdapter.ts"],"names":[],"mappings":"AACA,OAAO,KAAK,EAAE,qBAAqB,EAAE,WAAW,EAAE,MAAM,UAAU,CAAC;AA+CnE,eAAO,MAAM,oBAAoB,aACrB,qBAAqB,KAC9B,WAsCF,CAAC"}
@@ -1 +1 @@
1
- {"version":3,"file":"localStorageAdapter.d.ts","sourceRoot":"","sources":["../../src/adapters/localStorageAdapter.ts"],"names":[],"mappings":"AAAA,OAAO,KAAK,EAAE,WAAW,EAAE,qBAAqB,EAAE,MAAM,UAAU,CAAC;AAGnE,eAAO,MAAM,yBAAyB,GACpC,UAAU,qBAAqB,KAC9B,WAQA,CAAC"}
1
+ {"version":3,"file":"localStorageAdapter.d.ts","sourceRoot":"","sources":["../../src/adapters/localStorageAdapter.ts"],"names":[],"mappings":"AAAA,OAAO,KAAK,EAAE,WAAW,EAAE,qBAAqB,EAAE,MAAM,UAAU,CAAC;AAGnE,eAAO,MAAM,yBAAyB,aAC1B,qBAAqB,KAC9B,WAQA,CAAC"}
@@ -1 +1 @@
1
- {"version":3,"file":"sessionStorageAdapter.d.ts","sourceRoot":"","sources":["../../src/adapters/sessionStorageAdapter.ts"],"names":[],"mappings":"AAAA,OAAO,KAAK,EAAE,WAAW,EAAE,qBAAqB,EAAE,MAAM,UAAU,CAAC;AAGnE,eAAO,MAAM,2BAA2B,GACtC,UAAU,qBAAqB,KAC9B,WAQA,CAAC"}
1
+ {"version":3,"file":"sessionStorageAdapter.d.ts","sourceRoot":"","sources":["../../src/adapters/sessionStorageAdapter.ts"],"names":[],"mappings":"AAAA,OAAO,KAAK,EAAE,WAAW,EAAE,qBAAqB,EAAE,MAAM,UAAU,CAAC;AAGnE,eAAO,MAAM,2BAA2B,aAC5B,qBAAqB,KAC9B,WAQA,CAAC"}
@@ -1 +1 @@
1
- {"version":3,"file":"storageAdapter.d.ts","sourceRoot":"","sources":["../../src/adapters/storageAdapter.ts"],"names":[],"mappings":"AACA,OAAO,KAAK,EAEV,WAAW,EACX,qBAAqB,EACrB,WAAW,EACZ,MAAM,UAAU,CAAC;AAElB,eAAO,MAAM,oBAAoB,GAC/B,MAAM,MAAM,EACZ,gBAAgB,WAAW,GAAG,SAAS,EACvC,UAAU,qBAAqB,KAC9B,WAmEF,CAAC"}
1
+ {"version":3,"file":"storageAdapter.d.ts","sourceRoot":"","sources":["../../src/adapters/storageAdapter.ts"],"names":[],"mappings":"AACA,OAAO,KAAK,EAEV,WAAW,EACX,qBAAqB,EACrB,WAAW,EACZ,MAAM,UAAU,CAAC;AAElB,eAAO,MAAM,oBAAoB,SACzB,MAAM,kBACI,WAAW,GAAG,SAAS,YAC7B,qBAAqB,KAC9B,WAmEF,CAAC"}
@@ -1,15 +1,17 @@
1
1
  import type { HydrationStatus, NusmDevtoolsSnapshot, NusmEvent } from "../types";
2
- export type NusmDevtoolsEventMap = {
3
- "nusm:snapshot": NusmDevtoolsSnapshot;
4
- "nusm:event": NusmEvent;
5
- "nusm:hydration": {
6
- storeId: string;
7
- hydration: HydrationStatus;
8
- };
2
+ import type { NusmDevtoolsCommand, NusmDevtoolsCommandResult, NusmDevtoolsEventMap } from "./types";
3
+ export declare const getNusmDevtoolsClient: () => {
4
+ emit<TEvent extends keyof NusmDevtoolsEventMap & string>(eventSuffix: TEvent, payload: NusmDevtoolsEventMap[TEvent]): void;
5
+ on<TEvent extends keyof NusmDevtoolsEventMap & string>(eventSuffix: TEvent, callback: (event: {
6
+ payload: NusmDevtoolsEventMap[TEvent];
7
+ }) => void): () => void;
9
8
  };
10
- export declare const createNusmDevtoolsEmitter: (enabled: boolean) => {
11
- emitSnapshot: (snapshot: NusmDevtoolsSnapshot) => void;
12
- emitEvent: (event: NusmEvent) => void;
9
+ export declare const createNusmDevtoolsEmitter: (enabled: boolean, instanceId?: string) => {
10
+ emitCommand: (command: NusmDevtoolsCommand) => void;
11
+ emitCommandResult: (result: Omit<NusmDevtoolsCommandResult, "instanceId">) => void;
12
+ emitEvent: (event: Omit<NusmEvent, "instanceId">) => void;
13
13
  emitHydration: (storeId: string, hydration: HydrationStatus) => void;
14
+ emitSnapshot: (snapshot: Omit<NusmDevtoolsSnapshot, "instanceId">) => void;
15
+ onCommand: (listener: (command: NusmDevtoolsCommand) => void) => () => void;
14
16
  } | null;
15
17
  //# sourceMappingURL=client.d.ts.map
@@ -1 +1 @@
1
- {"version":3,"file":"client.d.ts","sourceRoot":"","sources":["../../src/devtools/client.ts"],"names":[],"mappings":"AACA,OAAO,KAAK,EAAE,eAAe,EAAE,oBAAoB,EAAE,SAAS,EAAE,MAAM,UAAU,CAAC;AAEjF,MAAM,MAAM,oBAAoB,GAAG;IACjC,eAAe,EAAE,oBAAoB,CAAC;IACtC,YAAY,EAAE,SAAS,CAAC;IACxB,gBAAgB,EAAE;QAAE,OAAO,EAAE,MAAM,CAAC;QAAC,SAAS,EAAE,eAAe,CAAA;KAAE,CAAC;CACnE,CAAC;AAEF,eAAO,MAAM,yBAAyB,GAAI,SAAS,OAAO;6BAS7B,oBAAoB;uBAG1B,SAAS;6BAGH,MAAM,aAAa,eAAe;QAI9D,CAAC"}
1
+ {"version":3,"file":"client.d.ts","sourceRoot":"","sources":["../../src/devtools/client.ts"],"names":[],"mappings":"AACA,OAAO,KAAK,EACV,eAAe,EACf,oBAAoB,EACpB,SAAS,EACV,MAAM,UAAU,CAAC;AAClB,OAAO,KAAK,EACV,mBAAmB,EACnB,yBAAyB,EACzB,oBAAoB,EACrB,MAAM,SAAS,CAAC;AAoBjB,eAAO,MAAM,qBAAqB;SAfzB,MAAM,SAAS,MAAM,oBAAoB,GAAG,MAAM,eACxC,MAAM,WACV,oBAAoB,CAAC,MAAM,CAAC,GACpC,IAAI;OACJ,MAAM,SAAS,MAAM,oBAAoB,GAAG,MAAM,eACtC,MAAM,YACT,CAAC,KAAK,EAAE;QAAE,OAAO,EAAE,oBAAoB,CAAC,MAAM,CAAC,CAAA;KAAE,KAAK,IAAI,GACnE,MAAM,IAAI;CA2ChB,CAAC;AAEF,eAAO,MAAM,yBAAyB,YAC3B,OAAO;2BAQS,mBAAmB;gCAIhC,IAAI,CAAC,yBAAyB,EAAE,YAAY,CAAC;uBAIpC,IAAI,CAAC,SAAS,EAAE,YAAY,CAAC;6BAGvB,MAAM,aAAa,eAAe;6BAGlC,IAAI,CAAC,oBAAoB,EAAE,YAAY,CAAC;0BAG3C,CAAC,OAAO,EAAE,mBAAmB,KAAK,IAAI,WAvEnD,IAAI;QA0EhB,CAAC"}
@@ -1,21 +1,61 @@
1
- import { EventClient } from "@tanstack/devtools-event-client";
2
- export const createNusmDevtoolsEmitter = (enabled) => {
3
- if (!enabled)
4
- return null;
5
- const client = new EventClient({
6
- pluginId: "nusm",
1
+ import { EventClient } from "@tanstack/devtools-event-client/production";
2
+ const devtoolsClients = new WeakMap();
3
+ const getDevtoolsTarget = () => globalThis.__TANSTACK_EVENT_TARGET__ ??
4
+ (typeof window === "undefined" ? globalThis : window);
5
+ export const getNusmDevtoolsClient = () => {
6
+ const target = getDevtoolsTarget();
7
+ const existing = devtoolsClients.get(target);
8
+ if (existing)
9
+ return existing;
10
+ const eventClient = new EventClient({
7
11
  enabled: true,
12
+ pluginId: "nusm",
8
13
  });
14
+ const withTarget = (operation) => {
15
+ if (!(target instanceof EventTarget))
16
+ return operation();
17
+ const currentTarget = globalThis.__TANSTACK_EVENT_TARGET__;
18
+ globalThis.__TANSTACK_EVENT_TARGET__ = target;
19
+ try {
20
+ return operation();
21
+ }
22
+ finally {
23
+ globalThis.__TANSTACK_EVENT_TARGET__ = currentTarget;
24
+ }
25
+ };
26
+ const client = {
27
+ emit(eventSuffix, payload) {
28
+ withTarget(() => eventClient.emit(eventSuffix, payload));
29
+ },
30
+ on(eventSuffix, callback) {
31
+ const stop = withTarget(() => eventClient.on(eventSuffix, callback));
32
+ return () => withTarget(stop);
33
+ },
34
+ };
35
+ devtoolsClients.set(target, client);
36
+ return client;
37
+ };
38
+ export const createNusmDevtoolsEmitter = (enabled, instanceId = "nusm-legacy-client") => {
39
+ if (!enabled)
40
+ return null;
41
+ const client = getNusmDevtoolsClient();
9
42
  return {
10
- emitSnapshot: (snapshot) => {
11
- client.emit("snapshot", snapshot);
43
+ emitCommand: (command) => {
44
+ client.emit("command", command);
45
+ },
46
+ emitCommandResult: (result) => {
47
+ client.emit("commandResult", { ...result, instanceId });
12
48
  },
13
49
  emitEvent: (event) => {
14
- client.emit("event", event);
50
+ client.emit("event", { ...event, instanceId });
15
51
  },
16
52
  emitHydration: (storeId, hydration) => {
17
- client.emit("hydration", { storeId, hydration });
53
+ client.emit("hydration", { hydration, instanceId, storeId });
54
+ },
55
+ emitSnapshot: (snapshot) => {
56
+ client.emit("snapshot", { ...snapshot, instanceId });
18
57
  },
58
+ onCommand: (listener) => client.on("command", (event) => listener(event.payload)),
19
59
  };
20
60
  };
21
61
  //# sourceMappingURL=client.js.map
@@ -1 +1 @@
1
- {"version":3,"file":"client.js","sourceRoot":"","sources":["../../src/devtools/client.ts"],"names":[],"mappings":"AAAA,OAAO,EAAE,WAAW,EAAE,MAAM,iCAAiC,CAAC;AAS9D,MAAM,CAAC,MAAM,yBAAyB,GAAG,CAAC,OAAgB,EAAE,EAAE;IAC5D,IAAI,CAAC,OAAO;QAAE,OAAO,IAAI,CAAC;IAE1B,MAAM,MAAM,GAAG,IAAI,WAAW,CAA+B;QAC3D,QAAQ,EAAE,MAAM;QAChB,OAAO,EAAE,IAAI;KACd,CAAC,CAAC;IAEH,OAAO;QACL,YAAY,EAAE,CAAC,QAA8B,EAAE,EAAE;YAC/C,MAAM,CAAC,IAAI,CAAC,UAAU,EAAE,QAAQ,CAAC,CAAC;QACpC,CAAC;QACD,SAAS,EAAE,CAAC,KAAgB,EAAE,EAAE;YAC9B,MAAM,CAAC,IAAI,CAAC,OAAO,EAAE,KAAK,CAAC,CAAC;QAC9B,CAAC;QACD,aAAa,EAAE,CAAC,OAAe,EAAE,SAA0B,EAAE,EAAE;YAC7D,MAAM,CAAC,IAAI,CAAC,WAAW,EAAE,EAAE,OAAO,EAAE,SAAS,EAAE,CAAC,CAAC;QACnD,CAAC;KACF,CAAC;AACJ,CAAC,CAAC"}
1
+ {"version":3,"file":"client.js","sourceRoot":"","sources":["../../src/devtools/client.ts"],"names":[],"mappings":"AAAA,OAAO,EAAE,WAAW,EAAE,MAAM,4CAA4C,CAAC;AAYzE,MAAM,eAAe,GAAG,IAAI,OAAO,EAYhC,CAAC;AAEJ,MAAM,iBAAiB,GAAG,GAAW,EAAE,CACrC,UAAU,CAAC,yBAAyB;IACpC,CAAC,OAAO,MAAM,KAAK,WAAW,CAAC,CAAC,CAAC,UAAU,CAAC,CAAC,CAAC,MAAM,CAAC,CAAC;AAExD,MAAM,CAAC,MAAM,qBAAqB,GAAG,GAAG,EAAE;IACxC,MAAM,MAAM,GAAG,iBAAiB,EAAE,CAAC;IACnC,MAAM,QAAQ,GAAG,eAAe,CAAC,GAAG,CAAC,MAAM,CAAC,CAAC;IAC7C,IAAI,QAAQ;QAAE,OAAO,QAAQ,CAAC;IAC9B,MAAM,WAAW,GAAG,IAAI,WAAW,CAAuB;QACxD,OAAO,EAAE,IAAI;QACb,QAAQ,EAAE,MAAM;KACjB,CAAC,CAAC;IACH,MAAM,UAAU,GAAG,CAAI,SAAkB,EAAK,EAAE;QAC9C,IAAI,CAAC,CAAC,MAAM,YAAY,WAAW,CAAC;YAAE,OAAO,SAAS,EAAE,CAAC;QACzD,MAAM,aAAa,GAAG,UAAU,CAAC,yBAAyB,CAAC;QAC3D,UAAU,CAAC,yBAAyB,GAAG,MAAM,CAAC;QAC9C,IAAI,CAAC;YACH,OAAO,SAAS,EAAE,CAAC;QACrB,CAAC;gBAAS,CAAC;YACT,UAAU,CAAC,yBAAyB,GAAG,aAAa,CAAC;QACvD,CAAC;IACH,CAAC,CAAC;IACF,MAAM,MAAM,GAAG;QACb,IAAI,CACF,WAAmB,EACnB,OAAqC;YAErC,UAAU,CAAC,GAAG,EAAE,CAAC,WAAW,CAAC,IAAI,CAAC,WAAW,EAAE,OAAO,CAAC,CAAC,CAAC;QAC3D,CAAC;QACD,EAAE,CACA,WAAmB,EACnB,QAAoE;YAEpE,MAAM,IAAI,GAAG,UAAU,CAAC,GAAG,EAAE,CAAC,WAAW,CAAC,EAAE,CAAC,WAAW,EAAE,QAAQ,CAAC,CAAC,CAAC;YACrE,OAAO,GAAG,EAAE,CAAC,UAAU,CAAC,IAAI,CAAC,CAAC;QAChC,CAAC;KACF,CAAC;IACF,eAAe,CAAC,GAAG,CAAC,MAAM,EAAE,MAAM,CAAC,CAAC;IACpC,OAAO,MAAM,CAAC;AAChB,CAAC,CAAC;AAEF,MAAM,CAAC,MAAM,yBAAyB,GAAG,CACvC,OAAgB,EAChB,UAAU,GAAG,oBAAoB,EACjC,EAAE;IACF,IAAI,CAAC,OAAO;QAAE,OAAO,IAAI,CAAC;IAE1B,MAAM,MAAM,GAAG,qBAAqB,EAAE,CAAC;IAEvC,OAAO;QACL,WAAW,EAAE,CAAC,OAA4B,EAAE,EAAE;YAC5C,MAAM,CAAC,IAAI,CAAC,SAAS,EAAE,OAAO,CAAC,CAAC;QAClC,CAAC;QACD,iBAAiB,EAAE,CACjB,MAAqD,EACrD,EAAE;YACF,MAAM,CAAC,IAAI,CAAC,eAAe,EAAE,EAAE,GAAG,MAAM,EAAE,UAAU,EAAE,CAAC,CAAC;QAC1D,CAAC;QACD,SAAS,EAAE,CAAC,KAAoC,EAAE,EAAE;YAClD,MAAM,CAAC,IAAI,CAAC,OAAO,EAAE,EAAE,GAAG,KAAK,EAAE,UAAU,EAAE,CAAC,CAAC;QACjD,CAAC;QACD,aAAa,EAAE,CAAC,OAAe,EAAE,SAA0B,EAAE,EAAE;YAC7D,MAAM,CAAC,IAAI,CAAC,WAAW,EAAE,EAAE,SAAS,EAAE,UAAU,EAAE,OAAO,EAAE,CAAC,CAAC;QAC/D,CAAC;QACD,YAAY,EAAE,CAAC,QAAkD,EAAE,EAAE;YACnE,MAAM,CAAC,IAAI,CAAC,UAAU,EAAE,EAAE,GAAG,QAAQ,EAAE,UAAU,EAAE,CAAC,CAAC;QACvD,CAAC;QACD,SAAS,EAAE,CAAC,QAAgD,EAAE,EAAE,CAC9D,MAAM,CAAC,EAAE,CAAC,SAAS,EAAE,CAAC,KAAK,EAAE,EAAE,CAAC,QAAQ,CAAC,KAAK,CAAC,OAAO,CAAC,CAAC;KAC3D,CAAC;AACJ,CAAC,CAAC"}
@@ -0,0 +1,9 @@
1
+ import type { TanStackDevtoolsPluginProps } from "@tanstack/devtools";
2
+ export declare class NusmDevtoolsCore {
3
+ private element;
4
+ private version;
5
+ constructor();
6
+ mount(element: HTMLElement, props: TanStackDevtoolsPluginProps): void;
7
+ unmount(): void;
8
+ }
9
+ //# sourceMappingURL=core.d.ts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"core.d.ts","sourceRoot":"","sources":["../../src/devtools/core.tsx"],"names":[],"mappings":"AAAA,OAAO,KAAK,EAAE,2BAA2B,EAAE,MAAM,oBAAoB,CAAC;AAOtE,qBAAa,gBAAgB;IAC3B,OAAO,CAAC,OAAO,CAA0B;IACzC,OAAO,CAAC,OAAO,CAAS;IAExB,cAGC;IAED,KAAK,CAAC,OAAO,EAAE,WAAW,EAAE,KAAK,EAAE,2BAA2B,QAU7D;IAED,OAAO,SAWN;CACF"}
@@ -0,0 +1,38 @@
1
+ import { jsx as _jsx } from "react/jsx-runtime";
2
+ import { createRoot } from "react-dom/client";
3
+ import { NusmDevtoolsPanel } from "./panel";
4
+ const rootEntries = new WeakMap();
5
+ export class NusmDevtoolsCore {
6
+ element;
7
+ version;
8
+ constructor() {
9
+ this.element = undefined;
10
+ this.version = 0;
11
+ }
12
+ mount(element, props) {
13
+ let entry = rootEntries.get(element);
14
+ if (!entry) {
15
+ entry = { root: createRoot(element), version: 0 };
16
+ rootEntries.set(element, entry);
17
+ }
18
+ entry.version += 1;
19
+ this.element = element;
20
+ this.version = entry.version;
21
+ entry.root.render(_jsx(NusmDevtoolsPanel, { ...props }));
22
+ }
23
+ unmount() {
24
+ const element = this.element;
25
+ const version = this.version;
26
+ this.element = undefined;
27
+ if (!element)
28
+ return;
29
+ queueMicrotask(() => {
30
+ const entry = rootEntries.get(element);
31
+ if (!entry || entry.version !== version)
32
+ return;
33
+ rootEntries.delete(element);
34
+ entry.root.unmount();
35
+ });
36
+ }
37
+ }
38
+ //# sourceMappingURL=core.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"core.js","sourceRoot":"","sources":["../../src/devtools/core.tsx"],"names":[],"mappings":";AACA,OAAO,EAAE,UAAU,EAAa,MAAM,kBAAkB,CAAC;AACzD,OAAO,EAAE,iBAAiB,EAAE,MAAM,SAAS,CAAC;AAG5C,MAAM,WAAW,GAAG,IAAI,OAAO,EAA0B,CAAC;AAE1D,MAAM,OAAO,gBAAgB;IACnB,OAAO,CAA0B;IACjC,OAAO,CAAS;IAExB;QACE,IAAI,CAAC,OAAO,GAAG,SAAS,CAAC;QACzB,IAAI,CAAC,OAAO,GAAG,CAAC,CAAC;IACnB,CAAC;IAED,KAAK,CAAC,OAAoB,EAAE,KAAkC;QAC5D,IAAI,KAAK,GAAG,WAAW,CAAC,GAAG,CAAC,OAAO,CAAC,CAAC;QACrC,IAAI,CAAC,KAAK,EAAE,CAAC;YACX,KAAK,GAAG,EAAE,IAAI,EAAE,UAAU,CAAC,OAAO,CAAC,EAAE,OAAO,EAAE,CAAC,EAAE,CAAC;YAClD,WAAW,CAAC,GAAG,CAAC,OAAO,EAAE,KAAK,CAAC,CAAC;QAClC,CAAC;QACD,KAAK,CAAC,OAAO,IAAI,CAAC,CAAC;QACnB,IAAI,CAAC,OAAO,GAAG,OAAO,CAAC;QACvB,IAAI,CAAC,OAAO,GAAG,KAAK,CAAC,OAAO,CAAC;QAC7B,KAAK,CAAC,IAAI,CAAC,MAAM,CAAC,KAAC,iBAAiB,OAAK,KAAK,GAAI,CAAC,CAAC;IACtD,CAAC;IAED,OAAO;QACL,MAAM,OAAO,GAAG,IAAI,CAAC,OAAO,CAAC;QAC7B,MAAM,OAAO,GAAG,IAAI,CAAC,OAAO,CAAC;QAC7B,IAAI,CAAC,OAAO,GAAG,SAAS,CAAC;QACzB,IAAI,CAAC,OAAO;YAAE,OAAO;QACrB,cAAc,CAAC,GAAG,EAAE;YAClB,MAAM,KAAK,GAAG,WAAW,CAAC,GAAG,CAAC,OAAO,CAAC,CAAC;YACvC,IAAI,CAAC,KAAK,IAAI,KAAK,CAAC,OAAO,KAAK,OAAO;gBAAE,OAAO;YAChD,WAAW,CAAC,MAAM,CAAC,OAAO,CAAC,CAAC;YAC5B,KAAK,CAAC,IAAI,CAAC,OAAO,EAAE,CAAC;QACvB,CAAC,CAAC,CAAC;IACL,CAAC;CACF"}
@@ -0,0 +1,4 @@
1
+ import type { InspectionLimits, InspectorRow } from "./panel-model";
2
+ import type { NusmDevtoolsPath } from "./types";
3
+ export declare const flattenInspectorValue: (value: unknown, query: string, path: NusmDevtoolsPath, formatPath: (path: NusmDevtoolsPath) => string, previewValue: (value: unknown) => string, limits: InspectionLimits) => InspectorRow[];
4
+ //# sourceMappingURL=flatten.d.ts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"flatten.d.ts","sourceRoot":"","sources":["../../src/devtools/flatten.ts"],"names":[],"mappings":"AAAA,OAAO,KAAK,EAAE,gBAAgB,EAAE,YAAY,EAAE,MAAM,eAAe,CAAC;AACpE,OAAO,KAAK,EAAE,gBAAgB,EAAE,MAAM,SAAS,CAAC;AAsLhD,eAAO,MAAM,qBAAqB,UACzB,OAAO,SACP,MAAM,QACP,gBAAgB,cACV,CAAC,IAAI,EAAE,gBAAgB,KAAK,MAAM,gBAChC,CAAC,KAAK,EAAE,OAAO,KAAK,MAAM,UAChC,gBAAgB,KACvB,YAAY,EAsBd,CAAC"}
@@ -0,0 +1,145 @@
1
+ const describeError = (error) => error instanceof Error ? error.message : String(error);
2
+ const inspectKeys = (candidate) => {
3
+ const keys = Reflect.ownKeys(candidate).filter((key) => typeof key === "string" && key !== "length");
4
+ if (!Array.isArray(candidate))
5
+ return keys;
6
+ return keys.map(Number).filter((key) => Number.isInteger(key) && key >= 0);
7
+ };
8
+ const uninspectableRow = (path, key, error) => ({
9
+ depth: path.length - 1,
10
+ key,
11
+ kind: "value",
12
+ path,
13
+ preview: `[Uninspectable: ${describeError(error)}]`,
14
+ value: undefined,
15
+ });
16
+ const classifyProperty = (value, context) => {
17
+ const entry = typeof value === "object" && value !== null ? value : undefined;
18
+ const circular = entry ? context.ancestors.has(entry) : false;
19
+ const kind = Array.isArray(value) ? "array" : entry ? "object" : "value";
20
+ const origin = entry ? context.origins.get(entry) : undefined;
21
+ const preview = circular
22
+ ? `[Circular → ${context.formatPath(origin ?? [])}]`
23
+ : context.previewValue(value);
24
+ return { circular, entry, kind, preview };
25
+ };
26
+ const inspectDataProperty = (key, path, value, context) => {
27
+ const classification = classifyProperty(value, context);
28
+ return {
29
+ entry: classification.circular ? undefined : classification.entry,
30
+ path,
31
+ row: {
32
+ depth: path.length - 1,
33
+ key,
34
+ kind: classification.kind,
35
+ path,
36
+ preview: classification.preview,
37
+ value: classification.circular ? undefined : value,
38
+ },
39
+ };
40
+ };
41
+ const inspectDescriptor = (descriptor, key, path, context) => {
42
+ if (!descriptor)
43
+ return { path };
44
+ if (!descriptor.enumerable)
45
+ return { path };
46
+ if ("value" in descriptor)
47
+ return inspectDataProperty(key, path, descriptor.value, context);
48
+ return {
49
+ path,
50
+ row: {
51
+ depth: path.length - 1,
52
+ key,
53
+ kind: "value",
54
+ path,
55
+ preview: "[Accessor not evaluated]",
56
+ value: undefined,
57
+ },
58
+ };
59
+ };
60
+ const inspectProperty = (candidate, key, currentPath, context) => {
61
+ const propertyKey = String(key);
62
+ const path = [...currentPath, key];
63
+ try {
64
+ return inspectDescriptor(Object.getOwnPropertyDescriptor(candidate, propertyKey), propertyKey, path, context);
65
+ }
66
+ catch (error) {
67
+ return { path, row: uninspectableRow(path, propertyKey, error) };
68
+ }
69
+ };
70
+ const markTruncated = (currentPath, reason, context) => {
71
+ const id = reason === "nodes"
72
+ ? reason
73
+ : `${reason}:${context.formatPath(currentPath)}`;
74
+ if (context.truncations.has(id))
75
+ return;
76
+ context.truncations.add(id);
77
+ context.rows.push({
78
+ depth: currentPath.length,
79
+ key: reason === "nodes" ? "Show more values" : "Expand nested values",
80
+ kind: "value",
81
+ path: [...currentPath, `<${reason}-truncated>`],
82
+ preview: reason === "nodes"
83
+ ? `${context.maxNodes.toLocaleString()}-row safety limit reached`
84
+ : `${context.maxDepth}-level safety limit reached`,
85
+ truncated: reason,
86
+ value: undefined,
87
+ });
88
+ };
89
+ const walkObject = (candidate, currentPath, context) => {
90
+ if (currentPath.length >= context.maxDepth) {
91
+ markTruncated(currentPath, "depth", context);
92
+ return;
93
+ }
94
+ if (context.nodeCount >= context.maxNodes) {
95
+ markTruncated(currentPath, "nodes", context);
96
+ return;
97
+ }
98
+ context.ancestors.add(candidate);
99
+ context.origins.set(candidate, currentPath);
100
+ let keys;
101
+ try {
102
+ keys = inspectKeys(candidate);
103
+ }
104
+ catch (error) {
105
+ context.rows.push(uninspectableRow([...currentPath, "<uninspectable>"], "<uninspectable>", error));
106
+ context.ancestors.delete(candidate);
107
+ return;
108
+ }
109
+ for (const key of keys) {
110
+ if (context.nodeCount >= context.maxNodes) {
111
+ markTruncated(currentPath, "nodes", context);
112
+ break;
113
+ }
114
+ const inspected = inspectProperty(candidate, key, currentPath, context);
115
+ if (inspected.row) {
116
+ context.rows.push(inspected.row);
117
+ context.nodeCount += 1;
118
+ }
119
+ if (inspected.entry)
120
+ walkObject(inspected.entry, inspected.path, context);
121
+ }
122
+ context.ancestors.delete(candidate);
123
+ };
124
+ export const flattenInspectorValue = (value, query, path, formatPath, previewValue, limits) => {
125
+ const rows = [];
126
+ if (typeof value === "object" && value !== null) {
127
+ walkObject(value, path, {
128
+ ancestors: new Set(),
129
+ formatPath,
130
+ maxDepth: limits.maxDepth ?? 16,
131
+ maxNodes: limits.maxNodes ?? 2_000,
132
+ nodeCount: 0,
133
+ origins: new WeakMap(),
134
+ previewValue,
135
+ rows,
136
+ truncations: new Set(),
137
+ });
138
+ }
139
+ const needle = query.trim().toLowerCase();
140
+ if (!needle)
141
+ return rows;
142
+ return rows.filter((row) => row.truncated ||
143
+ `${formatPath(row.path)} ${row.preview}`.toLowerCase().includes(needle));
144
+ };
145
+ //# sourceMappingURL=flatten.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"flatten.js","sourceRoot":"","sources":["../../src/devtools/flatten.ts"],"names":[],"mappings":"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"}
@@ -0,0 +1,4 @@
1
+ export { NusmLogo } from "./nusm-logo";
2
+ export { createNoOpNusmDevtoolsPlugin, createNusmDevtoolsPlugin, NoOpNusmReactDevtoolsPanel, NusmDevtoolsCore, NusmReactDevtoolsPanel, } from "./plugin";
3
+ export type { NusmDevtoolsCommand, NusmDevtoolsCommandInput, NusmDevtoolsLocation, NusmDevtoolsPath, } from "./types";
4
+ //# sourceMappingURL=index.d.ts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"index.d.ts","sourceRoot":"","sources":["../../src/devtools/index.ts"],"names":[],"mappings":"AAAA,OAAO,EAAE,QAAQ,EAAE,MAAM,aAAa,CAAC;AACvC,OAAO,EACL,4BAA4B,EAC5B,wBAAwB,EACxB,0BAA0B,EAC1B,gBAAgB,EAChB,sBAAsB,GACvB,MAAM,UAAU,CAAC;AAClB,YAAY,EACV,mBAAmB,EACnB,wBAAwB,EACxB,oBAAoB,EACpB,gBAAgB,GACjB,MAAM,SAAS,CAAC"}
@@ -0,0 +1,3 @@
1
+ export { NusmLogo } from "./nusm-logo";
2
+ export { createNoOpNusmDevtoolsPlugin, createNusmDevtoolsPlugin, NoOpNusmReactDevtoolsPanel, NusmDevtoolsCore, NusmReactDevtoolsPanel, } from "./plugin";
3
+ //# sourceMappingURL=index.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"index.js","sourceRoot":"","sources":["../../src/devtools/index.ts"],"names":[],"mappings":"AAAA,OAAO,EAAE,QAAQ,EAAE,MAAM,aAAa,CAAC;AACvC,OAAO,EACL,4BAA4B,EAC5B,wBAAwB,EACxB,0BAA0B,EAC1B,gBAAgB,EAChB,sBAAsB,GACvB,MAAM,UAAU,CAAC"}
@@ -0,0 +1,4 @@
1
+ import type { SVGProps } from "react";
2
+ export type NusmLogoProps = SVGProps<SVGSVGElement>;
3
+ export declare function NusmLogo({ "aria-label": ariaLabel, height, width, ...props }: NusmLogoProps): import("react").JSX.Element;
4
+ //# sourceMappingURL=nusm-logo.d.ts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"nusm-logo.d.ts","sourceRoot":"","sources":["../../src/devtools/nusm-logo.tsx"],"names":[],"mappings":"AAAA,OAAO,KAAK,EAAE,QAAQ,EAAE,MAAM,OAAO,CAAC;AAEtC,MAAM,MAAM,aAAa,GAAG,QAAQ,CAAC,aAAa,CAAC,CAAC;AAEpD,wBAAgB,QAAQ,CAAC,EACvB,YAAY,EAAE,SAAuB,EACrC,MAAW,EACX,KAAU,EACV,GAAG,KAAK,EACT,EAAE,aAAa,+BA6Cf"}
@@ -0,0 +1,5 @@
1
+ import { jsx as _jsx, jsxs as _jsxs } from "react/jsx-runtime";
2
+ export function NusmLogo({ "aria-label": ariaLabel = "nusm logo", height = 18, width = 34, ...props }) {
3
+ return (_jsxs("svg", { "aria-label": ariaLabel, height: height, role: "img", viewBox: "0 0 148 78", width: width, xmlns: "http://www.w3.org/2000/svg", ...props, children: [_jsx("ellipse", { cx: "74", cy: "40", fill: "#22d3ee", rx: "46", ry: "30" }), _jsx("ellipse", { cx: "74", cy: "44", fill: "#38bdf8", rx: "36", ry: "22" }), _jsx("ellipse", { cx: "64", cy: "42", fill: "#020617", rx: "4", ry: "5" }), _jsx("ellipse", { cx: "84", cy: "42", fill: "#020617", rx: "4", ry: "5" }), _jsx("path", { d: "M26 34 C8 24, 6 12, 14 6", fill: "none", stroke: "#0ea5e9", strokeLinecap: "round", strokeWidth: "6" }), _jsx("path", { d: "M28 40 C8 34, 4 26, 10 20", fill: "none", stroke: "#0ea5e9", strokeLinecap: "round", strokeWidth: "5" }), _jsx("path", { d: "M122 34 C140 24, 142 12, 134 6", fill: "none", stroke: "#0ea5e9", strokeLinecap: "round", strokeWidth: "6" }), _jsx("path", { d: "M120 40 C140 34, 144 26, 138 20", fill: "none", stroke: "#0ea5e9", strokeLinecap: "round", strokeWidth: "5" })] }));
4
+ }
5
+ //# sourceMappingURL=nusm-logo.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"nusm-logo.js","sourceRoot":"","sources":["../../src/devtools/nusm-logo.tsx"],"names":[],"mappings":";AAIA,MAAM,UAAU,QAAQ,CAAC,EACvB,YAAY,EAAE,SAAS,GAAG,WAAW,EACrC,MAAM,GAAG,EAAE,EACX,KAAK,GAAG,EAAE,EACV,GAAG,KAAK,EACM;IACd,OAAO,CACL,6BACc,SAAS,EACrB,MAAM,EAAE,MAAM,EACd,IAAI,EAAC,KAAK,EACV,OAAO,EAAC,YAAY,EACpB,KAAK,EAAE,KAAK,EACZ,KAAK,EAAC,4BAA4B,KAC9B,KAAK,aAET,kBAAS,EAAE,EAAC,IAAI,EAAC,EAAE,EAAC,IAAI,EAAC,IAAI,EAAC,SAAS,EAAC,EAAE,EAAC,IAAI,EAAC,EAAE,EAAC,IAAI,GAAG,EAC1D,kBAAS,EAAE,EAAC,IAAI,EAAC,EAAE,EAAC,IAAI,EAAC,IAAI,EAAC,SAAS,EAAC,EAAE,EAAC,IAAI,EAAC,EAAE,EAAC,IAAI,GAAG,EAC1D,kBAAS,EAAE,EAAC,IAAI,EAAC,EAAE,EAAC,IAAI,EAAC,IAAI,EAAC,SAAS,EAAC,EAAE,EAAC,GAAG,EAAC,EAAE,EAAC,GAAG,GAAG,EACxD,kBAAS,EAAE,EAAC,IAAI,EAAC,EAAE,EAAC,IAAI,EAAC,IAAI,EAAC,SAAS,EAAC,EAAE,EAAC,GAAG,EAAC,EAAE,EAAC,GAAG,GAAG,EACxD,eACE,CAAC,EAAC,0BAA0B,EAC5B,IAAI,EAAC,MAAM,EACX,MAAM,EAAC,SAAS,EAChB,aAAa,EAAC,OAAO,EACrB,WAAW,EAAC,GAAG,GACf,EACF,eACE,CAAC,EAAC,2BAA2B,EAC7B,IAAI,EAAC,MAAM,EACX,MAAM,EAAC,SAAS,EAChB,aAAa,EAAC,OAAO,EACrB,WAAW,EAAC,GAAG,GACf,EACF,eACE,CAAC,EAAC,gCAAgC,EAClC,IAAI,EAAC,MAAM,EACX,MAAM,EAAC,SAAS,EAChB,aAAa,EAAC,OAAO,EACrB,WAAW,EAAC,GAAG,GACf,EACF,eACE,CAAC,EAAC,iCAAiC,EACnC,IAAI,EAAC,MAAM,EACX,MAAM,EAAC,SAAS,EAChB,aAAa,EAAC,OAAO,EACrB,WAAW,EAAC,GAAG,GACf,IACE,CACP,CAAC;AACJ,CAAC"}
@@ -0,0 +1,13 @@
1
+ import type { NusmDevtoolsSnapshot } from "../types";
2
+ type ControlOptions = {
3
+ adapterFilter: string;
4
+ onAdapterFilter: (value: string) => void;
5
+ onQuery: (value: string) => void;
6
+ onStoreFilter: (value: string) => void;
7
+ query: string;
8
+ snapshots: Map<string, NusmDevtoolsSnapshot>;
9
+ storeFilter: string;
10
+ };
11
+ export declare const renderPanelControls: (options: ControlOptions) => HTMLElement;
12
+ export {};
13
+ //# sourceMappingURL=panel-controls.d.ts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"panel-controls.d.ts","sourceRoot":"","sources":["../../src/devtools/panel-controls.ts"],"names":[],"mappings":"AAAA,OAAO,KAAK,EAAE,oBAAoB,EAAE,MAAM,UAAU,CAAC;AASrD,KAAK,cAAc,GAAG;IACpB,aAAa,EAAE,MAAM,CAAC;IACtB,eAAe,EAAE,CAAC,KAAK,EAAE,MAAM,KAAK,IAAI,CAAC;IACzC,OAAO,EAAE,CAAC,KAAK,EAAE,MAAM,KAAK,IAAI,CAAC;IACjC,aAAa,EAAE,CAAC,KAAK,EAAE,MAAM,KAAK,IAAI,CAAC;IACvC,KAAK,EAAE,MAAM,CAAC;IACd,SAAS,EAAE,GAAG,CAAC,MAAM,EAAE,oBAAoB,CAAC,CAAC;IAC7C,WAAW,EAAE,MAAM,CAAC;CACrB,CAAC;AAEF,eAAO,MAAM,mBAAmB,YAAa,cAAc,KAAG,WAsC7D,CAAC"}
@@ -0,0 +1,32 @@
1
+ const option = (value, label) => {
2
+ const item = document.createElement("option");
3
+ item.value = value;
4
+ item.textContent = label;
5
+ return item;
6
+ };
7
+ export const renderPanelControls = (options) => {
8
+ const controls = document.createElement("div");
9
+ controls.className = "nusm-controls";
10
+ const search = document.createElement("input");
11
+ search.type = "search";
12
+ search.value = options.query;
13
+ search.placeholder = "Search stores and values";
14
+ search.setAttribute("aria-label", "Search stores and values");
15
+ search.addEventListener("input", () => options.onQuery(search.value));
16
+ const stores = document.createElement("select");
17
+ stores.setAttribute("aria-label", "Filter by store");
18
+ stores.append(option("all", "All stores"), ...[...options.snapshots.keys()].sort().map((id) => option(id, id)));
19
+ stores.value = options.storeFilter;
20
+ stores.addEventListener("change", () => options.onStoreFilter(stores.value));
21
+ const adapters = document.createElement("select");
22
+ adapters.setAttribute("aria-label", "Filter by adapter");
23
+ const adapterNames = [
24
+ ...new Set([...options.snapshots.values()].map((snapshot) => snapshot.adapterName ?? "memory")),
25
+ ].sort();
26
+ adapters.append(option("all", "All adapters"), ...adapterNames.map((name) => option(name, name)));
27
+ adapters.value = options.adapterFilter;
28
+ adapters.addEventListener("change", () => options.onAdapterFilter(adapters.value));
29
+ controls.append(search, stores, adapters);
30
+ return controls;
31
+ };
32
+ //# sourceMappingURL=panel-controls.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"panel-controls.js","sourceRoot":"","sources":["../../src/devtools/panel-controls.ts"],"names":[],"mappings":"AAEA,MAAM,MAAM,GAAG,CAAC,KAAa,EAAE,KAAa,EAAE,EAAE;IAC9C,MAAM,IAAI,GAAG,QAAQ,CAAC,aAAa,CAAC,QAAQ,CAAC,CAAC;IAC9C,IAAI,CAAC,KAAK,GAAG,KAAK,CAAC;IACnB,IAAI,CAAC,WAAW,GAAG,KAAK,CAAC;IACzB,OAAO,IAAI,CAAC;AACd,CAAC,CAAC;AAYF,MAAM,CAAC,MAAM,mBAAmB,GAAG,CAAC,OAAuB,EAAe,EAAE;IAC1E,MAAM,QAAQ,GAAG,QAAQ,CAAC,aAAa,CAAC,KAAK,CAAC,CAAC;IAC/C,QAAQ,CAAC,SAAS,GAAG,eAAe,CAAC;IACrC,MAAM,MAAM,GAAG,QAAQ,CAAC,aAAa,CAAC,OAAO,CAAC,CAAC;IAC/C,MAAM,CAAC,IAAI,GAAG,QAAQ,CAAC;IACvB,MAAM,CAAC,KAAK,GAAG,OAAO,CAAC,KAAK,CAAC;IAC7B,MAAM,CAAC,WAAW,GAAG,0BAA0B,CAAC;IAChD,MAAM,CAAC,YAAY,CAAC,YAAY,EAAE,0BAA0B,CAAC,CAAC;IAC9D,MAAM,CAAC,gBAAgB,CAAC,OAAO,EAAE,GAAG,EAAE,CAAC,OAAO,CAAC,OAAO,CAAC,MAAM,CAAC,KAAK,CAAC,CAAC,CAAC;IAEtE,MAAM,MAAM,GAAG,QAAQ,CAAC,aAAa,CAAC,QAAQ,CAAC,CAAC;IAChD,MAAM,CAAC,YAAY,CAAC,YAAY,EAAE,iBAAiB,CAAC,CAAC;IACrD,MAAM,CAAC,MAAM,CACX,MAAM,CAAC,KAAK,EAAE,YAAY,CAAC,EAC3B,GAAG,CAAC,GAAG,OAAO,CAAC,SAAS,CAAC,IAAI,EAAE,CAAC,CAAC,IAAI,EAAE,CAAC,GAAG,CAAC,CAAC,EAAE,EAAE,EAAE,CAAC,MAAM,CAAC,EAAE,EAAE,EAAE,CAAC,CAAC,CACpE,CAAC;IACF,MAAM,CAAC,KAAK,GAAG,OAAO,CAAC,WAAW,CAAC;IACnC,MAAM,CAAC,gBAAgB,CAAC,QAAQ,EAAE,GAAG,EAAE,CAAC,OAAO,CAAC,aAAa,CAAC,MAAM,CAAC,KAAK,CAAC,CAAC,CAAC;IAE7E,MAAM,QAAQ,GAAG,QAAQ,CAAC,aAAa,CAAC,QAAQ,CAAC,CAAC;IAClD,QAAQ,CAAC,YAAY,CAAC,YAAY,EAAE,mBAAmB,CAAC,CAAC;IACzD,MAAM,YAAY,GAAG;QACnB,GAAG,IAAI,GAAG,CACR,CAAC,GAAG,OAAO,CAAC,SAAS,CAAC,MAAM,EAAE,CAAC,CAAC,GAAG,CACjC,CAAC,QAAQ,EAAE,EAAE,CAAC,QAAQ,CAAC,WAAW,IAAI,QAAQ,CAC/C,CACF;KACF,CAAC,IAAI,EAAE,CAAC;IACT,QAAQ,CAAC,MAAM,CACb,MAAM,CAAC,KAAK,EAAE,cAAc,CAAC,EAC7B,GAAG,YAAY,CAAC,GAAG,CAAC,CAAC,IAAI,EAAE,EAAE,CAAC,MAAM,CAAC,IAAI,EAAE,IAAI,CAAC,CAAC,CAClD,CAAC;IACF,QAAQ,CAAC,KAAK,GAAG,OAAO,CAAC,aAAa,CAAC;IACvC,QAAQ,CAAC,gBAAgB,CAAC,QAAQ,EAAE,GAAG,EAAE,CACvC,OAAO,CAAC,eAAe,CAAC,QAAQ,CAAC,KAAK,CAAC,CACxC,CAAC;IACF,QAAQ,CAAC,MAAM,CAAC,MAAM,EAAE,MAAM,EAAE,QAAQ,CAAC,CAAC;IAC1C,OAAO,QAAQ,CAAC;AAClB,CAAC,CAAC"}
@@ -0,0 +1,15 @@
1
+ import type { NusmDevtoolsSnapshot, NusmEvent } from "../types";
2
+ import type { NusmDevtoolsCommandInput } from "./types";
3
+ type DetailOptions = {
4
+ details: HTMLElement;
5
+ editorEditable: boolean;
6
+ editorValue: string;
7
+ events: Map<string, NusmEvent[]>;
8
+ onCommand: (command: NusmDevtoolsCommandInput) => void;
9
+ onEditorInput: (value: string) => void;
10
+ onStatus: (status: string) => void;
11
+ selected: NusmDevtoolsSnapshot;
12
+ };
13
+ export declare const renderNusmStoreDetail: (options: DetailOptions) => void;
14
+ export {};
15
+ //# sourceMappingURL=panel-detail.d.ts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"panel-detail.d.ts","sourceRoot":"","sources":["../../src/devtools/panel-detail.ts"],"names":[],"mappings":"AAAA,OAAO,KAAK,EAAE,oBAAoB,EAAE,SAAS,EAAE,MAAM,UAAU,CAAC;AAEhE,OAAO,KAAK,EAAE,wBAAwB,EAAE,MAAM,SAAS,CAAC;AAExD,KAAK,aAAa,GAAG;IACnB,OAAO,EAAE,WAAW,CAAC;IACrB,cAAc,EAAE,OAAO,CAAC;IACxB,WAAW,EAAE,MAAM,CAAC;IACpB,MAAM,EAAE,GAAG,CAAC,MAAM,EAAE,SAAS,EAAE,CAAC,CAAC;IACjC,SAAS,EAAE,CAAC,OAAO,EAAE,wBAAwB,KAAK,IAAI,CAAC;IACvD,aAAa,EAAE,CAAC,KAAK,EAAE,MAAM,KAAK,IAAI,CAAC;IACvC,QAAQ,EAAE,CAAC,MAAM,EAAE,MAAM,KAAK,IAAI,CAAC;IACnC,QAAQ,EAAE,oBAAoB,CAAC;CAChC,CAAC;AAsHF,eAAO,MAAM,qBAAqB,YAAa,aAAa,SAyC3D,CAAC"}