@wcstack/notification 1.20.0 → 1.21.0

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
package/README.ja.md CHANGED
@@ -9,7 +9,7 @@ Notifications API をリアクティブな state と state 駆動のコマンド
9
9
 
10
10
  - **command サーフェス**: `request`, `notify`, `close`, `closeAll`
11
11
  - **input サーフェス**: `notice`(reactive な表示), `mode`, `body`, `icon`, `badge`, `tag`, `lang`, `dir`, `require-interaction`, `silent`, `renotify`, `manual`
12
- - **output state サーフェス**: `permission`, `granted`, `denied`, `prompt`, `unsupported`, `error`, `clicked`, `closed`, `shown`
12
+ - **output state サーフェス**: `permission`, `granted`, `denied`, `prompt`, `unsupported`, `error`, `errorInfo`, `clicked`, `closed`, `shown`
13
13
 
14
14
  `@wcstack/notification` は [CSBC](https://github.com/csbc-dev/arch/blob/main/README.md)(Core / Shell / Binding Contract)アーキテクチャに従います:
15
15
 
@@ -143,6 +143,7 @@ wireNotificationClicks();
143
143
  | `permission` | `wcs-notify:permission-change` | `"prompt"` / `"granted"` / `"denied"` / `"unsupported"`、live。 |
144
144
  | `granted` / `denied` / `prompt` / `unsupported` | `wcs-notify:permission-change` | `permission` から派生する便宜ブール。 |
145
145
  | `error` | `wcs-notify:error` | 失敗時の `{ error, message }`(never-throw)、無ければ `null`。 |
146
+ | `errorInfo` | `wcs-notify:error-info-changed` | 失敗を serializable な taxonomy(`WcsIoErrorInfo`: 安定した `code` / `phase` / `recoverable`)に写した値、無ければ `null`。additive —— `error` から派生し、`error` の形状は不変。 |
146
147
  | `clicked` | `wcs-notify:click` | 直近クリックの `{ tag, data, action }`(event-token 源)。 |
147
148
  | `closed` | `wcs-notify:close` | 直近クローズの `{ tag, data, action }`。 |
148
149
  | `shown` | `wcs-notify:show` | 直近表示の `{ tag, data, action }`。 |
@@ -223,6 +224,7 @@ form:has(wcs-notify:state(error)) .banner { display: block; }
223
224
  - **SW バックエンドは `close` を中継しない。** `@wcstack/notification/sw` ヘルパは `notificationclick` のみを配線し、`notificationclose` は配線しません。そのため `sw` バックエンドでは `closed` / `wcs-notify:close` は発火しません(close 用のワーカー越え中継がない)。`clicked` はクリック中継で動作しますが、`closed` は constructor バックエンド限定の信号です。
224
225
  - **Push API はスコープ外。** 本パッケージは Notifications API(ローカル通知)をラップします。サーバ起点の Push は別の関心事です。
225
226
  - **サイレント失敗(zero-log)。** wcstack のゼロ依存哲学に沿い、`<wcs-notify>` は決してログ出力も throw もしません。API 不在 → `permission = "unsupported"`、未許可や表示失敗 → `error` プロパティ。`error` / `permission` をバインドして反応してください。
227
+ - **`errorInfo` taxonomy(additive)。** `error` と並んで、`<wcs-notify>` は*同一の*失敗を安定した `WcsIoErrorInfo`(`code` / `phase` / `recoverable`)に分類した serializable な `errorInfo`(`wcs-notify:error-info-changed`)を公開します。`error` の形状は変えません。Core 自身の安定エラーコードがそのまま写像されます: `unsupported` → `capability-missing`(phase `probe`)、未許可の権限 → `not-allowed`、非文字列 title → `invalid-argument`(いずれも phase `start`)、表示失敗 → `show-failed`、Service Worker バックエンド不在 → `no-service-worker`(いずれも phase `execute`)、想定外のコードは防御的に `notify-error`(phase `execute`)へ畳まれます。6 つとも `recoverable: false` です。`errorInfo` は `error` とまったく同じタイミングで遷移し(回復時に `null` へクリア)、共有の `WcsIoErrorInfo` 型と `WCS_NOTIFY_ERROR_CODE` 定数は export されています。
226
228
  - **SSR(`@wcstack/server`)。** `static hasConnectedCallbackPromise = true` を宣言し `connectedCallbackPromise` を公開するため、サーバレンダラは接続時の権限プローブが解決するまで待ってからスナップショットします。
227
229
 
228
230
  ## 設定
package/README.md CHANGED
@@ -9,7 +9,7 @@ With `@wcstack/state`, `<wcs-notify>` can be bound directly through path contrac
9
9
 
10
10
  - **command surface**: `request`, `notify`, `close`, `closeAll`
11
11
  - **input surface**: `notice` (reactive show), `mode`, `body`, `icon`, `badge`, `tag`, `lang`, `dir`, `require-interaction`, `silent`, `renotify`, `manual`
12
- - **output state surface**: `permission`, `granted`, `denied`, `prompt`, `unsupported`, `error`, `clicked`, `closed`, `shown`
12
+ - **output state surface**: `permission`, `granted`, `denied`, `prompt`, `unsupported`, `error`, `errorInfo`, `clicked`, `closed`, `shown`
13
13
 
14
14
  `@wcstack/notification` follows the [CSBC](https://github.com/csbc-dev/arch/blob/main/README.md) (Core / Shell / Binding Contract) architecture:
15
15
 
@@ -143,6 +143,7 @@ It relays each click over `BroadcastChannel("wcs-notify")` (primary) and `client
143
143
  | `permission` | `wcs-notify:permission-change` | `"prompt"` / `"granted"` / `"denied"` / `"unsupported"`, live. |
144
144
  | `granted` / `denied` / `prompt` / `unsupported` | `wcs-notify:permission-change` | Convenience booleans derived from `permission`. |
145
145
  | `error` | `wcs-notify:error` | `{ error, message }` on a failure (never-throw), else `null`. |
146
+ | `errorInfo` | `wcs-notify:error-info-changed` | Serializable failure taxonomy (`WcsIoErrorInfo`: stable `code` / `phase` / `recoverable`) on a failure, else `null`. Additive — derived from `error`, whose shape is unchanged. |
146
147
  | `clicked` | `wcs-notify:click` | `{ tag, data, action }` of the last click (event-token source). |
147
148
  | `closed` | `wcs-notify:close` | `{ tag, data, action }` of the last close. |
148
149
  | `shown` | `wcs-notify:show` | `{ tag, data, action }` of the last shown notification. |
@@ -225,6 +226,7 @@ DevTools open; they are not a supported styling hook.
225
226
  - **The SW backend does not relay `close`.** The `@wcstack/notification/sw` helper wires `notificationclick` only, not `notificationclose`. So under the `sw` backend `closed` / `wcs-notify:close` never fires (there is no cross-worker relay for close). `clicked` still works via the click relay; `closed` is a constructor-backend-only signal.
226
227
  - **Push API is out of scope.** This package wraps the Notifications API (local notifications). Server-initiated Push is a separate concern.
227
228
  - **Silent failure handling (zero-log).** Consistent with wcstack's zero-dependency philosophy, `<wcs-notify>` never logs or throws. A missing API → `permission = "unsupported"`; a not-granted permission or a show failure → the `error` property. Bind `error` / `permission` to react.
229
+ - **`errorInfo` taxonomy (additive).** Alongside `error`, `<wcs-notify>` publishes a serializable `errorInfo` (`wcs-notify:error-info-changed`) that classifies the *same* failure into a stable `WcsIoErrorInfo` (`code` / `phase` / `recoverable`), without changing the `error` shape. The Core's own stable error code maps straight through: `unsupported` → `capability-missing` (phase `probe`); a not-granted permission → `not-allowed` and a non-string title → `invalid-argument` (both phase `start`); a show failure → `show-failed` and a missing Service Worker backend → `no-service-worker` (both phase `execute`); any unexpected code folds defensively to `notify-error` (phase `execute`). All six are `recoverable: false`. `errorInfo` transitions exactly when `error` does (cleared to `null` on recovery); the shared `WcsIoErrorInfo` type and the `WCS_NOTIFY_ERROR_CODE` constants are exported.
228
230
  - **SSR (`@wcstack/server`).** Declares `static hasConnectedCallbackPromise = true` and exposes `connectedCallbackPromise`, so the server renderer waits for the connect-time permission probe before snapshotting.
229
231
 
230
232
  ## Configuration
package/dist/index.d.ts CHANGED
@@ -1,3 +1,14 @@
1
+ /** operation error の phase(taxonomy)。 */
2
+ type WcsIoErrorPhase = "probe" | "start" | "execute" | "decode" | "commit" | "dispose";
3
+ /** serializable な error info(non-cloneable な cause とは分離。DevTools / remote へは info のみ)。 */
4
+ interface WcsIoErrorInfo {
5
+ readonly code: string;
6
+ readonly phase: WcsIoErrorPhase;
7
+ readonly recoverable: boolean;
8
+ readonly capabilityId?: string;
9
+ readonly message: string;
10
+ }
11
+
1
12
  interface IWcBindableProperty {
2
13
  readonly name: string;
3
14
  readonly event: string;
@@ -13,7 +24,8 @@ interface IWcBindableCommand {
13
24
  }
14
25
  interface IWcBindable {
15
26
  readonly protocol: "wc-bindable";
16
- readonly version: 1;
27
+ /** Integer protocol version. All versions >= 1 are core-compatible. */
28
+ readonly version: number;
17
29
  readonly properties: readonly IWcBindableProperty[];
18
30
  readonly inputs?: readonly IWcBindableInput[];
19
31
  readonly commands?: readonly IWcBindableCommand[];
@@ -109,6 +121,8 @@ interface WcsNotifyCoreValues {
109
121
  prompt: boolean;
110
122
  unsupported: boolean;
111
123
  error: WcsNotifyErrorDetail | null;
124
+ /** Additive failure taxonomy derived from `error` (stable code / phase / recoverable). */
125
+ errorInfo: WcsIoErrorInfo | null;
112
126
  clicked: WcsNotifyClickDetail | null;
113
127
  closed: WcsNotifyClickDetail | null;
114
128
  shown: WcsNotifyClickDetail | null;
@@ -179,6 +193,7 @@ declare class NotificationCore extends EventTarget {
179
193
  private _mode;
180
194
  private _permission;
181
195
  private _error;
196
+ private _errorInfo;
182
197
  private _lastClick;
183
198
  private _lastClose;
184
199
  private _lastShow;
@@ -200,6 +215,13 @@ declare class NotificationCore extends EventTarget {
200
215
  get prompt(): boolean;
201
216
  get unsupported(): boolean;
202
217
  get error(): WcsNotifyErrorDetail | null;
218
+ /**
219
+ * The last failure's serializable `WcsIoErrorInfo` (stable `code` / `phase` /
220
+ * `recoverable`), or null. Additive wc-bindable property (event
221
+ * `wcs-notify:error-info-changed`), derived from `error`; the existing `error`
222
+ * property/event are unchanged.
223
+ */
224
+ get errorInfo(): WcsIoErrorInfo | null;
203
225
  get clicked(): WcsNotifyClickDetail | null;
204
226
  get closed(): WcsNotifyClickDetail | null;
205
227
  get shown(): WcsNotifyClickDetail | null;
@@ -207,6 +229,7 @@ declare class NotificationCore extends EventTarget {
207
229
  get ready(): Promise<void>;
208
230
  private _setPermission;
209
231
  private _setError;
232
+ private _commitErrorInfo;
210
233
  private _emit;
211
234
  /**
212
235
  * Start observing the `notifications` permission and subscribing to Service
@@ -321,6 +344,7 @@ declare class WcsNotify extends HTMLElement {
321
344
  get prompt(): boolean;
322
345
  get unsupported(): boolean;
323
346
  get error(): WcsNotifyErrorDetail | null;
347
+ get errorInfo(): WcsIoErrorInfo | null;
324
348
  get clicked(): WcsNotifyClickDetail | null;
325
349
  get closed(): WcsNotifyClickDetail | null;
326
350
  get shown(): WcsNotifyClickDetail | null;
@@ -336,5 +360,37 @@ declare class WcsNotify extends HTMLElement {
336
360
  disconnectedCallback(): void;
337
361
  }
338
362
 
339
- export { NotificationCore, WcsNotify, bootstrapNotification, getConfig };
340
- export type { IWritableConfig, IWritableTagNames, NotificationPermissionRaw, NotifyBackend, NotifyOptions, PermissionStateOrUnsupported, WcsNotifyClickDetail, WcsNotifyCommands, WcsNotifyCoreCommands, WcsNotifyCoreValues, WcsNotifyErrorDetail, WcsNotifyInputs, WcsNotifySwMessage, WcsNotifyValues };
363
+ /**
364
+ * notificationCapabilities.ts
365
+ *
366
+ * Notification node 固有の error code(taxonomy)と derivation。汎用の error info 型は
367
+ * `./platformCapability.js`(/io-core/ から copy-distribution される生成ファイル)から
368
+ * import する。notification は監視(permission)と操作(notify/close)を 1 タグに併せ持つが、
369
+ * 競合する非同期 operation の lane は持たない(show は最新値で上書きされる momentary な
370
+ * 送出)ため、lane は採用せず error taxonomy(errorInfo)のみを追加する。
371
+ *
372
+ * sensor family と異なり、NotificationCore の error detail の `.error` は既に安定コード
373
+ * (`this._err(code, message)` が産出する `"unsupported"` / `"not-granted"` /
374
+ * `"invalid-title"` / `"show-failed"` / `"no-service-worker"`)であり、Error.name ではない。
375
+ * したがって derivation は `.error` コードを taxonomy に写すだけの純粋な map である。
376
+ * 想定外のコードは防御的に `notify-error` へ畳む。
377
+ */
378
+
379
+ /** 安定した notification error code(taxonomy)。値は公開キーとして固定。 */
380
+ declare const WCS_NOTIFY_ERROR_CODE: {
381
+ /** Notifications API 非対応(`globalThis.Notification` 不在)。 */
382
+ readonly CapabilityMissing: "capability-missing";
383
+ /** 権限が granted でない状態での notify()。 */
384
+ readonly NotAllowed: "not-allowed";
385
+ /** notify() に非文字列 title が渡された。 */
386
+ readonly InvalidArgument: "invalid-argument";
387
+ /** notification の生成 / 表示に失敗した(constructor 例外 / onerror / SW show reject)。 */
388
+ readonly ShowFailed: "show-failed";
389
+ /** SW backend が必要だが `navigator.serviceWorker` が不在。 */
390
+ readonly NoServiceWorker: "no-service-worker";
391
+ /** その他 / 想定外の error code に対する防御的 fallback。 */
392
+ readonly NotifyError: "notify-error";
393
+ };
394
+
395
+ export { NotificationCore, WCS_NOTIFY_ERROR_CODE, WcsNotify, bootstrapNotification, getConfig };
396
+ export type { IWritableConfig, IWritableTagNames, NotificationPermissionRaw, NotifyBackend, NotifyOptions, PermissionStateOrUnsupported, WcsIoErrorInfo, WcsIoErrorPhase, WcsNotifyClickDetail, WcsNotifyCommands, WcsNotifyCoreCommands, WcsNotifyCoreValues, WcsNotifyErrorDetail, WcsNotifyInputs, WcsNotifySwMessage, WcsNotifyValues };
package/dist/index.esm.js CHANGED
@@ -50,6 +50,69 @@ function setConfig(partialConfig) {
50
50
  frozenConfig = null;
51
51
  }
52
52
 
53
+ /**
54
+ * notificationCapabilities.ts
55
+ *
56
+ * Notification node 固有の error code(taxonomy)と derivation。汎用の error info 型は
57
+ * `./platformCapability.js`(/io-core/ から copy-distribution される生成ファイル)から
58
+ * import する。notification は監視(permission)と操作(notify/close)を 1 タグに併せ持つが、
59
+ * 競合する非同期 operation の lane は持たない(show は最新値で上書きされる momentary な
60
+ * 送出)ため、lane は採用せず error taxonomy(errorInfo)のみを追加する。
61
+ *
62
+ * sensor family と異なり、NotificationCore の error detail の `.error` は既に安定コード
63
+ * (`this._err(code, message)` が産出する `"unsupported"` / `"not-granted"` /
64
+ * `"invalid-title"` / `"show-failed"` / `"no-service-worker"`)であり、Error.name ではない。
65
+ * したがって derivation は `.error` コードを taxonomy に写すだけの純粋な map である。
66
+ * 想定外のコードは防御的に `notify-error` へ畳む。
67
+ */
68
+ /** 安定した notification error code(taxonomy)。値は公開キーとして固定。 */
69
+ const WCS_NOTIFY_ERROR_CODE = {
70
+ /** Notifications API 非対応(`globalThis.Notification` 不在)。 */
71
+ CapabilityMissing: "capability-missing",
72
+ /** 権限が granted でない状態での notify()。 */
73
+ NotAllowed: "not-allowed",
74
+ /** notify() に非文字列 title が渡された。 */
75
+ InvalidArgument: "invalid-argument",
76
+ /** notification の生成 / 表示に失敗した(constructor 例外 / onerror / SW show reject)。 */
77
+ ShowFailed: "show-failed",
78
+ /** SW backend が必要だが `navigator.serviceWorker` が不在。 */
79
+ NoServiceWorker: "no-service-worker",
80
+ /** その他 / 想定外の error code に対する防御的 fallback。 */
81
+ NotifyError: "notify-error",
82
+ };
83
+ /**
84
+ * notification の失敗を serializable な error taxonomy に写す。引数は
85
+ * `wcs-notify:error` の detail(`{ error, message }`)そのもの。`.error` は
86
+ * `NotificationCore._err()` が付与した安定コードで、Error.name ではない。
87
+ *
88
+ * - `"unsupported"` は開始前の能力欠如 → phase="probe" / capability-missing。
89
+ * - `"not-granted"` / `"invalid-title"` は show 手前の前提条件違反(権限・引数)→
90
+ * phase="start" / not-allowed・invalid-argument。
91
+ * - `"show-failed"` は show 実行中の失敗 → phase="execute" / show-failed。
92
+ * - `"no-service-worker"` は SW backend 要求時の transport 欠如 → phase="execute" /
93
+ * no-service-worker。
94
+ * - それ以外(未知コード)は防御的に phase="execute" / notify-error。
95
+ *
96
+ * いずれも retry で自動回復しない(recoverable=false)。
97
+ */
98
+ function deriveNotifyErrorInfo(error) {
99
+ const { error: code, message } = error;
100
+ switch (code) {
101
+ case "unsupported":
102
+ return { code: WCS_NOTIFY_ERROR_CODE.CapabilityMissing, phase: "probe", recoverable: false, message };
103
+ case "not-granted":
104
+ return { code: WCS_NOTIFY_ERROR_CODE.NotAllowed, phase: "start", recoverable: false, message };
105
+ case "invalid-title":
106
+ return { code: WCS_NOTIFY_ERROR_CODE.InvalidArgument, phase: "start", recoverable: false, message };
107
+ case "show-failed":
108
+ return { code: WCS_NOTIFY_ERROR_CODE.ShowFailed, phase: "execute", recoverable: false, message };
109
+ case "no-service-worker":
110
+ return { code: WCS_NOTIFY_ERROR_CODE.NoServiceWorker, phase: "execute", recoverable: false, message };
111
+ default:
112
+ return { code: WCS_NOTIFY_ERROR_CODE.NotifyError, phase: "execute", recoverable: false, message };
113
+ }
114
+ }
115
+
53
116
  /**
54
117
  * Headless desktop-notification primitive. A thin, framework-agnostic wrapper
55
118
  * around the Notifications API exposed through the wc-bindable protocol.
@@ -86,6 +149,12 @@ class NotificationCore extends EventTarget {
86
149
  { name: "prompt", event: "wcs-notify:permission-change", getter: (e) => e.detail === "prompt" },
87
150
  { name: "unsupported", event: "wcs-notify:permission-change", getter: (e) => e.detail === "unsupported" },
88
151
  { name: "error", event: "wcs-notify:error" },
152
+ // Serializable failure taxonomy (stable code / phase / recoverable), or null.
153
+ // Additive bindable output derived from `error.error` (the stable code the
154
+ // Core's `_err()` already produces); the existing `error` property/event are
155
+ // unchanged. Fires wcs-notify:error-info-changed. No lane — show is a
156
+ // momentary, last-value-wins send, not a competing async operation.
157
+ { name: "errorInfo", event: "wcs-notify:error-info-changed" },
89
158
  { name: "clicked", event: "wcs-notify:click", getter: (e) => e.detail },
90
159
  { name: "closed", event: "wcs-notify:close", getter: (e) => e.detail },
91
160
  { name: "shown", event: "wcs-notify:show", getter: (e) => e.detail },
@@ -101,6 +170,7 @@ class NotificationCore extends EventTarget {
101
170
  _mode = "auto";
102
171
  _permission = "prompt";
103
172
  _error = null;
173
+ _errorInfo = null;
104
174
  _lastClick = null;
105
175
  _lastClose = null;
106
176
  _lastShow = null;
@@ -157,6 +227,15 @@ class NotificationCore extends EventTarget {
157
227
  get error() {
158
228
  return this._error;
159
229
  }
230
+ /**
231
+ * The last failure's serializable `WcsIoErrorInfo` (stable `code` / `phase` /
232
+ * `recoverable`), or null. Additive wc-bindable property (event
233
+ * `wcs-notify:error-info-changed`), derived from `error`; the existing `error`
234
+ * property/event are unchanged.
235
+ */
236
+ get errorInfo() {
237
+ return this._errorInfo;
238
+ }
160
239
  get clicked() {
161
240
  return this._lastClick;
162
241
  }
@@ -184,11 +263,25 @@ class NotificationCore extends EventTarget {
184
263
  if (this._error === error)
185
264
  return;
186
265
  this._error = error;
266
+ // Keep the additive `errorInfo` taxonomy in sync with `error`: derive from the
267
+ // stable error code (or null on clear). Fires before the `error` event so an
268
+ // observer binding both sees the classification first, mirroring the io-node
269
+ // family.
270
+ this._commitErrorInfo(error === null ? null : deriveNotifyErrorInfo(error));
187
271
  this._target.dispatchEvent(new CustomEvent("wcs-notify:error", {
188
272
  detail: error,
189
273
  bubbles: true,
190
274
  }));
191
275
  }
276
+ // Called only from _setError (which already guards on error identity), so
277
+ // errorInfo transitions exactly when error does — no separate guard needed here.
278
+ _commitErrorInfo(info) {
279
+ this._errorInfo = info;
280
+ this._target.dispatchEvent(new CustomEvent("wcs-notify:error-info-changed", {
281
+ detail: info,
282
+ bubbles: true,
283
+ }));
284
+ }
192
285
  _emit(kind, detail) {
193
286
  if (kind === "click")
194
287
  this._lastClick = detail;
@@ -786,6 +879,9 @@ class WcsNotify extends HTMLElement {
786
879
  get error() {
787
880
  return this._core.error;
788
881
  }
882
+ get errorInfo() {
883
+ return this._core.errorInfo;
884
+ }
789
885
  get clicked() {
790
886
  return this._core.clicked;
791
887
  }
@@ -883,5 +979,5 @@ function bootstrapNotification(userConfig) {
883
979
  registerComponents();
884
980
  }
885
981
 
886
- export { NotificationCore, WcsNotify, bootstrapNotification, getConfig };
982
+ export { NotificationCore, WCS_NOTIFY_ERROR_CODE, WcsNotify, bootstrapNotification, getConfig };
887
983
  //# sourceMappingURL=index.esm.js.map
@@ -1 +1 @@
1
- {"version":3,"file":"index.esm.js","sources":["../src/config.ts","../src/core/NotificationCore.ts","../src/autoTrigger.ts","../src/components/Notify.ts","../src/registerComponents.ts","../src/bootstrapNotification.ts"],"sourcesContent":["import { IConfig, IWritableConfig } from \"./types.js\";\n\ninterface IInternalConfig extends IConfig {\n autoTrigger: boolean;\n triggerAttribute: string;\n tagNames: {\n notify: string;\n };\n}\n\nconst _config: IInternalConfig = {\n autoTrigger: true,\n triggerAttribute: \"data-notifytarget\",\n tagNames: {\n notify: \"wcs-notify\",\n },\n};\n\nfunction deepFreeze<T>(obj: T): T {\n if (obj === null || typeof obj !== \"object\") return obj;\n Object.freeze(obj);\n for (const key of Object.keys(obj)) {\n deepFreeze((obj as Record<string, unknown>)[key]);\n }\n return obj;\n}\n\nfunction deepClone<T>(obj: T): T {\n if (obj === null || typeof obj !== \"object\") return obj;\n const clone: Record<string, unknown> = {};\n for (const key of Object.keys(obj)) {\n clone[key] = deepClone((obj as Record<string, unknown>)[key]);\n }\n return clone as T;\n}\n\nlet frozenConfig: IConfig | null = null;\n\n// Internal, mutable live config used by the components/autoTrigger (they read it\n// at call time so setConfig() takes effect without re-import). Typed as the\n// readonly IConfig at the export boundary — the `as IConfig` is a compile-time\n// view only and does NOT freeze the object, so this export must stay\n// package-internal (it is not re-exported from exports.ts). Public consumers get\n// the deep-frozen clone from getConfig() instead.\nexport const config: IConfig = _config as IConfig;\n\nexport function getConfig(): IConfig {\n if (!frozenConfig) {\n frozenConfig = deepFreeze(deepClone(_config));\n }\n return frozenConfig;\n}\n\nexport function setConfig(partialConfig: IWritableConfig): void {\n if (typeof partialConfig.autoTrigger === \"boolean\") {\n _config.autoTrigger = partialConfig.autoTrigger;\n }\n if (typeof partialConfig.triggerAttribute === \"string\") {\n _config.triggerAttribute = partialConfig.triggerAttribute;\n }\n if (partialConfig.tagNames) {\n Object.assign(_config.tagNames, partialConfig.tagNames);\n }\n frozenConfig = null;\n}\n","import {\n IWcBindable, NotifyBackend, NotifyOptions, NotificationPermissionRaw,\n PermissionStateOrUnsupported, WcsNotifyClickDetail, WcsNotifyErrorDetail,\n} from \"../types.js\";\n\n// Wrapper stored in a notification's `data` so the Service Worker side (a\n// separate global scope with no access to this instance) can recover the\n// identity and the caller's payload. The constructor backend uses the same\n// wrapper for uniformity, and both paths unwrap it before emitting.\ninterface WcsNotifyData {\n __wcsId: string;\n payload: unknown;\n}\n\n// Message shape posted by `wireNotificationClicks()` (src/sw.ts) over both\n// BroadcastChannel and clients.postMessage. `id` is unique per click\n// (`tag#seq`), so the two transports delivering the *same* click de-dup, while\n// two genuine clicks on the same `tag` do not.\ninterface WcsNotifyInbound {\n __wcsNotify: true;\n id: string;\n tag: string;\n data: unknown;\n action: string;\n}\n\n/**\n * Headless desktop-notification primitive. A thin, framework-agnostic wrapper\n * around the Notifications API exposed through the wc-bindable protocol.\n *\n * Unlike `@wcstack/permission` (a read-only monitor — the Permissions API has no\n * `request()`), the Notifications API *does* expose `Notification.requestPermission()`,\n * so this node is self-contained: it both **requests/monitors** the permission and\n * **shows** notifications. It is the first @wcstack node where the command-token\n * (show: `notify`) and event-token (`click` / `close` / `show`) directions both\n * live in one tag.\n *\n * - **request()** asks for the `notifications` permission (`Notification.requestPermission`).\n * - **notify(title, options)** shows a notification and returns its identifying tag\n * (a caller `options.tag`, or a generated `wcs-<n>`). It picks a backend per\n * `mode`: the `Notification` constructor (desktop) or\n * `ServiceWorkerRegistration.showNotification()` (mobile). `\"auto\"` prefers the\n * constructor and falls back to the SW on a `TypeError`.\n * - **close(tag) / closeAll()** dismiss notifications by tag / all.\n * - Clicks flow back as the `wcs-notify:click` event: directly via the\n * Notification's `onclick` (constructor), or via the SW helper's\n * BroadcastChannel/postMessage relay (SW). `permission` mirrors the live grant.\n *\n * Failures never throw: they surface through `error` (and the `unsupported`\n * permission state) so they flow into the declarative state.\n */\nexport class NotificationCore extends EventTarget {\n static wcBindable: IWcBindable = {\n protocol: \"wc-bindable\",\n version: 1,\n properties: [\n { name: \"permission\", event: \"wcs-notify:permission-change\" },\n { name: \"granted\", event: \"wcs-notify:permission-change\", getter: (e: Event) => (e as CustomEvent).detail === \"granted\" },\n { name: \"denied\", event: \"wcs-notify:permission-change\", getter: (e: Event) => (e as CustomEvent).detail === \"denied\" },\n { name: \"prompt\", event: \"wcs-notify:permission-change\", getter: (e: Event) => (e as CustomEvent).detail === \"prompt\" },\n { name: \"unsupported\", event: \"wcs-notify:permission-change\", getter: (e: Event) => (e as CustomEvent).detail === \"unsupported\" },\n { name: \"error\", event: \"wcs-notify:error\" },\n { name: \"clicked\", event: \"wcs-notify:click\", getter: (e: Event) => (e as CustomEvent).detail },\n { name: \"closed\", event: \"wcs-notify:close\", getter: (e: Event) => (e as CustomEvent).detail },\n { name: \"shown\", event: \"wcs-notify:show\", getter: (e: Event) => (e as CustomEvent).detail },\n ],\n commands: [\n { name: \"request\", async: true },\n { name: \"notify\" },\n { name: \"close\" },\n { name: \"closeAll\" },\n ],\n };\n\n private _target: EventTarget;\n private _mode: NotifyBackend = \"auto\";\n\n private _permission: PermissionStateOrUnsupported = \"prompt\";\n private _error: WcsNotifyErrorDetail | null = null;\n private _lastClick: WcsNotifyClickDetail | null = null;\n private _lastClose: WcsNotifyClickDetail | null = null;\n private _lastShow: WcsNotifyClickDetail | null = null;\n\n // Live PermissionStatus (when the Permissions API can query `notifications`),\n // kept so its `change` listener can be removed on dispose().\n private _permissionStatus: PermissionStatus | null = null;\n // True once a permission subscription has been (or is being) established; reset\n // by dispose(). Guards observe() so a reconnect re-queries while a redundant\n // observe() on a live subscription does not.\n private _permissionSubscribed: boolean = false;\n\n // Monotonic id of the current lifecycle. Bumped by every observe() and by\n // dispose(). In-flight async work (permission query, SW show, inbound click)\n // captures it and bails if stale, so a query/click that resolves after a\n // disconnect — or after a rapid disconnect→reconnect — never mutates state or\n // dispatches on a torn-down element.\n private _gen: number = 0;\n\n // Resolves once the connect-time permission probe settles. The Shell exposes\n // this as connectedCallbackPromise so SSR can await it before snapshotting.\n private _ready: Promise<void> = Promise.resolve();\n\n // Counter for auto-assigned tags when the caller omits one.\n private _idSeq: number = 0;\n\n // Notifications created via the constructor backend, by tag, so close()/closeAll()\n // can dismiss them. The SW backend has no handle (showNotification returns void),\n // so its tags are tracked separately and closed via registration.getNotifications().\n private _constructed: Map<string, Notification> = new Map();\n private _swTags: Set<string> = new Set();\n\n // Click subscription handles (SW relay).\n private _channel: BroadcastChannel | null = null;\n private _serviceWorker: ServiceWorkerContainer | null = null;\n private _clicksSubscribed: boolean = false;\n // Per-click ids already handled, to de-dup the two relay transports. FIFO-capped\n // so a long session does not leak; the two transports always arrive in the same\n // tick, so a small cap is ample.\n private _seenIds: string[] = [];\n\n constructor(target?: EventTarget) {\n super();\n this._target = target ?? this;\n }\n\n get permission(): PermissionStateOrUnsupported {\n return this._permission;\n }\n\n get granted(): boolean {\n return this._permission === \"granted\";\n }\n\n get denied(): boolean {\n return this._permission === \"denied\";\n }\n\n get prompt(): boolean {\n return this._permission === \"prompt\";\n }\n\n get unsupported(): boolean {\n return this._permission === \"unsupported\";\n }\n\n get error(): WcsNotifyErrorDetail | null {\n return this._error;\n }\n\n get clicked(): WcsNotifyClickDetail | null {\n return this._lastClick;\n }\n\n get closed(): WcsNotifyClickDetail | null {\n return this._lastClose;\n }\n\n get shown(): WcsNotifyClickDetail | null {\n return this._lastShow;\n }\n\n /** Resolves once the current (or initial) permission probe settles. */\n get ready(): Promise<void> {\n return this._ready;\n }\n\n // --- State setters with event dispatch ---\n\n private _setPermission(state: PermissionStateOrUnsupported): void {\n if (this._permission === state) return;\n this._permission = state;\n this._target.dispatchEvent(new CustomEvent(\"wcs-notify:permission-change\", {\n detail: state,\n bubbles: true,\n }));\n }\n\n private _setError(error: WcsNotifyErrorDetail | null): void {\n if (this._error === error) return;\n this._error = error;\n this._target.dispatchEvent(new CustomEvent(\"wcs-notify:error\", {\n detail: error,\n bubbles: true,\n }));\n }\n\n private _emit(kind: \"click\" | \"close\" | \"show\", detail: WcsNotifyClickDetail): void {\n if (kind === \"click\") this._lastClick = detail;\n else if (kind === \"close\") this._lastClose = detail;\n else this._lastShow = detail;\n this._target.dispatchEvent(new CustomEvent(`wcs-notify:${kind}`, {\n detail,\n bubbles: true,\n }));\n }\n\n // --- Public API ---\n\n /**\n * Start observing the `notifications` permission and subscribing to Service\n * Worker click relays. `mode` selects the show backend (default `\"auto\"`).\n * Idempotent while already subscribed: it only updates the stored mode; to\n * restart, dispose() first. Returns a promise that resolves once the first\n * permission probe settles, for SSR.\n *\n * Headless callers must call observe() to begin; the Shell calls it from\n * connectedCallback once the element's attributes resolve.\n */\n observe(mode: NotifyBackend = \"auto\"): Promise<void> {\n this._mode = mode;\n if (!this._permissionSubscribed) {\n this._ready = this._initPermission();\n this._subscribeClicks();\n }\n return this._ready;\n }\n\n /**\n * Ask the user for the `notifications` permission. Resolves to the resulting\n * (normalized) permission state. Never throws: an unavailable API resolves to\n * `\"unsupported\"`.\n */\n async request(): Promise<PermissionStateOrUnsupported> {\n const api = this._api();\n if (!api || typeof api.requestPermission !== \"function\") {\n this._setPermission(\"unsupported\");\n return this._permission;\n }\n try {\n const result = await api.requestPermission();\n this._setPermission(this._normalize(result));\n } catch {\n // Some legacy engines may reject; keep the current state rather than throw.\n }\n return this._permission;\n }\n\n /**\n * Show a notification. Returns the identifying tag (the caller's `options.tag`,\n * or a generated `wcs-<n>` when omitted). Never throws: when the API is\n * unavailable or the permission is not granted it surfaces an `error` and\n * returns an empty string.\n */\n notify(title: string, options: NotifyOptions = {}): string {\n if (!this._api()) {\n this._setError(this._err(\"unsupported\", \"Notifications API is not available in this environment.\"));\n return \"\";\n }\n if (this._permission !== \"granted\") {\n this._setError(this._err(\"not-granted\", \"Notification permission is not granted; call request() first.\"));\n return \"\";\n }\n if (typeof title !== \"string\") {\n this._setError(this._err(\"invalid-title\", \"notify() requires a string title.\"));\n return \"\";\n }\n\n const tag = (typeof options.tag === \"string\" && options.tag !== \"\") ? options.tag : this._nextId();\n const payload = options.data;\n const data: WcsNotifyData = { __wcsId: tag, payload };\n const backendOptions: NotifyOptions = { ...options, tag, data };\n\n this._setError(null);\n this._show(title, backendOptions, tag, payload);\n return tag;\n }\n\n /** Dismiss the notification(s) with `tag` across both backends. */\n close(tag?: string): void {\n if (typeof tag !== \"string\" || tag === \"\") return;\n const n = this._constructed.get(tag);\n if (n) {\n n.close();\n this._constructed.delete(tag);\n }\n if (this._swTags.has(tag)) {\n this._closeSw(tag);\n this._swTags.delete(tag);\n }\n }\n\n /**\n * Dismiss every notification this instance has shown. Scoped to this instance's\n * own tags on both backends — the SW path closes each tracked tag individually\n * rather than enumerating the whole origin, so it never dismisses notifications\n * shown by another `<wcs-notify>` or by an unrelated code path.\n */\n closeAll(): void {\n for (const n of this._constructed.values()) {\n n.close();\n }\n this._constructed.clear();\n for (const tag of this._swTags) {\n this._closeSw(tag);\n }\n this._swTags.clear();\n }\n\n /**\n * Detach permission and click subscriptions. Open notifications are intentionally\n * **left on screen** (a notification outlives the page that posted it — that is\n * the point); use close()/closeAll() to dismiss. Call from the Shell's\n * disconnectedCallback. A later observe() resumes.\n */\n dispose(): void {\n this._permissionSubscribed = false;\n this._clicksSubscribed = false;\n this._gen++;\n if (this._permissionStatus) {\n this._permissionStatus.removeEventListener(\"change\", this._onPermissionChange);\n this._permissionStatus = null;\n }\n if (this._channel) {\n this._channel.removeEventListener(\"message\", this._onInbound);\n this._channel.close();\n this._channel = null;\n }\n if (this._serviceWorker) {\n this._serviceWorker.removeEventListener(\"message\", this._onInbound);\n this._serviceWorker = null;\n }\n }\n\n // --- Internal: permission ---\n\n private _initPermission(): Promise<void> {\n const api = this._api();\n if (!api) {\n this._setPermission(\"unsupported\");\n // Intentionally does NOT set _permissionSubscribed: there is no permission\n // listener to tear down, so a reconnect simply re-probes (idempotent — the\n // same-value guard suppresses any redundant dispatch and no listener is ever\n // attached). _subscribeClicks() is re-entered too, but its own\n // _clicksSubscribed guard short-circuits the second pass, so no transport is\n // double-subscribed. Mirrors @wcstack/permission's unsupported path.\n return Promise.resolve();\n }\n this._permissionSubscribed = true;\n // Prefer the Permissions API: it provides a live `change` event. Fall back to\n // the static `Notification.permission` when it is absent or rejects the\n // `notifications` descriptor.\n if (typeof navigator !== \"undefined\" && navigator.permissions && typeof navigator.permissions.query === \"function\") {\n const gen = ++this._gen;\n return navigator.permissions.query({ name: \"notifications\" }).then(\n (status) => {\n if (gen !== this._gen) return;\n this._permissionStatus = status;\n this._setPermission(this._normalize(status.state as NotificationPermissionRaw));\n status.addEventListener(\"change\", this._onPermissionChange);\n },\n () => {\n if (gen !== this._gen) return;\n // Permissions API rejected the `notifications` descriptor — fall back to\n // the static `Notification.permission` (api is in scope and non-null here).\n this._setPermission(this._normalize(api.permission));\n },\n );\n }\n // No Permissions API: read the static permission once (no live change events).\n this._setPermission(this._normalize(api.permission));\n return Promise.resolve();\n }\n\n private _onPermissionChange = (event: Event): void => {\n const status = event.target as PermissionStatus;\n this._setPermission(this._normalize(status.state as NotificationPermissionRaw));\n };\n\n // Normalize the Notifications API's `\"default\"` to `\"prompt\"` so this node shares\n // the four-value surface of @wcstack/permission. The Permissions API already\n // reports `\"prompt\"`, so it passes through unchanged.\n private _normalize(raw: NotificationPermissionRaw | string): PermissionStateOrUnsupported {\n if (raw === \"default\") return \"prompt\";\n if (raw === \"granted\" || raw === \"denied\" || raw === \"prompt\") return raw;\n return \"prompt\";\n }\n\n // --- Internal: showing ---\n\n private _show(title: string, options: NotifyOptions, tag: string, payload: unknown): void {\n if (this._mode === \"sw\") {\n this._showViaSw(title, options, tag, payload);\n return;\n }\n const handled = this._showViaConstructor(title, options, tag, payload);\n if (handled) return;\n // Constructor threw TypeError (e.g. mobile, where `new Notification` is illegal).\n if (this._mode === \"auto\") {\n this._showViaSw(title, options, tag, payload);\n } else {\n this._setError(this._err(\"show-failed\", \"new Notification() is not usable here and mode=\\\"constructor\\\" disallows the Service Worker fallback.\"));\n }\n }\n\n // Returns false only when the constructor threw a TypeError (the signal to fall\n // back to the SW backend); true when it showed or surfaced a non-TypeError error.\n private _showViaConstructor(title: string, options: NotifyOptions, tag: string, payload: unknown): boolean {\n const api = this._api()!;\n const gen = this._gen;\n let n: Notification;\n try {\n n = new api(title, options as NotificationOptions);\n } catch (e) {\n if (e instanceof TypeError) return false;\n this._setError(this._err(\"show-failed\", \"Failed to create the notification.\"));\n return true;\n }\n this._constructed.set(tag, n);\n n.onshow = (): void => {\n if (gen !== this._gen) return;\n this._emit(\"show\", { tag, data: payload, action: \"\" });\n };\n n.onclick = (): void => {\n if (gen !== this._gen) return;\n this._emit(\"click\", { tag, data: payload, action: \"\" });\n };\n n.onclose = (): void => {\n this._constructed.delete(tag);\n if (gen !== this._gen) return;\n this._emit(\"close\", { tag, data: payload, action: \"\" });\n };\n n.onerror = (): void => {\n if (gen !== this._gen) return;\n this._setError(this._err(\"show-failed\", \"The notification failed to display.\"));\n };\n return true;\n }\n\n private _showViaSw(title: string, options: NotifyOptions, tag: string, payload: unknown): void {\n const sw = navigator.serviceWorker as ServiceWorkerContainer | undefined;\n if (!sw) {\n this._setError(this._err(\"no-service-worker\", \"Service Worker is required to show this notification but is unavailable.\"));\n return;\n }\n const gen = this._gen;\n this._swTags.add(tag);\n // A notification deliberately outlives the page (see § dispose), so we do NOT\n // bail before showNotification on a stale gen — a notify() issued while\n // connected still shows. The stale-gen guards only suppress dispatching the\n // observable `show` / `error` back onto a torn-down element.\n sw.ready\n .then((registration) => registration.showNotification(title, options as NotificationOptions))\n .then(() => {\n if (gen !== this._gen) return;\n this._emit(\"show\", { tag, data: payload, action: \"\" });\n })\n .catch(() => {\n if (gen !== this._gen) return;\n this._setError(this._err(\"show-failed\", \"ServiceWorkerRegistration.showNotification() failed.\"));\n });\n }\n\n // Close the SW notification(s) carrying `tag`. Always scoped to a single tag —\n // both callers (close / closeAll) iterate their own tracked tags, so the whole\n // origin is never enumerated.\n private _closeSw(tag: string): void {\n const sw = navigator.serviceWorker as ServiceWorkerContainer | undefined;\n if (!sw) return;\n sw.ready.then((registration) => {\n return registration.getNotifications({ tag }).then((list) => {\n for (const n of list) n.close();\n });\n }).catch(() => {\n // Closing is best-effort; a failure to enumerate is not surfaced.\n });\n }\n\n // --- Internal: click relay (SW) ---\n\n private _subscribeClicks(): void {\n if (this._clicksSubscribed) return;\n this._clicksSubscribed = true;\n if (typeof BroadcastChannel === \"function\") {\n this._channel = new BroadcastChannel(\"wcs-notify\");\n this._channel.addEventListener(\"message\", this._onInbound);\n }\n const sw = navigator.serviceWorker as ServiceWorkerContainer | undefined;\n if (sw) {\n this._serviceWorker = sw;\n sw.addEventListener(\"message\", this._onInbound);\n }\n }\n\n private _onInbound = (event: Event): void => {\n const msg = (event as MessageEvent).data as WcsNotifyInbound | undefined;\n if (!msg || msg.__wcsNotify !== true) return;\n if (this._isDuplicate(msg.id)) return;\n this._emit(\"click\", { tag: msg.tag, data: this._unwrap(msg.data), action: msg.action });\n };\n\n private _isDuplicate(id: string): boolean {\n if (this._seenIds.includes(id)) return true;\n this._seenIds.push(id);\n if (this._seenIds.length > 50) this._seenIds.shift();\n return false;\n }\n\n private _unwrap(raw: unknown): unknown {\n if (raw !== null && typeof raw === \"object\" && \"__wcsId\" in raw) {\n return (raw as WcsNotifyData).payload;\n }\n return raw;\n }\n\n // --- Internal: misc ---\n\n // Resolve the global `Notification` constructor at call time (not cached) so\n // tests can install/remove it and so unsupported environments report correctly.\n private _api(): (typeof Notification) | undefined {\n const g = globalThis as unknown as { Notification?: typeof Notification };\n return typeof g.Notification === \"function\" ? g.Notification : undefined;\n }\n\n private _nextId(): string {\n return `wcs-${++this._idSeq}`;\n }\n\n private _err(error: string, message: string): WcsNotifyErrorDetail {\n return { error, message };\n }\n}\n","import { config } from \"./config.js\";\nimport type { WcsNotify } from \"./components/Notify.js\";\n\nlet registered = false;\n\nfunction handleClick(event: Event): void {\n const target = event.target;\n if (!(target instanceof Element)) return;\n\n // A misconfigured triggerAttribute (e.g. one with a space) makes the attribute\n // selector invalid and closest() throw SyntaxError; guard so a bad config\n // disables only this shortcut rather than killing every document click handler.\n let triggerElement: Element | null;\n try {\n triggerElement = target.closest<Element>(`[${config.triggerAttribute}]`);\n } catch {\n return;\n }\n if (!triggerElement) return;\n\n const notifyId = triggerElement.getAttribute(config.triggerAttribute);\n if (!notifyId) return;\n\n // Resolve the registered constructor at call time instead of importing Notify as\n // a value, avoiding a components/Notify.ts ⇄ autoTrigger.ts cycle\n // (Notify.connectedCallback() calls registerAutoTrigger()). instanceof against\n // the customElements registry keeps the same identity guarantee.\n const NotifyCtor = customElements.get(config.tagNames.notify);\n const notifyElement = document.getElementById(notifyId);\n if (!NotifyCtor || !(notifyElement instanceof NotifyCtor)) return;\n\n // The title comes from the trigger element: an explicit `data-notifytitle`\n // attribute wins, otherwise the element's trimmed text content. The body is an\n // optional `data-notifybody`. This keeps the click-driven shortcut declarative\n // without inventing a payload channel.\n const explicit = triggerElement.getAttribute(\"data-notifytitle\");\n // `Element.textContent` is spec-guaranteed non-null (only Document / DocumentType\n // nodes return null, never an Element), so the cast is sound and lets us avoid an\n // unreachable `?? \"\"` branch. `triggerElement` is always an Element here.\n const title = explicit !== null ? explicit : (triggerElement.textContent as string).trim();\n const body = triggerElement.getAttribute(\"data-notifybody\");\n\n (notifyElement as WcsNotify).notify(title, body !== null ? { body } : undefined);\n}\n\nexport function registerAutoTrigger(): void {\n if (registered) return;\n registered = true;\n document.addEventListener(\"click\", handleClick);\n}\n\nexport function unregisterAutoTrigger(): void {\n if (!registered) return;\n registered = false;\n document.removeEventListener(\"click\", handleClick);\n}\n","import { config } from \"../config.js\";\nimport {\n IWcBindable, NotifyBackend, NotifyOptions, PermissionStateOrUnsupported,\n WcsNotifyClickDetail, WcsNotifyErrorDetail,\n} from \"../types.js\";\nimport { NotificationCore } from \"../core/NotificationCore.js\";\nimport { registerAutoTrigger } from \"../autoTrigger.js\";\n\n/**\n * `<wcs-notify>` — declarative desktop notifications. Wraps NotificationCore and\n * exposes both directions in one tag:\n *\n * - **`notice`** (reactive input): writing a *changed* value shows a notification,\n * suppressing same-value writes so it fires only when the bound source actually\n * changes. The imperative `notify` command instead shows on demand (even the\n * same text again). See `docs/notification-tag-design.md` § 2.\n * - **`request` / `notify` / `close` / `closeAll`** commands (state → element).\n * - per-notification options (`body` / `icon` / `badge` / `tag` / `lang` / `dir` /\n * `require-interaction` / `silent` / `renotify`) as mirrored attributes.\n * - `mode` selects the show backend (`auto` / `sw` / `constructor`).\n * - the Core's observable surface (permission / granted / … / error / clicked /\n * closed / shown) via delegated getters; clicked/closed/shown carry the\n * `{ tag, data, action }` payload for event-token wiring.\n */\nexport class WcsNotify extends HTMLElement {\n static hasConnectedCallbackPromise = true;\n static wcBindable: IWcBindable = {\n ...NotificationCore.wcBindable,\n // Shell-level settable surface. `notice` is a momentary reactive command-property\n // with no mirrored attribute (it carries dynamic text, not declarative config),\n // mirroring <wcs-speak>'s `say`. The rest mirror their HTML attributes idempotently.\n inputs: [\n { name: \"notice\" },\n { name: \"mode\", attribute: \"mode\" },\n { name: \"body\", attribute: \"body\" },\n { name: \"icon\", attribute: \"icon\" },\n { name: \"badge\", attribute: \"badge\" },\n { name: \"tag\", attribute: \"tag\" },\n { name: \"lang\", attribute: \"lang\" },\n { name: \"dir\", attribute: \"dir\" },\n { name: \"requireInteraction\", attribute: \"require-interaction\" },\n { name: \"silent\", attribute: \"silent\" },\n { name: \"renotify\", attribute: \"renotify\" },\n { name: \"manual\", attribute: \"manual\" },\n ],\n commands: NotificationCore.wcBindable.commands,\n };\n\n private _core: NotificationCore;\n private _notice: string = \"\";\n private _connectedCallbackPromise: Promise<void> = Promise.resolve();\n private _internals: ElementInternals | null = null;\n\n constructor() {\n super();\n this._core = new NotificationCore(this);\n this._internals = this._initInternals();\n this._wireStates({\n \"wcs-notify:permission-change\": (d) => ({\n granted: d === \"granted\", denied: d === \"denied\",\n prompt: d === \"prompt\", unsupported: d === \"unsupported\",\n }),\n \"wcs-notify:error\": (d) => ({ error: d != null }),\n });\n }\n\n // CSS state reflection (:state()) — debug-only snapshot getter. NOT part of\n // wc-bindable (not a bind target); see README \"CSS styling with :state()\".\n // MUST NOT return the live CustomStateSet (that would let callers write\n // states from outside, defeating the point of :state() being read-only).\n get debugStates(): string[] {\n return this._internals ? [...this._internals.states] : [];\n }\n\n private _initInternals(): ElementInternals | null {\n // never-throw (async-io-node-guidelines.md §3.6): attachInternals is absent\n // in happy-dom / older environments, and pre-125 Chromium rejects\n // non-dashed state names from states.add() (probed and discarded here).\n // Either case silently disables reflection — the component still works,\n // it just doesn't expose :state() selectors.\n try {\n if (typeof this.attachInternals !== \"function\") return null;\n const internals = this.attachInternals();\n internals.states.add(\"wcs-probe\");\n internals.states.delete(\"wcs-probe\");\n return internals;\n } catch {\n return null;\n }\n }\n\n private _wireStates(map: Record<string, (detail: any) => Record<string, boolean>>): void {\n if (this._internals === null) return;\n const states = this._internals.states;\n for (const [event, toStates] of Object.entries(map)) {\n this.addEventListener(event, (e) => {\n const debug = this.hasAttribute(\"debug-states\");\n for (const [name, on] of Object.entries(toStates((e as CustomEvent).detail))) {\n try {\n if (on) { states.add(name); } else { states.delete(name); }\n } catch { /* never-throw */ }\n if (debug) this.toggleAttribute(`data-wcs-state-${name}`, on);\n }\n });\n }\n }\n\n // --- Attribute accessors ---\n\n get mode(): NotifyBackend {\n const m = this.getAttribute(\"mode\");\n return (m === \"sw\" || m === \"constructor\") ? m : \"auto\";\n }\n\n set mode(value: NotifyBackend) {\n this.setAttribute(\"mode\", value);\n }\n\n get body(): string {\n return this.getAttribute(\"body\") ?? \"\";\n }\n\n set body(value: string | null) {\n this._reflect(\"body\", value);\n }\n\n get icon(): string {\n return this.getAttribute(\"icon\") ?? \"\";\n }\n\n set icon(value: string | null) {\n this._reflect(\"icon\", value);\n }\n\n get badge(): string {\n return this.getAttribute(\"badge\") ?? \"\";\n }\n\n set badge(value: string | null) {\n this._reflect(\"badge\", value);\n }\n\n get tag(): string {\n return this.getAttribute(\"tag\") ?? \"\";\n }\n\n set tag(value: string | null) {\n this._reflect(\"tag\", value);\n }\n\n // NOTE: `lang` and `dir` intentionally repurpose the standard HTMLElement IDL\n // attributes as per-notification options (forwarded to NotificationOptions).\n // This element is always display:none, so overriding their normal rendering\n // semantics has no visual effect — but be aware the values mean \"the\n // notification's language/direction\", not the host element's.\n get lang(): string {\n return this.getAttribute(\"lang\") ?? \"\";\n }\n\n set lang(value: string | null) {\n this._reflect(\"lang\", value);\n }\n\n get dir(): string {\n return this.getAttribute(\"dir\") ?? \"\";\n }\n\n set dir(value: string | null) {\n this._reflect(\"dir\", value);\n }\n\n get requireInteraction(): boolean {\n return this.hasAttribute(\"require-interaction\");\n }\n\n set requireInteraction(value: boolean) {\n this._reflectBool(\"require-interaction\", value);\n }\n\n get silent(): boolean {\n return this.hasAttribute(\"silent\");\n }\n\n set silent(value: boolean) {\n this._reflectBool(\"silent\", value);\n }\n\n get renotify(): boolean {\n return this.hasAttribute(\"renotify\");\n }\n\n set renotify(value: boolean) {\n this._reflectBool(\"renotify\", value);\n }\n\n get manual(): boolean {\n return this.hasAttribute(\"manual\");\n }\n\n set manual(value: boolean) {\n this._reflectBool(\"manual\", value);\n }\n\n // --- Reactive command-property ---\n\n get notice(): string {\n return this._notice;\n }\n\n set notice(value: string | null) {\n // Reactive: writing a new value shows it. `manual` mutes the path entirely\n // (the imperative `notify` command still works). A conforming binder never\n // delivers `undefined` (it skips the write), but a direct assignment can, so\n // normalize null/undefined to a no-op.\n if (value == null) return;\n if (this.manual) return;\n const v = String(value);\n // Same-value guard: only show when the bound source actually changes. To show\n // the same text again on demand, use the `notify` command instead. (This is\n // the only spam guard the package provides — see docs § 2-c; debounce is the\n // caller's job via a filter, e.g. `notice@x|debounce(1000)`.)\n if (v === this._notice) return;\n this._notice = v;\n this.notify(v);\n }\n\n // --- Core delegated getters ---\n\n get permission(): PermissionStateOrUnsupported {\n return this._core.permission;\n }\n\n get granted(): boolean {\n return this._core.granted;\n }\n\n get denied(): boolean {\n return this._core.denied;\n }\n\n get prompt(): boolean {\n return this._core.prompt;\n }\n\n get unsupported(): boolean {\n return this._core.unsupported;\n }\n\n get error(): WcsNotifyErrorDetail | null {\n return this._core.error;\n }\n\n get clicked(): WcsNotifyClickDetail | null {\n return this._core.clicked;\n }\n\n get closed(): WcsNotifyClickDetail | null {\n return this._core.closed;\n }\n\n get shown(): WcsNotifyClickDetail | null {\n return this._core.shown;\n }\n\n get connectedCallbackPromise(): Promise<void> {\n return this._connectedCallbackPromise;\n }\n\n // --- Commands ---\n\n request(): Promise<PermissionStateOrUnsupported> {\n return this._core.request();\n }\n\n notify(title: string, options?: NotifyOptions): string {\n // Explicit options (from a command-token emit) win per-key over the attribute\n // defaults, so `notify.emit(title, { body })` still picks up the element's icon.\n return this._core.notify(title, { ...this._options(), ...(options ?? {}) });\n }\n\n close(tag?: string): void {\n this._core.close(tag);\n }\n\n closeAll(): void {\n this._core.closeAll();\n }\n\n // --- Internal ---\n\n private _reflect(name: string, value: string | null): void {\n if (value == null) {\n this.removeAttribute(name);\n } else {\n this.setAttribute(name, String(value));\n }\n }\n\n private _reflectBool(name: string, value: boolean): void {\n if (value) {\n this.setAttribute(name, \"\");\n } else {\n this.removeAttribute(name);\n }\n }\n\n private _options(): NotifyOptions {\n const o: NotifyOptions = {};\n if (this.body !== \"\") o.body = this.body;\n if (this.icon !== \"\") o.icon = this.icon;\n if (this.badge !== \"\") o.badge = this.badge;\n if (this.tag !== \"\") o.tag = this.tag;\n if (this.lang !== \"\") o.lang = this.lang;\n if (this.dir === \"auto\" || this.dir === \"ltr\" || this.dir === \"rtl\") o.dir = this.dir;\n if (this.requireInteraction) o.requireInteraction = true;\n if (this.silent) o.silent = true;\n if (this.renotify) o.renotify = true;\n return o;\n }\n\n // --- Lifecycle ---\n\n connectedCallback(): void {\n this.style.display = \"none\";\n if (config.autoTrigger) {\n registerAutoTrigger();\n }\n // Begin observing permission and subscribing to SW click relays (or revive\n // after a reconnect). The returned promise is held as connectedCallbackPromise\n // for SSR.\n this._connectedCallbackPromise = this._core.observe(this.mode);\n }\n\n disconnectedCallback(): void {\n // Detach subscriptions. Open notifications are left on screen (see Core docs);\n // call close()/closeAll() to dismiss.\n this._core.dispose();\n }\n}\n","import { WcsNotify } from \"./components/Notify.js\";\nimport { config } from \"./config.js\";\n\nexport function registerComponents(): void {\n if (!customElements.get(config.tagNames.notify)) {\n customElements.define(config.tagNames.notify, WcsNotify);\n }\n}\n","import { setConfig } from \"./config.js\";\nimport { registerComponents } from \"./registerComponents.js\";\nimport { IWritableConfig } from \"./types.js\";\n\nexport function bootstrapNotification(userConfig?: IWritableConfig): void {\n if (userConfig) {\n setConfig(userConfig);\n }\n registerComponents();\n}\n"],"names":[],"mappings":"AAUA,MAAM,OAAO,GAAoB;AAC/B,IAAA,WAAW,EAAE,IAAI;AACjB,IAAA,gBAAgB,EAAE,mBAAmB;AACrC,IAAA,QAAQ,EAAE;AACR,QAAA,MAAM,EAAE,YAAY;AACrB,KAAA;CACF;AAED,SAAS,UAAU,CAAI,GAAM,EAAA;AAC3B,IAAA,IAAI,GAAG,KAAK,IAAI,IAAI,OAAO,GAAG,KAAK,QAAQ;AAAE,QAAA,OAAO,GAAG;AACvD,IAAA,MAAM,CAAC,MAAM,CAAC,GAAG,CAAC;IAClB,KAAK,MAAM,GAAG,IAAI,MAAM,CAAC,IAAI,CAAC,GAAG,CAAC,EAAE;AAClC,QAAA,UAAU,CAAE,GAA+B,CAAC,GAAG,CAAC,CAAC;IACnD;AACA,IAAA,OAAO,GAAG;AACZ;AAEA,SAAS,SAAS,CAAI,GAAM,EAAA;AAC1B,IAAA,IAAI,GAAG,KAAK,IAAI,IAAI,OAAO,GAAG,KAAK,QAAQ;AAAE,QAAA,OAAO,GAAG;IACvD,MAAM,KAAK,GAA4B,EAAE;IACzC,KAAK,MAAM,GAAG,IAAI,MAAM,CAAC,IAAI,CAAC,GAAG,CAAC,EAAE;QAClC,KAAK,CAAC,GAAG,CAAC,GAAG,SAAS,CAAE,GAA+B,CAAC,GAAG,CAAC,CAAC;IAC/D;AACA,IAAA,OAAO,KAAU;AACnB;AAEA,IAAI,YAAY,GAAmB,IAAI;AAEvC;AACA;AACA;AACA;AACA;AACA;AACO,MAAM,MAAM,GAAY,OAAkB;SAEjC,SAAS,GAAA;IACvB,IAAI,CAAC,YAAY,EAAE;QACjB,YAAY,GAAG,UAAU,CAAC,SAAS,CAAC,OAAO,CAAC,CAAC;IAC/C;AACA,IAAA,OAAO,YAAY;AACrB;AAEM,SAAU,SAAS,CAAC,aAA8B,EAAA;AACtD,IAAA,IAAI,OAAO,aAAa,CAAC,WAAW,KAAK,SAAS,EAAE;AAClD,QAAA,OAAO,CAAC,WAAW,GAAG,aAAa,CAAC,WAAW;IACjD;AACA,IAAA,IAAI,OAAO,aAAa,CAAC,gBAAgB,KAAK,QAAQ,EAAE;AACtD,QAAA,OAAO,CAAC,gBAAgB,GAAG,aAAa,CAAC,gBAAgB;IAC3D;AACA,IAAA,IAAI,aAAa,CAAC,QAAQ,EAAE;QAC1B,MAAM,CAAC,MAAM,CAAC,OAAO,CAAC,QAAQ,EAAE,aAAa,CAAC,QAAQ,CAAC;IACzD;IACA,YAAY,GAAG,IAAI;AACrB;;ACtCA;;;;;;;;;;;;;;;;;;;;;;;;AAwBG;AACG,MAAO,gBAAiB,SAAQ,WAAW,CAAA;IAC/C,OAAO,UAAU,GAAgB;AAC/B,QAAA,QAAQ,EAAE,aAAa;AACvB,QAAA,OAAO,EAAE,CAAC;AACV,QAAA,UAAU,EAAE;AACV,YAAA,EAAE,IAAI,EAAE,YAAY,EAAE,KAAK,EAAE,8BAA8B,EAAE;YAC7D,EAAE,IAAI,EAAE,SAAS,EAAE,KAAK,EAAE,8BAA8B,EAAE,MAAM,EAAE,CAAC,CAAQ,KAAM,CAAiB,CAAC,MAAM,KAAK,SAAS,EAAE;YACzH,EAAE,IAAI,EAAE,QAAQ,EAAE,KAAK,EAAE,8BAA8B,EAAE,MAAM,EAAE,CAAC,CAAQ,KAAM,CAAiB,CAAC,MAAM,KAAK,QAAQ,EAAE;YACvH,EAAE,IAAI,EAAE,QAAQ,EAAE,KAAK,EAAE,8BAA8B,EAAE,MAAM,EAAE,CAAC,CAAQ,KAAM,CAAiB,CAAC,MAAM,KAAK,QAAQ,EAAE;YACvH,EAAE,IAAI,EAAE,aAAa,EAAE,KAAK,EAAE,8BAA8B,EAAE,MAAM,EAAE,CAAC,CAAQ,KAAM,CAAiB,CAAC,MAAM,KAAK,aAAa,EAAE;AACjI,YAAA,EAAE,IAAI,EAAE,OAAO,EAAE,KAAK,EAAE,kBAAkB,EAAE;AAC5C,YAAA,EAAE,IAAI,EAAE,SAAS,EAAE,KAAK,EAAE,kBAAkB,EAAE,MAAM,EAAE,CAAC,CAAQ,KAAM,CAAiB,CAAC,MAAM,EAAE;AAC/F,YAAA,EAAE,IAAI,EAAE,QAAQ,EAAE,KAAK,EAAE,kBAAkB,EAAE,MAAM,EAAE,CAAC,CAAQ,KAAM,CAAiB,CAAC,MAAM,EAAE;AAC9F,YAAA,EAAE,IAAI,EAAE,OAAO,EAAE,KAAK,EAAE,iBAAiB,EAAE,MAAM,EAAE,CAAC,CAAQ,KAAM,CAAiB,CAAC,MAAM,EAAE;AAC7F,SAAA;AACD,QAAA,QAAQ,EAAE;AACR,YAAA,EAAE,IAAI,EAAE,SAAS,EAAE,KAAK,EAAE,IAAI,EAAE;YAChC,EAAE,IAAI,EAAE,QAAQ,EAAE;YAClB,EAAE,IAAI,EAAE,OAAO,EAAE;YACjB,EAAE,IAAI,EAAE,UAAU,EAAE;AACrB,SAAA;KACF;AAEO,IAAA,OAAO;IACP,KAAK,GAAkB,MAAM;IAE7B,WAAW,GAAiC,QAAQ;IACpD,MAAM,GAAgC,IAAI;IAC1C,UAAU,GAAgC,IAAI;IAC9C,UAAU,GAAgC,IAAI;IAC9C,SAAS,GAAgC,IAAI;;;IAI7C,iBAAiB,GAA4B,IAAI;;;;IAIjD,qBAAqB,GAAY,KAAK;;;;;;IAOtC,IAAI,GAAW,CAAC;;;AAIhB,IAAA,MAAM,GAAkB,OAAO,CAAC,OAAO,EAAE;;IAGzC,MAAM,GAAW,CAAC;;;;AAKlB,IAAA,YAAY,GAA8B,IAAI,GAAG,EAAE;AACnD,IAAA,OAAO,GAAgB,IAAI,GAAG,EAAE;;IAGhC,QAAQ,GAA4B,IAAI;IACxC,cAAc,GAAkC,IAAI;IACpD,iBAAiB,GAAY,KAAK;;;;IAIlC,QAAQ,GAAa,EAAE;AAE/B,IAAA,WAAA,CAAY,MAAoB,EAAA;AAC9B,QAAA,KAAK,EAAE;AACP,QAAA,IAAI,CAAC,OAAO,GAAG,MAAM,IAAI,IAAI;IAC/B;AAEA,IAAA,IAAI,UAAU,GAAA;QACZ,OAAO,IAAI,CAAC,WAAW;IACzB;AAEA,IAAA,IAAI,OAAO,GAAA;AACT,QAAA,OAAO,IAAI,CAAC,WAAW,KAAK,SAAS;IACvC;AAEA,IAAA,IAAI,MAAM,GAAA;AACR,QAAA,OAAO,IAAI,CAAC,WAAW,KAAK,QAAQ;IACtC;AAEA,IAAA,IAAI,MAAM,GAAA;AACR,QAAA,OAAO,IAAI,CAAC,WAAW,KAAK,QAAQ;IACtC;AAEA,IAAA,IAAI,WAAW,GAAA;AACb,QAAA,OAAO,IAAI,CAAC,WAAW,KAAK,aAAa;IAC3C;AAEA,IAAA,IAAI,KAAK,GAAA;QACP,OAAO,IAAI,CAAC,MAAM;IACpB;AAEA,IAAA,IAAI,OAAO,GAAA;QACT,OAAO,IAAI,CAAC,UAAU;IACxB;AAEA,IAAA,IAAI,MAAM,GAAA;QACR,OAAO,IAAI,CAAC,UAAU;IACxB;AAEA,IAAA,IAAI,KAAK,GAAA;QACP,OAAO,IAAI,CAAC,SAAS;IACvB;;AAGA,IAAA,IAAI,KAAK,GAAA;QACP,OAAO,IAAI,CAAC,MAAM;IACpB;;AAIQ,IAAA,cAAc,CAAC,KAAmC,EAAA;AACxD,QAAA,IAAI,IAAI,CAAC,WAAW,KAAK,KAAK;YAAE;AAChC,QAAA,IAAI,CAAC,WAAW,GAAG,KAAK;QACxB,IAAI,CAAC,OAAO,CAAC,aAAa,CAAC,IAAI,WAAW,CAAC,8BAA8B,EAAE;AACzE,YAAA,MAAM,EAAE,KAAK;AACb,YAAA,OAAO,EAAE,IAAI;AACd,SAAA,CAAC,CAAC;IACL;AAEQ,IAAA,SAAS,CAAC,KAAkC,EAAA;AAClD,QAAA,IAAI,IAAI,CAAC,MAAM,KAAK,KAAK;YAAE;AAC3B,QAAA,IAAI,CAAC,MAAM,GAAG,KAAK;QACnB,IAAI,CAAC,OAAO,CAAC,aAAa,CAAC,IAAI,WAAW,CAAC,kBAAkB,EAAE;AAC7D,YAAA,MAAM,EAAE,KAAK;AACb,YAAA,OAAO,EAAE,IAAI;AACd,SAAA,CAAC,CAAC;IACL;IAEQ,KAAK,CAAC,IAAgC,EAAE,MAA4B,EAAA;QAC1E,IAAI,IAAI,KAAK,OAAO;AAAE,YAAA,IAAI,CAAC,UAAU,GAAG,MAAM;aACzC,IAAI,IAAI,KAAK,OAAO;AAAE,YAAA,IAAI,CAAC,UAAU,GAAG,MAAM;;AAC9C,YAAA,IAAI,CAAC,SAAS,GAAG,MAAM;QAC5B,IAAI,CAAC,OAAO,CAAC,aAAa,CAAC,IAAI,WAAW,CAAC,CAAA,WAAA,EAAc,IAAI,CAAA,CAAE,EAAE;YAC/D,MAAM;AACN,YAAA,OAAO,EAAE,IAAI;AACd,SAAA,CAAC,CAAC;IACL;;AAIA;;;;;;;;;AASG;IACH,OAAO,CAAC,OAAsB,MAAM,EAAA;AAClC,QAAA,IAAI,CAAC,KAAK,GAAG,IAAI;AACjB,QAAA,IAAI,CAAC,IAAI,CAAC,qBAAqB,EAAE;AAC/B,YAAA,IAAI,CAAC,MAAM,GAAG,IAAI,CAAC,eAAe,EAAE;YACpC,IAAI,CAAC,gBAAgB,EAAE;QACzB;QACA,OAAO,IAAI,CAAC,MAAM;IACpB;AAEA;;;;AAIG;AACH,IAAA,MAAM,OAAO,GAAA;AACX,QAAA,MAAM,GAAG,GAAG,IAAI,CAAC,IAAI,EAAE;QACvB,IAAI,CAAC,GAAG,IAAI,OAAO,GAAG,CAAC,iBAAiB,KAAK,UAAU,EAAE;AACvD,YAAA,IAAI,CAAC,cAAc,CAAC,aAAa,CAAC;YAClC,OAAO,IAAI,CAAC,WAAW;QACzB;AACA,QAAA,IAAI;AACF,YAAA,MAAM,MAAM,GAAG,MAAM,GAAG,CAAC,iBAAiB,EAAE;YAC5C,IAAI,CAAC,cAAc,CAAC,IAAI,CAAC,UAAU,CAAC,MAAM,CAAC,CAAC;QAC9C;AAAE,QAAA,MAAM;;QAER;QACA,OAAO,IAAI,CAAC,WAAW;IACzB;AAEA;;;;;AAKG;AACH,IAAA,MAAM,CAAC,KAAa,EAAE,OAAA,GAAyB,EAAE,EAAA;AAC/C,QAAA,IAAI,CAAC,IAAI,CAAC,IAAI,EAAE,EAAE;AAChB,YAAA,IAAI,CAAC,SAAS,CAAC,IAAI,CAAC,IAAI,CAAC,aAAa,EAAE,yDAAyD,CAAC,CAAC;AACnG,YAAA,OAAO,EAAE;QACX;AACA,QAAA,IAAI,IAAI,CAAC,WAAW,KAAK,SAAS,EAAE;AAClC,YAAA,IAAI,CAAC,SAAS,CAAC,IAAI,CAAC,IAAI,CAAC,aAAa,EAAE,+DAA+D,CAAC,CAAC;AACzG,YAAA,OAAO,EAAE;QACX;AACA,QAAA,IAAI,OAAO,KAAK,KAAK,QAAQ,EAAE;AAC7B,YAAA,IAAI,CAAC,SAAS,CAAC,IAAI,CAAC,IAAI,CAAC,eAAe,EAAE,mCAAmC,CAAC,CAAC;AAC/E,YAAA,OAAO,EAAE;QACX;AAEA,QAAA,MAAM,GAAG,GAAG,CAAC,OAAO,OAAO,CAAC,GAAG,KAAK,QAAQ,IAAI,OAAO,CAAC,GAAG,KAAK,EAAE,IAAI,OAAO,CAAC,GAAG,GAAG,IAAI,CAAC,OAAO,EAAE;AAClG,QAAA,MAAM,OAAO,GAAG,OAAO,CAAC,IAAI;QAC5B,MAAM,IAAI,GAAkB,EAAE,OAAO,EAAE,GAAG,EAAE,OAAO,EAAE;QACrD,MAAM,cAAc,GAAkB,EAAE,GAAG,OAAO,EAAE,GAAG,EAAE,IAAI,EAAE;AAE/D,QAAA,IAAI,CAAC,SAAS,CAAC,IAAI,CAAC;QACpB,IAAI,CAAC,KAAK,CAAC,KAAK,EAAE,cAAc,EAAE,GAAG,EAAE,OAAO,CAAC;AAC/C,QAAA,OAAO,GAAG;IACZ;;AAGA,IAAA,KAAK,CAAC,GAAY,EAAA;AAChB,QAAA,IAAI,OAAO,GAAG,KAAK,QAAQ,IAAI,GAAG,KAAK,EAAE;YAAE;QAC3C,MAAM,CAAC,GAAG,IAAI,CAAC,YAAY,CAAC,GAAG,CAAC,GAAG,CAAC;QACpC,IAAI,CAAC,EAAE;YACL,CAAC,CAAC,KAAK,EAAE;AACT,YAAA,IAAI,CAAC,YAAY,CAAC,MAAM,CAAC,GAAG,CAAC;QAC/B;QACA,IAAI,IAAI,CAAC,OAAO,CAAC,GAAG,CAAC,GAAG,CAAC,EAAE;AACzB,YAAA,IAAI,CAAC,QAAQ,CAAC,GAAG,CAAC;AAClB,YAAA,IAAI,CAAC,OAAO,CAAC,MAAM,CAAC,GAAG,CAAC;QAC1B;IACF;AAEA;;;;;AAKG;IACH,QAAQ,GAAA;QACN,KAAK,MAAM,CAAC,IAAI,IAAI,CAAC,YAAY,CAAC,MAAM,EAAE,EAAE;YAC1C,CAAC,CAAC,KAAK,EAAE;QACX;AACA,QAAA,IAAI,CAAC,YAAY,CAAC,KAAK,EAAE;AACzB,QAAA,KAAK,MAAM,GAAG,IAAI,IAAI,CAAC,OAAO,EAAE;AAC9B,YAAA,IAAI,CAAC,QAAQ,CAAC,GAAG,CAAC;QACpB;AACA,QAAA,IAAI,CAAC,OAAO,CAAC,KAAK,EAAE;IACtB;AAEA;;;;;AAKG;IACH,OAAO,GAAA;AACL,QAAA,IAAI,CAAC,qBAAqB,GAAG,KAAK;AAClC,QAAA,IAAI,CAAC,iBAAiB,GAAG,KAAK;QAC9B,IAAI,CAAC,IAAI,EAAE;AACX,QAAA,IAAI,IAAI,CAAC,iBAAiB,EAAE;YAC1B,IAAI,CAAC,iBAAiB,CAAC,mBAAmB,CAAC,QAAQ,EAAE,IAAI,CAAC,mBAAmB,CAAC;AAC9E,YAAA,IAAI,CAAC,iBAAiB,GAAG,IAAI;QAC/B;AACA,QAAA,IAAI,IAAI,CAAC,QAAQ,EAAE;YACjB,IAAI,CAAC,QAAQ,CAAC,mBAAmB,CAAC,SAAS,EAAE,IAAI,CAAC,UAAU,CAAC;AAC7D,YAAA,IAAI,CAAC,QAAQ,CAAC,KAAK,EAAE;AACrB,YAAA,IAAI,CAAC,QAAQ,GAAG,IAAI;QACtB;AACA,QAAA,IAAI,IAAI,CAAC,cAAc,EAAE;YACvB,IAAI,CAAC,cAAc,CAAC,mBAAmB,CAAC,SAAS,EAAE,IAAI,CAAC,UAAU,CAAC;AACnE,YAAA,IAAI,CAAC,cAAc,GAAG,IAAI;QAC5B;IACF;;IAIQ,eAAe,GAAA;AACrB,QAAA,MAAM,GAAG,GAAG,IAAI,CAAC,IAAI,EAAE;QACvB,IAAI,CAAC,GAAG,EAAE;AACR,YAAA,IAAI,CAAC,cAAc,CAAC,aAAa,CAAC;;;;;;;AAOlC,YAAA,OAAO,OAAO,CAAC,OAAO,EAAE;QAC1B;AACA,QAAA,IAAI,CAAC,qBAAqB,GAAG,IAAI;;;;AAIjC,QAAA,IAAI,OAAO,SAAS,KAAK,WAAW,IAAI,SAAS,CAAC,WAAW,IAAI,OAAO,SAAS,CAAC,WAAW,CAAC,KAAK,KAAK,UAAU,EAAE;AAClH,YAAA,MAAM,GAAG,GAAG,EAAE,IAAI,CAAC,IAAI;AACvB,YAAA,OAAO,SAAS,CAAC,WAAW,CAAC,KAAK,CAAC,EAAE,IAAI,EAAE,eAAe,EAAE,CAAC,CAAC,IAAI,CAChE,CAAC,MAAM,KAAI;AACT,gBAAA,IAAI,GAAG,KAAK,IAAI,CAAC,IAAI;oBAAE;AACvB,gBAAA,IAAI,CAAC,iBAAiB,GAAG,MAAM;AAC/B,gBAAA,IAAI,CAAC,cAAc,CAAC,IAAI,CAAC,UAAU,CAAC,MAAM,CAAC,KAAkC,CAAC,CAAC;gBAC/E,MAAM,CAAC,gBAAgB,CAAC,QAAQ,EAAE,IAAI,CAAC,mBAAmB,CAAC;YAC7D,CAAC,EACD,MAAK;AACH,gBAAA,IAAI,GAAG,KAAK,IAAI,CAAC,IAAI;oBAAE;;;AAGvB,gBAAA,IAAI,CAAC,cAAc,CAAC,IAAI,CAAC,UAAU,CAAC,GAAG,CAAC,UAAU,CAAC,CAAC;AACtD,YAAA,CAAC,CACF;QACH;;AAEA,QAAA,IAAI,CAAC,cAAc,CAAC,IAAI,CAAC,UAAU,CAAC,GAAG,CAAC,UAAU,CAAC,CAAC;AACpD,QAAA,OAAO,OAAO,CAAC,OAAO,EAAE;IAC1B;AAEQ,IAAA,mBAAmB,GAAG,CAAC,KAAY,KAAU;AACnD,QAAA,MAAM,MAAM,GAAG,KAAK,CAAC,MAA0B;AAC/C,QAAA,IAAI,CAAC,cAAc,CAAC,IAAI,CAAC,UAAU,CAAC,MAAM,CAAC,KAAkC,CAAC,CAAC;AACjF,IAAA,CAAC;;;;AAKO,IAAA,UAAU,CAAC,GAAuC,EAAA;QACxD,IAAI,GAAG,KAAK,SAAS;AAAE,YAAA,OAAO,QAAQ;QACtC,IAAI,GAAG,KAAK,SAAS,IAAI,GAAG,KAAK,QAAQ,IAAI,GAAG,KAAK,QAAQ;AAAE,YAAA,OAAO,GAAG;AACzE,QAAA,OAAO,QAAQ;IACjB;;AAIQ,IAAA,KAAK,CAAC,KAAa,EAAE,OAAsB,EAAE,GAAW,EAAE,OAAgB,EAAA;AAChF,QAAA,IAAI,IAAI,CAAC,KAAK,KAAK,IAAI,EAAE;YACvB,IAAI,CAAC,UAAU,CAAC,KAAK,EAAE,OAAO,EAAE,GAAG,EAAE,OAAO,CAAC;YAC7C;QACF;AACA,QAAA,MAAM,OAAO,GAAG,IAAI,CAAC,mBAAmB,CAAC,KAAK,EAAE,OAAO,EAAE,GAAG,EAAE,OAAO,CAAC;AACtE,QAAA,IAAI,OAAO;YAAE;;AAEb,QAAA,IAAI,IAAI,CAAC,KAAK,KAAK,MAAM,EAAE;YACzB,IAAI,CAAC,UAAU,CAAC,KAAK,EAAE,OAAO,EAAE,GAAG,EAAE,OAAO,CAAC;QAC/C;aAAO;AACL,YAAA,IAAI,CAAC,SAAS,CAAC,IAAI,CAAC,IAAI,CAAC,aAAa,EAAE,uGAAuG,CAAC,CAAC;QACnJ;IACF;;;AAIQ,IAAA,mBAAmB,CAAC,KAAa,EAAE,OAAsB,EAAE,GAAW,EAAE,OAAgB,EAAA;AAC9F,QAAA,MAAM,GAAG,GAAG,IAAI,CAAC,IAAI,EAAG;AACxB,QAAA,MAAM,GAAG,GAAG,IAAI,CAAC,IAAI;AACrB,QAAA,IAAI,CAAe;AACnB,QAAA,IAAI;YACF,CAAC,GAAG,IAAI,GAAG,CAAC,KAAK,EAAE,OAA8B,CAAC;QACpD;QAAE,OAAO,CAAC,EAAE;YACV,IAAI,CAAC,YAAY,SAAS;AAAE,gBAAA,OAAO,KAAK;AACxC,YAAA,IAAI,CAAC,SAAS,CAAC,IAAI,CAAC,IAAI,CAAC,aAAa,EAAE,oCAAoC,CAAC,CAAC;AAC9E,YAAA,OAAO,IAAI;QACb;QACA,IAAI,CAAC,YAAY,CAAC,GAAG,CAAC,GAAG,EAAE,CAAC,CAAC;AAC7B,QAAA,CAAC,CAAC,MAAM,GAAG,MAAW;AACpB,YAAA,IAAI,GAAG,KAAK,IAAI,CAAC,IAAI;gBAAE;AACvB,YAAA,IAAI,CAAC,KAAK,CAAC,MAAM,EAAE,EAAE,GAAG,EAAE,IAAI,EAAE,OAAO,EAAE,MAAM,EAAE,EAAE,EAAE,CAAC;AACxD,QAAA,CAAC;AACD,QAAA,CAAC,CAAC,OAAO,GAAG,MAAW;AACrB,YAAA,IAAI,GAAG,KAAK,IAAI,CAAC,IAAI;gBAAE;AACvB,YAAA,IAAI,CAAC,KAAK,CAAC,OAAO,EAAE,EAAE,GAAG,EAAE,IAAI,EAAE,OAAO,EAAE,MAAM,EAAE,EAAE,EAAE,CAAC;AACzD,QAAA,CAAC;AACD,QAAA,CAAC,CAAC,OAAO,GAAG,MAAW;AACrB,YAAA,IAAI,CAAC,YAAY,CAAC,MAAM,CAAC,GAAG,CAAC;AAC7B,YAAA,IAAI,GAAG,KAAK,IAAI,CAAC,IAAI;gBAAE;AACvB,YAAA,IAAI,CAAC,KAAK,CAAC,OAAO,EAAE,EAAE,GAAG,EAAE,IAAI,EAAE,OAAO,EAAE,MAAM,EAAE,EAAE,EAAE,CAAC;AACzD,QAAA,CAAC;AACD,QAAA,CAAC,CAAC,OAAO,GAAG,MAAW;AACrB,YAAA,IAAI,GAAG,KAAK,IAAI,CAAC,IAAI;gBAAE;AACvB,YAAA,IAAI,CAAC,SAAS,CAAC,IAAI,CAAC,IAAI,CAAC,aAAa,EAAE,qCAAqC,CAAC,CAAC;AACjF,QAAA,CAAC;AACD,QAAA,OAAO,IAAI;IACb;AAEQ,IAAA,UAAU,CAAC,KAAa,EAAE,OAAsB,EAAE,GAAW,EAAE,OAAgB,EAAA;AACrF,QAAA,MAAM,EAAE,GAAG,SAAS,CAAC,aAAmD;QACxE,IAAI,CAAC,EAAE,EAAE;AACP,YAAA,IAAI,CAAC,SAAS,CAAC,IAAI,CAAC,IAAI,CAAC,mBAAmB,EAAE,0EAA0E,CAAC,CAAC;YAC1H;QACF;AACA,QAAA,MAAM,GAAG,GAAG,IAAI,CAAC,IAAI;AACrB,QAAA,IAAI,CAAC,OAAO,CAAC,GAAG,CAAC,GAAG,CAAC;;;;;AAKrB,QAAA,EAAE,CAAC;AACA,aAAA,IAAI,CAAC,CAAC,YAAY,KAAK,YAAY,CAAC,gBAAgB,CAAC,KAAK,EAAE,OAA8B,CAAC;aAC3F,IAAI,CAAC,MAAK;AACT,YAAA,IAAI,GAAG,KAAK,IAAI,CAAC,IAAI;gBAAE;AACvB,YAAA,IAAI,CAAC,KAAK,CAAC,MAAM,EAAE,EAAE,GAAG,EAAE,IAAI,EAAE,OAAO,EAAE,MAAM,EAAE,EAAE,EAAE,CAAC;AACxD,QAAA,CAAC;aACA,KAAK,CAAC,MAAK;AACV,YAAA,IAAI,GAAG,KAAK,IAAI,CAAC,IAAI;gBAAE;AACvB,YAAA,IAAI,CAAC,SAAS,CAAC,IAAI,CAAC,IAAI,CAAC,aAAa,EAAE,sDAAsD,CAAC,CAAC;AAClG,QAAA,CAAC,CAAC;IACN;;;;AAKQ,IAAA,QAAQ,CAAC,GAAW,EAAA;AAC1B,QAAA,MAAM,EAAE,GAAG,SAAS,CAAC,aAAmD;AACxE,QAAA,IAAI,CAAC,EAAE;YAAE;QACT,EAAE,CAAC,KAAK,CAAC,IAAI,CAAC,CAAC,YAAY,KAAI;AAC7B,YAAA,OAAO,YAAY,CAAC,gBAAgB,CAAC,EAAE,GAAG,EAAE,CAAC,CAAC,IAAI,CAAC,CAAC,IAAI,KAAI;gBAC1D,KAAK,MAAM,CAAC,IAAI,IAAI;oBAAE,CAAC,CAAC,KAAK,EAAE;AACjC,YAAA,CAAC,CAAC;AACJ,QAAA,CAAC,CAAC,CAAC,KAAK,CAAC,MAAK;;AAEd,QAAA,CAAC,CAAC;IACJ;;IAIQ,gBAAgB,GAAA;QACtB,IAAI,IAAI,CAAC,iBAAiB;YAAE;AAC5B,QAAA,IAAI,CAAC,iBAAiB,GAAG,IAAI;AAC7B,QAAA,IAAI,OAAO,gBAAgB,KAAK,UAAU,EAAE;YAC1C,IAAI,CAAC,QAAQ,GAAG,IAAI,gBAAgB,CAAC,YAAY,CAAC;YAClD,IAAI,CAAC,QAAQ,CAAC,gBAAgB,CAAC,SAAS,EAAE,IAAI,CAAC,UAAU,CAAC;QAC5D;AACA,QAAA,MAAM,EAAE,GAAG,SAAS,CAAC,aAAmD;QACxE,IAAI,EAAE,EAAE;AACN,YAAA,IAAI,CAAC,cAAc,GAAG,EAAE;YACxB,EAAE,CAAC,gBAAgB,CAAC,SAAS,EAAE,IAAI,CAAC,UAAU,CAAC;QACjD;IACF;AAEQ,IAAA,UAAU,GAAG,CAAC,KAAY,KAAU;AAC1C,QAAA,MAAM,GAAG,GAAI,KAAsB,CAAC,IAAoC;AACxE,QAAA,IAAI,CAAC,GAAG,IAAI,GAAG,CAAC,WAAW,KAAK,IAAI;YAAE;AACtC,QAAA,IAAI,IAAI,CAAC,YAAY,CAAC,GAAG,CAAC,EAAE,CAAC;YAAE;AAC/B,QAAA,IAAI,CAAC,KAAK,CAAC,OAAO,EAAE,EAAE,GAAG,EAAE,GAAG,CAAC,GAAG,EAAE,IAAI,EAAE,IAAI,CAAC,OAAO,CAAC,GAAG,CAAC,IAAI,CAAC,EAAE,MAAM,EAAE,GAAG,CAAC,MAAM,EAAE,CAAC;AACzF,IAAA,CAAC;AAEO,IAAA,YAAY,CAAC,EAAU,EAAA;AAC7B,QAAA,IAAI,IAAI,CAAC,QAAQ,CAAC,QAAQ,CAAC,EAAE,CAAC;AAAE,YAAA,OAAO,IAAI;AAC3C,QAAA,IAAI,CAAC,QAAQ,CAAC,IAAI,CAAC,EAAE,CAAC;AACtB,QAAA,IAAI,IAAI,CAAC,QAAQ,CAAC,MAAM,GAAG,EAAE;AAAE,YAAA,IAAI,CAAC,QAAQ,CAAC,KAAK,EAAE;AACpD,QAAA,OAAO,KAAK;IACd;AAEQ,IAAA,OAAO,CAAC,GAAY,EAAA;AAC1B,QAAA,IAAI,GAAG,KAAK,IAAI,IAAI,OAAO,GAAG,KAAK,QAAQ,IAAI,SAAS,IAAI,GAAG,EAAE;YAC/D,OAAQ,GAAqB,CAAC,OAAO;QACvC;AACA,QAAA,OAAO,GAAG;IACZ;;;;IAMQ,IAAI,GAAA;QACV,MAAM,CAAC,GAAG,UAA+D;AACzE,QAAA,OAAO,OAAO,CAAC,CAAC,YAAY,KAAK,UAAU,GAAG,CAAC,CAAC,YAAY,GAAG,SAAS;IAC1E;IAEQ,OAAO,GAAA;AACb,QAAA,OAAO,OAAO,EAAE,IAAI,CAAC,MAAM,EAAE;IAC/B;IAEQ,IAAI,CAAC,KAAa,EAAE,OAAe,EAAA;AACzC,QAAA,OAAO,EAAE,KAAK,EAAE,OAAO,EAAE;IAC3B;;;ACpgBF,IAAI,UAAU,GAAG,KAAK;AAEtB,SAAS,WAAW,CAAC,KAAY,EAAA;AAC/B,IAAA,MAAM,MAAM,GAAG,KAAK,CAAC,MAAM;AAC3B,IAAA,IAAI,EAAE,MAAM,YAAY,OAAO,CAAC;QAAE;;;;AAKlC,IAAA,IAAI,cAA8B;AAClC,IAAA,IAAI;QACF,cAAc,GAAG,MAAM,CAAC,OAAO,CAAU,CAAA,CAAA,EAAI,MAAM,CAAC,gBAAgB,CAAA,CAAA,CAAG,CAAC;IAC1E;AAAE,IAAA,MAAM;QACN;IACF;AACA,IAAA,IAAI,CAAC,cAAc;QAAE;IAErB,MAAM,QAAQ,GAAG,cAAc,CAAC,YAAY,CAAC,MAAM,CAAC,gBAAgB,CAAC;AACrE,IAAA,IAAI,CAAC,QAAQ;QAAE;;;;;AAMf,IAAA,MAAM,UAAU,GAAG,cAAc,CAAC,GAAG,CAAC,MAAM,CAAC,QAAQ,CAAC,MAAM,CAAC;IAC7D,MAAM,aAAa,GAAG,QAAQ,CAAC,cAAc,CAAC,QAAQ,CAAC;IACvD,IAAI,CAAC,UAAU,IAAI,EAAE,aAAa,YAAY,UAAU,CAAC;QAAE;;;;;IAM3D,MAAM,QAAQ,GAAG,cAAc,CAAC,YAAY,CAAC,kBAAkB,CAAC;;;;AAIhE,IAAA,MAAM,KAAK,GAAG,QAAQ,KAAK,IAAI,GAAG,QAAQ,GAAI,cAAc,CAAC,WAAsB,CAAC,IAAI,EAAE;IAC1F,MAAM,IAAI,GAAG,cAAc,CAAC,YAAY,CAAC,iBAAiB,CAAC;AAE1D,IAAA,aAA2B,CAAC,MAAM,CAAC,KAAK,EAAE,IAAI,KAAK,IAAI,GAAG,EAAE,IAAI,EAAE,GAAG,SAAS,CAAC;AAClF;SAEgB,mBAAmB,GAAA;AACjC,IAAA,IAAI,UAAU;QAAE;IAChB,UAAU,GAAG,IAAI;AACjB,IAAA,QAAQ,CAAC,gBAAgB,CAAC,OAAO,EAAE,WAAW,CAAC;AACjD;;ACzCA;;;;;;;;;;;;;;;AAeG;AACG,MAAO,SAAU,SAAQ,WAAW,CAAA;AACxC,IAAA,OAAO,2BAA2B,GAAG,IAAI;IACzC,OAAO,UAAU,GAAgB;QAC/B,GAAG,gBAAgB,CAAC,UAAU;;;;AAI9B,QAAA,MAAM,EAAE;YACN,EAAE,IAAI,EAAE,QAAQ,EAAE;AAClB,YAAA,EAAE,IAAI,EAAE,MAAM,EAAE,SAAS,EAAE,MAAM,EAAE;AACnC,YAAA,EAAE,IAAI,EAAE,MAAM,EAAE,SAAS,EAAE,MAAM,EAAE;AACnC,YAAA,EAAE,IAAI,EAAE,MAAM,EAAE,SAAS,EAAE,MAAM,EAAE;AACnC,YAAA,EAAE,IAAI,EAAE,OAAO,EAAE,SAAS,EAAE,OAAO,EAAE;AACrC,YAAA,EAAE,IAAI,EAAE,KAAK,EAAE,SAAS,EAAE,KAAK,EAAE;AACjC,YAAA,EAAE,IAAI,EAAE,MAAM,EAAE,SAAS,EAAE,MAAM,EAAE;AACnC,YAAA,EAAE,IAAI,EAAE,KAAK,EAAE,SAAS,EAAE,KAAK,EAAE;AACjC,YAAA,EAAE,IAAI,EAAE,oBAAoB,EAAE,SAAS,EAAE,qBAAqB,EAAE;AAChE,YAAA,EAAE,IAAI,EAAE,QAAQ,EAAE,SAAS,EAAE,QAAQ,EAAE;AACvC,YAAA,EAAE,IAAI,EAAE,UAAU,EAAE,SAAS,EAAE,UAAU,EAAE;AAC3C,YAAA,EAAE,IAAI,EAAE,QAAQ,EAAE,SAAS,EAAE,QAAQ,EAAE;AACxC,SAAA;AACD,QAAA,QAAQ,EAAE,gBAAgB,CAAC,UAAU,CAAC,QAAQ;KAC/C;AAEO,IAAA,KAAK;IACL,OAAO,GAAW,EAAE;AACpB,IAAA,yBAAyB,GAAkB,OAAO,CAAC,OAAO,EAAE;IAC5D,UAAU,GAA4B,IAAI;AAElD,IAAA,WAAA,GAAA;AACE,QAAA,KAAK,EAAE;QACP,IAAI,CAAC,KAAK,GAAG,IAAI,gBAAgB,CAAC,IAAI,CAAC;AACvC,QAAA,IAAI,CAAC,UAAU,GAAG,IAAI,CAAC,cAAc,EAAE;QACvC,IAAI,CAAC,WAAW,CAAC;AACf,YAAA,8BAA8B,EAAE,CAAC,CAAC,MAAM;gBACtC,OAAO,EAAE,CAAC,KAAK,SAAS,EAAE,MAAM,EAAE,CAAC,KAAK,QAAQ;gBAChD,MAAM,EAAE,CAAC,KAAK,QAAQ,EAAE,WAAW,EAAE,CAAC,KAAK,aAAa;aACzD,CAAC;AACF,YAAA,kBAAkB,EAAE,CAAC,CAAC,MAAM,EAAE,KAAK,EAAE,CAAC,IAAI,IAAI,EAAE,CAAC;AAClD,SAAA,CAAC;IACJ;;;;;AAMA,IAAA,IAAI,WAAW,GAAA;AACb,QAAA,OAAO,IAAI,CAAC,UAAU,GAAG,CAAC,GAAG,IAAI,CAAC,UAAU,CAAC,MAAM,CAAC,GAAG,EAAE;IAC3D;IAEQ,cAAc,GAAA;;;;;;AAMpB,QAAA,IAAI;AACF,YAAA,IAAI,OAAO,IAAI,CAAC,eAAe,KAAK,UAAU;AAAE,gBAAA,OAAO,IAAI;AAC3D,YAAA,MAAM,SAAS,GAAG,IAAI,CAAC,eAAe,EAAE;AACxC,YAAA,SAAS,CAAC,MAAM,CAAC,GAAG,CAAC,WAAW,CAAC;AACjC,YAAA,SAAS,CAAC,MAAM,CAAC,MAAM,CAAC,WAAW,CAAC;AACpC,YAAA,OAAO,SAAS;QAClB;AAAE,QAAA,MAAM;AACN,YAAA,OAAO,IAAI;QACb;IACF;AAEQ,IAAA,WAAW,CAAC,GAA6D,EAAA;AAC/E,QAAA,IAAI,IAAI,CAAC,UAAU,KAAK,IAAI;YAAE;AAC9B,QAAA,MAAM,MAAM,GAAG,IAAI,CAAC,UAAU,CAAC,MAAM;AACrC,QAAA,KAAK,MAAM,CAAC,KAAK,EAAE,QAAQ,CAAC,IAAI,MAAM,CAAC,OAAO,CAAC,GAAG,CAAC,EAAE;YACnD,IAAI,CAAC,gBAAgB,CAAC,KAAK,EAAE,CAAC,CAAC,KAAI;gBACjC,MAAM,KAAK,GAAG,IAAI,CAAC,YAAY,CAAC,cAAc,CAAC;AAC/C,gBAAA,KAAK,MAAM,CAAC,IAAI,EAAE,EAAE,CAAC,IAAI,MAAM,CAAC,OAAO,CAAC,QAAQ,CAAE,CAAiB,CAAC,MAAM,CAAC,CAAC,EAAE;AAC5E,oBAAA,IAAI;wBACF,IAAI,EAAE,EAAE;AAAE,4BAAA,MAAM,CAAC,GAAG,CAAC,IAAI,CAAC;wBAAE;6BAAO;AAAE,4BAAA,MAAM,CAAC,MAAM,CAAC,IAAI,CAAC;wBAAE;oBAC5D;AAAE,oBAAA,MAAM,oBAAoB;AAC5B,oBAAA,IAAI,KAAK;wBAAE,IAAI,CAAC,eAAe,CAAC,CAAA,eAAA,EAAkB,IAAI,CAAA,CAAE,EAAE,EAAE,CAAC;gBAC/D;AACF,YAAA,CAAC,CAAC;QACJ;IACF;;AAIA,IAAA,IAAI,IAAI,GAAA;QACN,MAAM,CAAC,GAAG,IAAI,CAAC,YAAY,CAAC,MAAM,CAAC;AACnC,QAAA,OAAO,CAAC,CAAC,KAAK,IAAI,IAAI,CAAC,KAAK,aAAa,IAAI,CAAC,GAAG,MAAM;IACzD;IAEA,IAAI,IAAI,CAAC,KAAoB,EAAA;AAC3B,QAAA,IAAI,CAAC,YAAY,CAAC,MAAM,EAAE,KAAK,CAAC;IAClC;AAEA,IAAA,IAAI,IAAI,GAAA;QACN,OAAO,IAAI,CAAC,YAAY,CAAC,MAAM,CAAC,IAAI,EAAE;IACxC;IAEA,IAAI,IAAI,CAAC,KAAoB,EAAA;AAC3B,QAAA,IAAI,CAAC,QAAQ,CAAC,MAAM,EAAE,KAAK,CAAC;IAC9B;AAEA,IAAA,IAAI,IAAI,GAAA;QACN,OAAO,IAAI,CAAC,YAAY,CAAC,MAAM,CAAC,IAAI,EAAE;IACxC;IAEA,IAAI,IAAI,CAAC,KAAoB,EAAA;AAC3B,QAAA,IAAI,CAAC,QAAQ,CAAC,MAAM,EAAE,KAAK,CAAC;IAC9B;AAEA,IAAA,IAAI,KAAK,GAAA;QACP,OAAO,IAAI,CAAC,YAAY,CAAC,OAAO,CAAC,IAAI,EAAE;IACzC;IAEA,IAAI,KAAK,CAAC,KAAoB,EAAA;AAC5B,QAAA,IAAI,CAAC,QAAQ,CAAC,OAAO,EAAE,KAAK,CAAC;IAC/B;AAEA,IAAA,IAAI,GAAG,GAAA;QACL,OAAO,IAAI,CAAC,YAAY,CAAC,KAAK,CAAC,IAAI,EAAE;IACvC;IAEA,IAAI,GAAG,CAAC,KAAoB,EAAA;AAC1B,QAAA,IAAI,CAAC,QAAQ,CAAC,KAAK,EAAE,KAAK,CAAC;IAC7B;;;;;;AAOA,IAAA,IAAI,IAAI,GAAA;QACN,OAAO,IAAI,CAAC,YAAY,CAAC,MAAM,CAAC,IAAI,EAAE;IACxC;IAEA,IAAI,IAAI,CAAC,KAAoB,EAAA;AAC3B,QAAA,IAAI,CAAC,QAAQ,CAAC,MAAM,EAAE,KAAK,CAAC;IAC9B;AAEA,IAAA,IAAI,GAAG,GAAA;QACL,OAAO,IAAI,CAAC,YAAY,CAAC,KAAK,CAAC,IAAI,EAAE;IACvC;IAEA,IAAI,GAAG,CAAC,KAAoB,EAAA;AAC1B,QAAA,IAAI,CAAC,QAAQ,CAAC,KAAK,EAAE,KAAK,CAAC;IAC7B;AAEA,IAAA,IAAI,kBAAkB,GAAA;AACpB,QAAA,OAAO,IAAI,CAAC,YAAY,CAAC,qBAAqB,CAAC;IACjD;IAEA,IAAI,kBAAkB,CAAC,KAAc,EAAA;AACnC,QAAA,IAAI,CAAC,YAAY,CAAC,qBAAqB,EAAE,KAAK,CAAC;IACjD;AAEA,IAAA,IAAI,MAAM,GAAA;AACR,QAAA,OAAO,IAAI,CAAC,YAAY,CAAC,QAAQ,CAAC;IACpC;IAEA,IAAI,MAAM,CAAC,KAAc,EAAA;AACvB,QAAA,IAAI,CAAC,YAAY,CAAC,QAAQ,EAAE,KAAK,CAAC;IACpC;AAEA,IAAA,IAAI,QAAQ,GAAA;AACV,QAAA,OAAO,IAAI,CAAC,YAAY,CAAC,UAAU,CAAC;IACtC;IAEA,IAAI,QAAQ,CAAC,KAAc,EAAA;AACzB,QAAA,IAAI,CAAC,YAAY,CAAC,UAAU,EAAE,KAAK,CAAC;IACtC;AAEA,IAAA,IAAI,MAAM,GAAA;AACR,QAAA,OAAO,IAAI,CAAC,YAAY,CAAC,QAAQ,CAAC;IACpC;IAEA,IAAI,MAAM,CAAC,KAAc,EAAA;AACvB,QAAA,IAAI,CAAC,YAAY,CAAC,QAAQ,EAAE,KAAK,CAAC;IACpC;;AAIA,IAAA,IAAI,MAAM,GAAA;QACR,OAAO,IAAI,CAAC,OAAO;IACrB;IAEA,IAAI,MAAM,CAAC,KAAoB,EAAA;;;;;QAK7B,IAAI,KAAK,IAAI,IAAI;YAAE;QACnB,IAAI,IAAI,CAAC,MAAM;YAAE;AACjB,QAAA,MAAM,CAAC,GAAG,MAAM,CAAC,KAAK,CAAC;;;;;AAKvB,QAAA,IAAI,CAAC,KAAK,IAAI,CAAC,OAAO;YAAE;AACxB,QAAA,IAAI,CAAC,OAAO,GAAG,CAAC;AAChB,QAAA,IAAI,CAAC,MAAM,CAAC,CAAC,CAAC;IAChB;;AAIA,IAAA,IAAI,UAAU,GAAA;AACZ,QAAA,OAAO,IAAI,CAAC,KAAK,CAAC,UAAU;IAC9B;AAEA,IAAA,IAAI,OAAO,GAAA;AACT,QAAA,OAAO,IAAI,CAAC,KAAK,CAAC,OAAO;IAC3B;AAEA,IAAA,IAAI,MAAM,GAAA;AACR,QAAA,OAAO,IAAI,CAAC,KAAK,CAAC,MAAM;IAC1B;AAEA,IAAA,IAAI,MAAM,GAAA;AACR,QAAA,OAAO,IAAI,CAAC,KAAK,CAAC,MAAM;IAC1B;AAEA,IAAA,IAAI,WAAW,GAAA;AACb,QAAA,OAAO,IAAI,CAAC,KAAK,CAAC,WAAW;IAC/B;AAEA,IAAA,IAAI,KAAK,GAAA;AACP,QAAA,OAAO,IAAI,CAAC,KAAK,CAAC,KAAK;IACzB;AAEA,IAAA,IAAI,OAAO,GAAA;AACT,QAAA,OAAO,IAAI,CAAC,KAAK,CAAC,OAAO;IAC3B;AAEA,IAAA,IAAI,MAAM,GAAA;AACR,QAAA,OAAO,IAAI,CAAC,KAAK,CAAC,MAAM;IAC1B;AAEA,IAAA,IAAI,KAAK,GAAA;AACP,QAAA,OAAO,IAAI,CAAC,KAAK,CAAC,KAAK;IACzB;AAEA,IAAA,IAAI,wBAAwB,GAAA;QAC1B,OAAO,IAAI,CAAC,yBAAyB;IACvC;;IAIA,OAAO,GAAA;AACL,QAAA,OAAO,IAAI,CAAC,KAAK,CAAC,OAAO,EAAE;IAC7B;IAEA,MAAM,CAAC,KAAa,EAAE,OAAuB,EAAA;;;QAG3C,OAAO,IAAI,CAAC,KAAK,CAAC,MAAM,CAAC,KAAK,EAAE,EAAE,GAAG,IAAI,CAAC,QAAQ,EAAE,EAAE,IAAI,OAAO,IAAI,EAAE,CAAC,EAAE,CAAC;IAC7E;AAEA,IAAA,KAAK,CAAC,GAAY,EAAA;AAChB,QAAA,IAAI,CAAC,KAAK,CAAC,KAAK,CAAC,GAAG,CAAC;IACvB;IAEA,QAAQ,GAAA;AACN,QAAA,IAAI,CAAC,KAAK,CAAC,QAAQ,EAAE;IACvB;;IAIQ,QAAQ,CAAC,IAAY,EAAE,KAAoB,EAAA;AACjD,QAAA,IAAI,KAAK,IAAI,IAAI,EAAE;AACjB,YAAA,IAAI,CAAC,eAAe,CAAC,IAAI,CAAC;QAC5B;aAAO;YACL,IAAI,CAAC,YAAY,CAAC,IAAI,EAAE,MAAM,CAAC,KAAK,CAAC,CAAC;QACxC;IACF;IAEQ,YAAY,CAAC,IAAY,EAAE,KAAc,EAAA;QAC/C,IAAI,KAAK,EAAE;AACT,YAAA,IAAI,CAAC,YAAY,CAAC,IAAI,EAAE,EAAE,CAAC;QAC7B;aAAO;AACL,YAAA,IAAI,CAAC,eAAe,CAAC,IAAI,CAAC;QAC5B;IACF;IAEQ,QAAQ,GAAA;QACd,MAAM,CAAC,GAAkB,EAAE;AAC3B,QAAA,IAAI,IAAI,CAAC,IAAI,KAAK,EAAE;AAAE,YAAA,CAAC,CAAC,IAAI,GAAG,IAAI,CAAC,IAAI;AACxC,QAAA,IAAI,IAAI,CAAC,IAAI,KAAK,EAAE;AAAE,YAAA,CAAC,CAAC,IAAI,GAAG,IAAI,CAAC,IAAI;AACxC,QAAA,IAAI,IAAI,CAAC,KAAK,KAAK,EAAE;AAAE,YAAA,CAAC,CAAC,KAAK,GAAG,IAAI,CAAC,KAAK;AAC3C,QAAA,IAAI,IAAI,CAAC,GAAG,KAAK,EAAE;AAAE,YAAA,CAAC,CAAC,GAAG,GAAG,IAAI,CAAC,GAAG;AACrC,QAAA,IAAI,IAAI,CAAC,IAAI,KAAK,EAAE;AAAE,YAAA,CAAC,CAAC,IAAI,GAAG,IAAI,CAAC,IAAI;AACxC,QAAA,IAAI,IAAI,CAAC,GAAG,KAAK,MAAM,IAAI,IAAI,CAAC,GAAG,KAAK,KAAK,IAAI,IAAI,CAAC,GAAG,KAAK,KAAK;AAAE,YAAA,CAAC,CAAC,GAAG,GAAG,IAAI,CAAC,GAAG;QACrF,IAAI,IAAI,CAAC,kBAAkB;AAAE,YAAA,CAAC,CAAC,kBAAkB,GAAG,IAAI;QACxD,IAAI,IAAI,CAAC,MAAM;AAAE,YAAA,CAAC,CAAC,MAAM,GAAG,IAAI;QAChC,IAAI,IAAI,CAAC,QAAQ;AAAE,YAAA,CAAC,CAAC,QAAQ,GAAG,IAAI;AACpC,QAAA,OAAO,CAAC;IACV;;IAIA,iBAAiB,GAAA;AACf,QAAA,IAAI,CAAC,KAAK,CAAC,OAAO,GAAG,MAAM;AAC3B,QAAA,IAAI,MAAM,CAAC,WAAW,EAAE;AACtB,YAAA,mBAAmB,EAAE;QACvB;;;;AAIA,QAAA,IAAI,CAAC,yBAAyB,GAAG,IAAI,CAAC,KAAK,CAAC,OAAO,CAAC,IAAI,CAAC,IAAI,CAAC;IAChE;IAEA,oBAAoB,GAAA;;;AAGlB,QAAA,IAAI,CAAC,KAAK,CAAC,OAAO,EAAE;IACtB;;;SC9Uc,kBAAkB,GAAA;AAChC,IAAA,IAAI,CAAC,cAAc,CAAC,GAAG,CAAC,MAAM,CAAC,QAAQ,CAAC,MAAM,CAAC,EAAE;QAC/C,cAAc,CAAC,MAAM,CAAC,MAAM,CAAC,QAAQ,CAAC,MAAM,EAAE,SAAS,CAAC;IAC1D;AACF;;ACHM,SAAU,qBAAqB,CAAC,UAA4B,EAAA;IAChE,IAAI,UAAU,EAAE;QACd,SAAS,CAAC,UAAU,CAAC;IACvB;AACA,IAAA,kBAAkB,EAAE;AACtB;;;;"}
1
+ {"version":3,"file":"index.esm.js","sources":["../src/config.ts","../src/core/notificationCapabilities.ts","../src/core/NotificationCore.ts","../src/autoTrigger.ts","../src/components/Notify.ts","../src/registerComponents.ts","../src/bootstrapNotification.ts"],"sourcesContent":["import { IConfig, IWritableConfig } from \"./types.js\";\n\ninterface IInternalConfig extends IConfig {\n autoTrigger: boolean;\n triggerAttribute: string;\n tagNames: {\n notify: string;\n };\n}\n\nconst _config: IInternalConfig = {\n autoTrigger: true,\n triggerAttribute: \"data-notifytarget\",\n tagNames: {\n notify: \"wcs-notify\",\n },\n};\n\nfunction deepFreeze<T>(obj: T): T {\n if (obj === null || typeof obj !== \"object\") return obj;\n Object.freeze(obj);\n for (const key of Object.keys(obj)) {\n deepFreeze((obj as Record<string, unknown>)[key]);\n }\n return obj;\n}\n\nfunction deepClone<T>(obj: T): T {\n if (obj === null || typeof obj !== \"object\") return obj;\n const clone: Record<string, unknown> = {};\n for (const key of Object.keys(obj)) {\n clone[key] = deepClone((obj as Record<string, unknown>)[key]);\n }\n return clone as T;\n}\n\nlet frozenConfig: IConfig | null = null;\n\n// Internal, mutable live config used by the components/autoTrigger (they read it\n// at call time so setConfig() takes effect without re-import). Typed as the\n// readonly IConfig at the export boundary — the `as IConfig` is a compile-time\n// view only and does NOT freeze the object, so this export must stay\n// package-internal (it is not re-exported from exports.ts). Public consumers get\n// the deep-frozen clone from getConfig() instead.\nexport const config: IConfig = _config as IConfig;\n\nexport function getConfig(): IConfig {\n if (!frozenConfig) {\n frozenConfig = deepFreeze(deepClone(_config));\n }\n return frozenConfig;\n}\n\nexport function setConfig(partialConfig: IWritableConfig): void {\n if (typeof partialConfig.autoTrigger === \"boolean\") {\n _config.autoTrigger = partialConfig.autoTrigger;\n }\n if (typeof partialConfig.triggerAttribute === \"string\") {\n _config.triggerAttribute = partialConfig.triggerAttribute;\n }\n if (partialConfig.tagNames) {\n Object.assign(_config.tagNames, partialConfig.tagNames);\n }\n frozenConfig = null;\n}\n","/**\n * notificationCapabilities.ts\n *\n * Notification node 固有の error code(taxonomy)と derivation。汎用の error info 型は\n * `./platformCapability.js`(/io-core/ から copy-distribution される生成ファイル)から\n * import する。notification は監視(permission)と操作(notify/close)を 1 タグに併せ持つが、\n * 競合する非同期 operation の lane は持たない(show は最新値で上書きされる momentary な\n * 送出)ため、lane は採用せず error taxonomy(errorInfo)のみを追加する。\n *\n * sensor family と異なり、NotificationCore の error detail の `.error` は既に安定コード\n * (`this._err(code, message)` が産出する `\"unsupported\"` / `\"not-granted\"` /\n * `\"invalid-title\"` / `\"show-failed\"` / `\"no-service-worker\"`)であり、Error.name ではない。\n * したがって derivation は `.error` コードを taxonomy に写すだけの純粋な map である。\n * 想定外のコードは防御的に `notify-error` へ畳む。\n */\n\nimport type { WcsIoErrorInfo } from \"./platformCapability.js\";\nimport type { WcsNotifyErrorDetail } from \"../types.js\";\n\n/** 安定した notification error code(taxonomy)。値は公開キーとして固定。 */\nexport const WCS_NOTIFY_ERROR_CODE = {\n /** Notifications API 非対応(`globalThis.Notification` 不在)。 */\n CapabilityMissing: \"capability-missing\",\n /** 権限が granted でない状態での notify()。 */\n NotAllowed: \"not-allowed\",\n /** notify() に非文字列 title が渡された。 */\n InvalidArgument: \"invalid-argument\",\n /** notification の生成 / 表示に失敗した(constructor 例外 / onerror / SW show reject)。 */\n ShowFailed: \"show-failed\",\n /** SW backend が必要だが `navigator.serviceWorker` が不在。 */\n NoServiceWorker: \"no-service-worker\",\n /** その他 / 想定外の error code に対する防御的 fallback。 */\n NotifyError: \"notify-error\",\n} as const;\n\n/**\n * notification の失敗を serializable な error taxonomy に写す。引数は\n * `wcs-notify:error` の detail(`{ error, message }`)そのもの。`.error` は\n * `NotificationCore._err()` が付与した安定コードで、Error.name ではない。\n *\n * - `\"unsupported\"` は開始前の能力欠如 → phase=\"probe\" / capability-missing。\n * - `\"not-granted\"` / `\"invalid-title\"` は show 手前の前提条件違反(権限・引数)→\n * phase=\"start\" / not-allowed・invalid-argument。\n * - `\"show-failed\"` は show 実行中の失敗 → phase=\"execute\" / show-failed。\n * - `\"no-service-worker\"` は SW backend 要求時の transport 欠如 → phase=\"execute\" /\n * no-service-worker。\n * - それ以外(未知コード)は防御的に phase=\"execute\" / notify-error。\n *\n * いずれも retry で自動回復しない(recoverable=false)。\n */\nexport function deriveNotifyErrorInfo(error: WcsNotifyErrorDetail): WcsIoErrorInfo {\n const { error: code, message } = error;\n switch (code) {\n case \"unsupported\":\n return { code: WCS_NOTIFY_ERROR_CODE.CapabilityMissing, phase: \"probe\", recoverable: false, message };\n case \"not-granted\":\n return { code: WCS_NOTIFY_ERROR_CODE.NotAllowed, phase: \"start\", recoverable: false, message };\n case \"invalid-title\":\n return { code: WCS_NOTIFY_ERROR_CODE.InvalidArgument, phase: \"start\", recoverable: false, message };\n case \"show-failed\":\n return { code: WCS_NOTIFY_ERROR_CODE.ShowFailed, phase: \"execute\", recoverable: false, message };\n case \"no-service-worker\":\n return { code: WCS_NOTIFY_ERROR_CODE.NoServiceWorker, phase: \"execute\", recoverable: false, message };\n default:\n return { code: WCS_NOTIFY_ERROR_CODE.NotifyError, phase: \"execute\", recoverable: false, message };\n }\n}\n","import {\n IWcBindable, NotifyBackend, NotifyOptions, NotificationPermissionRaw,\n PermissionStateOrUnsupported, WcsNotifyClickDetail, WcsNotifyErrorDetail,\n} from \"../types.js\";\nimport { WcsIoErrorInfo } from \"./platformCapability.js\";\nimport { deriveNotifyErrorInfo } from \"./notificationCapabilities.js\";\n\n// Wrapper stored in a notification's `data` so the Service Worker side (a\n// separate global scope with no access to this instance) can recover the\n// identity and the caller's payload. The constructor backend uses the same\n// wrapper for uniformity, and both paths unwrap it before emitting.\ninterface WcsNotifyData {\n __wcsId: string;\n payload: unknown;\n}\n\n// Message shape posted by `wireNotificationClicks()` (src/sw.ts) over both\n// BroadcastChannel and clients.postMessage. `id` is unique per click\n// (`tag#seq`), so the two transports delivering the *same* click de-dup, while\n// two genuine clicks on the same `tag` do not.\ninterface WcsNotifyInbound {\n __wcsNotify: true;\n id: string;\n tag: string;\n data: unknown;\n action: string;\n}\n\n/**\n * Headless desktop-notification primitive. A thin, framework-agnostic wrapper\n * around the Notifications API exposed through the wc-bindable protocol.\n *\n * Unlike `@wcstack/permission` (a read-only monitor — the Permissions API has no\n * `request()`), the Notifications API *does* expose `Notification.requestPermission()`,\n * so this node is self-contained: it both **requests/monitors** the permission and\n * **shows** notifications. It is the first @wcstack node where the command-token\n * (show: `notify`) and event-token (`click` / `close` / `show`) directions both\n * live in one tag.\n *\n * - **request()** asks for the `notifications` permission (`Notification.requestPermission`).\n * - **notify(title, options)** shows a notification and returns its identifying tag\n * (a caller `options.tag`, or a generated `wcs-<n>`). It picks a backend per\n * `mode`: the `Notification` constructor (desktop) or\n * `ServiceWorkerRegistration.showNotification()` (mobile). `\"auto\"` prefers the\n * constructor and falls back to the SW on a `TypeError`.\n * - **close(tag) / closeAll()** dismiss notifications by tag / all.\n * - Clicks flow back as the `wcs-notify:click` event: directly via the\n * Notification's `onclick` (constructor), or via the SW helper's\n * BroadcastChannel/postMessage relay (SW). `permission` mirrors the live grant.\n *\n * Failures never throw: they surface through `error` (and the `unsupported`\n * permission state) so they flow into the declarative state.\n */\nexport class NotificationCore extends EventTarget {\n static wcBindable: IWcBindable = {\n protocol: \"wc-bindable\",\n version: 1,\n properties: [\n { name: \"permission\", event: \"wcs-notify:permission-change\" },\n { name: \"granted\", event: \"wcs-notify:permission-change\", getter: (e: Event) => (e as CustomEvent).detail === \"granted\" },\n { name: \"denied\", event: \"wcs-notify:permission-change\", getter: (e: Event) => (e as CustomEvent).detail === \"denied\" },\n { name: \"prompt\", event: \"wcs-notify:permission-change\", getter: (e: Event) => (e as CustomEvent).detail === \"prompt\" },\n { name: \"unsupported\", event: \"wcs-notify:permission-change\", getter: (e: Event) => (e as CustomEvent).detail === \"unsupported\" },\n { name: \"error\", event: \"wcs-notify:error\" },\n // Serializable failure taxonomy (stable code / phase / recoverable), or null.\n // Additive bindable output derived from `error.error` (the stable code the\n // Core's `_err()` already produces); the existing `error` property/event are\n // unchanged. Fires wcs-notify:error-info-changed. No lane — show is a\n // momentary, last-value-wins send, not a competing async operation.\n { name: \"errorInfo\", event: \"wcs-notify:error-info-changed\" },\n { name: \"clicked\", event: \"wcs-notify:click\", getter: (e: Event) => (e as CustomEvent).detail },\n { name: \"closed\", event: \"wcs-notify:close\", getter: (e: Event) => (e as CustomEvent).detail },\n { name: \"shown\", event: \"wcs-notify:show\", getter: (e: Event) => (e as CustomEvent).detail },\n ],\n commands: [\n { name: \"request\", async: true },\n { name: \"notify\" },\n { name: \"close\" },\n { name: \"closeAll\" },\n ],\n };\n\n private _target: EventTarget;\n private _mode: NotifyBackend = \"auto\";\n\n private _permission: PermissionStateOrUnsupported = \"prompt\";\n private _error: WcsNotifyErrorDetail | null = null;\n private _errorInfo: WcsIoErrorInfo | null = null;\n private _lastClick: WcsNotifyClickDetail | null = null;\n private _lastClose: WcsNotifyClickDetail | null = null;\n private _lastShow: WcsNotifyClickDetail | null = null;\n\n // Live PermissionStatus (when the Permissions API can query `notifications`),\n // kept so its `change` listener can be removed on dispose().\n private _permissionStatus: PermissionStatus | null = null;\n // True once a permission subscription has been (or is being) established; reset\n // by dispose(). Guards observe() so a reconnect re-queries while a redundant\n // observe() on a live subscription does not.\n private _permissionSubscribed: boolean = false;\n\n // Monotonic id of the current lifecycle. Bumped by every observe() and by\n // dispose(). In-flight async work (permission query, SW show, inbound click)\n // captures it and bails if stale, so a query/click that resolves after a\n // disconnect — or after a rapid disconnect→reconnect — never mutates state or\n // dispatches on a torn-down element.\n private _gen: number = 0;\n\n // Resolves once the connect-time permission probe settles. The Shell exposes\n // this as connectedCallbackPromise so SSR can await it before snapshotting.\n private _ready: Promise<void> = Promise.resolve();\n\n // Counter for auto-assigned tags when the caller omits one.\n private _idSeq: number = 0;\n\n // Notifications created via the constructor backend, by tag, so close()/closeAll()\n // can dismiss them. The SW backend has no handle (showNotification returns void),\n // so its tags are tracked separately and closed via registration.getNotifications().\n private _constructed: Map<string, Notification> = new Map();\n private _swTags: Set<string> = new Set();\n\n // Click subscription handles (SW relay).\n private _channel: BroadcastChannel | null = null;\n private _serviceWorker: ServiceWorkerContainer | null = null;\n private _clicksSubscribed: boolean = false;\n // Per-click ids already handled, to de-dup the two relay transports. FIFO-capped\n // so a long session does not leak; the two transports always arrive in the same\n // tick, so a small cap is ample.\n private _seenIds: string[] = [];\n\n constructor(target?: EventTarget) {\n super();\n this._target = target ?? this;\n }\n\n get permission(): PermissionStateOrUnsupported {\n return this._permission;\n }\n\n get granted(): boolean {\n return this._permission === \"granted\";\n }\n\n get denied(): boolean {\n return this._permission === \"denied\";\n }\n\n get prompt(): boolean {\n return this._permission === \"prompt\";\n }\n\n get unsupported(): boolean {\n return this._permission === \"unsupported\";\n }\n\n get error(): WcsNotifyErrorDetail | null {\n return this._error;\n }\n\n /**\n * The last failure's serializable `WcsIoErrorInfo` (stable `code` / `phase` /\n * `recoverable`), or null. Additive wc-bindable property (event\n * `wcs-notify:error-info-changed`), derived from `error`; the existing `error`\n * property/event are unchanged.\n */\n get errorInfo(): WcsIoErrorInfo | null {\n return this._errorInfo;\n }\n\n get clicked(): WcsNotifyClickDetail | null {\n return this._lastClick;\n }\n\n get closed(): WcsNotifyClickDetail | null {\n return this._lastClose;\n }\n\n get shown(): WcsNotifyClickDetail | null {\n return this._lastShow;\n }\n\n /** Resolves once the current (or initial) permission probe settles. */\n get ready(): Promise<void> {\n return this._ready;\n }\n\n // --- State setters with event dispatch ---\n\n private _setPermission(state: PermissionStateOrUnsupported): void {\n if (this._permission === state) return;\n this._permission = state;\n this._target.dispatchEvent(new CustomEvent(\"wcs-notify:permission-change\", {\n detail: state,\n bubbles: true,\n }));\n }\n\n private _setError(error: WcsNotifyErrorDetail | null): void {\n if (this._error === error) return;\n this._error = error;\n // Keep the additive `errorInfo` taxonomy in sync with `error`: derive from the\n // stable error code (or null on clear). Fires before the `error` event so an\n // observer binding both sees the classification first, mirroring the io-node\n // family.\n this._commitErrorInfo(error === null ? null : deriveNotifyErrorInfo(error));\n this._target.dispatchEvent(new CustomEvent(\"wcs-notify:error\", {\n detail: error,\n bubbles: true,\n }));\n }\n\n // Called only from _setError (which already guards on error identity), so\n // errorInfo transitions exactly when error does — no separate guard needed here.\n private _commitErrorInfo(info: WcsIoErrorInfo | null): void {\n this._errorInfo = info;\n this._target.dispatchEvent(new CustomEvent(\"wcs-notify:error-info-changed\", {\n detail: info,\n bubbles: true,\n }));\n }\n\n private _emit(kind: \"click\" | \"close\" | \"show\", detail: WcsNotifyClickDetail): void {\n if (kind === \"click\") this._lastClick = detail;\n else if (kind === \"close\") this._lastClose = detail;\n else this._lastShow = detail;\n this._target.dispatchEvent(new CustomEvent(`wcs-notify:${kind}`, {\n detail,\n bubbles: true,\n }));\n }\n\n // --- Public API ---\n\n /**\n * Start observing the `notifications` permission and subscribing to Service\n * Worker click relays. `mode` selects the show backend (default `\"auto\"`).\n * Idempotent while already subscribed: it only updates the stored mode; to\n * restart, dispose() first. Returns a promise that resolves once the first\n * permission probe settles, for SSR.\n *\n * Headless callers must call observe() to begin; the Shell calls it from\n * connectedCallback once the element's attributes resolve.\n */\n observe(mode: NotifyBackend = \"auto\"): Promise<void> {\n this._mode = mode;\n if (!this._permissionSubscribed) {\n this._ready = this._initPermission();\n this._subscribeClicks();\n }\n return this._ready;\n }\n\n /**\n * Ask the user for the `notifications` permission. Resolves to the resulting\n * (normalized) permission state. Never throws: an unavailable API resolves to\n * `\"unsupported\"`.\n */\n async request(): Promise<PermissionStateOrUnsupported> {\n const api = this._api();\n if (!api || typeof api.requestPermission !== \"function\") {\n this._setPermission(\"unsupported\");\n return this._permission;\n }\n try {\n const result = await api.requestPermission();\n this._setPermission(this._normalize(result));\n } catch {\n // Some legacy engines may reject; keep the current state rather than throw.\n }\n return this._permission;\n }\n\n /**\n * Show a notification. Returns the identifying tag (the caller's `options.tag`,\n * or a generated `wcs-<n>` when omitted). Never throws: when the API is\n * unavailable or the permission is not granted it surfaces an `error` and\n * returns an empty string.\n */\n notify(title: string, options: NotifyOptions = {}): string {\n if (!this._api()) {\n this._setError(this._err(\"unsupported\", \"Notifications API is not available in this environment.\"));\n return \"\";\n }\n if (this._permission !== \"granted\") {\n this._setError(this._err(\"not-granted\", \"Notification permission is not granted; call request() first.\"));\n return \"\";\n }\n if (typeof title !== \"string\") {\n this._setError(this._err(\"invalid-title\", \"notify() requires a string title.\"));\n return \"\";\n }\n\n const tag = (typeof options.tag === \"string\" && options.tag !== \"\") ? options.tag : this._nextId();\n const payload = options.data;\n const data: WcsNotifyData = { __wcsId: tag, payload };\n const backendOptions: NotifyOptions = { ...options, tag, data };\n\n this._setError(null);\n this._show(title, backendOptions, tag, payload);\n return tag;\n }\n\n /** Dismiss the notification(s) with `tag` across both backends. */\n close(tag?: string): void {\n if (typeof tag !== \"string\" || tag === \"\") return;\n const n = this._constructed.get(tag);\n if (n) {\n n.close();\n this._constructed.delete(tag);\n }\n if (this._swTags.has(tag)) {\n this._closeSw(tag);\n this._swTags.delete(tag);\n }\n }\n\n /**\n * Dismiss every notification this instance has shown. Scoped to this instance's\n * own tags on both backends — the SW path closes each tracked tag individually\n * rather than enumerating the whole origin, so it never dismisses notifications\n * shown by another `<wcs-notify>` or by an unrelated code path.\n */\n closeAll(): void {\n for (const n of this._constructed.values()) {\n n.close();\n }\n this._constructed.clear();\n for (const tag of this._swTags) {\n this._closeSw(tag);\n }\n this._swTags.clear();\n }\n\n /**\n * Detach permission and click subscriptions. Open notifications are intentionally\n * **left on screen** (a notification outlives the page that posted it — that is\n * the point); use close()/closeAll() to dismiss. Call from the Shell's\n * disconnectedCallback. A later observe() resumes.\n */\n dispose(): void {\n this._permissionSubscribed = false;\n this._clicksSubscribed = false;\n this._gen++;\n if (this._permissionStatus) {\n this._permissionStatus.removeEventListener(\"change\", this._onPermissionChange);\n this._permissionStatus = null;\n }\n if (this._channel) {\n this._channel.removeEventListener(\"message\", this._onInbound);\n this._channel.close();\n this._channel = null;\n }\n if (this._serviceWorker) {\n this._serviceWorker.removeEventListener(\"message\", this._onInbound);\n this._serviceWorker = null;\n }\n }\n\n // --- Internal: permission ---\n\n private _initPermission(): Promise<void> {\n const api = this._api();\n if (!api) {\n this._setPermission(\"unsupported\");\n // Intentionally does NOT set _permissionSubscribed: there is no permission\n // listener to tear down, so a reconnect simply re-probes (idempotent — the\n // same-value guard suppresses any redundant dispatch and no listener is ever\n // attached). _subscribeClicks() is re-entered too, but its own\n // _clicksSubscribed guard short-circuits the second pass, so no transport is\n // double-subscribed. Mirrors @wcstack/permission's unsupported path.\n return Promise.resolve();\n }\n this._permissionSubscribed = true;\n // Prefer the Permissions API: it provides a live `change` event. Fall back to\n // the static `Notification.permission` when it is absent or rejects the\n // `notifications` descriptor.\n if (typeof navigator !== \"undefined\" && navigator.permissions && typeof navigator.permissions.query === \"function\") {\n const gen = ++this._gen;\n return navigator.permissions.query({ name: \"notifications\" }).then(\n (status) => {\n if (gen !== this._gen) return;\n this._permissionStatus = status;\n this._setPermission(this._normalize(status.state as NotificationPermissionRaw));\n status.addEventListener(\"change\", this._onPermissionChange);\n },\n () => {\n if (gen !== this._gen) return;\n // Permissions API rejected the `notifications` descriptor — fall back to\n // the static `Notification.permission` (api is in scope and non-null here).\n this._setPermission(this._normalize(api.permission));\n },\n );\n }\n // No Permissions API: read the static permission once (no live change events).\n this._setPermission(this._normalize(api.permission));\n return Promise.resolve();\n }\n\n private _onPermissionChange = (event: Event): void => {\n const status = event.target as PermissionStatus;\n this._setPermission(this._normalize(status.state as NotificationPermissionRaw));\n };\n\n // Normalize the Notifications API's `\"default\"` to `\"prompt\"` so this node shares\n // the four-value surface of @wcstack/permission. The Permissions API already\n // reports `\"prompt\"`, so it passes through unchanged.\n private _normalize(raw: NotificationPermissionRaw | string): PermissionStateOrUnsupported {\n if (raw === \"default\") return \"prompt\";\n if (raw === \"granted\" || raw === \"denied\" || raw === \"prompt\") return raw;\n return \"prompt\";\n }\n\n // --- Internal: showing ---\n\n private _show(title: string, options: NotifyOptions, tag: string, payload: unknown): void {\n if (this._mode === \"sw\") {\n this._showViaSw(title, options, tag, payload);\n return;\n }\n const handled = this._showViaConstructor(title, options, tag, payload);\n if (handled) return;\n // Constructor threw TypeError (e.g. mobile, where `new Notification` is illegal).\n if (this._mode === \"auto\") {\n this._showViaSw(title, options, tag, payload);\n } else {\n this._setError(this._err(\"show-failed\", \"new Notification() is not usable here and mode=\\\"constructor\\\" disallows the Service Worker fallback.\"));\n }\n }\n\n // Returns false only when the constructor threw a TypeError (the signal to fall\n // back to the SW backend); true when it showed or surfaced a non-TypeError error.\n private _showViaConstructor(title: string, options: NotifyOptions, tag: string, payload: unknown): boolean {\n const api = this._api()!;\n const gen = this._gen;\n let n: Notification;\n try {\n n = new api(title, options as NotificationOptions);\n } catch (e) {\n if (e instanceof TypeError) return false;\n this._setError(this._err(\"show-failed\", \"Failed to create the notification.\"));\n return true;\n }\n this._constructed.set(tag, n);\n n.onshow = (): void => {\n if (gen !== this._gen) return;\n this._emit(\"show\", { tag, data: payload, action: \"\" });\n };\n n.onclick = (): void => {\n if (gen !== this._gen) return;\n this._emit(\"click\", { tag, data: payload, action: \"\" });\n };\n n.onclose = (): void => {\n this._constructed.delete(tag);\n if (gen !== this._gen) return;\n this._emit(\"close\", { tag, data: payload, action: \"\" });\n };\n n.onerror = (): void => {\n if (gen !== this._gen) return;\n this._setError(this._err(\"show-failed\", \"The notification failed to display.\"));\n };\n return true;\n }\n\n private _showViaSw(title: string, options: NotifyOptions, tag: string, payload: unknown): void {\n const sw = navigator.serviceWorker as ServiceWorkerContainer | undefined;\n if (!sw) {\n this._setError(this._err(\"no-service-worker\", \"Service Worker is required to show this notification but is unavailable.\"));\n return;\n }\n const gen = this._gen;\n this._swTags.add(tag);\n // A notification deliberately outlives the page (see § dispose), so we do NOT\n // bail before showNotification on a stale gen — a notify() issued while\n // connected still shows. The stale-gen guards only suppress dispatching the\n // observable `show` / `error` back onto a torn-down element.\n sw.ready\n .then((registration) => registration.showNotification(title, options as NotificationOptions))\n .then(() => {\n if (gen !== this._gen) return;\n this._emit(\"show\", { tag, data: payload, action: \"\" });\n })\n .catch(() => {\n if (gen !== this._gen) return;\n this._setError(this._err(\"show-failed\", \"ServiceWorkerRegistration.showNotification() failed.\"));\n });\n }\n\n // Close the SW notification(s) carrying `tag`. Always scoped to a single tag —\n // both callers (close / closeAll) iterate their own tracked tags, so the whole\n // origin is never enumerated.\n private _closeSw(tag: string): void {\n const sw = navigator.serviceWorker as ServiceWorkerContainer | undefined;\n if (!sw) return;\n sw.ready.then((registration) => {\n return registration.getNotifications({ tag }).then((list) => {\n for (const n of list) n.close();\n });\n }).catch(() => {\n // Closing is best-effort; a failure to enumerate is not surfaced.\n });\n }\n\n // --- Internal: click relay (SW) ---\n\n private _subscribeClicks(): void {\n if (this._clicksSubscribed) return;\n this._clicksSubscribed = true;\n if (typeof BroadcastChannel === \"function\") {\n this._channel = new BroadcastChannel(\"wcs-notify\");\n this._channel.addEventListener(\"message\", this._onInbound);\n }\n const sw = navigator.serviceWorker as ServiceWorkerContainer | undefined;\n if (sw) {\n this._serviceWorker = sw;\n sw.addEventListener(\"message\", this._onInbound);\n }\n }\n\n private _onInbound = (event: Event): void => {\n const msg = (event as MessageEvent).data as WcsNotifyInbound | undefined;\n if (!msg || msg.__wcsNotify !== true) return;\n if (this._isDuplicate(msg.id)) return;\n this._emit(\"click\", { tag: msg.tag, data: this._unwrap(msg.data), action: msg.action });\n };\n\n private _isDuplicate(id: string): boolean {\n if (this._seenIds.includes(id)) return true;\n this._seenIds.push(id);\n if (this._seenIds.length > 50) this._seenIds.shift();\n return false;\n }\n\n private _unwrap(raw: unknown): unknown {\n if (raw !== null && typeof raw === \"object\" && \"__wcsId\" in raw) {\n return (raw as WcsNotifyData).payload;\n }\n return raw;\n }\n\n // --- Internal: misc ---\n\n // Resolve the global `Notification` constructor at call time (not cached) so\n // tests can install/remove it and so unsupported environments report correctly.\n private _api(): (typeof Notification) | undefined {\n const g = globalThis as unknown as { Notification?: typeof Notification };\n return typeof g.Notification === \"function\" ? g.Notification : undefined;\n }\n\n private _nextId(): string {\n return `wcs-${++this._idSeq}`;\n }\n\n private _err(error: string, message: string): WcsNotifyErrorDetail {\n return { error, message };\n }\n}\n","import { config } from \"./config.js\";\nimport type { WcsNotify } from \"./components/Notify.js\";\n\nlet registered = false;\n\nfunction handleClick(event: Event): void {\n const target = event.target;\n if (!(target instanceof Element)) return;\n\n // A misconfigured triggerAttribute (e.g. one with a space) makes the attribute\n // selector invalid and closest() throw SyntaxError; guard so a bad config\n // disables only this shortcut rather than killing every document click handler.\n let triggerElement: Element | null;\n try {\n triggerElement = target.closest<Element>(`[${config.triggerAttribute}]`);\n } catch {\n return;\n }\n if (!triggerElement) return;\n\n const notifyId = triggerElement.getAttribute(config.triggerAttribute);\n if (!notifyId) return;\n\n // Resolve the registered constructor at call time instead of importing Notify as\n // a value, avoiding a components/Notify.ts ⇄ autoTrigger.ts cycle\n // (Notify.connectedCallback() calls registerAutoTrigger()). instanceof against\n // the customElements registry keeps the same identity guarantee.\n const NotifyCtor = customElements.get(config.tagNames.notify);\n const notifyElement = document.getElementById(notifyId);\n if (!NotifyCtor || !(notifyElement instanceof NotifyCtor)) return;\n\n // The title comes from the trigger element: an explicit `data-notifytitle`\n // attribute wins, otherwise the element's trimmed text content. The body is an\n // optional `data-notifybody`. This keeps the click-driven shortcut declarative\n // without inventing a payload channel.\n const explicit = triggerElement.getAttribute(\"data-notifytitle\");\n // `Element.textContent` is spec-guaranteed non-null (only Document / DocumentType\n // nodes return null, never an Element), so the cast is sound and lets us avoid an\n // unreachable `?? \"\"` branch. `triggerElement` is always an Element here.\n const title = explicit !== null ? explicit : (triggerElement.textContent as string).trim();\n const body = triggerElement.getAttribute(\"data-notifybody\");\n\n (notifyElement as WcsNotify).notify(title, body !== null ? { body } : undefined);\n}\n\nexport function registerAutoTrigger(): void {\n if (registered) return;\n registered = true;\n document.addEventListener(\"click\", handleClick);\n}\n\nexport function unregisterAutoTrigger(): void {\n if (!registered) return;\n registered = false;\n document.removeEventListener(\"click\", handleClick);\n}\n","import { config } from \"../config.js\";\nimport {\n IWcBindable, NotifyBackend, NotifyOptions, PermissionStateOrUnsupported,\n WcsNotifyClickDetail, WcsNotifyErrorDetail,\n} from \"../types.js\";\nimport { NotificationCore } from \"../core/NotificationCore.js\";\nimport { WcsIoErrorInfo } from \"../core/platformCapability.js\";\nimport { registerAutoTrigger } from \"../autoTrigger.js\";\n\n/**\n * `<wcs-notify>` — declarative desktop notifications. Wraps NotificationCore and\n * exposes both directions in one tag:\n *\n * - **`notice`** (reactive input): writing a *changed* value shows a notification,\n * suppressing same-value writes so it fires only when the bound source actually\n * changes. The imperative `notify` command instead shows on demand (even the\n * same text again). See `docs/notification-tag-design.md` § 2.\n * - **`request` / `notify` / `close` / `closeAll`** commands (state → element).\n * - per-notification options (`body` / `icon` / `badge` / `tag` / `lang` / `dir` /\n * `require-interaction` / `silent` / `renotify`) as mirrored attributes.\n * - `mode` selects the show backend (`auto` / `sw` / `constructor`).\n * - the Core's observable surface (permission / granted / … / error / clicked /\n * closed / shown) via delegated getters; clicked/closed/shown carry the\n * `{ tag, data, action }` payload for event-token wiring.\n */\nexport class WcsNotify extends HTMLElement {\n static hasConnectedCallbackPromise = true;\n static wcBindable: IWcBindable = {\n ...NotificationCore.wcBindable,\n // Shell-level settable surface. `notice` is a momentary reactive command-property\n // with no mirrored attribute (it carries dynamic text, not declarative config),\n // mirroring <wcs-speak>'s `say`. The rest mirror their HTML attributes idempotently.\n inputs: [\n { name: \"notice\" },\n { name: \"mode\", attribute: \"mode\" },\n { name: \"body\", attribute: \"body\" },\n { name: \"icon\", attribute: \"icon\" },\n { name: \"badge\", attribute: \"badge\" },\n { name: \"tag\", attribute: \"tag\" },\n { name: \"lang\", attribute: \"lang\" },\n { name: \"dir\", attribute: \"dir\" },\n { name: \"requireInteraction\", attribute: \"require-interaction\" },\n { name: \"silent\", attribute: \"silent\" },\n { name: \"renotify\", attribute: \"renotify\" },\n { name: \"manual\", attribute: \"manual\" },\n ],\n commands: NotificationCore.wcBindable.commands,\n };\n\n private _core: NotificationCore;\n private _notice: string = \"\";\n private _connectedCallbackPromise: Promise<void> = Promise.resolve();\n private _internals: ElementInternals | null = null;\n\n constructor() {\n super();\n this._core = new NotificationCore(this);\n this._internals = this._initInternals();\n this._wireStates({\n \"wcs-notify:permission-change\": (d) => ({\n granted: d === \"granted\", denied: d === \"denied\",\n prompt: d === \"prompt\", unsupported: d === \"unsupported\",\n }),\n \"wcs-notify:error\": (d) => ({ error: d != null }),\n });\n }\n\n // CSS state reflection (:state()) — debug-only snapshot getter. NOT part of\n // wc-bindable (not a bind target); see README \"CSS styling with :state()\".\n // MUST NOT return the live CustomStateSet (that would let callers write\n // states from outside, defeating the point of :state() being read-only).\n get debugStates(): string[] {\n return this._internals ? [...this._internals.states] : [];\n }\n\n private _initInternals(): ElementInternals | null {\n // never-throw (async-io-node-guidelines.md §3.6): attachInternals is absent\n // in happy-dom / older environments, and pre-125 Chromium rejects\n // non-dashed state names from states.add() (probed and discarded here).\n // Either case silently disables reflection — the component still works,\n // it just doesn't expose :state() selectors.\n try {\n if (typeof this.attachInternals !== \"function\") return null;\n const internals = this.attachInternals();\n internals.states.add(\"wcs-probe\");\n internals.states.delete(\"wcs-probe\");\n return internals;\n } catch {\n return null;\n }\n }\n\n private _wireStates(map: Record<string, (detail: any) => Record<string, boolean>>): void {\n if (this._internals === null) return;\n const states = this._internals.states;\n for (const [event, toStates] of Object.entries(map)) {\n this.addEventListener(event, (e) => {\n const debug = this.hasAttribute(\"debug-states\");\n for (const [name, on] of Object.entries(toStates((e as CustomEvent).detail))) {\n try {\n if (on) { states.add(name); } else { states.delete(name); }\n } catch { /* never-throw */ }\n if (debug) this.toggleAttribute(`data-wcs-state-${name}`, on);\n }\n });\n }\n }\n\n // --- Attribute accessors ---\n\n get mode(): NotifyBackend {\n const m = this.getAttribute(\"mode\");\n return (m === \"sw\" || m === \"constructor\") ? m : \"auto\";\n }\n\n set mode(value: NotifyBackend) {\n this.setAttribute(\"mode\", value);\n }\n\n get body(): string {\n return this.getAttribute(\"body\") ?? \"\";\n }\n\n set body(value: string | null) {\n this._reflect(\"body\", value);\n }\n\n get icon(): string {\n return this.getAttribute(\"icon\") ?? \"\";\n }\n\n set icon(value: string | null) {\n this._reflect(\"icon\", value);\n }\n\n get badge(): string {\n return this.getAttribute(\"badge\") ?? \"\";\n }\n\n set badge(value: string | null) {\n this._reflect(\"badge\", value);\n }\n\n get tag(): string {\n return this.getAttribute(\"tag\") ?? \"\";\n }\n\n set tag(value: string | null) {\n this._reflect(\"tag\", value);\n }\n\n // NOTE: `lang` and `dir` intentionally repurpose the standard HTMLElement IDL\n // attributes as per-notification options (forwarded to NotificationOptions).\n // This element is always display:none, so overriding their normal rendering\n // semantics has no visual effect — but be aware the values mean \"the\n // notification's language/direction\", not the host element's.\n get lang(): string {\n return this.getAttribute(\"lang\") ?? \"\";\n }\n\n set lang(value: string | null) {\n this._reflect(\"lang\", value);\n }\n\n get dir(): string {\n return this.getAttribute(\"dir\") ?? \"\";\n }\n\n set dir(value: string | null) {\n this._reflect(\"dir\", value);\n }\n\n get requireInteraction(): boolean {\n return this.hasAttribute(\"require-interaction\");\n }\n\n set requireInteraction(value: boolean) {\n this._reflectBool(\"require-interaction\", value);\n }\n\n get silent(): boolean {\n return this.hasAttribute(\"silent\");\n }\n\n set silent(value: boolean) {\n this._reflectBool(\"silent\", value);\n }\n\n get renotify(): boolean {\n return this.hasAttribute(\"renotify\");\n }\n\n set renotify(value: boolean) {\n this._reflectBool(\"renotify\", value);\n }\n\n get manual(): boolean {\n return this.hasAttribute(\"manual\");\n }\n\n set manual(value: boolean) {\n this._reflectBool(\"manual\", value);\n }\n\n // --- Reactive command-property ---\n\n get notice(): string {\n return this._notice;\n }\n\n set notice(value: string | null) {\n // Reactive: writing a new value shows it. `manual` mutes the path entirely\n // (the imperative `notify` command still works). A conforming binder never\n // delivers `undefined` (it skips the write), but a direct assignment can, so\n // normalize null/undefined to a no-op.\n if (value == null) return;\n if (this.manual) return;\n const v = String(value);\n // Same-value guard: only show when the bound source actually changes. To show\n // the same text again on demand, use the `notify` command instead. (This is\n // the only spam guard the package provides — see docs § 2-c; debounce is the\n // caller's job via a filter, e.g. `notice@x|debounce(1000)`.)\n if (v === this._notice) return;\n this._notice = v;\n this.notify(v);\n }\n\n // --- Core delegated getters ---\n\n get permission(): PermissionStateOrUnsupported {\n return this._core.permission;\n }\n\n get granted(): boolean {\n return this._core.granted;\n }\n\n get denied(): boolean {\n return this._core.denied;\n }\n\n get prompt(): boolean {\n return this._core.prompt;\n }\n\n get unsupported(): boolean {\n return this._core.unsupported;\n }\n\n get error(): WcsNotifyErrorDetail | null {\n return this._core.error;\n }\n\n get errorInfo(): WcsIoErrorInfo | null {\n return this._core.errorInfo;\n }\n\n get clicked(): WcsNotifyClickDetail | null {\n return this._core.clicked;\n }\n\n get closed(): WcsNotifyClickDetail | null {\n return this._core.closed;\n }\n\n get shown(): WcsNotifyClickDetail | null {\n return this._core.shown;\n }\n\n get connectedCallbackPromise(): Promise<void> {\n return this._connectedCallbackPromise;\n }\n\n // --- Commands ---\n\n request(): Promise<PermissionStateOrUnsupported> {\n return this._core.request();\n }\n\n notify(title: string, options?: NotifyOptions): string {\n // Explicit options (from a command-token emit) win per-key over the attribute\n // defaults, so `notify.emit(title, { body })` still picks up the element's icon.\n return this._core.notify(title, { ...this._options(), ...(options ?? {}) });\n }\n\n close(tag?: string): void {\n this._core.close(tag);\n }\n\n closeAll(): void {\n this._core.closeAll();\n }\n\n // --- Internal ---\n\n private _reflect(name: string, value: string | null): void {\n if (value == null) {\n this.removeAttribute(name);\n } else {\n this.setAttribute(name, String(value));\n }\n }\n\n private _reflectBool(name: string, value: boolean): void {\n if (value) {\n this.setAttribute(name, \"\");\n } else {\n this.removeAttribute(name);\n }\n }\n\n private _options(): NotifyOptions {\n const o: NotifyOptions = {};\n if (this.body !== \"\") o.body = this.body;\n if (this.icon !== \"\") o.icon = this.icon;\n if (this.badge !== \"\") o.badge = this.badge;\n if (this.tag !== \"\") o.tag = this.tag;\n if (this.lang !== \"\") o.lang = this.lang;\n if (this.dir === \"auto\" || this.dir === \"ltr\" || this.dir === \"rtl\") o.dir = this.dir;\n if (this.requireInteraction) o.requireInteraction = true;\n if (this.silent) o.silent = true;\n if (this.renotify) o.renotify = true;\n return o;\n }\n\n // --- Lifecycle ---\n\n connectedCallback(): void {\n this.style.display = \"none\";\n if (config.autoTrigger) {\n registerAutoTrigger();\n }\n // Begin observing permission and subscribing to SW click relays (or revive\n // after a reconnect). The returned promise is held as connectedCallbackPromise\n // for SSR.\n this._connectedCallbackPromise = this._core.observe(this.mode);\n }\n\n disconnectedCallback(): void {\n // Detach subscriptions. Open notifications are left on screen (see Core docs);\n // call close()/closeAll() to dismiss.\n this._core.dispose();\n }\n}\n","import { WcsNotify } from \"./components/Notify.js\";\nimport { config } from \"./config.js\";\n\nexport function registerComponents(): void {\n if (!customElements.get(config.tagNames.notify)) {\n customElements.define(config.tagNames.notify, WcsNotify);\n }\n}\n","import { setConfig } from \"./config.js\";\nimport { registerComponents } from \"./registerComponents.js\";\nimport { IWritableConfig } from \"./types.js\";\n\nexport function bootstrapNotification(userConfig?: IWritableConfig): void {\n if (userConfig) {\n setConfig(userConfig);\n }\n registerComponents();\n}\n"],"names":[],"mappings":"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"}
@@ -1,2 +1,2 @@
1
- const t={autoTrigger:!0,triggerAttribute:"data-notifytarget",tagNames:{notify:"wcs-notify"}};function e(t){if(null===t||"object"!=typeof t)return t;Object.freeze(t);for(const i of Object.keys(t))e(t[i]);return t}function i(t){if(null===t||"object"!=typeof t)return t;const e={};for(const s of Object.keys(t))e[s]=i(t[s]);return e}let s=null;const r=t;function n(){return s||(s=e(i(t))),s}class o extends EventTarget{static wcBindable={protocol:"wc-bindable",version:1,properties:[{name:"permission",event:"wcs-notify:permission-change"},{name:"granted",event:"wcs-notify:permission-change",getter:t=>"granted"===t.detail},{name:"denied",event:"wcs-notify:permission-change",getter:t=>"denied"===t.detail},{name:"prompt",event:"wcs-notify:permission-change",getter:t=>"prompt"===t.detail},{name:"unsupported",event:"wcs-notify:permission-change",getter:t=>"unsupported"===t.detail},{name:"error",event:"wcs-notify:error"},{name:"clicked",event:"wcs-notify:click",getter:t=>t.detail},{name:"closed",event:"wcs-notify:close",getter:t=>t.detail},{name:"shown",event:"wcs-notify:show",getter:t=>t.detail}],commands:[{name:"request",async:!0},{name:"notify"},{name:"close"},{name:"closeAll"}]};_target;_mode="auto";_permission="prompt";_error=null;_lastClick=null;_lastClose=null;_lastShow=null;_permissionStatus=null;_permissionSubscribed=!1;_gen=0;_ready=Promise.resolve();_idSeq=0;_constructed=new Map;_swTags=new Set;_channel=null;_serviceWorker=null;_clicksSubscribed=!1;_seenIds=[];constructor(t){super(),this._target=t??this}get permission(){return this._permission}get granted(){return"granted"===this._permission}get denied(){return"denied"===this._permission}get prompt(){return"prompt"===this._permission}get unsupported(){return"unsupported"===this._permission}get error(){return this._error}get clicked(){return this._lastClick}get closed(){return this._lastClose}get shown(){return this._lastShow}get ready(){return this._ready}_setPermission(t){this._permission!==t&&(this._permission=t,this._target.dispatchEvent(new CustomEvent("wcs-notify:permission-change",{detail:t,bubbles:!0})))}_setError(t){this._error!==t&&(this._error=t,this._target.dispatchEvent(new CustomEvent("wcs-notify:error",{detail:t,bubbles:!0})))}_emit(t,e){"click"===t?this._lastClick=e:"close"===t?this._lastClose=e:this._lastShow=e,this._target.dispatchEvent(new CustomEvent(`wcs-notify:${t}`,{detail:e,bubbles:!0}))}observe(t="auto"){return this._mode=t,this._permissionSubscribed||(this._ready=this._initPermission(),this._subscribeClicks()),this._ready}async request(){const t=this._api();if(!t||"function"!=typeof t.requestPermission)return this._setPermission("unsupported"),this._permission;try{const e=await t.requestPermission();this._setPermission(this._normalize(e))}catch{}return this._permission}notify(t,e={}){if(!this._api())return this._setError(this._err("unsupported","Notifications API is not available in this environment.")),"";if("granted"!==this._permission)return this._setError(this._err("not-granted","Notification permission is not granted; call request() first.")),"";if("string"!=typeof t)return this._setError(this._err("invalid-title","notify() requires a string title.")),"";const i="string"==typeof e.tag&&""!==e.tag?e.tag:this._nextId(),s=e.data,r={__wcsId:i,payload:s},n={...e,tag:i,data:r};return this._setError(null),this._show(t,n,i,s),i}close(t){if("string"!=typeof t||""===t)return;const e=this._constructed.get(t);e&&(e.close(),this._constructed.delete(t)),this._swTags.has(t)&&(this._closeSw(t),this._swTags.delete(t))}closeAll(){for(const t of this._constructed.values())t.close();this._constructed.clear();for(const t of this._swTags)this._closeSw(t);this._swTags.clear()}dispose(){this._permissionSubscribed=!1,this._clicksSubscribed=!1,this._gen++,this._permissionStatus&&(this._permissionStatus.removeEventListener("change",this._onPermissionChange),this._permissionStatus=null),this._channel&&(this._channel.removeEventListener("message",this._onInbound),this._channel.close(),this._channel=null),this._serviceWorker&&(this._serviceWorker.removeEventListener("message",this._onInbound),this._serviceWorker=null)}_initPermission(){const t=this._api();if(!t)return this._setPermission("unsupported"),Promise.resolve();if(this._permissionSubscribed=!0,"undefined"!=typeof navigator&&navigator.permissions&&"function"==typeof navigator.permissions.query){const e=++this._gen;return navigator.permissions.query({name:"notifications"}).then(t=>{e===this._gen&&(this._permissionStatus=t,this._setPermission(this._normalize(t.state)),t.addEventListener("change",this._onPermissionChange))},()=>{e===this._gen&&this._setPermission(this._normalize(t.permission))})}return this._setPermission(this._normalize(t.permission)),Promise.resolve()}_onPermissionChange=t=>{const e=t.target;this._setPermission(this._normalize(e.state))};_normalize(t){return"default"===t?"prompt":"granted"===t||"denied"===t||"prompt"===t?t:"prompt"}_show(t,e,i,s){if("sw"===this._mode)return void this._showViaSw(t,e,i,s);this._showViaConstructor(t,e,i,s)||("auto"===this._mode?this._showViaSw(t,e,i,s):this._setError(this._err("show-failed",'new Notification() is not usable here and mode="constructor" disallows the Service Worker fallback.')))}_showViaConstructor(t,e,i,s){const r=this._api(),n=this._gen;let o;try{o=new r(t,e)}catch(t){return!(t instanceof TypeError)&&(this._setError(this._err("show-failed","Failed to create the notification.")),!0)}return this._constructed.set(i,o),o.onshow=()=>{n===this._gen&&this._emit("show",{tag:i,data:s,action:""})},o.onclick=()=>{n===this._gen&&this._emit("click",{tag:i,data:s,action:""})},o.onclose=()=>{this._constructed.delete(i),n===this._gen&&this._emit("close",{tag:i,data:s,action:""})},o.onerror=()=>{n===this._gen&&this._setError(this._err("show-failed","The notification failed to display."))},!0}_showViaSw(t,e,i,s){const r=navigator.serviceWorker;if(!r)return void this._setError(this._err("no-service-worker","Service Worker is required to show this notification but is unavailable."));const n=this._gen;this._swTags.add(i),r.ready.then(i=>i.showNotification(t,e)).then(()=>{n===this._gen&&this._emit("show",{tag:i,data:s,action:""})}).catch(()=>{n===this._gen&&this._setError(this._err("show-failed","ServiceWorkerRegistration.showNotification() failed."))})}_closeSw(t){const e=navigator.serviceWorker;e&&e.ready.then(e=>e.getNotifications({tag:t}).then(t=>{for(const e of t)e.close()})).catch(()=>{})}_subscribeClicks(){if(this._clicksSubscribed)return;this._clicksSubscribed=!0,"function"==typeof BroadcastChannel&&(this._channel=new BroadcastChannel("wcs-notify"),this._channel.addEventListener("message",this._onInbound));const t=navigator.serviceWorker;t&&(this._serviceWorker=t,t.addEventListener("message",this._onInbound))}_onInbound=t=>{const e=t.data;e&&!0===e.__wcsNotify&&(this._isDuplicate(e.id)||this._emit("click",{tag:e.tag,data:this._unwrap(e.data),action:e.action}))};_isDuplicate(t){return!!this._seenIds.includes(t)||(this._seenIds.push(t),this._seenIds.length>50&&this._seenIds.shift(),!1)}_unwrap(t){return null!==t&&"object"==typeof t&&"__wcsId"in t?t.payload:t}_api(){const t=globalThis;return"function"==typeof t.Notification?t.Notification:void 0}_nextId(){return"wcs-"+ ++this._idSeq}_err(t,e){return{error:t,message:e}}}let a=!1;function c(t){const e=t.target;if(!(e instanceof Element))return;let i;try{i=e.closest(`[${r.triggerAttribute}]`)}catch{return}if(!i)return;const s=i.getAttribute(r.triggerAttribute);if(!s)return;const n=customElements.get(r.tagNames.notify),o=document.getElementById(s);if(!(n&&o instanceof n))return;const a=i.getAttribute("data-notifytitle"),c=null!==a?a:i.textContent.trim(),h=i.getAttribute("data-notifybody");o.notify(c,null!==h?{body:h}:void 0)}class h extends HTMLElement{static hasConnectedCallbackPromise=!0;static wcBindable={...o.wcBindable,inputs:[{name:"notice"},{name:"mode",attribute:"mode"},{name:"body",attribute:"body"},{name:"icon",attribute:"icon"},{name:"badge",attribute:"badge"},{name:"tag",attribute:"tag"},{name:"lang",attribute:"lang"},{name:"dir",attribute:"dir"},{name:"requireInteraction",attribute:"require-interaction"},{name:"silent",attribute:"silent"},{name:"renotify",attribute:"renotify"},{name:"manual",attribute:"manual"}],commands:o.wcBindable.commands};_core;_notice="";_connectedCallbackPromise=Promise.resolve();_internals=null;constructor(){super(),this._core=new o(this),this._internals=this._initInternals(),this._wireStates({"wcs-notify:permission-change":t=>({granted:"granted"===t,denied:"denied"===t,prompt:"prompt"===t,unsupported:"unsupported"===t}),"wcs-notify:error":t=>({error:null!=t})})}get debugStates(){return this._internals?[...this._internals.states]:[]}_initInternals(){try{if("function"!=typeof this.attachInternals)return null;const t=this.attachInternals();return t.states.add("wcs-probe"),t.states.delete("wcs-probe"),t}catch{return null}}_wireStates(t){if(null===this._internals)return;const e=this._internals.states;for(const[i,s]of Object.entries(t))this.addEventListener(i,t=>{const i=this.hasAttribute("debug-states");for(const[r,n]of Object.entries(s(t.detail))){try{n?e.add(r):e.delete(r)}catch{}i&&this.toggleAttribute(`data-wcs-state-${r}`,n)}})}get mode(){const t=this.getAttribute("mode");return"sw"===t||"constructor"===t?t:"auto"}set mode(t){this.setAttribute("mode",t)}get body(){return this.getAttribute("body")??""}set body(t){this._reflect("body",t)}get icon(){return this.getAttribute("icon")??""}set icon(t){this._reflect("icon",t)}get badge(){return this.getAttribute("badge")??""}set badge(t){this._reflect("badge",t)}get tag(){return this.getAttribute("tag")??""}set tag(t){this._reflect("tag",t)}get lang(){return this.getAttribute("lang")??""}set lang(t){this._reflect("lang",t)}get dir(){return this.getAttribute("dir")??""}set dir(t){this._reflect("dir",t)}get requireInteraction(){return this.hasAttribute("require-interaction")}set requireInteraction(t){this._reflectBool("require-interaction",t)}get silent(){return this.hasAttribute("silent")}set silent(t){this._reflectBool("silent",t)}get renotify(){return this.hasAttribute("renotify")}set renotify(t){this._reflectBool("renotify",t)}get manual(){return this.hasAttribute("manual")}set manual(t){this._reflectBool("manual",t)}get notice(){return this._notice}set notice(t){if(null==t)return;if(this.manual)return;const e=String(t);e!==this._notice&&(this._notice=e,this.notify(e))}get permission(){return this._core.permission}get granted(){return this._core.granted}get denied(){return this._core.denied}get prompt(){return this._core.prompt}get unsupported(){return this._core.unsupported}get error(){return this._core.error}get clicked(){return this._core.clicked}get closed(){return this._core.closed}get shown(){return this._core.shown}get connectedCallbackPromise(){return this._connectedCallbackPromise}request(){return this._core.request()}notify(t,e){return this._core.notify(t,{...this._options(),...e??{}})}close(t){this._core.close(t)}closeAll(){this._core.closeAll()}_reflect(t,e){null==e?this.removeAttribute(t):this.setAttribute(t,String(e))}_reflectBool(t,e){e?this.setAttribute(t,""):this.removeAttribute(t)}_options(){const t={};return""!==this.body&&(t.body=this.body),""!==this.icon&&(t.icon=this.icon),""!==this.badge&&(t.badge=this.badge),""!==this.tag&&(t.tag=this.tag),""!==this.lang&&(t.lang=this.lang),"auto"!==this.dir&&"ltr"!==this.dir&&"rtl"!==this.dir||(t.dir=this.dir),this.requireInteraction&&(t.requireInteraction=!0),this.silent&&(t.silent=!0),this.renotify&&(t.renotify=!0),t}connectedCallback(){this.style.display="none",r.autoTrigger&&(a||(a=!0,document.addEventListener("click",c))),this._connectedCallbackPromise=this._core.observe(this.mode)}disconnectedCallback(){this._core.dispose()}}function l(e){var i;e&&("boolean"==typeof(i=e).autoTrigger&&(t.autoTrigger=i.autoTrigger),"string"==typeof i.triggerAttribute&&(t.triggerAttribute=i.triggerAttribute),i.tagNames&&Object.assign(t.tagNames,i.tagNames),s=null),customElements.get(r.tagNames.notify)||customElements.define(r.tagNames.notify,h)}export{o as NotificationCore,h as WcsNotify,l as bootstrapNotification,n as getConfig};
1
+ const t={autoTrigger:!0,triggerAttribute:"data-notifytarget",tagNames:{notify:"wcs-notify"}};function e(t){if(null===t||"object"!=typeof t)return t;Object.freeze(t);for(const i of Object.keys(t))e(t[i]);return t}function i(t){if(null===t||"object"!=typeof t)return t;const e={};for(const s of Object.keys(t))e[s]=i(t[s]);return e}let s=null;const r=t;function n(){return s||(s=e(i(t))),s}const o={CapabilityMissing:"capability-missing",NotAllowed:"not-allowed",InvalidArgument:"invalid-argument",ShowFailed:"show-failed",NoServiceWorker:"no-service-worker",NotifyError:"notify-error"};class a extends EventTarget{static wcBindable={protocol:"wc-bindable",version:1,properties:[{name:"permission",event:"wcs-notify:permission-change"},{name:"granted",event:"wcs-notify:permission-change",getter:t=>"granted"===t.detail},{name:"denied",event:"wcs-notify:permission-change",getter:t=>"denied"===t.detail},{name:"prompt",event:"wcs-notify:permission-change",getter:t=>"prompt"===t.detail},{name:"unsupported",event:"wcs-notify:permission-change",getter:t=>"unsupported"===t.detail},{name:"error",event:"wcs-notify:error"},{name:"errorInfo",event:"wcs-notify:error-info-changed"},{name:"clicked",event:"wcs-notify:click",getter:t=>t.detail},{name:"closed",event:"wcs-notify:close",getter:t=>t.detail},{name:"shown",event:"wcs-notify:show",getter:t=>t.detail}],commands:[{name:"request",async:!0},{name:"notify"},{name:"close"},{name:"closeAll"}]};_target;_mode="auto";_permission="prompt";_error=null;_errorInfo=null;_lastClick=null;_lastClose=null;_lastShow=null;_permissionStatus=null;_permissionSubscribed=!1;_gen=0;_ready=Promise.resolve();_idSeq=0;_constructed=new Map;_swTags=new Set;_channel=null;_serviceWorker=null;_clicksSubscribed=!1;_seenIds=[];constructor(t){super(),this._target=t??this}get permission(){return this._permission}get granted(){return"granted"===this._permission}get denied(){return"denied"===this._permission}get prompt(){return"prompt"===this._permission}get unsupported(){return"unsupported"===this._permission}get error(){return this._error}get errorInfo(){return this._errorInfo}get clicked(){return this._lastClick}get closed(){return this._lastClose}get shown(){return this._lastShow}get ready(){return this._ready}_setPermission(t){this._permission!==t&&(this._permission=t,this._target.dispatchEvent(new CustomEvent("wcs-notify:permission-change",{detail:t,bubbles:!0})))}_setError(t){this._error!==t&&(this._error=t,this._commitErrorInfo(null===t?null:function(t){const{error:e,message:i}=t;switch(e){case"unsupported":return{code:o.CapabilityMissing,phase:"probe",recoverable:!1,message:i};case"not-granted":return{code:o.NotAllowed,phase:"start",recoverable:!1,message:i};case"invalid-title":return{code:o.InvalidArgument,phase:"start",recoverable:!1,message:i};case"show-failed":return{code:o.ShowFailed,phase:"execute",recoverable:!1,message:i};case"no-service-worker":return{code:o.NoServiceWorker,phase:"execute",recoverable:!1,message:i};default:return{code:o.NotifyError,phase:"execute",recoverable:!1,message:i}}}(t)),this._target.dispatchEvent(new CustomEvent("wcs-notify:error",{detail:t,bubbles:!0})))}_commitErrorInfo(t){this._errorInfo=t,this._target.dispatchEvent(new CustomEvent("wcs-notify:error-info-changed",{detail:t,bubbles:!0}))}_emit(t,e){"click"===t?this._lastClick=e:"close"===t?this._lastClose=e:this._lastShow=e,this._target.dispatchEvent(new CustomEvent(`wcs-notify:${t}`,{detail:e,bubbles:!0}))}observe(t="auto"){return this._mode=t,this._permissionSubscribed||(this._ready=this._initPermission(),this._subscribeClicks()),this._ready}async request(){const t=this._api();if(!t||"function"!=typeof t.requestPermission)return this._setPermission("unsupported"),this._permission;try{const e=await t.requestPermission();this._setPermission(this._normalize(e))}catch{}return this._permission}notify(t,e={}){if(!this._api())return this._setError(this._err("unsupported","Notifications API is not available in this environment.")),"";if("granted"!==this._permission)return this._setError(this._err("not-granted","Notification permission is not granted; call request() first.")),"";if("string"!=typeof t)return this._setError(this._err("invalid-title","notify() requires a string title.")),"";const i="string"==typeof e.tag&&""!==e.tag?e.tag:this._nextId(),s=e.data,r={__wcsId:i,payload:s},n={...e,tag:i,data:r};return this._setError(null),this._show(t,n,i,s),i}close(t){if("string"!=typeof t||""===t)return;const e=this._constructed.get(t);e&&(e.close(),this._constructed.delete(t)),this._swTags.has(t)&&(this._closeSw(t),this._swTags.delete(t))}closeAll(){for(const t of this._constructed.values())t.close();this._constructed.clear();for(const t of this._swTags)this._closeSw(t);this._swTags.clear()}dispose(){this._permissionSubscribed=!1,this._clicksSubscribed=!1,this._gen++,this._permissionStatus&&(this._permissionStatus.removeEventListener("change",this._onPermissionChange),this._permissionStatus=null),this._channel&&(this._channel.removeEventListener("message",this._onInbound),this._channel.close(),this._channel=null),this._serviceWorker&&(this._serviceWorker.removeEventListener("message",this._onInbound),this._serviceWorker=null)}_initPermission(){const t=this._api();if(!t)return this._setPermission("unsupported"),Promise.resolve();if(this._permissionSubscribed=!0,"undefined"!=typeof navigator&&navigator.permissions&&"function"==typeof navigator.permissions.query){const e=++this._gen;return navigator.permissions.query({name:"notifications"}).then(t=>{e===this._gen&&(this._permissionStatus=t,this._setPermission(this._normalize(t.state)),t.addEventListener("change",this._onPermissionChange))},()=>{e===this._gen&&this._setPermission(this._normalize(t.permission))})}return this._setPermission(this._normalize(t.permission)),Promise.resolve()}_onPermissionChange=t=>{const e=t.target;this._setPermission(this._normalize(e.state))};_normalize(t){return"default"===t?"prompt":"granted"===t||"denied"===t||"prompt"===t?t:"prompt"}_show(t,e,i,s){if("sw"===this._mode)return void this._showViaSw(t,e,i,s);this._showViaConstructor(t,e,i,s)||("auto"===this._mode?this._showViaSw(t,e,i,s):this._setError(this._err("show-failed",'new Notification() is not usable here and mode="constructor" disallows the Service Worker fallback.')))}_showViaConstructor(t,e,i,s){const r=this._api(),n=this._gen;let o;try{o=new r(t,e)}catch(t){return!(t instanceof TypeError)&&(this._setError(this._err("show-failed","Failed to create the notification.")),!0)}return this._constructed.set(i,o),o.onshow=()=>{n===this._gen&&this._emit("show",{tag:i,data:s,action:""})},o.onclick=()=>{n===this._gen&&this._emit("click",{tag:i,data:s,action:""})},o.onclose=()=>{this._constructed.delete(i),n===this._gen&&this._emit("close",{tag:i,data:s,action:""})},o.onerror=()=>{n===this._gen&&this._setError(this._err("show-failed","The notification failed to display."))},!0}_showViaSw(t,e,i,s){const r=navigator.serviceWorker;if(!r)return void this._setError(this._err("no-service-worker","Service Worker is required to show this notification but is unavailable."));const n=this._gen;this._swTags.add(i),r.ready.then(i=>i.showNotification(t,e)).then(()=>{n===this._gen&&this._emit("show",{tag:i,data:s,action:""})}).catch(()=>{n===this._gen&&this._setError(this._err("show-failed","ServiceWorkerRegistration.showNotification() failed."))})}_closeSw(t){const e=navigator.serviceWorker;e&&e.ready.then(e=>e.getNotifications({tag:t}).then(t=>{for(const e of t)e.close()})).catch(()=>{})}_subscribeClicks(){if(this._clicksSubscribed)return;this._clicksSubscribed=!0,"function"==typeof BroadcastChannel&&(this._channel=new BroadcastChannel("wcs-notify"),this._channel.addEventListener("message",this._onInbound));const t=navigator.serviceWorker;t&&(this._serviceWorker=t,t.addEventListener("message",this._onInbound))}_onInbound=t=>{const e=t.data;e&&!0===e.__wcsNotify&&(this._isDuplicate(e.id)||this._emit("click",{tag:e.tag,data:this._unwrap(e.data),action:e.action}))};_isDuplicate(t){return!!this._seenIds.includes(t)||(this._seenIds.push(t),this._seenIds.length>50&&this._seenIds.shift(),!1)}_unwrap(t){return null!==t&&"object"==typeof t&&"__wcsId"in t?t.payload:t}_api(){const t=globalThis;return"function"==typeof t.Notification?t.Notification:void 0}_nextId(){return"wcs-"+ ++this._idSeq}_err(t,e){return{error:t,message:e}}}let c=!1;function h(t){const e=t.target;if(!(e instanceof Element))return;let i;try{i=e.closest(`[${r.triggerAttribute}]`)}catch{return}if(!i)return;const s=i.getAttribute(r.triggerAttribute);if(!s)return;const n=customElements.get(r.tagNames.notify),o=document.getElementById(s);if(!(n&&o instanceof n))return;const a=i.getAttribute("data-notifytitle"),c=null!==a?a:i.textContent.trim(),h=i.getAttribute("data-notifybody");o.notify(c,null!==h?{body:h}:void 0)}class l extends HTMLElement{static hasConnectedCallbackPromise=!0;static wcBindable={...a.wcBindable,inputs:[{name:"notice"},{name:"mode",attribute:"mode"},{name:"body",attribute:"body"},{name:"icon",attribute:"icon"},{name:"badge",attribute:"badge"},{name:"tag",attribute:"tag"},{name:"lang",attribute:"lang"},{name:"dir",attribute:"dir"},{name:"requireInteraction",attribute:"require-interaction"},{name:"silent",attribute:"silent"},{name:"renotify",attribute:"renotify"},{name:"manual",attribute:"manual"}],commands:a.wcBindable.commands};_core;_notice="";_connectedCallbackPromise=Promise.resolve();_internals=null;constructor(){super(),this._core=new a(this),this._internals=this._initInternals(),this._wireStates({"wcs-notify:permission-change":t=>({granted:"granted"===t,denied:"denied"===t,prompt:"prompt"===t,unsupported:"unsupported"===t}),"wcs-notify:error":t=>({error:null!=t})})}get debugStates(){return this._internals?[...this._internals.states]:[]}_initInternals(){try{if("function"!=typeof this.attachInternals)return null;const t=this.attachInternals();return t.states.add("wcs-probe"),t.states.delete("wcs-probe"),t}catch{return null}}_wireStates(t){if(null===this._internals)return;const e=this._internals.states;for(const[i,s]of Object.entries(t))this.addEventListener(i,t=>{const i=this.hasAttribute("debug-states");for(const[r,n]of Object.entries(s(t.detail))){try{n?e.add(r):e.delete(r)}catch{}i&&this.toggleAttribute(`data-wcs-state-${r}`,n)}})}get mode(){const t=this.getAttribute("mode");return"sw"===t||"constructor"===t?t:"auto"}set mode(t){this.setAttribute("mode",t)}get body(){return this.getAttribute("body")??""}set body(t){this._reflect("body",t)}get icon(){return this.getAttribute("icon")??""}set icon(t){this._reflect("icon",t)}get badge(){return this.getAttribute("badge")??""}set badge(t){this._reflect("badge",t)}get tag(){return this.getAttribute("tag")??""}set tag(t){this._reflect("tag",t)}get lang(){return this.getAttribute("lang")??""}set lang(t){this._reflect("lang",t)}get dir(){return this.getAttribute("dir")??""}set dir(t){this._reflect("dir",t)}get requireInteraction(){return this.hasAttribute("require-interaction")}set requireInteraction(t){this._reflectBool("require-interaction",t)}get silent(){return this.hasAttribute("silent")}set silent(t){this._reflectBool("silent",t)}get renotify(){return this.hasAttribute("renotify")}set renotify(t){this._reflectBool("renotify",t)}get manual(){return this.hasAttribute("manual")}set manual(t){this._reflectBool("manual",t)}get notice(){return this._notice}set notice(t){if(null==t)return;if(this.manual)return;const e=String(t);e!==this._notice&&(this._notice=e,this.notify(e))}get permission(){return this._core.permission}get granted(){return this._core.granted}get denied(){return this._core.denied}get prompt(){return this._core.prompt}get unsupported(){return this._core.unsupported}get error(){return this._core.error}get errorInfo(){return this._core.errorInfo}get clicked(){return this._core.clicked}get closed(){return this._core.closed}get shown(){return this._core.shown}get connectedCallbackPromise(){return this._connectedCallbackPromise}request(){return this._core.request()}notify(t,e){return this._core.notify(t,{...this._options(),...e??{}})}close(t){this._core.close(t)}closeAll(){this._core.closeAll()}_reflect(t,e){null==e?this.removeAttribute(t):this.setAttribute(t,String(e))}_reflectBool(t,e){e?this.setAttribute(t,""):this.removeAttribute(t)}_options(){const t={};return""!==this.body&&(t.body=this.body),""!==this.icon&&(t.icon=this.icon),""!==this.badge&&(t.badge=this.badge),""!==this.tag&&(t.tag=this.tag),""!==this.lang&&(t.lang=this.lang),"auto"!==this.dir&&"ltr"!==this.dir&&"rtl"!==this.dir||(t.dir=this.dir),this.requireInteraction&&(t.requireInteraction=!0),this.silent&&(t.silent=!0),this.renotify&&(t.renotify=!0),t}connectedCallback(){this.style.display="none",r.autoTrigger&&(c||(c=!0,document.addEventListener("click",h))),this._connectedCallbackPromise=this._core.observe(this.mode)}disconnectedCallback(){this._core.dispose()}}function u(e){var i;e&&("boolean"==typeof(i=e).autoTrigger&&(t.autoTrigger=i.autoTrigger),"string"==typeof i.triggerAttribute&&(t.triggerAttribute=i.triggerAttribute),i.tagNames&&Object.assign(t.tagNames,i.tagNames),s=null),customElements.get(r.tagNames.notify)||customElements.define(r.tagNames.notify,l)}export{a as NotificationCore,o as WCS_NOTIFY_ERROR_CODE,l as WcsNotify,u as bootstrapNotification,n as getConfig};
2
2
  //# sourceMappingURL=index.esm.min.js.map
@@ -1 +1 @@
1
- {"version":3,"file":"index.esm.min.js","sources":["../src/config.ts","../src/core/NotificationCore.ts","../src/autoTrigger.ts","../src/components/Notify.ts","../src/bootstrapNotification.ts","../src/registerComponents.ts"],"sourcesContent":["import { IConfig, IWritableConfig } from \"./types.js\";\n\ninterface IInternalConfig extends IConfig {\n autoTrigger: boolean;\n triggerAttribute: string;\n tagNames: {\n notify: string;\n };\n}\n\nconst _config: IInternalConfig = {\n autoTrigger: true,\n triggerAttribute: \"data-notifytarget\",\n tagNames: {\n notify: \"wcs-notify\",\n },\n};\n\nfunction deepFreeze<T>(obj: T): T {\n if (obj === null || typeof obj !== \"object\") return obj;\n Object.freeze(obj);\n for (const key of Object.keys(obj)) {\n deepFreeze((obj as Record<string, unknown>)[key]);\n }\n return obj;\n}\n\nfunction deepClone<T>(obj: T): T {\n if (obj === null || typeof obj !== \"object\") return obj;\n const clone: Record<string, unknown> = {};\n for (const key of Object.keys(obj)) {\n clone[key] = deepClone((obj as Record<string, unknown>)[key]);\n }\n return clone as T;\n}\n\nlet frozenConfig: IConfig | null = null;\n\n// Internal, mutable live config used by the components/autoTrigger (they read it\n// at call time so setConfig() takes effect without re-import). Typed as the\n// readonly IConfig at the export boundary — the `as IConfig` is a compile-time\n// view only and does NOT freeze the object, so this export must stay\n// package-internal (it is not re-exported from exports.ts). Public consumers get\n// the deep-frozen clone from getConfig() instead.\nexport const config: IConfig = _config as IConfig;\n\nexport function getConfig(): IConfig {\n if (!frozenConfig) {\n frozenConfig = deepFreeze(deepClone(_config));\n }\n return frozenConfig;\n}\n\nexport function setConfig(partialConfig: IWritableConfig): void {\n if (typeof partialConfig.autoTrigger === \"boolean\") {\n _config.autoTrigger = partialConfig.autoTrigger;\n }\n if (typeof partialConfig.triggerAttribute === \"string\") {\n _config.triggerAttribute = partialConfig.triggerAttribute;\n }\n if (partialConfig.tagNames) {\n Object.assign(_config.tagNames, partialConfig.tagNames);\n }\n frozenConfig = null;\n}\n","import {\n IWcBindable, NotifyBackend, NotifyOptions, NotificationPermissionRaw,\n PermissionStateOrUnsupported, WcsNotifyClickDetail, WcsNotifyErrorDetail,\n} from \"../types.js\";\n\n// Wrapper stored in a notification's `data` so the Service Worker side (a\n// separate global scope with no access to this instance) can recover the\n// identity and the caller's payload. The constructor backend uses the same\n// wrapper for uniformity, and both paths unwrap it before emitting.\ninterface WcsNotifyData {\n __wcsId: string;\n payload: unknown;\n}\n\n// Message shape posted by `wireNotificationClicks()` (src/sw.ts) over both\n// BroadcastChannel and clients.postMessage. `id` is unique per click\n// (`tag#seq`), so the two transports delivering the *same* click de-dup, while\n// two genuine clicks on the same `tag` do not.\ninterface WcsNotifyInbound {\n __wcsNotify: true;\n id: string;\n tag: string;\n data: unknown;\n action: string;\n}\n\n/**\n * Headless desktop-notification primitive. A thin, framework-agnostic wrapper\n * around the Notifications API exposed through the wc-bindable protocol.\n *\n * Unlike `@wcstack/permission` (a read-only monitor — the Permissions API has no\n * `request()`), the Notifications API *does* expose `Notification.requestPermission()`,\n * so this node is self-contained: it both **requests/monitors** the permission and\n * **shows** notifications. It is the first @wcstack node where the command-token\n * (show: `notify`) and event-token (`click` / `close` / `show`) directions both\n * live in one tag.\n *\n * - **request()** asks for the `notifications` permission (`Notification.requestPermission`).\n * - **notify(title, options)** shows a notification and returns its identifying tag\n * (a caller `options.tag`, or a generated `wcs-<n>`). It picks a backend per\n * `mode`: the `Notification` constructor (desktop) or\n * `ServiceWorkerRegistration.showNotification()` (mobile). `\"auto\"` prefers the\n * constructor and falls back to the SW on a `TypeError`.\n * - **close(tag) / closeAll()** dismiss notifications by tag / all.\n * - Clicks flow back as the `wcs-notify:click` event: directly via the\n * Notification's `onclick` (constructor), or via the SW helper's\n * BroadcastChannel/postMessage relay (SW). `permission` mirrors the live grant.\n *\n * Failures never throw: they surface through `error` (and the `unsupported`\n * permission state) so they flow into the declarative state.\n */\nexport class NotificationCore extends EventTarget {\n static wcBindable: IWcBindable = {\n protocol: \"wc-bindable\",\n version: 1,\n properties: [\n { name: \"permission\", event: \"wcs-notify:permission-change\" },\n { name: \"granted\", event: \"wcs-notify:permission-change\", getter: (e: Event) => (e as CustomEvent).detail === \"granted\" },\n { name: \"denied\", event: \"wcs-notify:permission-change\", getter: (e: Event) => (e as CustomEvent).detail === \"denied\" },\n { name: \"prompt\", event: \"wcs-notify:permission-change\", getter: (e: Event) => (e as CustomEvent).detail === \"prompt\" },\n { name: \"unsupported\", event: \"wcs-notify:permission-change\", getter: (e: Event) => (e as CustomEvent).detail === \"unsupported\" },\n { name: \"error\", event: \"wcs-notify:error\" },\n { name: \"clicked\", event: \"wcs-notify:click\", getter: (e: Event) => (e as CustomEvent).detail },\n { name: \"closed\", event: \"wcs-notify:close\", getter: (e: Event) => (e as CustomEvent).detail },\n { name: \"shown\", event: \"wcs-notify:show\", getter: (e: Event) => (e as CustomEvent).detail },\n ],\n commands: [\n { name: \"request\", async: true },\n { name: \"notify\" },\n { name: \"close\" },\n { name: \"closeAll\" },\n ],\n };\n\n private _target: EventTarget;\n private _mode: NotifyBackend = \"auto\";\n\n private _permission: PermissionStateOrUnsupported = \"prompt\";\n private _error: WcsNotifyErrorDetail | null = null;\n private _lastClick: WcsNotifyClickDetail | null = null;\n private _lastClose: WcsNotifyClickDetail | null = null;\n private _lastShow: WcsNotifyClickDetail | null = null;\n\n // Live PermissionStatus (when the Permissions API can query `notifications`),\n // kept so its `change` listener can be removed on dispose().\n private _permissionStatus: PermissionStatus | null = null;\n // True once a permission subscription has been (or is being) established; reset\n // by dispose(). Guards observe() so a reconnect re-queries while a redundant\n // observe() on a live subscription does not.\n private _permissionSubscribed: boolean = false;\n\n // Monotonic id of the current lifecycle. Bumped by every observe() and by\n // dispose(). In-flight async work (permission query, SW show, inbound click)\n // captures it and bails if stale, so a query/click that resolves after a\n // disconnect — or after a rapid disconnect→reconnect — never mutates state or\n // dispatches on a torn-down element.\n private _gen: number = 0;\n\n // Resolves once the connect-time permission probe settles. The Shell exposes\n // this as connectedCallbackPromise so SSR can await it before snapshotting.\n private _ready: Promise<void> = Promise.resolve();\n\n // Counter for auto-assigned tags when the caller omits one.\n private _idSeq: number = 0;\n\n // Notifications created via the constructor backend, by tag, so close()/closeAll()\n // can dismiss them. The SW backend has no handle (showNotification returns void),\n // so its tags are tracked separately and closed via registration.getNotifications().\n private _constructed: Map<string, Notification> = new Map();\n private _swTags: Set<string> = new Set();\n\n // Click subscription handles (SW relay).\n private _channel: BroadcastChannel | null = null;\n private _serviceWorker: ServiceWorkerContainer | null = null;\n private _clicksSubscribed: boolean = false;\n // Per-click ids already handled, to de-dup the two relay transports. FIFO-capped\n // so a long session does not leak; the two transports always arrive in the same\n // tick, so a small cap is ample.\n private _seenIds: string[] = [];\n\n constructor(target?: EventTarget) {\n super();\n this._target = target ?? this;\n }\n\n get permission(): PermissionStateOrUnsupported {\n return this._permission;\n }\n\n get granted(): boolean {\n return this._permission === \"granted\";\n }\n\n get denied(): boolean {\n return this._permission === \"denied\";\n }\n\n get prompt(): boolean {\n return this._permission === \"prompt\";\n }\n\n get unsupported(): boolean {\n return this._permission === \"unsupported\";\n }\n\n get error(): WcsNotifyErrorDetail | null {\n return this._error;\n }\n\n get clicked(): WcsNotifyClickDetail | null {\n return this._lastClick;\n }\n\n get closed(): WcsNotifyClickDetail | null {\n return this._lastClose;\n }\n\n get shown(): WcsNotifyClickDetail | null {\n return this._lastShow;\n }\n\n /** Resolves once the current (or initial) permission probe settles. */\n get ready(): Promise<void> {\n return this._ready;\n }\n\n // --- State setters with event dispatch ---\n\n private _setPermission(state: PermissionStateOrUnsupported): void {\n if (this._permission === state) return;\n this._permission = state;\n this._target.dispatchEvent(new CustomEvent(\"wcs-notify:permission-change\", {\n detail: state,\n bubbles: true,\n }));\n }\n\n private _setError(error: WcsNotifyErrorDetail | null): void {\n if (this._error === error) return;\n this._error = error;\n this._target.dispatchEvent(new CustomEvent(\"wcs-notify:error\", {\n detail: error,\n bubbles: true,\n }));\n }\n\n private _emit(kind: \"click\" | \"close\" | \"show\", detail: WcsNotifyClickDetail): void {\n if (kind === \"click\") this._lastClick = detail;\n else if (kind === \"close\") this._lastClose = detail;\n else this._lastShow = detail;\n this._target.dispatchEvent(new CustomEvent(`wcs-notify:${kind}`, {\n detail,\n bubbles: true,\n }));\n }\n\n // --- Public API ---\n\n /**\n * Start observing the `notifications` permission and subscribing to Service\n * Worker click relays. `mode` selects the show backend (default `\"auto\"`).\n * Idempotent while already subscribed: it only updates the stored mode; to\n * restart, dispose() first. Returns a promise that resolves once the first\n * permission probe settles, for SSR.\n *\n * Headless callers must call observe() to begin; the Shell calls it from\n * connectedCallback once the element's attributes resolve.\n */\n observe(mode: NotifyBackend = \"auto\"): Promise<void> {\n this._mode = mode;\n if (!this._permissionSubscribed) {\n this._ready = this._initPermission();\n this._subscribeClicks();\n }\n return this._ready;\n }\n\n /**\n * Ask the user for the `notifications` permission. Resolves to the resulting\n * (normalized) permission state. Never throws: an unavailable API resolves to\n * `\"unsupported\"`.\n */\n async request(): Promise<PermissionStateOrUnsupported> {\n const api = this._api();\n if (!api || typeof api.requestPermission !== \"function\") {\n this._setPermission(\"unsupported\");\n return this._permission;\n }\n try {\n const result = await api.requestPermission();\n this._setPermission(this._normalize(result));\n } catch {\n // Some legacy engines may reject; keep the current state rather than throw.\n }\n return this._permission;\n }\n\n /**\n * Show a notification. Returns the identifying tag (the caller's `options.tag`,\n * or a generated `wcs-<n>` when omitted). Never throws: when the API is\n * unavailable or the permission is not granted it surfaces an `error` and\n * returns an empty string.\n */\n notify(title: string, options: NotifyOptions = {}): string {\n if (!this._api()) {\n this._setError(this._err(\"unsupported\", \"Notifications API is not available in this environment.\"));\n return \"\";\n }\n if (this._permission !== \"granted\") {\n this._setError(this._err(\"not-granted\", \"Notification permission is not granted; call request() first.\"));\n return \"\";\n }\n if (typeof title !== \"string\") {\n this._setError(this._err(\"invalid-title\", \"notify() requires a string title.\"));\n return \"\";\n }\n\n const tag = (typeof options.tag === \"string\" && options.tag !== \"\") ? options.tag : this._nextId();\n const payload = options.data;\n const data: WcsNotifyData = { __wcsId: tag, payload };\n const backendOptions: NotifyOptions = { ...options, tag, data };\n\n this._setError(null);\n this._show(title, backendOptions, tag, payload);\n return tag;\n }\n\n /** Dismiss the notification(s) with `tag` across both backends. */\n close(tag?: string): void {\n if (typeof tag !== \"string\" || tag === \"\") return;\n const n = this._constructed.get(tag);\n if (n) {\n n.close();\n this._constructed.delete(tag);\n }\n if (this._swTags.has(tag)) {\n this._closeSw(tag);\n this._swTags.delete(tag);\n }\n }\n\n /**\n * Dismiss every notification this instance has shown. Scoped to this instance's\n * own tags on both backends — the SW path closes each tracked tag individually\n * rather than enumerating the whole origin, so it never dismisses notifications\n * shown by another `<wcs-notify>` or by an unrelated code path.\n */\n closeAll(): void {\n for (const n of this._constructed.values()) {\n n.close();\n }\n this._constructed.clear();\n for (const tag of this._swTags) {\n this._closeSw(tag);\n }\n this._swTags.clear();\n }\n\n /**\n * Detach permission and click subscriptions. Open notifications are intentionally\n * **left on screen** (a notification outlives the page that posted it — that is\n * the point); use close()/closeAll() to dismiss. Call from the Shell's\n * disconnectedCallback. A later observe() resumes.\n */\n dispose(): void {\n this._permissionSubscribed = false;\n this._clicksSubscribed = false;\n this._gen++;\n if (this._permissionStatus) {\n this._permissionStatus.removeEventListener(\"change\", this._onPermissionChange);\n this._permissionStatus = null;\n }\n if (this._channel) {\n this._channel.removeEventListener(\"message\", this._onInbound);\n this._channel.close();\n this._channel = null;\n }\n if (this._serviceWorker) {\n this._serviceWorker.removeEventListener(\"message\", this._onInbound);\n this._serviceWorker = null;\n }\n }\n\n // --- Internal: permission ---\n\n private _initPermission(): Promise<void> {\n const api = this._api();\n if (!api) {\n this._setPermission(\"unsupported\");\n // Intentionally does NOT set _permissionSubscribed: there is no permission\n // listener to tear down, so a reconnect simply re-probes (idempotent — the\n // same-value guard suppresses any redundant dispatch and no listener is ever\n // attached). _subscribeClicks() is re-entered too, but its own\n // _clicksSubscribed guard short-circuits the second pass, so no transport is\n // double-subscribed. Mirrors @wcstack/permission's unsupported path.\n return Promise.resolve();\n }\n this._permissionSubscribed = true;\n // Prefer the Permissions API: it provides a live `change` event. Fall back to\n // the static `Notification.permission` when it is absent or rejects the\n // `notifications` descriptor.\n if (typeof navigator !== \"undefined\" && navigator.permissions && typeof navigator.permissions.query === \"function\") {\n const gen = ++this._gen;\n return navigator.permissions.query({ name: \"notifications\" }).then(\n (status) => {\n if (gen !== this._gen) return;\n this._permissionStatus = status;\n this._setPermission(this._normalize(status.state as NotificationPermissionRaw));\n status.addEventListener(\"change\", this._onPermissionChange);\n },\n () => {\n if (gen !== this._gen) return;\n // Permissions API rejected the `notifications` descriptor — fall back to\n // the static `Notification.permission` (api is in scope and non-null here).\n this._setPermission(this._normalize(api.permission));\n },\n );\n }\n // No Permissions API: read the static permission once (no live change events).\n this._setPermission(this._normalize(api.permission));\n return Promise.resolve();\n }\n\n private _onPermissionChange = (event: Event): void => {\n const status = event.target as PermissionStatus;\n this._setPermission(this._normalize(status.state as NotificationPermissionRaw));\n };\n\n // Normalize the Notifications API's `\"default\"` to `\"prompt\"` so this node shares\n // the four-value surface of @wcstack/permission. The Permissions API already\n // reports `\"prompt\"`, so it passes through unchanged.\n private _normalize(raw: NotificationPermissionRaw | string): PermissionStateOrUnsupported {\n if (raw === \"default\") return \"prompt\";\n if (raw === \"granted\" || raw === \"denied\" || raw === \"prompt\") return raw;\n return \"prompt\";\n }\n\n // --- Internal: showing ---\n\n private _show(title: string, options: NotifyOptions, tag: string, payload: unknown): void {\n if (this._mode === \"sw\") {\n this._showViaSw(title, options, tag, payload);\n return;\n }\n const handled = this._showViaConstructor(title, options, tag, payload);\n if (handled) return;\n // Constructor threw TypeError (e.g. mobile, where `new Notification` is illegal).\n if (this._mode === \"auto\") {\n this._showViaSw(title, options, tag, payload);\n } else {\n this._setError(this._err(\"show-failed\", \"new Notification() is not usable here and mode=\\\"constructor\\\" disallows the Service Worker fallback.\"));\n }\n }\n\n // Returns false only when the constructor threw a TypeError (the signal to fall\n // back to the SW backend); true when it showed or surfaced a non-TypeError error.\n private _showViaConstructor(title: string, options: NotifyOptions, tag: string, payload: unknown): boolean {\n const api = this._api()!;\n const gen = this._gen;\n let n: Notification;\n try {\n n = new api(title, options as NotificationOptions);\n } catch (e) {\n if (e instanceof TypeError) return false;\n this._setError(this._err(\"show-failed\", \"Failed to create the notification.\"));\n return true;\n }\n this._constructed.set(tag, n);\n n.onshow = (): void => {\n if (gen !== this._gen) return;\n this._emit(\"show\", { tag, data: payload, action: \"\" });\n };\n n.onclick = (): void => {\n if (gen !== this._gen) return;\n this._emit(\"click\", { tag, data: payload, action: \"\" });\n };\n n.onclose = (): void => {\n this._constructed.delete(tag);\n if (gen !== this._gen) return;\n this._emit(\"close\", { tag, data: payload, action: \"\" });\n };\n n.onerror = (): void => {\n if (gen !== this._gen) return;\n this._setError(this._err(\"show-failed\", \"The notification failed to display.\"));\n };\n return true;\n }\n\n private _showViaSw(title: string, options: NotifyOptions, tag: string, payload: unknown): void {\n const sw = navigator.serviceWorker as ServiceWorkerContainer | undefined;\n if (!sw) {\n this._setError(this._err(\"no-service-worker\", \"Service Worker is required to show this notification but is unavailable.\"));\n return;\n }\n const gen = this._gen;\n this._swTags.add(tag);\n // A notification deliberately outlives the page (see § dispose), so we do NOT\n // bail before showNotification on a stale gen — a notify() issued while\n // connected still shows. The stale-gen guards only suppress dispatching the\n // observable `show` / `error` back onto a torn-down element.\n sw.ready\n .then((registration) => registration.showNotification(title, options as NotificationOptions))\n .then(() => {\n if (gen !== this._gen) return;\n this._emit(\"show\", { tag, data: payload, action: \"\" });\n })\n .catch(() => {\n if (gen !== this._gen) return;\n this._setError(this._err(\"show-failed\", \"ServiceWorkerRegistration.showNotification() failed.\"));\n });\n }\n\n // Close the SW notification(s) carrying `tag`. Always scoped to a single tag —\n // both callers (close / closeAll) iterate their own tracked tags, so the whole\n // origin is never enumerated.\n private _closeSw(tag: string): void {\n const sw = navigator.serviceWorker as ServiceWorkerContainer | undefined;\n if (!sw) return;\n sw.ready.then((registration) => {\n return registration.getNotifications({ tag }).then((list) => {\n for (const n of list) n.close();\n });\n }).catch(() => {\n // Closing is best-effort; a failure to enumerate is not surfaced.\n });\n }\n\n // --- Internal: click relay (SW) ---\n\n private _subscribeClicks(): void {\n if (this._clicksSubscribed) return;\n this._clicksSubscribed = true;\n if (typeof BroadcastChannel === \"function\") {\n this._channel = new BroadcastChannel(\"wcs-notify\");\n this._channel.addEventListener(\"message\", this._onInbound);\n }\n const sw = navigator.serviceWorker as ServiceWorkerContainer | undefined;\n if (sw) {\n this._serviceWorker = sw;\n sw.addEventListener(\"message\", this._onInbound);\n }\n }\n\n private _onInbound = (event: Event): void => {\n const msg = (event as MessageEvent).data as WcsNotifyInbound | undefined;\n if (!msg || msg.__wcsNotify !== true) return;\n if (this._isDuplicate(msg.id)) return;\n this._emit(\"click\", { tag: msg.tag, data: this._unwrap(msg.data), action: msg.action });\n };\n\n private _isDuplicate(id: string): boolean {\n if (this._seenIds.includes(id)) return true;\n this._seenIds.push(id);\n if (this._seenIds.length > 50) this._seenIds.shift();\n return false;\n }\n\n private _unwrap(raw: unknown): unknown {\n if (raw !== null && typeof raw === \"object\" && \"__wcsId\" in raw) {\n return (raw as WcsNotifyData).payload;\n }\n return raw;\n }\n\n // --- Internal: misc ---\n\n // Resolve the global `Notification` constructor at call time (not cached) so\n // tests can install/remove it and so unsupported environments report correctly.\n private _api(): (typeof Notification) | undefined {\n const g = globalThis as unknown as { Notification?: typeof Notification };\n return typeof g.Notification === \"function\" ? g.Notification : undefined;\n }\n\n private _nextId(): string {\n return `wcs-${++this._idSeq}`;\n }\n\n private _err(error: string, message: string): WcsNotifyErrorDetail {\n return { error, message };\n }\n}\n","import { config } from \"./config.js\";\nimport type { WcsNotify } from \"./components/Notify.js\";\n\nlet registered = false;\n\nfunction handleClick(event: Event): void {\n const target = event.target;\n if (!(target instanceof Element)) return;\n\n // A misconfigured triggerAttribute (e.g. one with a space) makes the attribute\n // selector invalid and closest() throw SyntaxError; guard so a bad config\n // disables only this shortcut rather than killing every document click handler.\n let triggerElement: Element | null;\n try {\n triggerElement = target.closest<Element>(`[${config.triggerAttribute}]`);\n } catch {\n return;\n }\n if (!triggerElement) return;\n\n const notifyId = triggerElement.getAttribute(config.triggerAttribute);\n if (!notifyId) return;\n\n // Resolve the registered constructor at call time instead of importing Notify as\n // a value, avoiding a components/Notify.ts ⇄ autoTrigger.ts cycle\n // (Notify.connectedCallback() calls registerAutoTrigger()). instanceof against\n // the customElements registry keeps the same identity guarantee.\n const NotifyCtor = customElements.get(config.tagNames.notify);\n const notifyElement = document.getElementById(notifyId);\n if (!NotifyCtor || !(notifyElement instanceof NotifyCtor)) return;\n\n // The title comes from the trigger element: an explicit `data-notifytitle`\n // attribute wins, otherwise the element's trimmed text content. The body is an\n // optional `data-notifybody`. This keeps the click-driven shortcut declarative\n // without inventing a payload channel.\n const explicit = triggerElement.getAttribute(\"data-notifytitle\");\n // `Element.textContent` is spec-guaranteed non-null (only Document / DocumentType\n // nodes return null, never an Element), so the cast is sound and lets us avoid an\n // unreachable `?? \"\"` branch. `triggerElement` is always an Element here.\n const title = explicit !== null ? explicit : (triggerElement.textContent as string).trim();\n const body = triggerElement.getAttribute(\"data-notifybody\");\n\n (notifyElement as WcsNotify).notify(title, body !== null ? { body } : undefined);\n}\n\nexport function registerAutoTrigger(): void {\n if (registered) return;\n registered = true;\n document.addEventListener(\"click\", handleClick);\n}\n\nexport function unregisterAutoTrigger(): void {\n if (!registered) return;\n registered = false;\n document.removeEventListener(\"click\", handleClick);\n}\n","import { config } from \"../config.js\";\nimport {\n IWcBindable, NotifyBackend, NotifyOptions, PermissionStateOrUnsupported,\n WcsNotifyClickDetail, WcsNotifyErrorDetail,\n} from \"../types.js\";\nimport { NotificationCore } from \"../core/NotificationCore.js\";\nimport { registerAutoTrigger } from \"../autoTrigger.js\";\n\n/**\n * `<wcs-notify>` — declarative desktop notifications. Wraps NotificationCore and\n * exposes both directions in one tag:\n *\n * - **`notice`** (reactive input): writing a *changed* value shows a notification,\n * suppressing same-value writes so it fires only when the bound source actually\n * changes. The imperative `notify` command instead shows on demand (even the\n * same text again). See `docs/notification-tag-design.md` § 2.\n * - **`request` / `notify` / `close` / `closeAll`** commands (state → element).\n * - per-notification options (`body` / `icon` / `badge` / `tag` / `lang` / `dir` /\n * `require-interaction` / `silent` / `renotify`) as mirrored attributes.\n * - `mode` selects the show backend (`auto` / `sw` / `constructor`).\n * - the Core's observable surface (permission / granted / … / error / clicked /\n * closed / shown) via delegated getters; clicked/closed/shown carry the\n * `{ tag, data, action }` payload for event-token wiring.\n */\nexport class WcsNotify extends HTMLElement {\n static hasConnectedCallbackPromise = true;\n static wcBindable: IWcBindable = {\n ...NotificationCore.wcBindable,\n // Shell-level settable surface. `notice` is a momentary reactive command-property\n // with no mirrored attribute (it carries dynamic text, not declarative config),\n // mirroring <wcs-speak>'s `say`. The rest mirror their HTML attributes idempotently.\n inputs: [\n { name: \"notice\" },\n { name: \"mode\", attribute: \"mode\" },\n { name: \"body\", attribute: \"body\" },\n { name: \"icon\", attribute: \"icon\" },\n { name: \"badge\", attribute: \"badge\" },\n { name: \"tag\", attribute: \"tag\" },\n { name: \"lang\", attribute: \"lang\" },\n { name: \"dir\", attribute: \"dir\" },\n { name: \"requireInteraction\", attribute: \"require-interaction\" },\n { name: \"silent\", attribute: \"silent\" },\n { name: \"renotify\", attribute: \"renotify\" },\n { name: \"manual\", attribute: \"manual\" },\n ],\n commands: NotificationCore.wcBindable.commands,\n };\n\n private _core: NotificationCore;\n private _notice: string = \"\";\n private _connectedCallbackPromise: Promise<void> = Promise.resolve();\n private _internals: ElementInternals | null = null;\n\n constructor() {\n super();\n this._core = new NotificationCore(this);\n this._internals = this._initInternals();\n this._wireStates({\n \"wcs-notify:permission-change\": (d) => ({\n granted: d === \"granted\", denied: d === \"denied\",\n prompt: d === \"prompt\", unsupported: d === \"unsupported\",\n }),\n \"wcs-notify:error\": (d) => ({ error: d != null }),\n });\n }\n\n // CSS state reflection (:state()) — debug-only snapshot getter. NOT part of\n // wc-bindable (not a bind target); see README \"CSS styling with :state()\".\n // MUST NOT return the live CustomStateSet (that would let callers write\n // states from outside, defeating the point of :state() being read-only).\n get debugStates(): string[] {\n return this._internals ? [...this._internals.states] : [];\n }\n\n private _initInternals(): ElementInternals | null {\n // never-throw (async-io-node-guidelines.md §3.6): attachInternals is absent\n // in happy-dom / older environments, and pre-125 Chromium rejects\n // non-dashed state names from states.add() (probed and discarded here).\n // Either case silently disables reflection — the component still works,\n // it just doesn't expose :state() selectors.\n try {\n if (typeof this.attachInternals !== \"function\") return null;\n const internals = this.attachInternals();\n internals.states.add(\"wcs-probe\");\n internals.states.delete(\"wcs-probe\");\n return internals;\n } catch {\n return null;\n }\n }\n\n private _wireStates(map: Record<string, (detail: any) => Record<string, boolean>>): void {\n if (this._internals === null) return;\n const states = this._internals.states;\n for (const [event, toStates] of Object.entries(map)) {\n this.addEventListener(event, (e) => {\n const debug = this.hasAttribute(\"debug-states\");\n for (const [name, on] of Object.entries(toStates((e as CustomEvent).detail))) {\n try {\n if (on) { states.add(name); } else { states.delete(name); }\n } catch { /* never-throw */ }\n if (debug) this.toggleAttribute(`data-wcs-state-${name}`, on);\n }\n });\n }\n }\n\n // --- Attribute accessors ---\n\n get mode(): NotifyBackend {\n const m = this.getAttribute(\"mode\");\n return (m === \"sw\" || m === \"constructor\") ? m : \"auto\";\n }\n\n set mode(value: NotifyBackend) {\n this.setAttribute(\"mode\", value);\n }\n\n get body(): string {\n return this.getAttribute(\"body\") ?? \"\";\n }\n\n set body(value: string | null) {\n this._reflect(\"body\", value);\n }\n\n get icon(): string {\n return this.getAttribute(\"icon\") ?? \"\";\n }\n\n set icon(value: string | null) {\n this._reflect(\"icon\", value);\n }\n\n get badge(): string {\n return this.getAttribute(\"badge\") ?? \"\";\n }\n\n set badge(value: string | null) {\n this._reflect(\"badge\", value);\n }\n\n get tag(): string {\n return this.getAttribute(\"tag\") ?? \"\";\n }\n\n set tag(value: string | null) {\n this._reflect(\"tag\", value);\n }\n\n // NOTE: `lang` and `dir` intentionally repurpose the standard HTMLElement IDL\n // attributes as per-notification options (forwarded to NotificationOptions).\n // This element is always display:none, so overriding their normal rendering\n // semantics has no visual effect — but be aware the values mean \"the\n // notification's language/direction\", not the host element's.\n get lang(): string {\n return this.getAttribute(\"lang\") ?? \"\";\n }\n\n set lang(value: string | null) {\n this._reflect(\"lang\", value);\n }\n\n get dir(): string {\n return this.getAttribute(\"dir\") ?? \"\";\n }\n\n set dir(value: string | null) {\n this._reflect(\"dir\", value);\n }\n\n get requireInteraction(): boolean {\n return this.hasAttribute(\"require-interaction\");\n }\n\n set requireInteraction(value: boolean) {\n this._reflectBool(\"require-interaction\", value);\n }\n\n get silent(): boolean {\n return this.hasAttribute(\"silent\");\n }\n\n set silent(value: boolean) {\n this._reflectBool(\"silent\", value);\n }\n\n get renotify(): boolean {\n return this.hasAttribute(\"renotify\");\n }\n\n set renotify(value: boolean) {\n this._reflectBool(\"renotify\", value);\n }\n\n get manual(): boolean {\n return this.hasAttribute(\"manual\");\n }\n\n set manual(value: boolean) {\n this._reflectBool(\"manual\", value);\n }\n\n // --- Reactive command-property ---\n\n get notice(): string {\n return this._notice;\n }\n\n set notice(value: string | null) {\n // Reactive: writing a new value shows it. `manual` mutes the path entirely\n // (the imperative `notify` command still works). A conforming binder never\n // delivers `undefined` (it skips the write), but a direct assignment can, so\n // normalize null/undefined to a no-op.\n if (value == null) return;\n if (this.manual) return;\n const v = String(value);\n // Same-value guard: only show when the bound source actually changes. To show\n // the same text again on demand, use the `notify` command instead. (This is\n // the only spam guard the package provides — see docs § 2-c; debounce is the\n // caller's job via a filter, e.g. `notice@x|debounce(1000)`.)\n if (v === this._notice) return;\n this._notice = v;\n this.notify(v);\n }\n\n // --- Core delegated getters ---\n\n get permission(): PermissionStateOrUnsupported {\n return this._core.permission;\n }\n\n get granted(): boolean {\n return this._core.granted;\n }\n\n get denied(): boolean {\n return this._core.denied;\n }\n\n get prompt(): boolean {\n return this._core.prompt;\n }\n\n get unsupported(): boolean {\n return this._core.unsupported;\n }\n\n get error(): WcsNotifyErrorDetail | null {\n return this._core.error;\n }\n\n get clicked(): WcsNotifyClickDetail | null {\n return this._core.clicked;\n }\n\n get closed(): WcsNotifyClickDetail | null {\n return this._core.closed;\n }\n\n get shown(): WcsNotifyClickDetail | null {\n return this._core.shown;\n }\n\n get connectedCallbackPromise(): Promise<void> {\n return this._connectedCallbackPromise;\n }\n\n // --- Commands ---\n\n request(): Promise<PermissionStateOrUnsupported> {\n return this._core.request();\n }\n\n notify(title: string, options?: NotifyOptions): string {\n // Explicit options (from a command-token emit) win per-key over the attribute\n // defaults, so `notify.emit(title, { body })` still picks up the element's icon.\n return this._core.notify(title, { ...this._options(), ...(options ?? {}) });\n }\n\n close(tag?: string): void {\n this._core.close(tag);\n }\n\n closeAll(): void {\n this._core.closeAll();\n }\n\n // --- Internal ---\n\n private _reflect(name: string, value: string | null): void {\n if (value == null) {\n this.removeAttribute(name);\n } else {\n this.setAttribute(name, String(value));\n }\n }\n\n private _reflectBool(name: string, value: boolean): void {\n if (value) {\n this.setAttribute(name, \"\");\n } else {\n this.removeAttribute(name);\n }\n }\n\n private _options(): NotifyOptions {\n const o: NotifyOptions = {};\n if (this.body !== \"\") o.body = this.body;\n if (this.icon !== \"\") o.icon = this.icon;\n if (this.badge !== \"\") o.badge = this.badge;\n if (this.tag !== \"\") o.tag = this.tag;\n if (this.lang !== \"\") o.lang = this.lang;\n if (this.dir === \"auto\" || this.dir === \"ltr\" || this.dir === \"rtl\") o.dir = this.dir;\n if (this.requireInteraction) o.requireInteraction = true;\n if (this.silent) o.silent = true;\n if (this.renotify) o.renotify = true;\n return o;\n }\n\n // --- Lifecycle ---\n\n connectedCallback(): void {\n this.style.display = \"none\";\n if (config.autoTrigger) {\n registerAutoTrigger();\n }\n // Begin observing permission and subscribing to SW click relays (or revive\n // after a reconnect). The returned promise is held as connectedCallbackPromise\n // for SSR.\n this._connectedCallbackPromise = this._core.observe(this.mode);\n }\n\n disconnectedCallback(): void {\n // Detach subscriptions. Open notifications are left on screen (see Core docs);\n // call close()/closeAll() to dismiss.\n this._core.dispose();\n }\n}\n","import { setConfig } from \"./config.js\";\nimport { registerComponents } from \"./registerComponents.js\";\nimport { IWritableConfig } from \"./types.js\";\n\nexport function bootstrapNotification(userConfig?: IWritableConfig): void {\n if (userConfig) {\n setConfig(userConfig);\n }\n registerComponents();\n}\n","import { WcsNotify } from \"./components/Notify.js\";\nimport { config } from \"./config.js\";\n\nexport function registerComponents(): void {\n if (!customElements.get(config.tagNames.notify)) {\n customElements.define(config.tagNames.notify, WcsNotify);\n }\n}\n"],"names":["_config","autoTrigger","triggerAttribute","tagNames","notify","deepFreeze","obj","Object","freeze","key","keys","deepClone","clone","frozenConfig","config","getConfig","NotificationCore","EventTarget","static","protocol","version","properties","name","event","getter","e","detail","commands","async","_target","_mode","_permission","_error","_lastClick","_lastClose","_lastShow","_permissionStatus","_permissionSubscribed","_gen","_ready","Promise","resolve","_idSeq","_constructed","Map","_swTags","Set","_channel","_serviceWorker","_clicksSubscribed","_seenIds","constructor","target","super","this","permission","granted","denied","prompt","unsupported","error","clicked","closed","shown","ready","_setPermission","state","dispatchEvent","CustomEvent","bubbles","_setError","_emit","kind","observe","mode","_initPermission","_subscribeClicks","request","api","_api","requestPermission","result","_normalize","title","options","_err","tag","_nextId","payload","data","__wcsId","backendOptions","_show","close","n","get","delete","has","_closeSw","closeAll","values","clear","dispose","removeEventListener","_onPermissionChange","_onInbound","navigator","permissions","query","gen","then","status","addEventListener","raw","_showViaSw","_showViaConstructor","TypeError","set","onshow","action","onclick","onclose","onerror","sw","serviceWorker","add","registration","showNotification","catch","getNotifications","list","BroadcastChannel","msg","__wcsNotify","_isDuplicate","id","_unwrap","includes","push","length","shift","g","globalThis","Notification","undefined","message","registered","handleClick","Element","triggerElement","closest","notifyId","getAttribute","NotifyCtor","customElements","notifyElement","document","getElementById","explicit","textContent","trim","body","WcsNotify","HTMLElement","wcBindable","inputs","attribute","_core","_notice","_connectedCallbackPromise","_internals","_initInternals","_wireStates","d","debugStates","states","attachInternals","internals","map","toStates","entries","debug","hasAttribute","on","toggleAttribute","m","value","setAttribute","_reflect","icon","badge","lang","dir","requireInteraction","_reflectBool","silent","renotify","manual","notice","v","String","connectedCallbackPromise","_options","removeAttribute","o","connectedCallback","style","display","disconnectedCallback","bootstrapNotification","userConfig","partialConfig","assign","define"],"mappings":"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"}
1
+ {"version":3,"file":"index.esm.min.js","sources":["../src/config.ts","../src/core/notificationCapabilities.ts","../src/core/NotificationCore.ts","../src/autoTrigger.ts","../src/components/Notify.ts","../src/bootstrapNotification.ts","../src/registerComponents.ts"],"sourcesContent":["import { IConfig, IWritableConfig } from \"./types.js\";\n\ninterface IInternalConfig extends IConfig {\n autoTrigger: boolean;\n triggerAttribute: string;\n tagNames: {\n notify: string;\n };\n}\n\nconst _config: IInternalConfig = {\n autoTrigger: true,\n triggerAttribute: \"data-notifytarget\",\n tagNames: {\n notify: \"wcs-notify\",\n },\n};\n\nfunction deepFreeze<T>(obj: T): T {\n if (obj === null || typeof obj !== \"object\") return obj;\n Object.freeze(obj);\n for (const key of Object.keys(obj)) {\n deepFreeze((obj as Record<string, unknown>)[key]);\n }\n return obj;\n}\n\nfunction deepClone<T>(obj: T): T {\n if (obj === null || typeof obj !== \"object\") return obj;\n const clone: Record<string, unknown> = {};\n for (const key of Object.keys(obj)) {\n clone[key] = deepClone((obj as Record<string, unknown>)[key]);\n }\n return clone as T;\n}\n\nlet frozenConfig: IConfig | null = null;\n\n// Internal, mutable live config used by the components/autoTrigger (they read it\n// at call time so setConfig() takes effect without re-import). Typed as the\n// readonly IConfig at the export boundary — the `as IConfig` is a compile-time\n// view only and does NOT freeze the object, so this export must stay\n// package-internal (it is not re-exported from exports.ts). Public consumers get\n// the deep-frozen clone from getConfig() instead.\nexport const config: IConfig = _config as IConfig;\n\nexport function getConfig(): IConfig {\n if (!frozenConfig) {\n frozenConfig = deepFreeze(deepClone(_config));\n }\n return frozenConfig;\n}\n\nexport function setConfig(partialConfig: IWritableConfig): void {\n if (typeof partialConfig.autoTrigger === \"boolean\") {\n _config.autoTrigger = partialConfig.autoTrigger;\n }\n if (typeof partialConfig.triggerAttribute === \"string\") {\n _config.triggerAttribute = partialConfig.triggerAttribute;\n }\n if (partialConfig.tagNames) {\n Object.assign(_config.tagNames, partialConfig.tagNames);\n }\n frozenConfig = null;\n}\n","/**\n * notificationCapabilities.ts\n *\n * Notification node 固有の error code(taxonomy)と derivation。汎用の error info 型は\n * `./platformCapability.js`(/io-core/ から copy-distribution される生成ファイル)から\n * import する。notification は監視(permission)と操作(notify/close)を 1 タグに併せ持つが、\n * 競合する非同期 operation の lane は持たない(show は最新値で上書きされる momentary な\n * 送出)ため、lane は採用せず error taxonomy(errorInfo)のみを追加する。\n *\n * sensor family と異なり、NotificationCore の error detail の `.error` は既に安定コード\n * (`this._err(code, message)` が産出する `\"unsupported\"` / `\"not-granted\"` /\n * `\"invalid-title\"` / `\"show-failed\"` / `\"no-service-worker\"`)であり、Error.name ではない。\n * したがって derivation は `.error` コードを taxonomy に写すだけの純粋な map である。\n * 想定外のコードは防御的に `notify-error` へ畳む。\n */\n\nimport type { WcsIoErrorInfo } from \"./platformCapability.js\";\nimport type { WcsNotifyErrorDetail } from \"../types.js\";\n\n/** 安定した notification error code(taxonomy)。値は公開キーとして固定。 */\nexport const WCS_NOTIFY_ERROR_CODE = {\n /** Notifications API 非対応(`globalThis.Notification` 不在)。 */\n CapabilityMissing: \"capability-missing\",\n /** 権限が granted でない状態での notify()。 */\n NotAllowed: \"not-allowed\",\n /** notify() に非文字列 title が渡された。 */\n InvalidArgument: \"invalid-argument\",\n /** notification の生成 / 表示に失敗した(constructor 例外 / onerror / SW show reject)。 */\n ShowFailed: \"show-failed\",\n /** SW backend が必要だが `navigator.serviceWorker` が不在。 */\n NoServiceWorker: \"no-service-worker\",\n /** その他 / 想定外の error code に対する防御的 fallback。 */\n NotifyError: \"notify-error\",\n} as const;\n\n/**\n * notification の失敗を serializable な error taxonomy に写す。引数は\n * `wcs-notify:error` の detail(`{ error, message }`)そのもの。`.error` は\n * `NotificationCore._err()` が付与した安定コードで、Error.name ではない。\n *\n * - `\"unsupported\"` は開始前の能力欠如 → phase=\"probe\" / capability-missing。\n * - `\"not-granted\"` / `\"invalid-title\"` は show 手前の前提条件違反(権限・引数)→\n * phase=\"start\" / not-allowed・invalid-argument。\n * - `\"show-failed\"` は show 実行中の失敗 → phase=\"execute\" / show-failed。\n * - `\"no-service-worker\"` は SW backend 要求時の transport 欠如 → phase=\"execute\" /\n * no-service-worker。\n * - それ以外(未知コード)は防御的に phase=\"execute\" / notify-error。\n *\n * いずれも retry で自動回復しない(recoverable=false)。\n */\nexport function deriveNotifyErrorInfo(error: WcsNotifyErrorDetail): WcsIoErrorInfo {\n const { error: code, message } = error;\n switch (code) {\n case \"unsupported\":\n return { code: WCS_NOTIFY_ERROR_CODE.CapabilityMissing, phase: \"probe\", recoverable: false, message };\n case \"not-granted\":\n return { code: WCS_NOTIFY_ERROR_CODE.NotAllowed, phase: \"start\", recoverable: false, message };\n case \"invalid-title\":\n return { code: WCS_NOTIFY_ERROR_CODE.InvalidArgument, phase: \"start\", recoverable: false, message };\n case \"show-failed\":\n return { code: WCS_NOTIFY_ERROR_CODE.ShowFailed, phase: \"execute\", recoverable: false, message };\n case \"no-service-worker\":\n return { code: WCS_NOTIFY_ERROR_CODE.NoServiceWorker, phase: \"execute\", recoverable: false, message };\n default:\n return { code: WCS_NOTIFY_ERROR_CODE.NotifyError, phase: \"execute\", recoverable: false, message };\n }\n}\n","import {\n IWcBindable, NotifyBackend, NotifyOptions, NotificationPermissionRaw,\n PermissionStateOrUnsupported, WcsNotifyClickDetail, WcsNotifyErrorDetail,\n} from \"../types.js\";\nimport { WcsIoErrorInfo } from \"./platformCapability.js\";\nimport { deriveNotifyErrorInfo } from \"./notificationCapabilities.js\";\n\n// Wrapper stored in a notification's `data` so the Service Worker side (a\n// separate global scope with no access to this instance) can recover the\n// identity and the caller's payload. The constructor backend uses the same\n// wrapper for uniformity, and both paths unwrap it before emitting.\ninterface WcsNotifyData {\n __wcsId: string;\n payload: unknown;\n}\n\n// Message shape posted by `wireNotificationClicks()` (src/sw.ts) over both\n// BroadcastChannel and clients.postMessage. `id` is unique per click\n// (`tag#seq`), so the two transports delivering the *same* click de-dup, while\n// two genuine clicks on the same `tag` do not.\ninterface WcsNotifyInbound {\n __wcsNotify: true;\n id: string;\n tag: string;\n data: unknown;\n action: string;\n}\n\n/**\n * Headless desktop-notification primitive. A thin, framework-agnostic wrapper\n * around the Notifications API exposed through the wc-bindable protocol.\n *\n * Unlike `@wcstack/permission` (a read-only monitor — the Permissions API has no\n * `request()`), the Notifications API *does* expose `Notification.requestPermission()`,\n * so this node is self-contained: it both **requests/monitors** the permission and\n * **shows** notifications. It is the first @wcstack node where the command-token\n * (show: `notify`) and event-token (`click` / `close` / `show`) directions both\n * live in one tag.\n *\n * - **request()** asks for the `notifications` permission (`Notification.requestPermission`).\n * - **notify(title, options)** shows a notification and returns its identifying tag\n * (a caller `options.tag`, or a generated `wcs-<n>`). It picks a backend per\n * `mode`: the `Notification` constructor (desktop) or\n * `ServiceWorkerRegistration.showNotification()` (mobile). `\"auto\"` prefers the\n * constructor and falls back to the SW on a `TypeError`.\n * - **close(tag) / closeAll()** dismiss notifications by tag / all.\n * - Clicks flow back as the `wcs-notify:click` event: directly via the\n * Notification's `onclick` (constructor), or via the SW helper's\n * BroadcastChannel/postMessage relay (SW). `permission` mirrors the live grant.\n *\n * Failures never throw: they surface through `error` (and the `unsupported`\n * permission state) so they flow into the declarative state.\n */\nexport class NotificationCore extends EventTarget {\n static wcBindable: IWcBindable = {\n protocol: \"wc-bindable\",\n version: 1,\n properties: [\n { name: \"permission\", event: \"wcs-notify:permission-change\" },\n { name: \"granted\", event: \"wcs-notify:permission-change\", getter: (e: Event) => (e as CustomEvent).detail === \"granted\" },\n { name: \"denied\", event: \"wcs-notify:permission-change\", getter: (e: Event) => (e as CustomEvent).detail === \"denied\" },\n { name: \"prompt\", event: \"wcs-notify:permission-change\", getter: (e: Event) => (e as CustomEvent).detail === \"prompt\" },\n { name: \"unsupported\", event: \"wcs-notify:permission-change\", getter: (e: Event) => (e as CustomEvent).detail === \"unsupported\" },\n { name: \"error\", event: \"wcs-notify:error\" },\n // Serializable failure taxonomy (stable code / phase / recoverable), or null.\n // Additive bindable output derived from `error.error` (the stable code the\n // Core's `_err()` already produces); the existing `error` property/event are\n // unchanged. Fires wcs-notify:error-info-changed. No lane — show is a\n // momentary, last-value-wins send, not a competing async operation.\n { name: \"errorInfo\", event: \"wcs-notify:error-info-changed\" },\n { name: \"clicked\", event: \"wcs-notify:click\", getter: (e: Event) => (e as CustomEvent).detail },\n { name: \"closed\", event: \"wcs-notify:close\", getter: (e: Event) => (e as CustomEvent).detail },\n { name: \"shown\", event: \"wcs-notify:show\", getter: (e: Event) => (e as CustomEvent).detail },\n ],\n commands: [\n { name: \"request\", async: true },\n { name: \"notify\" },\n { name: \"close\" },\n { name: \"closeAll\" },\n ],\n };\n\n private _target: EventTarget;\n private _mode: NotifyBackend = \"auto\";\n\n private _permission: PermissionStateOrUnsupported = \"prompt\";\n private _error: WcsNotifyErrorDetail | null = null;\n private _errorInfo: WcsIoErrorInfo | null = null;\n private _lastClick: WcsNotifyClickDetail | null = null;\n private _lastClose: WcsNotifyClickDetail | null = null;\n private _lastShow: WcsNotifyClickDetail | null = null;\n\n // Live PermissionStatus (when the Permissions API can query `notifications`),\n // kept so its `change` listener can be removed on dispose().\n private _permissionStatus: PermissionStatus | null = null;\n // True once a permission subscription has been (or is being) established; reset\n // by dispose(). Guards observe() so a reconnect re-queries while a redundant\n // observe() on a live subscription does not.\n private _permissionSubscribed: boolean = false;\n\n // Monotonic id of the current lifecycle. Bumped by every observe() and by\n // dispose(). In-flight async work (permission query, SW show, inbound click)\n // captures it and bails if stale, so a query/click that resolves after a\n // disconnect — or after a rapid disconnect→reconnect — never mutates state or\n // dispatches on a torn-down element.\n private _gen: number = 0;\n\n // Resolves once the connect-time permission probe settles. The Shell exposes\n // this as connectedCallbackPromise so SSR can await it before snapshotting.\n private _ready: Promise<void> = Promise.resolve();\n\n // Counter for auto-assigned tags when the caller omits one.\n private _idSeq: number = 0;\n\n // Notifications created via the constructor backend, by tag, so close()/closeAll()\n // can dismiss them. The SW backend has no handle (showNotification returns void),\n // so its tags are tracked separately and closed via registration.getNotifications().\n private _constructed: Map<string, Notification> = new Map();\n private _swTags: Set<string> = new Set();\n\n // Click subscription handles (SW relay).\n private _channel: BroadcastChannel | null = null;\n private _serviceWorker: ServiceWorkerContainer | null = null;\n private _clicksSubscribed: boolean = false;\n // Per-click ids already handled, to de-dup the two relay transports. FIFO-capped\n // so a long session does not leak; the two transports always arrive in the same\n // tick, so a small cap is ample.\n private _seenIds: string[] = [];\n\n constructor(target?: EventTarget) {\n super();\n this._target = target ?? this;\n }\n\n get permission(): PermissionStateOrUnsupported {\n return this._permission;\n }\n\n get granted(): boolean {\n return this._permission === \"granted\";\n }\n\n get denied(): boolean {\n return this._permission === \"denied\";\n }\n\n get prompt(): boolean {\n return this._permission === \"prompt\";\n }\n\n get unsupported(): boolean {\n return this._permission === \"unsupported\";\n }\n\n get error(): WcsNotifyErrorDetail | null {\n return this._error;\n }\n\n /**\n * The last failure's serializable `WcsIoErrorInfo` (stable `code` / `phase` /\n * `recoverable`), or null. Additive wc-bindable property (event\n * `wcs-notify:error-info-changed`), derived from `error`; the existing `error`\n * property/event are unchanged.\n */\n get errorInfo(): WcsIoErrorInfo | null {\n return this._errorInfo;\n }\n\n get clicked(): WcsNotifyClickDetail | null {\n return this._lastClick;\n }\n\n get closed(): WcsNotifyClickDetail | null {\n return this._lastClose;\n }\n\n get shown(): WcsNotifyClickDetail | null {\n return this._lastShow;\n }\n\n /** Resolves once the current (or initial) permission probe settles. */\n get ready(): Promise<void> {\n return this._ready;\n }\n\n // --- State setters with event dispatch ---\n\n private _setPermission(state: PermissionStateOrUnsupported): void {\n if (this._permission === state) return;\n this._permission = state;\n this._target.dispatchEvent(new CustomEvent(\"wcs-notify:permission-change\", {\n detail: state,\n bubbles: true,\n }));\n }\n\n private _setError(error: WcsNotifyErrorDetail | null): void {\n if (this._error === error) return;\n this._error = error;\n // Keep the additive `errorInfo` taxonomy in sync with `error`: derive from the\n // stable error code (or null on clear). Fires before the `error` event so an\n // observer binding both sees the classification first, mirroring the io-node\n // family.\n this._commitErrorInfo(error === null ? null : deriveNotifyErrorInfo(error));\n this._target.dispatchEvent(new CustomEvent(\"wcs-notify:error\", {\n detail: error,\n bubbles: true,\n }));\n }\n\n // Called only from _setError (which already guards on error identity), so\n // errorInfo transitions exactly when error does — no separate guard needed here.\n private _commitErrorInfo(info: WcsIoErrorInfo | null): void {\n this._errorInfo = info;\n this._target.dispatchEvent(new CustomEvent(\"wcs-notify:error-info-changed\", {\n detail: info,\n bubbles: true,\n }));\n }\n\n private _emit(kind: \"click\" | \"close\" | \"show\", detail: WcsNotifyClickDetail): void {\n if (kind === \"click\") this._lastClick = detail;\n else if (kind === \"close\") this._lastClose = detail;\n else this._lastShow = detail;\n this._target.dispatchEvent(new CustomEvent(`wcs-notify:${kind}`, {\n detail,\n bubbles: true,\n }));\n }\n\n // --- Public API ---\n\n /**\n * Start observing the `notifications` permission and subscribing to Service\n * Worker click relays. `mode` selects the show backend (default `\"auto\"`).\n * Idempotent while already subscribed: it only updates the stored mode; to\n * restart, dispose() first. Returns a promise that resolves once the first\n * permission probe settles, for SSR.\n *\n * Headless callers must call observe() to begin; the Shell calls it from\n * connectedCallback once the element's attributes resolve.\n */\n observe(mode: NotifyBackend = \"auto\"): Promise<void> {\n this._mode = mode;\n if (!this._permissionSubscribed) {\n this._ready = this._initPermission();\n this._subscribeClicks();\n }\n return this._ready;\n }\n\n /**\n * Ask the user for the `notifications` permission. Resolves to the resulting\n * (normalized) permission state. Never throws: an unavailable API resolves to\n * `\"unsupported\"`.\n */\n async request(): Promise<PermissionStateOrUnsupported> {\n const api = this._api();\n if (!api || typeof api.requestPermission !== \"function\") {\n this._setPermission(\"unsupported\");\n return this._permission;\n }\n try {\n const result = await api.requestPermission();\n this._setPermission(this._normalize(result));\n } catch {\n // Some legacy engines may reject; keep the current state rather than throw.\n }\n return this._permission;\n }\n\n /**\n * Show a notification. Returns the identifying tag (the caller's `options.tag`,\n * or a generated `wcs-<n>` when omitted). Never throws: when the API is\n * unavailable or the permission is not granted it surfaces an `error` and\n * returns an empty string.\n */\n notify(title: string, options: NotifyOptions = {}): string {\n if (!this._api()) {\n this._setError(this._err(\"unsupported\", \"Notifications API is not available in this environment.\"));\n return \"\";\n }\n if (this._permission !== \"granted\") {\n this._setError(this._err(\"not-granted\", \"Notification permission is not granted; call request() first.\"));\n return \"\";\n }\n if (typeof title !== \"string\") {\n this._setError(this._err(\"invalid-title\", \"notify() requires a string title.\"));\n return \"\";\n }\n\n const tag = (typeof options.tag === \"string\" && options.tag !== \"\") ? options.tag : this._nextId();\n const payload = options.data;\n const data: WcsNotifyData = { __wcsId: tag, payload };\n const backendOptions: NotifyOptions = { ...options, tag, data };\n\n this._setError(null);\n this._show(title, backendOptions, tag, payload);\n return tag;\n }\n\n /** Dismiss the notification(s) with `tag` across both backends. */\n close(tag?: string): void {\n if (typeof tag !== \"string\" || tag === \"\") return;\n const n = this._constructed.get(tag);\n if (n) {\n n.close();\n this._constructed.delete(tag);\n }\n if (this._swTags.has(tag)) {\n this._closeSw(tag);\n this._swTags.delete(tag);\n }\n }\n\n /**\n * Dismiss every notification this instance has shown. Scoped to this instance's\n * own tags on both backends — the SW path closes each tracked tag individually\n * rather than enumerating the whole origin, so it never dismisses notifications\n * shown by another `<wcs-notify>` or by an unrelated code path.\n */\n closeAll(): void {\n for (const n of this._constructed.values()) {\n n.close();\n }\n this._constructed.clear();\n for (const tag of this._swTags) {\n this._closeSw(tag);\n }\n this._swTags.clear();\n }\n\n /**\n * Detach permission and click subscriptions. Open notifications are intentionally\n * **left on screen** (a notification outlives the page that posted it — that is\n * the point); use close()/closeAll() to dismiss. Call from the Shell's\n * disconnectedCallback. A later observe() resumes.\n */\n dispose(): void {\n this._permissionSubscribed = false;\n this._clicksSubscribed = false;\n this._gen++;\n if (this._permissionStatus) {\n this._permissionStatus.removeEventListener(\"change\", this._onPermissionChange);\n this._permissionStatus = null;\n }\n if (this._channel) {\n this._channel.removeEventListener(\"message\", this._onInbound);\n this._channel.close();\n this._channel = null;\n }\n if (this._serviceWorker) {\n this._serviceWorker.removeEventListener(\"message\", this._onInbound);\n this._serviceWorker = null;\n }\n }\n\n // --- Internal: permission ---\n\n private _initPermission(): Promise<void> {\n const api = this._api();\n if (!api) {\n this._setPermission(\"unsupported\");\n // Intentionally does NOT set _permissionSubscribed: there is no permission\n // listener to tear down, so a reconnect simply re-probes (idempotent — the\n // same-value guard suppresses any redundant dispatch and no listener is ever\n // attached). _subscribeClicks() is re-entered too, but its own\n // _clicksSubscribed guard short-circuits the second pass, so no transport is\n // double-subscribed. Mirrors @wcstack/permission's unsupported path.\n return Promise.resolve();\n }\n this._permissionSubscribed = true;\n // Prefer the Permissions API: it provides a live `change` event. Fall back to\n // the static `Notification.permission` when it is absent or rejects the\n // `notifications` descriptor.\n if (typeof navigator !== \"undefined\" && navigator.permissions && typeof navigator.permissions.query === \"function\") {\n const gen = ++this._gen;\n return navigator.permissions.query({ name: \"notifications\" }).then(\n (status) => {\n if (gen !== this._gen) return;\n this._permissionStatus = status;\n this._setPermission(this._normalize(status.state as NotificationPermissionRaw));\n status.addEventListener(\"change\", this._onPermissionChange);\n },\n () => {\n if (gen !== this._gen) return;\n // Permissions API rejected the `notifications` descriptor — fall back to\n // the static `Notification.permission` (api is in scope and non-null here).\n this._setPermission(this._normalize(api.permission));\n },\n );\n }\n // No Permissions API: read the static permission once (no live change events).\n this._setPermission(this._normalize(api.permission));\n return Promise.resolve();\n }\n\n private _onPermissionChange = (event: Event): void => {\n const status = event.target as PermissionStatus;\n this._setPermission(this._normalize(status.state as NotificationPermissionRaw));\n };\n\n // Normalize the Notifications API's `\"default\"` to `\"prompt\"` so this node shares\n // the four-value surface of @wcstack/permission. The Permissions API already\n // reports `\"prompt\"`, so it passes through unchanged.\n private _normalize(raw: NotificationPermissionRaw | string): PermissionStateOrUnsupported {\n if (raw === \"default\") return \"prompt\";\n if (raw === \"granted\" || raw === \"denied\" || raw === \"prompt\") return raw;\n return \"prompt\";\n }\n\n // --- Internal: showing ---\n\n private _show(title: string, options: NotifyOptions, tag: string, payload: unknown): void {\n if (this._mode === \"sw\") {\n this._showViaSw(title, options, tag, payload);\n return;\n }\n const handled = this._showViaConstructor(title, options, tag, payload);\n if (handled) return;\n // Constructor threw TypeError (e.g. mobile, where `new Notification` is illegal).\n if (this._mode === \"auto\") {\n this._showViaSw(title, options, tag, payload);\n } else {\n this._setError(this._err(\"show-failed\", \"new Notification() is not usable here and mode=\\\"constructor\\\" disallows the Service Worker fallback.\"));\n }\n }\n\n // Returns false only when the constructor threw a TypeError (the signal to fall\n // back to the SW backend); true when it showed or surfaced a non-TypeError error.\n private _showViaConstructor(title: string, options: NotifyOptions, tag: string, payload: unknown): boolean {\n const api = this._api()!;\n const gen = this._gen;\n let n: Notification;\n try {\n n = new api(title, options as NotificationOptions);\n } catch (e) {\n if (e instanceof TypeError) return false;\n this._setError(this._err(\"show-failed\", \"Failed to create the notification.\"));\n return true;\n }\n this._constructed.set(tag, n);\n n.onshow = (): void => {\n if (gen !== this._gen) return;\n this._emit(\"show\", { tag, data: payload, action: \"\" });\n };\n n.onclick = (): void => {\n if (gen !== this._gen) return;\n this._emit(\"click\", { tag, data: payload, action: \"\" });\n };\n n.onclose = (): void => {\n this._constructed.delete(tag);\n if (gen !== this._gen) return;\n this._emit(\"close\", { tag, data: payload, action: \"\" });\n };\n n.onerror = (): void => {\n if (gen !== this._gen) return;\n this._setError(this._err(\"show-failed\", \"The notification failed to display.\"));\n };\n return true;\n }\n\n private _showViaSw(title: string, options: NotifyOptions, tag: string, payload: unknown): void {\n const sw = navigator.serviceWorker as ServiceWorkerContainer | undefined;\n if (!sw) {\n this._setError(this._err(\"no-service-worker\", \"Service Worker is required to show this notification but is unavailable.\"));\n return;\n }\n const gen = this._gen;\n this._swTags.add(tag);\n // A notification deliberately outlives the page (see § dispose), so we do NOT\n // bail before showNotification on a stale gen — a notify() issued while\n // connected still shows. The stale-gen guards only suppress dispatching the\n // observable `show` / `error` back onto a torn-down element.\n sw.ready\n .then((registration) => registration.showNotification(title, options as NotificationOptions))\n .then(() => {\n if (gen !== this._gen) return;\n this._emit(\"show\", { tag, data: payload, action: \"\" });\n })\n .catch(() => {\n if (gen !== this._gen) return;\n this._setError(this._err(\"show-failed\", \"ServiceWorkerRegistration.showNotification() failed.\"));\n });\n }\n\n // Close the SW notification(s) carrying `tag`. Always scoped to a single tag —\n // both callers (close / closeAll) iterate their own tracked tags, so the whole\n // origin is never enumerated.\n private _closeSw(tag: string): void {\n const sw = navigator.serviceWorker as ServiceWorkerContainer | undefined;\n if (!sw) return;\n sw.ready.then((registration) => {\n return registration.getNotifications({ tag }).then((list) => {\n for (const n of list) n.close();\n });\n }).catch(() => {\n // Closing is best-effort; a failure to enumerate is not surfaced.\n });\n }\n\n // --- Internal: click relay (SW) ---\n\n private _subscribeClicks(): void {\n if (this._clicksSubscribed) return;\n this._clicksSubscribed = true;\n if (typeof BroadcastChannel === \"function\") {\n this._channel = new BroadcastChannel(\"wcs-notify\");\n this._channel.addEventListener(\"message\", this._onInbound);\n }\n const sw = navigator.serviceWorker as ServiceWorkerContainer | undefined;\n if (sw) {\n this._serviceWorker = sw;\n sw.addEventListener(\"message\", this._onInbound);\n }\n }\n\n private _onInbound = (event: Event): void => {\n const msg = (event as MessageEvent).data as WcsNotifyInbound | undefined;\n if (!msg || msg.__wcsNotify !== true) return;\n if (this._isDuplicate(msg.id)) return;\n this._emit(\"click\", { tag: msg.tag, data: this._unwrap(msg.data), action: msg.action });\n };\n\n private _isDuplicate(id: string): boolean {\n if (this._seenIds.includes(id)) return true;\n this._seenIds.push(id);\n if (this._seenIds.length > 50) this._seenIds.shift();\n return false;\n }\n\n private _unwrap(raw: unknown): unknown {\n if (raw !== null && typeof raw === \"object\" && \"__wcsId\" in raw) {\n return (raw as WcsNotifyData).payload;\n }\n return raw;\n }\n\n // --- Internal: misc ---\n\n // Resolve the global `Notification` constructor at call time (not cached) so\n // tests can install/remove it and so unsupported environments report correctly.\n private _api(): (typeof Notification) | undefined {\n const g = globalThis as unknown as { Notification?: typeof Notification };\n return typeof g.Notification === \"function\" ? g.Notification : undefined;\n }\n\n private _nextId(): string {\n return `wcs-${++this._idSeq}`;\n }\n\n private _err(error: string, message: string): WcsNotifyErrorDetail {\n return { error, message };\n }\n}\n","import { config } from \"./config.js\";\nimport type { WcsNotify } from \"./components/Notify.js\";\n\nlet registered = false;\n\nfunction handleClick(event: Event): void {\n const target = event.target;\n if (!(target instanceof Element)) return;\n\n // A misconfigured triggerAttribute (e.g. one with a space) makes the attribute\n // selector invalid and closest() throw SyntaxError; guard so a bad config\n // disables only this shortcut rather than killing every document click handler.\n let triggerElement: Element | null;\n try {\n triggerElement = target.closest<Element>(`[${config.triggerAttribute}]`);\n } catch {\n return;\n }\n if (!triggerElement) return;\n\n const notifyId = triggerElement.getAttribute(config.triggerAttribute);\n if (!notifyId) return;\n\n // Resolve the registered constructor at call time instead of importing Notify as\n // a value, avoiding a components/Notify.ts ⇄ autoTrigger.ts cycle\n // (Notify.connectedCallback() calls registerAutoTrigger()). instanceof against\n // the customElements registry keeps the same identity guarantee.\n const NotifyCtor = customElements.get(config.tagNames.notify);\n const notifyElement = document.getElementById(notifyId);\n if (!NotifyCtor || !(notifyElement instanceof NotifyCtor)) return;\n\n // The title comes from the trigger element: an explicit `data-notifytitle`\n // attribute wins, otherwise the element's trimmed text content. The body is an\n // optional `data-notifybody`. This keeps the click-driven shortcut declarative\n // without inventing a payload channel.\n const explicit = triggerElement.getAttribute(\"data-notifytitle\");\n // `Element.textContent` is spec-guaranteed non-null (only Document / DocumentType\n // nodes return null, never an Element), so the cast is sound and lets us avoid an\n // unreachable `?? \"\"` branch. `triggerElement` is always an Element here.\n const title = explicit !== null ? explicit : (triggerElement.textContent as string).trim();\n const body = triggerElement.getAttribute(\"data-notifybody\");\n\n (notifyElement as WcsNotify).notify(title, body !== null ? { body } : undefined);\n}\n\nexport function registerAutoTrigger(): void {\n if (registered) return;\n registered = true;\n document.addEventListener(\"click\", handleClick);\n}\n\nexport function unregisterAutoTrigger(): void {\n if (!registered) return;\n registered = false;\n document.removeEventListener(\"click\", handleClick);\n}\n","import { config } from \"../config.js\";\nimport {\n IWcBindable, NotifyBackend, NotifyOptions, PermissionStateOrUnsupported,\n WcsNotifyClickDetail, WcsNotifyErrorDetail,\n} from \"../types.js\";\nimport { NotificationCore } from \"../core/NotificationCore.js\";\nimport { WcsIoErrorInfo } from \"../core/platformCapability.js\";\nimport { registerAutoTrigger } from \"../autoTrigger.js\";\n\n/**\n * `<wcs-notify>` — declarative desktop notifications. Wraps NotificationCore and\n * exposes both directions in one tag:\n *\n * - **`notice`** (reactive input): writing a *changed* value shows a notification,\n * suppressing same-value writes so it fires only when the bound source actually\n * changes. The imperative `notify` command instead shows on demand (even the\n * same text again). See `docs/notification-tag-design.md` § 2.\n * - **`request` / `notify` / `close` / `closeAll`** commands (state → element).\n * - per-notification options (`body` / `icon` / `badge` / `tag` / `lang` / `dir` /\n * `require-interaction` / `silent` / `renotify`) as mirrored attributes.\n * - `mode` selects the show backend (`auto` / `sw` / `constructor`).\n * - the Core's observable surface (permission / granted / … / error / clicked /\n * closed / shown) via delegated getters; clicked/closed/shown carry the\n * `{ tag, data, action }` payload for event-token wiring.\n */\nexport class WcsNotify extends HTMLElement {\n static hasConnectedCallbackPromise = true;\n static wcBindable: IWcBindable = {\n ...NotificationCore.wcBindable,\n // Shell-level settable surface. `notice` is a momentary reactive command-property\n // with no mirrored attribute (it carries dynamic text, not declarative config),\n // mirroring <wcs-speak>'s `say`. The rest mirror their HTML attributes idempotently.\n inputs: [\n { name: \"notice\" },\n { name: \"mode\", attribute: \"mode\" },\n { name: \"body\", attribute: \"body\" },\n { name: \"icon\", attribute: \"icon\" },\n { name: \"badge\", attribute: \"badge\" },\n { name: \"tag\", attribute: \"tag\" },\n { name: \"lang\", attribute: \"lang\" },\n { name: \"dir\", attribute: \"dir\" },\n { name: \"requireInteraction\", attribute: \"require-interaction\" },\n { name: \"silent\", attribute: \"silent\" },\n { name: \"renotify\", attribute: \"renotify\" },\n { name: \"manual\", attribute: \"manual\" },\n ],\n commands: NotificationCore.wcBindable.commands,\n };\n\n private _core: NotificationCore;\n private _notice: string = \"\";\n private _connectedCallbackPromise: Promise<void> = Promise.resolve();\n private _internals: ElementInternals | null = null;\n\n constructor() {\n super();\n this._core = new NotificationCore(this);\n this._internals = this._initInternals();\n this._wireStates({\n \"wcs-notify:permission-change\": (d) => ({\n granted: d === \"granted\", denied: d === \"denied\",\n prompt: d === \"prompt\", unsupported: d === \"unsupported\",\n }),\n \"wcs-notify:error\": (d) => ({ error: d != null }),\n });\n }\n\n // CSS state reflection (:state()) — debug-only snapshot getter. NOT part of\n // wc-bindable (not a bind target); see README \"CSS styling with :state()\".\n // MUST NOT return the live CustomStateSet (that would let callers write\n // states from outside, defeating the point of :state() being read-only).\n get debugStates(): string[] {\n return this._internals ? [...this._internals.states] : [];\n }\n\n private _initInternals(): ElementInternals | null {\n // never-throw (async-io-node-guidelines.md §3.6): attachInternals is absent\n // in happy-dom / older environments, and pre-125 Chromium rejects\n // non-dashed state names from states.add() (probed and discarded here).\n // Either case silently disables reflection — the component still works,\n // it just doesn't expose :state() selectors.\n try {\n if (typeof this.attachInternals !== \"function\") return null;\n const internals = this.attachInternals();\n internals.states.add(\"wcs-probe\");\n internals.states.delete(\"wcs-probe\");\n return internals;\n } catch {\n return null;\n }\n }\n\n private _wireStates(map: Record<string, (detail: any) => Record<string, boolean>>): void {\n if (this._internals === null) return;\n const states = this._internals.states;\n for (const [event, toStates] of Object.entries(map)) {\n this.addEventListener(event, (e) => {\n const debug = this.hasAttribute(\"debug-states\");\n for (const [name, on] of Object.entries(toStates((e as CustomEvent).detail))) {\n try {\n if (on) { states.add(name); } else { states.delete(name); }\n } catch { /* never-throw */ }\n if (debug) this.toggleAttribute(`data-wcs-state-${name}`, on);\n }\n });\n }\n }\n\n // --- Attribute accessors ---\n\n get mode(): NotifyBackend {\n const m = this.getAttribute(\"mode\");\n return (m === \"sw\" || m === \"constructor\") ? m : \"auto\";\n }\n\n set mode(value: NotifyBackend) {\n this.setAttribute(\"mode\", value);\n }\n\n get body(): string {\n return this.getAttribute(\"body\") ?? \"\";\n }\n\n set body(value: string | null) {\n this._reflect(\"body\", value);\n }\n\n get icon(): string {\n return this.getAttribute(\"icon\") ?? \"\";\n }\n\n set icon(value: string | null) {\n this._reflect(\"icon\", value);\n }\n\n get badge(): string {\n return this.getAttribute(\"badge\") ?? \"\";\n }\n\n set badge(value: string | null) {\n this._reflect(\"badge\", value);\n }\n\n get tag(): string {\n return this.getAttribute(\"tag\") ?? \"\";\n }\n\n set tag(value: string | null) {\n this._reflect(\"tag\", value);\n }\n\n // NOTE: `lang` and `dir` intentionally repurpose the standard HTMLElement IDL\n // attributes as per-notification options (forwarded to NotificationOptions).\n // This element is always display:none, so overriding their normal rendering\n // semantics has no visual effect — but be aware the values mean \"the\n // notification's language/direction\", not the host element's.\n get lang(): string {\n return this.getAttribute(\"lang\") ?? \"\";\n }\n\n set lang(value: string | null) {\n this._reflect(\"lang\", value);\n }\n\n get dir(): string {\n return this.getAttribute(\"dir\") ?? \"\";\n }\n\n set dir(value: string | null) {\n this._reflect(\"dir\", value);\n }\n\n get requireInteraction(): boolean {\n return this.hasAttribute(\"require-interaction\");\n }\n\n set requireInteraction(value: boolean) {\n this._reflectBool(\"require-interaction\", value);\n }\n\n get silent(): boolean {\n return this.hasAttribute(\"silent\");\n }\n\n set silent(value: boolean) {\n this._reflectBool(\"silent\", value);\n }\n\n get renotify(): boolean {\n return this.hasAttribute(\"renotify\");\n }\n\n set renotify(value: boolean) {\n this._reflectBool(\"renotify\", value);\n }\n\n get manual(): boolean {\n return this.hasAttribute(\"manual\");\n }\n\n set manual(value: boolean) {\n this._reflectBool(\"manual\", value);\n }\n\n // --- Reactive command-property ---\n\n get notice(): string {\n return this._notice;\n }\n\n set notice(value: string | null) {\n // Reactive: writing a new value shows it. `manual` mutes the path entirely\n // (the imperative `notify` command still works). A conforming binder never\n // delivers `undefined` (it skips the write), but a direct assignment can, so\n // normalize null/undefined to a no-op.\n if (value == null) return;\n if (this.manual) return;\n const v = String(value);\n // Same-value guard: only show when the bound source actually changes. To show\n // the same text again on demand, use the `notify` command instead. (This is\n // the only spam guard the package provides — see docs § 2-c; debounce is the\n // caller's job via a filter, e.g. `notice@x|debounce(1000)`.)\n if (v === this._notice) return;\n this._notice = v;\n this.notify(v);\n }\n\n // --- Core delegated getters ---\n\n get permission(): PermissionStateOrUnsupported {\n return this._core.permission;\n }\n\n get granted(): boolean {\n return this._core.granted;\n }\n\n get denied(): boolean {\n return this._core.denied;\n }\n\n get prompt(): boolean {\n return this._core.prompt;\n }\n\n get unsupported(): boolean {\n return this._core.unsupported;\n }\n\n get error(): WcsNotifyErrorDetail | null {\n return this._core.error;\n }\n\n get errorInfo(): WcsIoErrorInfo | null {\n return this._core.errorInfo;\n }\n\n get clicked(): WcsNotifyClickDetail | null {\n return this._core.clicked;\n }\n\n get closed(): WcsNotifyClickDetail | null {\n return this._core.closed;\n }\n\n get shown(): WcsNotifyClickDetail | null {\n return this._core.shown;\n }\n\n get connectedCallbackPromise(): Promise<void> {\n return this._connectedCallbackPromise;\n }\n\n // --- Commands ---\n\n request(): Promise<PermissionStateOrUnsupported> {\n return this._core.request();\n }\n\n notify(title: string, options?: NotifyOptions): string {\n // Explicit options (from a command-token emit) win per-key over the attribute\n // defaults, so `notify.emit(title, { body })` still picks up the element's icon.\n return this._core.notify(title, { ...this._options(), ...(options ?? {}) });\n }\n\n close(tag?: string): void {\n this._core.close(tag);\n }\n\n closeAll(): void {\n this._core.closeAll();\n }\n\n // --- Internal ---\n\n private _reflect(name: string, value: string | null): void {\n if (value == null) {\n this.removeAttribute(name);\n } else {\n this.setAttribute(name, String(value));\n }\n }\n\n private _reflectBool(name: string, value: boolean): void {\n if (value) {\n this.setAttribute(name, \"\");\n } else {\n this.removeAttribute(name);\n }\n }\n\n private _options(): NotifyOptions {\n const o: NotifyOptions = {};\n if (this.body !== \"\") o.body = this.body;\n if (this.icon !== \"\") o.icon = this.icon;\n if (this.badge !== \"\") o.badge = this.badge;\n if (this.tag !== \"\") o.tag = this.tag;\n if (this.lang !== \"\") o.lang = this.lang;\n if (this.dir === \"auto\" || this.dir === \"ltr\" || this.dir === \"rtl\") o.dir = this.dir;\n if (this.requireInteraction) o.requireInteraction = true;\n if (this.silent) o.silent = true;\n if (this.renotify) o.renotify = true;\n return o;\n }\n\n // --- Lifecycle ---\n\n connectedCallback(): void {\n this.style.display = \"none\";\n if (config.autoTrigger) {\n registerAutoTrigger();\n }\n // Begin observing permission and subscribing to SW click relays (or revive\n // after a reconnect). The returned promise is held as connectedCallbackPromise\n // for SSR.\n this._connectedCallbackPromise = this._core.observe(this.mode);\n }\n\n disconnectedCallback(): void {\n // Detach subscriptions. Open notifications are left on screen (see Core docs);\n // call close()/closeAll() to dismiss.\n this._core.dispose();\n }\n}\n","import { setConfig } from \"./config.js\";\nimport { registerComponents } from \"./registerComponents.js\";\nimport { IWritableConfig } from \"./types.js\";\n\nexport function bootstrapNotification(userConfig?: IWritableConfig): void {\n if (userConfig) {\n setConfig(userConfig);\n }\n registerComponents();\n}\n","import { WcsNotify } from \"./components/Notify.js\";\nimport { config } from \"./config.js\";\n\nexport function registerComponents(): void {\n if (!customElements.get(config.tagNames.notify)) {\n customElements.define(config.tagNames.notify, WcsNotify);\n }\n}\n"],"names":["_config","autoTrigger","triggerAttribute","tagNames","notify","deepFreeze","obj","Object","freeze","key","keys","deepClone","clone","frozenConfig","config","getConfig","WCS_NOTIFY_ERROR_CODE","CapabilityMissing","NotAllowed","InvalidArgument","ShowFailed","NoServiceWorker","NotifyError","NotificationCore","EventTarget","static","protocol","version","properties","name","event","getter","e","detail","commands","async","_target","_mode","_permission","_error","_errorInfo","_lastClick","_lastClose","_lastShow","_permissionStatus","_permissionSubscribed","_gen","_ready","Promise","resolve","_idSeq","_constructed","Map","_swTags","Set","_channel","_serviceWorker","_clicksSubscribed","_seenIds","constructor","target","super","this","permission","granted","denied","prompt","unsupported","error","errorInfo","clicked","closed","shown","ready","_setPermission","state","dispatchEvent","CustomEvent","bubbles","_setError","_commitErrorInfo","code","message","phase","recoverable","deriveNotifyErrorInfo","info","_emit","kind","observe","mode","_initPermission","_subscribeClicks","request","api","_api","requestPermission","result","_normalize","title","options","_err","tag","_nextId","payload","data","__wcsId","backendOptions","_show","close","n","get","delete","has","_closeSw","closeAll","values","clear","dispose","removeEventListener","_onPermissionChange","_onInbound","navigator","permissions","query","gen","then","status","addEventListener","raw","_showViaSw","_showViaConstructor","TypeError","set","onshow","action","onclick","onclose","onerror","sw","serviceWorker","add","registration","showNotification","catch","getNotifications","list","BroadcastChannel","msg","__wcsNotify","_isDuplicate","id","_unwrap","includes","push","length","shift","g","globalThis","Notification","undefined","registered","handleClick","Element","triggerElement","closest","notifyId","getAttribute","NotifyCtor","customElements","notifyElement","document","getElementById","explicit","textContent","trim","body","WcsNotify","HTMLElement","wcBindable","inputs","attribute","_core","_notice","_connectedCallbackPromise","_internals","_initInternals","_wireStates","d","debugStates","states","attachInternals","internals","map","toStates","entries","debug","hasAttribute","on","toggleAttribute","m","value","setAttribute","_reflect","icon","badge","lang","dir","requireInteraction","_reflectBool","silent","renotify","manual","notice","v","String","connectedCallbackPromise","_options","removeAttribute","o","connectedCallback","style","display","disconnectedCallback","bootstrapNotification","userConfig","partialConfig","assign","define"],"mappings":"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"}
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "@wcstack/notification",
3
- "version": "1.20.0",
3
+ "version": "1.21.0",
4
4
  "description": "Declarative desktop-notification component for Web Components. Framework-agnostic Notifications API wrapper via wc-bindable-protocol, with Service Worker support.",
5
5
  "type": "module",
6
6
  "main": "./dist/index.esm.js",