nostr-wot-sdk 0.4.2 → 0.5.0

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
package/CHANGELOG.md CHANGED
@@ -5,6 +5,27 @@ All notable changes to this project will be documented in this file.
5
5
  The format is based on [Keep a Changelog](https://keepachangelog.com/en/1.0.0/),
6
6
  and this project adheres to [Semantic Versioning](https://semver.org/spec/v2.0.0.html).
7
7
 
8
+ ## [0.5.0] - 2025-02-05
9
+
10
+ ### Changed
11
+
12
+ - **Simplified extension connection** - Removed event-based connection flow
13
+ - SDK now simply checks `window.nostr.wot` directly
14
+ - Extension auto-injects when enabled, no handshake needed
15
+ - Faster and more reliable connection
16
+
17
+ - **React context simplified**
18
+ - Removed `ExtensionConnector` usage
19
+ - `useExtension()` hook now returns simpler state: `isConnected`, `isChecking`, `isChecked`, `refresh`
20
+ - Removed `extensionOptions` prop from `WoTProvider`
21
+ - State is now `'checking' | 'connected' | 'not-available'`
22
+
23
+ ### Removed
24
+
25
+ - Removed event-based connection (`nostr-wot-check`, `nostr-wot-connect` events)
26
+ - Removed `ExtensionConnectionOptions` from React exports
27
+ - Extension connection utilities (`checkExtension`, `connectExtension`, `checkAndConnect`, `ExtensionConnector`) are still exported but deprecated
28
+
8
29
  ## [0.4.2] - 2025-02-05
9
30
 
10
31
  ### Fixed
@@ -180,6 +201,7 @@ function Profile({ pubkey }) {
180
201
  - TypeScript support with full type definitions
181
202
  - Error classes: `WoTError`, `NetworkError`, `NotFoundError`, `TimeoutError`, `ValidationError`
182
203
 
204
+ [0.5.0]: https://github.com/nostr-wot/nostr-wot-sdk/compare/v0.4.2...v0.5.0
183
205
  [0.4.2]: https://github.com/nostr-wot/nostr-wot-sdk/compare/v0.4.1...v0.4.2
184
206
  [0.4.1]: https://github.com/nostr-wot/nostr-wot-sdk/compare/v0.4.0...v0.4.1
185
207
  [0.4.0]: https://github.com/nostr-wot/nostr-wot-sdk/compare/v0.3.2...v0.4.0
package/README.md CHANGED
@@ -251,7 +251,7 @@ Install the [Nostr WoT Extension](https://github.com/nostr-wot/nostr-wot-extensi
251
251
  - **Privacy** — Queries never leave your browser
252
252
  - **Offline** — Works without internet once synced
253
253
 
254
- The SDK automatically detects and connects to the extension using an event-based handshake. When the extension is present, it **always takes priority** over oracle settings.
254
+ The SDK automatically detects the extension via `window.nostr.wot`. When the extension is present (with auto-inject enabled), it **always takes priority** over oracle settings.
255
255
 
256
256
  ```javascript
257
257
  const wot = new WoT({
@@ -269,60 +269,16 @@ if (await wot.isUsingExtension()) {
269
269
  }
270
270
  ```
271
271
 
272
- ### Extension Connection Utilities
273
-
274
- For advanced use cases, the SDK exports low-level extension connection functions:
275
-
276
- ```javascript
277
- import {
278
- checkExtension, // Check if extension is installed
279
- connectExtension, // Connect to the extension
280
- checkAndConnect, // Check and connect in one call
281
- ExtensionConnector // Stateful connector class
282
- } from 'nostr-wot-sdk';
283
-
284
- // Check if extension is installed (100ms timeout)
285
- const isInstalled = await checkExtension();
286
-
287
- // Connect to extension (5s timeout)
288
- const extension = await connectExtension();
289
-
290
- // Or do both in one call
291
- const result = await checkAndConnect();
292
- if (result.state === 'connected') {
293
- const distance = await result.extension.getDistance('target...');
294
- }
295
-
296
- // For stateful connection management
297
- const connector = new ExtensionConnector();
298
- connector.subscribe((result) => {
299
- console.log('State changed:', result.state);
300
- });
301
- await connector.connect();
302
- ```
303
-
304
- #### Extension Events
305
-
306
- The SDK uses a standard event-based protocol to communicate with the extension:
307
-
308
- | Event | Direction | Purpose |
309
- |-------|-----------|---------|
310
- | `nostr-wot-check` | Page → Extension | Check if extension installed |
311
- | `nostr-wot-present` | Extension → Page | Response confirming presence |
312
- | `nostr-wot-connect` | Page → Extension | Request API injection |
313
- | `nostr-wot-ready` | Extension → Page | API is ready at `window.nostr.wot` |
314
- | `nostr-wot-error` | Extension → Page | Injection failed with error |
315
-
316
272
  ## Framework Integration
317
273
 
318
274
  ### React
319
275
 
320
- The SDK provides first-class React support with automatic extension detection and connection. Just wrap your app with `WoTProvider` and you're ready to go — no additional configuration needed.
276
+ The SDK provides first-class React support with automatic extension detection. Just wrap your app with `WoTProvider` and you're ready to go — no additional configuration needed.
321
277
 
322
278
  ```javascript
323
279
  import { WoTProvider, useWoT, useExtension } from 'nostr-wot-sdk/react';
324
280
 
325
- // Wrap your app - automatically connects to extension
281
+ // Wrap your app - automatically detects extension
326
282
  function App() {
327
283
  return (
328
284
  <WoTProvider>
@@ -333,13 +289,11 @@ function App() {
333
289
 
334
290
  // Check extension status anywhere
335
291
  function ExtensionStatus() {
336
- const { isConnected, isConnecting, isInstalled, error } = useExtension();
292
+ const { isConnected, isChecking } = useExtension();
337
293
 
338
- if (isConnecting) return <span>Connecting to extension...</span>;
339
- if (!isInstalled) return <span>Install the WoT extension for best experience</span>;
340
- if (error) return <span>Error: {error}</span>;
341
- if (isConnected) return <span>Connected to extension!</span>;
342
- return null;
294
+ if (isChecking) return <span>Checking for extension...</span>;
295
+ if (isConnected) return <span>Extension connected!</span>;
296
+ return <span>Extension not available</span>;
343
297
  }
344
298
 
345
299
  // Use WoT data in components
@@ -363,16 +317,10 @@ function Profile({ pubkey }) {
363
317
  #### Provider Options
364
318
 
365
319
  ```javascript
366
- // With fallback for when extension is not installed
320
+ // With fallback for when extension is not available
367
321
  <WoTProvider options={{
368
322
  fallback: { myPubkey: 'abc123...' }
369
323
  }}>
370
-
371
- // Custom extension connection timeouts
372
- <WoTProvider extensionOptions={{
373
- checkTimeout: 100, // Extension detection timeout (ms)
374
- connectTimeout: 5000 // Connection timeout (ms)
375
- }}>
376
324
  ```
377
325
 
378
326
  #### Available Hooks
@@ -388,17 +336,15 @@ function Profile({ pubkey }) {
388
336
 
389
337
  #### Extension State
390
338
 
391
- The `useExtension()` hook provides detailed extension status:
339
+ The `useExtension()` hook provides extension status:
392
340
 
393
341
  ```javascript
394
342
  const {
395
- state, // 'idle' | 'checking' | 'connecting' | 'connected' | 'not-installed' | 'error'
343
+ state, // 'checking' | 'connected' | 'not-available'
396
344
  isConnected, // Extension is connected and ready
397
- isConnecting, // Currently checking/connecting
398
- isInstalled, // Extension is installed (may still be connecting)
399
- isChecked, // Initial check complete
400
- error, // Error message if connection failed
401
- connect, // Function to manually retry connection
345
+ isChecking, // Currently checking
346
+ isChecked, // Check complete
347
+ refresh, // Function to re-check extension availability
402
348
  } = useExtension();
403
349
  ```
404
350
 
package/dist/index.cjs CHANGED
@@ -85,236 +85,10 @@ function chunk(array, size) {
85
85
  return chunks;
86
86
  }
87
87
 
88
- // src/extension.ts
89
- function checkExtension(timeout = 100) {
90
- return new Promise((resolve) => {
91
- var _a;
92
- if (typeof window === "undefined") {
93
- resolve(false);
94
- return;
95
- }
96
- const win = window;
97
- if ((_a = win.nostr) == null ? void 0 : _a.wot) {
98
- resolve(true);
99
- return;
100
- }
101
- const handler = () => {
102
- window.removeEventListener("nostr-wot-present", handler);
103
- clearTimeout(timer);
104
- resolve(true);
105
- };
106
- window.addEventListener("nostr-wot-present", handler);
107
- const timer = setTimeout(() => {
108
- window.removeEventListener("nostr-wot-present", handler);
109
- resolve(false);
110
- }, timeout);
111
- window.dispatchEvent(new CustomEvent("nostr-wot-check"));
112
- });
113
- }
114
- function connectExtension(timeout = 5e3) {
115
- return new Promise((resolve, reject) => {
116
- var _a;
117
- if (typeof window === "undefined") {
118
- reject(new Error("Not in browser environment"));
119
- return;
120
- }
121
- const win = window;
122
- if ((_a = win.nostr) == null ? void 0 : _a.wot) {
123
- resolve(win.nostr.wot);
124
- return;
125
- }
126
- let timer;
127
- const onReady = () => {
128
- var _a2;
129
- cleanup();
130
- const ext = (_a2 = window.nostr) == null ? void 0 : _a2.wot;
131
- if (ext) {
132
- resolve(ext);
133
- } else {
134
- reject(new Error("Extension ready event fired but API not found"));
135
- }
136
- };
137
- const onError = (e) => {
138
- cleanup();
139
- const detail = e.detail;
140
- reject(new Error((detail == null ? void 0 : detail.error) || "Connection failed"));
141
- };
142
- const cleanup = () => {
143
- clearTimeout(timer);
144
- window.removeEventListener("nostr-wot-ready", onReady);
145
- window.removeEventListener("nostr-wot-error", onError);
146
- };
147
- window.addEventListener("nostr-wot-ready", onReady);
148
- window.addEventListener("nostr-wot-error", onError);
149
- window.dispatchEvent(new CustomEvent("nostr-wot-connect"));
150
- timer = setTimeout(() => {
151
- cleanup();
152
- reject(new Error("Connection timeout"));
153
- }, timeout);
154
- });
155
- }
156
- async function checkAndConnect(options = {}) {
157
- var _a;
158
- const { checkTimeout = 100, connectTimeout = 5e3, autoConnect = true } = options;
159
- if (typeof window === "undefined") {
160
- return { state: "not-installed", extension: null };
161
- }
162
- const win = window;
163
- if ((_a = win.nostr) == null ? void 0 : _a.wot) {
164
- return { state: "connected", extension: win.nostr.wot };
165
- }
166
- const isInstalled = await checkExtension(checkTimeout);
167
- if (!isInstalled) {
168
- return { state: "not-installed", extension: null };
169
- }
170
- if (!autoConnect) {
171
- return { state: "idle", extension: null };
172
- }
173
- try {
174
- const extension = await connectExtension(connectTimeout);
175
- return { state: "connected", extension };
176
- } catch (error) {
177
- return {
178
- state: "error",
179
- extension: null,
180
- error: error instanceof Error ? error.message : "Unknown error"
181
- };
182
- }
183
- }
184
- var ExtensionConnector = class {
185
- constructor(options = {}) {
186
- this.options = options;
187
- this.state = "idle";
188
- this.extension = null;
189
- this.connectionPromise = null;
190
- this.listeners = /* @__PURE__ */ new Set();
191
- }
192
- /**
193
- * Get current state
194
- */
195
- getState() {
196
- return this.state;
197
- }
198
- /**
199
- * Get current extension instance
200
- */
201
- getExtension() {
202
- return this.extension;
203
- }
204
- /**
205
- * Get current error
206
- */
207
- getError() {
208
- return this.error;
209
- }
210
- /**
211
- * Get current result
212
- */
213
- getResult() {
214
- return {
215
- state: this.state,
216
- extension: this.extension,
217
- error: this.error
218
- };
219
- }
220
- /**
221
- * Subscribe to state changes
222
- */
223
- subscribe(listener) {
224
- this.listeners.add(listener);
225
- return () => {
226
- this.listeners.delete(listener);
227
- };
228
- }
229
- notify() {
230
- const result = this.getResult();
231
- for (const listener of this.listeners) {
232
- listener(result);
233
- }
234
- }
235
- setState(state, extension = null, error) {
236
- this.state = state;
237
- this.extension = extension;
238
- this.error = error;
239
- this.notify();
240
- }
241
- /**
242
- * Connect to the extension
243
- * Returns existing promise if already connecting
244
- */
245
- async connect() {
246
- if (this.state === "connected" && this.extension) {
247
- return this.getResult();
248
- }
249
- if (this.connectionPromise) {
250
- return this.connectionPromise;
251
- }
252
- this.connectionPromise = this.doConnect();
253
- const result = await this.connectionPromise;
254
- this.connectionPromise = null;
255
- return result;
256
- }
257
- async doConnect() {
258
- var _a;
259
- const { checkTimeout = 100, connectTimeout = 5e3 } = this.options;
260
- if (typeof window === "undefined") {
261
- this.setState("not-installed");
262
- return this.getResult();
263
- }
264
- const win = window;
265
- if ((_a = win.nostr) == null ? void 0 : _a.wot) {
266
- this.setState("connected", win.nostr.wot);
267
- return this.getResult();
268
- }
269
- this.setState("checking");
270
- const isInstalled = await checkExtension(checkTimeout);
271
- if (!isInstalled) {
272
- this.setState("not-installed");
273
- return this.getResult();
274
- }
275
- this.setState("connecting");
276
- try {
277
- const extension = await connectExtension(connectTimeout);
278
- this.setState("connected", extension);
279
- } catch (error) {
280
- this.setState(
281
- "error",
282
- null,
283
- error instanceof Error ? error.message : "Unknown error"
284
- );
285
- }
286
- return this.getResult();
287
- }
288
- /**
289
- * Reset state and disconnect
290
- */
291
- reset() {
292
- this.state = "idle";
293
- this.extension = null;
294
- this.error = void 0;
295
- this.connectionPromise = null;
296
- this.notify();
297
- }
298
- };
299
- var defaultConnector = null;
300
- function getDefaultConnector(options) {
301
- if (!defaultConnector) {
302
- defaultConnector = new ExtensionConnector(options);
303
- }
304
- return defaultConnector;
305
- }
306
- function resetDefaultConnector() {
307
- if (defaultConnector) {
308
- defaultConnector.reset();
309
- defaultConnector = null;
310
- }
311
- }
312
-
313
88
  // src/wot.ts
314
89
  var WoT = class {
315
90
  constructor(options = {}) {
316
91
  this.extension = null;
317
- this.extensionChecked = false;
318
92
  this.extensionPubkey = null;
319
93
  var _a, _b, _c, _d, _e, _f, _g, _h, _i, _j, _k;
320
94
  this.fallbackOptions = (_a = options.fallback) != null ? _a : null;
@@ -335,16 +109,15 @@ var WoT = class {
335
109
  }
336
110
  /**
337
111
  * Checks if browser extension is available and returns it
338
- * Uses event-based connection flow for reliable detection
339
- * Always returns fresh reference from window.nostr.wot to handle extension reloads
112
+ * Simply checks window.nostr.wot - extension auto-injects when enabled
113
+ * Always returns fresh reference to handle extension reloads
340
114
  */
341
115
  async getExtension() {
342
- var _a, _b, _c;
116
+ var _a, _b;
343
117
  if (typeof window === "undefined") return null;
344
118
  const win = window;
345
119
  if ((_a = win.nostr) == null ? void 0 : _a.wot) {
346
120
  this.extension = win.nostr.wot;
347
- this.extensionChecked = true;
348
121
  if (!this.extensionPubkey) {
349
122
  try {
350
123
  this.extensionPubkey = await this.extension.getMyPubkey();
@@ -359,27 +132,8 @@ var WoT = class {
359
132
  }
360
133
  return this.extension;
361
134
  }
362
- if (this.extensionChecked) return this.extension;
363
- this.extensionChecked = true;
364
- const result = await checkAndConnect({
365
- checkTimeout: 100,
366
- connectTimeout: 5e3,
367
- autoConnect: true
368
- });
369
- if (result.state === "connected" && result.extension) {
370
- this.extension = result.extension;
371
- try {
372
- this.extensionPubkey = await this.extension.getMyPubkey();
373
- } catch (e) {
374
- if ((_c = win.nostr) == null ? void 0 : _c.getPublicKey) {
375
- try {
376
- this.extensionPubkey = await win.nostr.getPublicKey();
377
- } catch (e2) {
378
- }
379
- }
380
- }
381
- }
382
- return this.extension;
135
+ this.extension = null;
136
+ return null;
383
137
  }
384
138
  /**
385
139
  * Gets the effective pubkey (from extension or fallback)
@@ -823,6 +577,231 @@ var WoT = class {
823
577
  }
824
578
  };
825
579
 
580
+ // src/extension.ts
581
+ function checkExtension(timeout = 100) {
582
+ return new Promise((resolve) => {
583
+ var _a;
584
+ if (typeof window === "undefined") {
585
+ resolve(false);
586
+ return;
587
+ }
588
+ const win = window;
589
+ if ((_a = win.nostr) == null ? void 0 : _a.wot) {
590
+ resolve(true);
591
+ return;
592
+ }
593
+ const handler = () => {
594
+ window.removeEventListener("nostr-wot-present", handler);
595
+ clearTimeout(timer);
596
+ resolve(true);
597
+ };
598
+ window.addEventListener("nostr-wot-present", handler);
599
+ const timer = setTimeout(() => {
600
+ window.removeEventListener("nostr-wot-present", handler);
601
+ resolve(false);
602
+ }, timeout);
603
+ window.dispatchEvent(new CustomEvent("nostr-wot-check"));
604
+ });
605
+ }
606
+ function connectExtension(timeout = 5e3) {
607
+ return new Promise((resolve, reject) => {
608
+ var _a;
609
+ if (typeof window === "undefined") {
610
+ reject(new Error("Not in browser environment"));
611
+ return;
612
+ }
613
+ const win = window;
614
+ if ((_a = win.nostr) == null ? void 0 : _a.wot) {
615
+ resolve(win.nostr.wot);
616
+ return;
617
+ }
618
+ let timer;
619
+ const onReady = () => {
620
+ var _a2;
621
+ cleanup();
622
+ const ext = (_a2 = window.nostr) == null ? void 0 : _a2.wot;
623
+ if (ext) {
624
+ resolve(ext);
625
+ } else {
626
+ reject(new Error("Extension ready event fired but API not found"));
627
+ }
628
+ };
629
+ const onError = (e) => {
630
+ cleanup();
631
+ const detail = e.detail;
632
+ reject(new Error((detail == null ? void 0 : detail.error) || "Connection failed"));
633
+ };
634
+ const cleanup = () => {
635
+ clearTimeout(timer);
636
+ window.removeEventListener("nostr-wot-ready", onReady);
637
+ window.removeEventListener("nostr-wot-error", onError);
638
+ };
639
+ window.addEventListener("nostr-wot-ready", onReady);
640
+ window.addEventListener("nostr-wot-error", onError);
641
+ window.dispatchEvent(new CustomEvent("nostr-wot-connect"));
642
+ timer = setTimeout(() => {
643
+ cleanup();
644
+ reject(new Error("Connection timeout"));
645
+ }, timeout);
646
+ });
647
+ }
648
+ async function checkAndConnect(options = {}) {
649
+ var _a;
650
+ const { checkTimeout = 100, connectTimeout = 5e3, autoConnect = true } = options;
651
+ if (typeof window === "undefined") {
652
+ return { state: "not-installed", extension: null };
653
+ }
654
+ const win = window;
655
+ if ((_a = win.nostr) == null ? void 0 : _a.wot) {
656
+ return { state: "connected", extension: win.nostr.wot };
657
+ }
658
+ const isInstalled = await checkExtension(checkTimeout);
659
+ if (!isInstalled) {
660
+ return { state: "not-installed", extension: null };
661
+ }
662
+ if (!autoConnect) {
663
+ return { state: "idle", extension: null };
664
+ }
665
+ try {
666
+ const extension = await connectExtension(connectTimeout);
667
+ return { state: "connected", extension };
668
+ } catch (error) {
669
+ return {
670
+ state: "error",
671
+ extension: null,
672
+ error: error instanceof Error ? error.message : "Unknown error"
673
+ };
674
+ }
675
+ }
676
+ var ExtensionConnector = class {
677
+ constructor(options = {}) {
678
+ this.options = options;
679
+ this.state = "idle";
680
+ this.extension = null;
681
+ this.connectionPromise = null;
682
+ this.listeners = /* @__PURE__ */ new Set();
683
+ }
684
+ /**
685
+ * Get current state
686
+ */
687
+ getState() {
688
+ return this.state;
689
+ }
690
+ /**
691
+ * Get current extension instance
692
+ */
693
+ getExtension() {
694
+ return this.extension;
695
+ }
696
+ /**
697
+ * Get current error
698
+ */
699
+ getError() {
700
+ return this.error;
701
+ }
702
+ /**
703
+ * Get current result
704
+ */
705
+ getResult() {
706
+ return {
707
+ state: this.state,
708
+ extension: this.extension,
709
+ error: this.error
710
+ };
711
+ }
712
+ /**
713
+ * Subscribe to state changes
714
+ */
715
+ subscribe(listener) {
716
+ this.listeners.add(listener);
717
+ return () => {
718
+ this.listeners.delete(listener);
719
+ };
720
+ }
721
+ notify() {
722
+ const result = this.getResult();
723
+ for (const listener of this.listeners) {
724
+ listener(result);
725
+ }
726
+ }
727
+ setState(state, extension = null, error) {
728
+ this.state = state;
729
+ this.extension = extension;
730
+ this.error = error;
731
+ this.notify();
732
+ }
733
+ /**
734
+ * Connect to the extension
735
+ * Returns existing promise if already connecting
736
+ */
737
+ async connect() {
738
+ if (this.state === "connected" && this.extension) {
739
+ return this.getResult();
740
+ }
741
+ if (this.connectionPromise) {
742
+ return this.connectionPromise;
743
+ }
744
+ this.connectionPromise = this.doConnect();
745
+ const result = await this.connectionPromise;
746
+ this.connectionPromise = null;
747
+ return result;
748
+ }
749
+ async doConnect() {
750
+ var _a;
751
+ const { checkTimeout = 100, connectTimeout = 5e3 } = this.options;
752
+ if (typeof window === "undefined") {
753
+ this.setState("not-installed");
754
+ return this.getResult();
755
+ }
756
+ const win = window;
757
+ if ((_a = win.nostr) == null ? void 0 : _a.wot) {
758
+ this.setState("connected", win.nostr.wot);
759
+ return this.getResult();
760
+ }
761
+ this.setState("checking");
762
+ const isInstalled = await checkExtension(checkTimeout);
763
+ if (!isInstalled) {
764
+ this.setState("not-installed");
765
+ return this.getResult();
766
+ }
767
+ this.setState("connecting");
768
+ try {
769
+ const extension = await connectExtension(connectTimeout);
770
+ this.setState("connected", extension);
771
+ } catch (error) {
772
+ this.setState(
773
+ "error",
774
+ null,
775
+ error instanceof Error ? error.message : "Unknown error"
776
+ );
777
+ }
778
+ return this.getResult();
779
+ }
780
+ /**
781
+ * Reset state and disconnect
782
+ */
783
+ reset() {
784
+ this.state = "idle";
785
+ this.extension = null;
786
+ this.error = void 0;
787
+ this.connectionPromise = null;
788
+ this.notify();
789
+ }
790
+ };
791
+ var defaultConnector = null;
792
+ function getDefaultConnector(options) {
793
+ if (!defaultConnector) {
794
+ defaultConnector = new ExtensionConnector(options);
795
+ }
796
+ return defaultConnector;
797
+ }
798
+ function resetDefaultConnector() {
799
+ if (defaultConnector) {
800
+ defaultConnector.reset();
801
+ defaultConnector = null;
802
+ }
803
+ }
804
+
826
805
  exports.DEFAULT_MAX_HOPS = DEFAULT_MAX_HOPS;
827
806
  exports.DEFAULT_ORACLE = DEFAULT_ORACLE;
828
807
  exports.DEFAULT_TIMEOUT = DEFAULT_TIMEOUT;
package/dist/index.d.cts CHANGED
@@ -365,13 +365,12 @@ declare class WoT {
365
365
  private readonly timeout;
366
366
  private readonly fallbackOptions;
367
367
  private extension;
368
- private extensionChecked;
369
368
  private extensionPubkey;
370
369
  constructor(options?: WoTOptions);
371
370
  /**
372
371
  * Checks if browser extension is available and returns it
373
- * Uses event-based connection flow for reliable detection
374
- * Always returns fresh reference from window.nostr.wot to handle extension reloads
372
+ * Simply checks window.nostr.wot - extension auto-injects when enabled
373
+ * Always returns fresh reference to handle extension reloads
375
374
  */
376
375
  private getExtension;
377
376
  /**