@adartem/adlib-attributes 0.1.0 → 0.1.1

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/package.json CHANGED
@@ -1,30 +1,19 @@
1
1
  {
2
2
  "name": "@adartem/adlib-attributes",
3
- "version": "0.1.0",
4
- "description": "Core unifié + runtime global des attributs AdLib (ad-*).",
3
+ "version": "0.1.1",
4
+ "description": "ADARTEM AdLib Attributes (ad-*).",
5
+ "homepage": "https://adartem.fr/attributes",
5
6
  "license": "MIT",
6
7
  "private": false,
8
+ "publishConfig": {
9
+ "access": "public"
10
+ },
7
11
  "type": "module",
8
- "main": "./dist/index.cjs",
9
- "module": "./dist/index.js",
10
- "types": "./dist/index.d.ts",
11
- "exports": {
12
- ".": {
13
- "types": "./dist/index.d.ts",
14
- "import": "./dist/index.js",
15
- "require": "./dist/index.cjs",
16
- "default": "./dist/index.js"
17
- },
18
- "./core": {
19
- "types": "./dist/core/index.d.ts",
20
- "import": "./dist/core/index.js",
21
- "require": "./dist/core/index.cjs",
22
- "default": "./dist/core/index.js"
23
- },
24
- "./attributes.js": {
25
- "import": "./attributes.js",
26
- "default": "./attributes.js"
27
- }
12
+ "main": "attributes.js",
13
+ "repository": {
14
+ "type": "git",
15
+ "url": "git+https://github.com/adartem/adlib.git",
16
+ "directory": "packages/adlib-attributes"
28
17
  },
29
18
  "files": [
30
19
  "dist",
@@ -33,15 +22,6 @@
33
22
  "README.md",
34
23
  "LICENSE"
35
24
  ],
36
- "sideEffects": [
37
- "./attributes.js"
38
- ],
39
- "engines": {
40
- "node": ">=20"
41
- },
42
- "publishConfig": {
43
- "access": "public"
44
- },
45
25
  "keywords": [
46
26
  "adlib",
47
27
  "adartem",
@@ -50,19 +30,31 @@
50
30
  "cdn",
51
31
  "declarative"
52
32
  ],
33
+ "author": {
34
+ "name": "Adartem",
35
+ "url": "https://adartem.fr/"
36
+ },
37
+ "bugs": {
38
+ "url": "https://github.com/adartem/adlib/issues"
39
+ },
53
40
  "dependencies": {
54
- "@adartem/adlib-utils": "0.1.0"
41
+ "@adartem/adlib-utils": "0.1.0",
42
+ "@adartem/ad-list": "0.1.0"
43
+ },
44
+ "devDependencies": {
45
+ "@types/node": "^20.14.9",
46
+ "cross-env": "^10.1.0",
47
+ "esbuild": "^0.27.2",
48
+ "esbuild-plugin-inline-worker": "^0.1.1",
49
+ "tsx": "^4.19.2"
55
50
  },
56
51
  "scripts": {
57
- "build": "pnpm run build:js && pnpm run build:types",
58
- "build:js": "tsup --config tsup.config.ts",
59
- "build:types": "tsc -p tsconfig.build.json",
60
- "postbuild": "tsx ../../ops/adartem-ops/scripts/copy-attributes-entry.ts",
61
- "dev": "tsup --config tsup.config.ts --watch",
62
- "typecheck": "tsc -p tsconfig.json --noEmit",
63
- "lint": "eslint . --ext .ts",
64
- "lint:fix": "eslint . --ext .ts --fix",
65
- "format": "prettier -w .",
66
- "test": "vitest run -c vitest.config.ts"
52
+ "dev": "cross-env NODE_ENV=development tsx ./bin/build.ts",
53
+ "build": "cross-env NODE_ENV=production tsx ./bin/build.ts",
54
+ "lint": "eslint ./src && prettier --check ./src",
55
+ "lint:fix": "eslint ./src --fix && prettier --write ./src",
56
+ "typecheck": "tsc --noEmit",
57
+ "test": "vitest run -c ../../vitest.config.ts && pnpm playwright test --pass-with-no-tests",
58
+ "test:headed": "pnpm playwright test --headed --pass-with-no-tests"
67
59
  }
68
60
  }
@@ -1,2 +0,0 @@
1
- function N(e){return e.startsWith("ad-")&&e.length>3}function I(e){return e.startsWith("data-")?e.slice(5):e}function V(e){return typeof e!="object"||e===null?!1:typeof e.querySelectorAll=="function"}function j(e=document){if(!V(e))return[];let t=new Set,r=e.querySelectorAll("*");for(let i of Array.from(r))for(let s of Array.from(i.attributes)){let a=I(s.name);N(a)&&t.add(a)}return Array.from(t)}function k(){return typeof window<"u"&&typeof document<"u"}function z(e=!1){return{debug:(...t)=>{e&&console.warn("[debug]",...t)},warn:(...t)=>{console.warn("[warn]",...t)},error:(...t)=>{console.error("[error]",...t)}}}function B(e){return typeof Element<"u"&&e instanceof Element}function U(e,t){try{return e.matches(t)}catch{return!1}}function Y(e,t){let r=e;for(;r;){if(B(r)&&U(r,t))return r;r=B(r)?r.parentElement:null}return null}function W(e){return t=>{let r=e.entries.slice();for(let i of r){let s=Y(t.target,i.selector);if(s&&(i.handler(t,s),i.once)){let a=e.entries.indexOf(i);a>=0&&e.entries.splice(a,1)}}}}function J(e){return e instanceof Document?e.documentElement??e:e}function x(e={}){let t=e.root??document,r=z(!!e.debug),i=new Map,s=new Map,a=new Map;function g(u,l,o,n={}){let c=!!n.capture,f=!!n.passive,m=a.get(u);if(m)return m.entries.push({selector:l,handler:o,once:!!n.once}),()=>{let v=m.entries.findIndex(S=>S.selector===l&&S.handler===o);v>=0&&m.entries.splice(v,1),m.entries.length===0&&(t.removeEventListener(u,m.listener,{capture:m.capture}),a.delete(u))};let w={capture:c,passive:f,entries:[{selector:l,handler:o,once:!!n.once}],listener:()=>{}},_=W(w);return w.listener=_,a.set(u,w),t.addEventListener(u,_,{capture:c,passive:f}),()=>{let v=a.get(u);if(!v)return;let S=v.entries.findIndex(q=>q.selector===l&&q.handler===o);S>=0&&v.entries.splice(S,1),v.entries.length===0&&(t.removeEventListener(u,v.listener,{capture:v.capture}),a.delete(u))}}function d(u,l,o){let n=new CustomEvent(l,{detail:o,bubbles:!0});u.dispatchEvent(n)}function y(u){i.set(u.key,u)}function p(u){i.delete(u)}function M(u,l){let o=i.get(u);if(!o||s.has(u))return;let n=o.init(O);s.set(u,n)}function A(u){let l=s.get(u);l&&(l.destroy(),s.delete(u))}function h(u){for(let l of i.keys())M(l)}function R(){for(let u of s.keys())A(u)}let b=null;function D(u=t){return b?()=>{}:(b=new MutationObserver(l=>{}),b.observe(J(u),{subtree:!0,childList:!0,attributes:!1}),()=>E())}function E(){b&&(b.disconnect(),b=null)}function C(){E(),R();for(let[u,l]of a.entries())t.removeEventListener(u,l.listener,{capture:l.capture});a.clear(),i.clear(),s.clear()}function K(){return r}let O={on:g,emit:d,register:y,unregister:p,mount:M,unmount:A,mountAll:h,unmountAll:R,observe:D,stopObserving:E,destroy:C,getLogger:K};return O}var L=null;function $(e={}){return L||(L=x({autoMount:!0,...e}),(e.autoMount??!0)&&typeof document<"u"&&(document.readyState==="loading"?document.addEventListener("DOMContentLoaded",()=>{L?.mountAll()},{once:!0}):L.mountAll()),L)}function X(e){return e.trim().replace(/\/+$/,"")}function Z(e){return X(e.base??e.registry)}function ee(e){return(e.version??"").trim()||"latest"}function te(e,t,r){return`${e}/@adartem/${t}@${r}/dist/index.js`}var ne={"ad-click":"ad-click"};function T(e,t){let r=Z(t),i=ee(t),s=ne[e];return s?te(r,s,i):null}var re="https://cdn.jsdelivr.net/npm";function oe(e,t){return e[t]??(e[t]={key:t,status:"idle"})}function ie(e){return e.status==="ready"||e.status==="error"}function se(e){return e instanceof Error?e:new Error(String(e))}function H(e){let t=(e??"").trim();if(t)return t.replace(/\/+$/,"")}function ue(e){let t=H(e.config?.registry)??re,r=(e.config?.version??e.version).trim()||e.version,i={registry:t,version:r},s=H(e.config?.base);return s&&(i.base=s),i}function ce(e,t){let r=e&&typeof e=="object"?e.default??e:e;if(!r||typeof r!="object")throw new Error(`Invalid module definition for ${t}`);let i=r;if(typeof i.key!="string"||typeof i.init!="function")throw new Error(`Invalid module definition for ${t}`);if(i.key!==t)throw new Error(`Module key mismatch: expected "${t}", got "${i.key}"`);return i}function Q(e){let t=e.debug??!1,r=e.auto??!1,i=e.core==null,s=e.core??x({debug:t,autoMount:!1}),a=s.getLogger(),g=ue(e),d={},y=[],p=null;function M(...o){t&&a.debug("[AdLib Runtime]",...o)}function A(...o){a.error("[AdLib Runtime]",...o)}function h(o,n){for(let c=y.length-1;c>=0;c--){let f=y[c];if(f&&f.key===o){y.splice(c,1);try{f.cb(n)}catch(m){A("push callback failed",o,m)}}}}function R(o){let n=d[o];if(n){try{n.instance?.destroy?.()}catch(c){A("destroyModule failed",o,c)}delete n.instance,delete n.def,delete n.error,delete n.promise,n.status="idle"}}async function b(o){let n=oe(d,o);if(n.status==="ready"||n.status==="error")return n;if(n.status==="loading"&&n.promise)return n.promise;let c=T(o,g);if(!c)return n.status="error",n.error=new Error(`Unknown module key: ${o}`),h(o,n),n;n.status="loading",M("load()",o,"->",c);let f=(async()=>{try{let m=await import(c),w=ce(m,o);return n.def=w,n.instance||(n.instance=w.init(s)),n.status="ready",delete n.error,delete n.promise,h(o,n),n}catch(m){return n.status="error",n.error=se(m),delete n.promise,h(o,n),n}})();return n.promise=f,f}async function D(o){return M("reload()",o),R(o),b(o)}function E(o,n){let c=d[o];if(c&&ie(c)){try{n(c)}catch(f){A("push callback failed",o,f)}return}y.push({key:o,cb:n})}function C(o=document){let n=j(o);for(let c of n)b(c)}function K(){k()&&(p||(p=new MutationObserver(o=>{for(let n of o)for(let c of Array.from(n.addedNodes))c instanceof HTMLElement&&C(c)}),p.observe(document.documentElement,{childList:!0,subtree:!0})))}function O(){p?.disconnect(),p=null}function u(o){M("destroy()"),O();for(let n of Object.values(d))try{n.instance?.destroy?.()}catch(c){A("destroy module failed",n.key,c)}if(i)try{s.destroy()}catch(n){A("core.destroy failed",n)}for(let n of Object.keys(d))delete d[n];y.length=0,!o?.keepGlobal&&typeof window<"u"&&delete window.AdLibAttributes}let l={version:e.version,config:g,core:s,debug:t,modules:d,load:b,push:E,reload:D,destroy:u};if(typeof window<"u"){let o=window.AdLibAttributesQueue;if(Array.isArray(o)&&o.length>0){let n=o.splice(0,o.length);for(let[c,f]of n)l.push(c,f)}}return r&&k()&&(C(document.body??document),K()),l}function ae(e){return typeof e=="object"&&e!==null&&typeof e.getAttributeNames=="function"}function le(e){return Array.isArray(e)&&e.every(t=>typeof t=="string")}function de(e){if(typeof e!="object"||e===null)return!1;let t=e.attributes;if(typeof t!="object"||t===null)return!1;let r=t;return typeof r.length=="number"&&typeof r.item=="function"}function fe(e){return typeof e!="object"||e===null?!1:typeof e.querySelectorAll=="function"}function me(e){if(ae(e)){let t=e.getAttributeNames();if(le(t))return t}if(de(e)){let t=[];for(let r=0;r<e.attributes.length;r++){let i=e.attributes.item(r);i&&typeof i.name=="string"&&i.name&&t.push(i.name)}return t}return[]}function ge(e){let t=(e.getAttribute("type")??"").trim();if(t&&t!=="module")return!1;let r=(e.getAttribute("src")??"").trim();return r?r.includes("attributes.js"):!1}function P(e){if(typeof e!="string")return;let t=e.trim();return t||void 0}function G(e,t){if(typeof e!="string")return t;let r=e.trim().toLowerCase();return r===""||r==="true"||r==="1"||r==="yes"||r==="on"?!0:r==="false"||r==="0"||r==="no"||r==="off"?!1:t}function pe(e){let t=e.dataset??{},r=G(t.adlibDebug,!1),i=G(t.adlibAuto,!0),s=P(t.adlibRegistry),a=P(t.adlibVersion),g=P(t.adlibBase),d={};return s&&(d.registry=s),a&&(d.version=a),g&&(d.base=g),{debug:r,auto:i,config:d}}function F(e=document){if(!fe(e))return[];let t=Array.from(e.querySelectorAll("script")),r=[];for(let i of t){if(!(i instanceof HTMLScriptElement)||!ge(i))continue;let s=new Set;for(let a of me(i)){let g=I(a);N(g)&&s.add(g)}r.push({el:i,requestedKeys:Array.from(s),loaderConfig:pe(i)})}return r}var ye="0.1.0";(function(){if(!k()||window.AdLibAttributes)return;let t=F(document),r=t[0],i=r?.loaderConfig.debug??!1,s=r?.loaderConfig.auto??!0,a=r?.loaderConfig.config??{},g=$({root:document,debug:i}),d=Q({version:ye,core:g,debug:i,auto:s,config:a});window.AdLibAttributes=d;let y=new Set;for(let p of t)for(let M of p.requestedKeys)y.add(M);for(let p of y)d.load(p).catch(()=>{})})();
2
- //# sourceMappingURL=attributes.js.map
@@ -1 +0,0 @@
1
- {"version":3,"sources":["../../adlib-utils/src/attributes/keys.ts","../../adlib-utils/src/dom/guards.ts","../../adlib-utils/src/dom/scan.ts","../../adlib-utils/src/env/bool.ts","../../adlib-utils/src/env/index.ts","../src/core/index.ts","../src/runtime/module-map.ts","../src/runtime/runtime.ts","../src/runtime/script-detection.ts","../src/runtime/attributes.ts"],"sourcesContent":["import type { ModuleKey } from '../types';\n\nexport function isModuleKey(value: string): value is ModuleKey {\n return value.startsWith('ad-') && value.length > 3;\n}\n\nexport function normalizeAttributeName(name: string): string {\n return name.startsWith('data-') ? name.slice(5) : name;\n}","export type QuerySelectorAllHost = {\n querySelectorAll(selectors: string): NodeListOf<Element>;\n};\n\n/**\n * Type guard: vérifie que `value` expose bien `querySelectorAll`.\n * - sans `any`\n * - sans accès unsafe\n */\nexport function hasQuerySelectorAll(value: unknown): value is QuerySelectorAllHost {\n if (typeof value !== 'object' || value === null) return false;\n\n // On passe par une signature \"indexée\" typée en unknown,\n // puis on raffine vers Function.\n const v = value as Record<string, unknown>;\n const qsa = v['querySelectorAll'];\n\n return typeof qsa === 'function';\n}","import { isModuleKey, normalizeAttributeName } from '../attributes/keys';\nimport type { ModuleKey } from '../types';\nimport { hasQuerySelectorAll } from './guards';\n\nexport function collectModuleKeysFromDOM(root: ParentNode = document): ModuleKey[] {\n if (!hasQuerySelectorAll(root)) return [];\n\n const found = new Set<string>();\n const elements = root.querySelectorAll<HTMLElement>('*');\n\n for (const el of Array.from(elements)) {\n for (const attr of Array.from(el.attributes)) {\n const normalized = normalizeAttributeName(attr.name);\n if (!isModuleKey(normalized)) continue;\n found.add(normalized);\n }\n }\n\n return Array.from(found) as ModuleKey[];\n}","export function parseBoolAttr(v: string | null): boolean | undefined {\n if (v == null) return undefined;\n const s = v.trim().toLowerCase();\n if (s === '' || s === '1' || s === 'true') return true;\n if (s === '0' || s === 'false') return false;\n return undefined;\n}","export function isBrowser(): boolean {\n return typeof window !== 'undefined' && typeof document !== 'undefined';\n}\n\nexport function isServer(): boolean {\n return !isBrowser();\n}\n\nexport * from './bool';","/* --------------------------------------------------------------------------\n * AdLib Attributes · Core\n *\n * Primitives partagées utilisées par le runtime et les modules d’attributs :\n * - délégation d’événements (listeners uniques sur une racine)\n * - registre de modules (définitions + instances)\n * - cycle de vie (mount/unmount/destroy)\n * - observation DOM (signal de changements, orchestration pilotée par le runtime)\n * -------------------------------------------------------------------------- */\n\nexport type Disposer = () => void;\nexport type Cleanup = void | Disposer;\n\nexport type CoreLogger = {\n debug: (...args: unknown[]) => void;\n warn: (...args: unknown[]) => void;\n error: (...args: unknown[]) => void;\n};\n\nexport type CoreOptions = {\n /** Root document/shadow root to bind listeners & observer (defaults to document). */\n root?: Document | ShadowRoot;\n /** Enable debug logs (printed as console.warn with \"[debug]\"). */\n debug?: boolean;\n /** Auto-mount modules on DOMContentLoaded when using singleton. Default: true. */\n autoMount?: boolean;\n};\n\nexport type DelegatedHandler = (e: Event, matched: Element) => void;\n\nexport type OnOptions = {\n /** If true, this delegated handler will run once then auto-unsubscribe. */\n once?: boolean;\n /** Capture phase for the underlying listener (per event type, first call wins). */\n capture?: boolean;\n /** Passive flag for the underlying listener (per event type, first call wins). */\n passive?: boolean;\n};\n\nexport interface Core {\n /**\n * Event delegation: listen on root and invoke handler when an ancestor matches selector.\n * Returns a disposer to remove this specific handler.\n */\n on: (type: string, selector: string, handler: DelegatedHandler, options?: OnOptions) => Disposer;\n\n /** Emit a CustomEvent from a given element. */\n emit: (el: Element, name: string, detail?: unknown) => void;\n\n /** Register a module definition. */\n register: (def: AdLibModuleDefinition) => void;\n\n /** Unregister a module definition by key. */\n unregister: (key: ModuleKey) => void;\n\n /** Mount a module by key, optionally on a given root. */\n mount: (key: ModuleKey, root?: ParentNode) => void;\n\n /** Unmount a module instance by key. */\n unmount: (key: ModuleKey) => void;\n\n /** Mount all registered modules. */\n mountAll: (root?: ParentNode) => void;\n\n /** Unmount all mounted modules. */\n unmountAll: () => void;\n\n /**\n * Observe dynamic DOM changes on a given root.\n *\n * Rôle :\n * - fournir un signal de changement DOM (ajouts/retraits de nœuds)\n * - permettre au runtime d’orchestrer un rescan/remount si nécessaire\n *\n * Retourne un disposer pour arrêter l’observation.\n */\n observe: (root?: ParentNode) => Disposer;\n\n /** Stop observing dynamic DOM changes. */\n stopObserving: () => void;\n\n /** Destroy core: unmount all, remove listeners, disconnect observer. */\n destroy: () => void;\n\n /** Core logger (debug/warn/error). */\n getLogger: () => CoreLogger;\n}\n\n/** Module key type (ex: 'ad-click'). */\nexport type ModuleKey = `ad-${string}`;\n\nexport interface AdLibModuleInstance {\n key: ModuleKey;\n destroy(): void;\n restart?(options?: { rescan?: boolean }): void;\n}\n\nexport interface AdLibModuleDefinition {\n key: ModuleKey;\n init(core: Core): AdLibModuleInstance;\n}\n\n/* --------------------------------- Internals -------------------------------- */\n\ntype DelegatedEntry = {\n selector: string;\n handler: DelegatedHandler;\n once: boolean;\n};\n\ntype EventListenerInfo = {\n capture: boolean;\n passive: boolean;\n listener: (e: Event) => void;\n entries: DelegatedEntry[];\n};\n\nfunction createLogger(debug = false): CoreLogger {\n return {\n debug: (...args: unknown[]) => {\n if (!debug) return;\n console.warn('[debug]', ...args);\n },\n warn: (...args: unknown[]) => {\n console.warn('[warn]', ...args);\n },\n error: (...args: unknown[]) => {\n console.error('[error]', ...args);\n },\n };\n}\n\nfunction isElement(value: unknown): value is Element {\n // Garde-fou typé : vérifie l’existence de Element (tests / environnements non DOM).\n return typeof Element !== 'undefined' && value instanceof Element;\n}\n\nfunction safeMatches(el: Element, selector: string): boolean {\n try {\n return el.matches(selector);\n } catch {\n return false;\n }\n}\n\nfunction findClosestMatching(target: EventTarget | null, selector: string): Element | null {\n let cur: EventTarget | null = target;\n\n while (cur) {\n if (isElement(cur) && safeMatches(cur, selector)) return cur;\n cur = isElement(cur) ? cur.parentElement : null;\n }\n\n return null;\n}\n\nfunction createDelegatedListener(info: EventListenerInfo) {\n return (e: Event) => {\n // Copie défensive : la liste peut être modifiée par un handler \"once\".\n const entries = info.entries.slice();\n\n for (const entry of entries) {\n const matched = findClosestMatching(e.target, entry.selector);\n if (!matched) continue;\n\n entry.handler(e, matched);\n\n if (entry.once) {\n const idx = info.entries.indexOf(entry);\n if (idx >= 0) info.entries.splice(idx, 1);\n }\n }\n };\n}\n\nfunction resolveObserverTarget(root: ParentNode): Node {\n // MutationObserver attend un Node.\n // - Document => document.documentElement si disponible, sinon le document lui-même\n // - ShadowRoot / Element => observe directement\n if (root instanceof Document) return root.documentElement ?? root;\n return root as unknown as Node;\n}\n\n/* ---------------------------------- Core ---------------------------------- */\n\nexport function createCore(options: CoreOptions = {}): Core {\n const root: Document | ShadowRoot = options.root ?? document;\n const logger = createLogger(!!options.debug);\n\n const defs = new Map<ModuleKey, AdLibModuleDefinition>();\n const instances = new Map<ModuleKey, AdLibModuleInstance>();\n\n const listenersByType = new Map<string, EventListenerInfo>();\n\n function on(type: string, selector: string, handler: DelegatedHandler, opts: OnOptions = {}): Disposer {\n const capture = !!opts.capture;\n const passive = !!opts.passive;\n\n const existing = listenersByType.get(type);\n if (existing) {\n existing.entries.push({ selector, handler, once: !!opts.once });\n\n return () => {\n const idx = existing.entries.findIndex((e) => e.selector === selector && e.handler === handler);\n if (idx >= 0) existing.entries.splice(idx, 1);\n\n // ✅ Si c'était le dernier handler, on retire le listener racine et on nettoie la map\n if (existing.entries.length === 0) {\n root.removeEventListener(type, existing.listener, { capture: existing.capture });\n listenersByType.delete(type);\n }\n };\n }\n\n const info: EventListenerInfo = {\n capture,\n passive,\n entries: [{ selector, handler, once: !!opts.once }],\n listener: () => {},\n };\n\n const listener = createDelegatedListener(info);\n info.listener = listener;\n\n listenersByType.set(type, info);\n\n root.addEventListener(type, listener, { capture, passive });\n\n // ✅ Disposer “handler-level” (pas “type-level”)\n return () => {\n const cur = listenersByType.get(type);\n if (!cur) return;\n\n const idx = cur.entries.findIndex((e) => e.selector === selector && e.handler === handler);\n if (idx >= 0) cur.entries.splice(idx, 1);\n\n if (cur.entries.length === 0) {\n root.removeEventListener(type, cur.listener, { capture: cur.capture });\n listenersByType.delete(type);\n }\n };\n }\n\n function emit(el: Element, name: string, detail?: unknown) {\n const ev = new CustomEvent(name, { detail, bubbles: true });\n el.dispatchEvent(ev);\n }\n\n function register(def: AdLibModuleDefinition) {\n defs.set(def.key, def);\n }\n\n function unregister(key: ModuleKey) {\n defs.delete(key);\n }\n\n function mount(key: ModuleKey, _root?: ParentNode) {\n const def = defs.get(key);\n if (!def) return;\n if (instances.has(key)) return;\n\n const inst = def.init(api);\n instances.set(key, inst);\n }\n\n function unmount(key: ModuleKey) {\n const inst = instances.get(key);\n if (!inst) return;\n inst.destroy();\n instances.delete(key);\n }\n\n function mountAll(_root?: ParentNode) {\n for (const key of defs.keys()) mount(key);\n }\n\n function unmountAll() {\n for (const key of instances.keys()) unmount(key);\n }\n\n let observer: MutationObserver | null = null;\n\n function observe(observedRoot: ParentNode = root): Disposer {\n if (observer) return () => {};\n\n observer = new MutationObserver((_mutations) => {\n // Signal DOM : le runtime est responsable de décider quoi charger / recharger.\n // Le core garantit uniquement une observation stable et désinscriptible.\n });\n\n observer.observe(resolveObserverTarget(observedRoot), {\n subtree: true,\n childList: true,\n attributes: false,\n });\n\n return () => stopObserving();\n }\n\n function stopObserving() {\n if (!observer) return;\n observer.disconnect();\n observer = null;\n }\n\n function destroy() {\n stopObserving();\n unmountAll();\n\n for (const [type, info] of listenersByType.entries()) {\n root.removeEventListener(type, info.listener, { capture: info.capture });\n }\n\n listenersByType.clear();\n defs.clear();\n instances.clear();\n }\n\n function getLogger() {\n return logger;\n }\n\n const api: Core = {\n on,\n emit,\n register,\n unregister,\n mount,\n unmount,\n mountAll,\n unmountAll,\n observe,\n stopObserving,\n destroy,\n getLogger,\n };\n\n return api;\n}\n\n/* ----------------------------- Singleton helpers ---------------------------- */\n\nlet singleton: Core | null = null;\n\nexport function getCoreSingleton(options: CoreOptions = {}): Core {\n if (singleton) return singleton;\n singleton = createCore({ autoMount: true, ...options });\n\n const shouldAutoMount = options.autoMount ?? true;\n if (shouldAutoMount && typeof document !== 'undefined') {\n if (document.readyState === 'loading') {\n document.addEventListener(\n 'DOMContentLoaded',\n () => {\n singleton?.mountAll();\n },\n { once: true }\n );\n } else {\n singleton.mountAll();\n }\n }\n\n return singleton;\n}\n\nexport default createCore;","import type { ModuleKey, RuntimeConfig } from './types';\n\nfunction normalizeOrigin(origin: string): string {\n return origin.trim().replace(/\\/+$/, '');\n}\n\nfunction resolveOrigin(config: RuntimeConfig): string {\n // `base` permet de forcer une origine de chargement (ex: CDN custom).\n // Sinon, on utilise `registry` (ex: jsDelivr / unpkg / registry interne).\n return normalizeOrigin(config.base ?? config.registry);\n}\n\nfunction resolveVersion(config: RuntimeConfig): string {\n const v = (config.version ?? '').trim();\n return v || 'latest';\n}\n\n/**\n * Construit le chemin d'import ESM d'un module à partir de la configuration runtime.\n * Format :\n * {origin}/@adartem/{package}@{version}/dist/index.js\n */\nfunction makeEsmImportPath(origin: string, pkgName: string, version: string): string {\n return `${origin}/@adartem/${pkgName}@${version}/dist/index.js`;\n}\n\nconst PACKAGE_BY_KEY: Record<ModuleKey, string> = {\n 'ad-click': 'ad-click',\n};\n\nexport function getImportPathForModule(key: ModuleKey, config: RuntimeConfig): string | null {\n const origin = resolveOrigin(config);\n const version = resolveVersion(config);\n\n const pkgName = PACKAGE_BY_KEY[key];\n if (!pkgName) return null;\n\n return makeEsmImportPath(origin, pkgName, version);\n}","import { collectModuleKeysFromDOM, isBrowser } from '@adartem/adlib-utils';\n\nimport type { Core } from '../core';\nimport { createCore } from '../core';\nimport { getImportPathForModule } from './module-map';\nimport type {\n AdLibModuleDefinition,\n AdLibRuntime,\n GlobalQueueItem,\n ModuleKey,\n RuntimeConfig,\n RuntimeModuleState,\n RuntimeOptions,\n} from './types';\n\n/**\n * Runtime robuste:\n * - load() : import + init(core) + état\n * - push() : callbacks avant/après load\n * - queue globale window.AdLibAttributesQueue\n * - reload() : destroy module + re-init\n * - auto (optionnel) : scan DOM minimal + MutationObserver\n */\n\ntype QueueEntry = {\n key: ModuleKey;\n cb: (state: RuntimeModuleState) => void;\n};\n\nconst DEFAULT_REGISTRY = 'https://cdn.jsdelivr.net/npm';\n\nfunction stateOf(modules: Record<string, RuntimeModuleState>, key: ModuleKey): RuntimeModuleState {\n return (modules[key] ??= { key, status: 'idle' });\n}\n\nfunction isReadyOrError(s: RuntimeModuleState) {\n return s.status === 'ready' || s.status === 'error';\n}\n\nfunction toError(err: unknown): Error {\n return err instanceof Error ? err : new Error(String(err));\n}\n\nfunction normalizeUrlBase(value?: string): string | undefined {\n const v = (value ?? '').trim();\n if (!v) return undefined;\n return v.replace(/\\/+$/, '');\n}\n\nfunction resolveConfig(options: RuntimeOptions): RuntimeConfig {\n const registry = normalizeUrlBase(options.config?.registry) ?? DEFAULT_REGISTRY;\n const version = (options.config?.version ?? options.version).trim() || options.version;\n\n const out: RuntimeConfig = { registry, version };\n\n const base = normalizeUrlBase(options.config?.base);\n if (base) out.base = base; // ✅ n’ajoute pas la clé si undefined\n\n return out;\n}\n\n/**\n * Valide/normalise le résultat d'un import dynamique vers une AdLibModuleDefinition.\n * Permet d'éviter les `any` et les accès unsafe.\n */\nfunction toModuleDefinition(mod: unknown, expectedKey: ModuleKey): AdLibModuleDefinition {\n const candidate = (() => {\n if (mod && typeof mod === 'object') {\n const record = mod as Record<string, unknown>;\n return record.default ?? mod;\n }\n return mod;\n })();\n\n if (!candidate || typeof candidate !== 'object') {\n throw new Error(`Invalid module definition for ${expectedKey}`);\n }\n\n const def = candidate as Partial<AdLibModuleDefinition>;\n\n if (typeof def.key !== 'string' || typeof def.init !== 'function') {\n throw new Error(`Invalid module definition for ${expectedKey}`);\n }\n\n // Sécurité: clé cohérente\n if (def.key !== expectedKey) {\n throw new Error(`Module key mismatch: expected \"${expectedKey}\", got \"${def.key}\"`);\n }\n\n return def as AdLibModuleDefinition;\n}\n\nexport function createRuntime(options: RuntimeOptions): AdLibRuntime {\n const debug = options.debug ?? false;\n const auto = options.auto ?? false;\n\n // ✅ Ownership: runtime propriétaire uniquement si options.core est absent (null/undefined)\n const ownsCore = options.core == null;\n\n // ✅ Runtime ne récupère jamais le singleton tout seul.\n // - si core injecté => utilisé tel quel, et NON détruit par runtime.destroy()\n // - sinon => core dédié, détruit par runtime.destroy()\n const core: Core =\n options.core ??\n createCore({\n debug,\n autoMount: false,\n });\n\n const logger = core.getLogger();\n const config = resolveConfig(options);\n\n const modules: Record<string, RuntimeModuleState> = {};\n const queue: QueueEntry[] = [];\n\n let observer: MutationObserver | null = null;\n\n function log(...args: unknown[]) {\n if (!debug) return;\n logger.debug('[AdLib Runtime]', ...args);\n }\n\n function logError(...args: unknown[]) {\n logger.error('[AdLib Runtime]', ...args);\n }\n\n function flush(key: ModuleKey, st: RuntimeModuleState) {\n for (let i = queue.length - 1; i >= 0; i--) {\n const entry = queue[i];\n if (!entry) continue;\n if (entry.key === key) {\n queue.splice(i, 1);\n try {\n entry.cb(st);\n } catch (e) {\n logError('push callback failed', key, e);\n }\n }\n }\n }\n\n function destroyModule(key: ModuleKey) {\n const st = modules[key];\n if (!st) return;\n\n try {\n st.instance?.destroy?.();\n } catch (e) {\n logError('destroyModule failed', key, e);\n }\n\n delete st.instance;\n delete st.def;\n delete st.error;\n delete st.promise;\n\n st.status = 'idle';\n }\n\n async function load(key: ModuleKey): Promise<RuntimeModuleState> {\n const st = stateOf(modules, key);\n\n if (st.status === 'ready') return st;\n if (st.status === 'error') return st;\n\n if (st.status === 'loading' && st.promise) return st.promise;\n\n const importPath = getImportPathForModule(key, config);\n if (!importPath) {\n st.status = 'error';\n st.error = new Error(`Unknown module key: ${key}`);\n flush(key, st);\n return st;\n }\n\n st.status = 'loading';\n log('load()', key, '->', importPath);\n\n const promise: Promise<RuntimeModuleState> = (async () => {\n try {\n const mod: unknown = await import(/* @vite-ignore */ importPath);\n const def = toModuleDefinition(mod, key);\n\n st.def = def;\n\n if (!st.instance) {\n st.instance = def.init(core);\n }\n\n st.status = 'ready';\n delete st.error;\n delete st.promise;\n\n flush(key, st);\n return st;\n } catch (err) {\n st.status = 'error';\n st.error = toError(err);\n delete st.promise;\n\n flush(key, st);\n return st;\n }\n })();\n\n st.promise = promise;\n return promise;\n }\n\n async function reload(key: ModuleKey): Promise<RuntimeModuleState> {\n log('reload()', key);\n destroyModule(key);\n return load(key);\n }\n\n function push(key: ModuleKey, cb: (state: RuntimeModuleState) => void) {\n const st = modules[key];\n if (st && isReadyOrError(st)) {\n try {\n cb(st);\n } catch (e) {\n logError('push callback failed', key, e);\n }\n return;\n }\n queue.push({ key, cb });\n }\n\n function autoLoadFromDOM(root: ParentNode = document) {\n const keys = collectModuleKeysFromDOM(root);\n for (const key of keys) void load(key);\n }\n\n function startObserver() {\n if (!isBrowser()) return;\n if (observer) return;\n\n observer = new MutationObserver((mutations) => {\n for (const m of mutations) {\n for (const node of Array.from(m.addedNodes)) {\n if (!(node instanceof HTMLElement)) continue;\n autoLoadFromDOM(node);\n }\n }\n });\n\n observer.observe(document.documentElement, { childList: true, subtree: true });\n }\n\n function stopObserver() {\n observer?.disconnect();\n observer = null;\n }\n\n function destroy(opts?: { keepGlobal?: boolean }) {\n log('destroy()');\n\n stopObserver();\n\n for (const st of Object.values(modules)) {\n try {\n st.instance?.destroy?.();\n } catch (e) {\n logError('destroy module failed', st.key, e);\n }\n }\n\n // ✅ Ownership rule: ne détruit le core QUE si le runtime l'a créé\n if (ownsCore) {\n try {\n core.destroy();\n } catch (e) {\n logError('core.destroy failed', e);\n }\n }\n\n for (const k of Object.keys(modules)) delete modules[k];\n queue.length = 0;\n\n if (!opts?.keepGlobal && typeof window !== 'undefined') {\n delete window.AdLibAttributes;\n }\n }\n\n const runtime: AdLibRuntime = {\n version: options.version,\n config,\n core,\n debug,\n modules,\n load,\n push,\n reload,\n destroy,\n };\n\n if (typeof window !== 'undefined') {\n const globalQ = window.AdLibAttributesQueue;\n if (Array.isArray(globalQ) && globalQ.length > 0) {\n const items: GlobalQueueItem[] = globalQ.splice(0, globalQ.length);\n for (const [key, cb] of items) runtime.push(key, cb);\n }\n }\n\n if (auto && isBrowser()) {\n autoLoadFromDOM(document.body ?? document);\n startObserver();\n }\n\n return runtime;\n}","import { isModuleKey, normalizeAttributeName } from '@adartem/adlib-utils';\n\nimport type { LoaderScriptConfig, LoaderScriptInfo, RuntimeConfig } from './types';\n\n/** Helpers DOM-agnostic (compat jsdom + environnements DOM partiels) */\n\ntype AttrLike = { name: string };\ntype AttributesLike = {\n length: number;\n item(index: number): AttrLike | null;\n};\n\nfunction hasGetAttributeNames(el: unknown): el is { getAttributeNames(): unknown } {\n return (\n typeof el === 'object' &&\n el !== null &&\n typeof (el as { getAttributeNames?: unknown }).getAttributeNames === 'function'\n );\n}\n\nfunction isStringArray(value: unknown): value is string[] {\n return Array.isArray(value) && value.every((v) => typeof v === 'string');\n}\n\nfunction hasAttributesLike(el: unknown): el is { attributes: AttributesLike } {\n if (typeof el !== 'object' || el === null) return false;\n\n const attrs = (el as { attributes?: unknown }).attributes;\n if (typeof attrs !== 'object' || attrs === null) return false;\n\n const a = attrs as Partial<AttributesLike>;\n return typeof a.length === 'number' && typeof a.item === 'function';\n}\n\nfunction hasQuerySelectorAll(\n root: unknown,\n): root is ParentNode & { querySelectorAll(selectors: string): NodeListOf<Element> } {\n if (typeof root !== 'object' || root === null) return false;\n return typeof (root as { querySelectorAll?: unknown }).querySelectorAll === 'function';\n}\n\n/** Safe wrapper (jsdom + navigateurs anciens + environnements DOM partiels) */\nfunction getAttributeNamesSafe(el: Element): string[] {\n // 1) voie moderne: getAttributeNames()\n if (hasGetAttributeNames(el)) {\n const maybe = el.getAttributeNames();\n if (isStringArray(maybe)) return maybe;\n }\n\n // 2) fallback: attributes NamedNodeMap-like (structure minimale)\n if (hasAttributesLike(el)) {\n const out: string[] = [];\n for (let i = 0; i < el.attributes.length; i++) {\n const attr = el.attributes.item(i);\n if (attr && typeof attr.name === 'string' && attr.name) out.push(attr.name);\n }\n return out;\n }\n\n return [];\n}\n\n/**\n * Heuristique “loader script” :\n * - <script type=\"module\" src=\".../attributes.js\">\n * Tolérant aux chemins (CDN, querystring, chemins relatifs/absolus).\n */\nfunction isAttributesLoaderScript(s: HTMLScriptElement): boolean {\n const type = (s.getAttribute('type') ?? '').trim();\n if (type && type !== 'module') return false;\n\n const src = (s.getAttribute('src') ?? '').trim();\n if (!src) return false;\n\n return src.includes('attributes.js');\n}\n\nfunction pickNonEmptyString(value: unknown): string | undefined {\n if (typeof value !== 'string') return undefined;\n const v = value.trim();\n return v ? v : undefined;\n}\n\nfunction parseBoolean(value: unknown, fallback: boolean): boolean {\n if (typeof value !== 'string') return fallback;\n const v = value.trim().toLowerCase();\n if (v === '' || v === 'true' || v === '1' || v === 'yes' || v === 'on') return true;\n if (v === 'false' || v === '0' || v === 'no' || v === 'off') return false;\n return fallback;\n}\n\n/**\n * Source unique de vérité: lit data-adlib-* depuis le <script> et retourne une config normalisée.\n * Conventions dataset camelCase :\n * - data-adlib-registry => dataset.adlibRegistry\n * - data-adlib-version => dataset.adlibVersion\n * - data-adlib-base => dataset.adlibBase\n * - data-adlib-auto => dataset.adlibAuto\n * - data-adlib-debug => dataset.adlibDebug\n */\nfunction readLoaderConfig(s: HTMLScriptElement): LoaderScriptConfig {\n // dataset est standard sur HTMLScriptElement en DOM.\n // Fallback léger pour les environnements DOM incomplets.\n const ds = (s as unknown as { dataset?: Record<string, string> }).dataset ?? {};\n\n const debug = parseBoolean(ds.adlibDebug, false);\n const auto = parseBoolean(ds.adlibAuto, true);\n\n const registry = pickNonEmptyString(ds.adlibRegistry);\n const version = pickNonEmptyString(ds.adlibVersion);\n const base = pickNonEmptyString(ds.adlibBase);\n\n // ✅ exactOptionalPropertyTypes-safe : ne pas inclure les clés si undefined\n const config: Partial<RuntimeConfig> = {};\n if (registry) config.registry = registry;\n if (version) config.version = version;\n if (base) config.base = base;\n\n return { debug, auto, config };\n}\n\nexport function findLoaderScripts(root: ParentNode = document): LoaderScriptInfo[] {\n if (!hasQuerySelectorAll(root)) return [];\n\n const scripts = Array.from(root.querySelectorAll('script'));\n const result: LoaderScriptInfo[] = [];\n\n for (const script of scripts) {\n if (!(script instanceof HTMLScriptElement)) continue;\n if (!isAttributesLoaderScript(script)) continue;\n\n const requested = new Set<LoaderScriptInfo['requestedKeys'][number]>();\n\n for (const rawName of getAttributeNamesSafe(script)) {\n const name = normalizeAttributeName(rawName);\n if (isModuleKey(name)) requested.add(name);\n }\n\n result.push({\n el: script,\n requestedKeys: Array.from(requested),\n loaderConfig: readLoaderConfig(script),\n });\n }\n\n return result;\n}","import { isBrowser } from '@adartem/adlib-utils';\n\nimport { getCoreSingleton } from '../core';\nimport { createRuntime } from './runtime';\nimport { findLoaderScripts } from './script-detection';\nimport type { ModuleKey } from './types';\n\ndeclare const __ADLIB_VERSION__: string | undefined;\n\n// Vitest / dev (TS direct) => la constante n'existe pas\n// Build tsup => la constante est injectée (string)\nconst VERSION = typeof __ADLIB_VERSION__ === 'string' ? __ADLIB_VERSION__ : 'dev';\n\n(function bootstrap() {\n if (!isBrowser()) return;\n\n // Ne pas re-bootstrap si déjà présent\n if (window.AdLibAttributes) return;\n\n const loaders = findLoaderScripts(document);\n const primary = loaders[0];\n\n // ✅ Source unique de vérité: script-detection.ts normalise data-adlib-*\n const debug = primary?.loaderConfig.debug ?? false;\n const auto = primary?.loaderConfig.auto ?? true;\n const config = primary?.loaderConfig.config ?? {};\n\n const core = getCoreSingleton({ root: document, debug });\n const runtime = createRuntime({\n version: VERSION,\n core,\n debug,\n auto,\n config,\n });\n\n // Expose global\n window.AdLibAttributes = runtime;\n\n // 1) Modules demandés via attributs du <script ... attributes.js ...>\n const requested = new Set<ModuleKey>();\n for (const info of loaders) {\n for (const k of info.requestedKeys) requested.add(k);\n }\n\n // 2) Chargement initial\n for (const key of requested) {\n runtime.load(key).catch(() => {\n // le runtime gère déjà l'état error ; ici on évite de throw global\n });\n }\n})();"],"mappings":"AAEO,SAASA,EAAYC,EAAmC,CAC7D,OAAOA,EAAM,WAAW,KAAK,GAAKA,EAAM,OAAS,CACnD,CAEO,SAASC,EAAuBC,EAAsB,CAC3D,OAAOA,EAAK,WAAW,OAAO,EAAIA,EAAK,MAAM,CAAC,EAAIA,CACpD,CCCO,SAASC,EAAoBH,EAA+C,CACjF,OAAI,OAAOA,GAAU,UAAYA,IAAU,KAAa,GAOjD,OAHGA,EACI,kBAEQ,UACxB,CCdO,SAASI,EAAyBC,EAAmB,SAAuB,CACjF,GAAI,CAACF,EAAoBE,CAAI,EAAA,MAAU,CAAA,EAEvC,IAAMC,EAAA,IAAY,IACZC,EAAWF,EAAK,iBAA8B,GAAG,EAEvD,QAAWG,KAAM,MAAM,KAAKD,CAAQ,EAClC,QAAWE,KAAQ,MAAM,KAAKD,EAAG,UAAU,EAAG,CAC5C,IAAME,EAAaT,EAAuBQ,EAAK,IAAI,EAC9CV,EAAYW,CAAU,GAC3BJ,EAAM,IAAII,CAAU,CACtB,CAGF,OAAO,MAAM,KAAKJ,CAAK,CACzB,CEnBO,SAASK,GAAqB,CACnC,OAAO,OAAO,OAAW,KAAe,OAAO,SAAa,GAC9D,CCmHA,SAASC,EAAaC,EAAQ,GAAmB,CAC/C,MAAO,CACL,MAAO,IAAIC,IAAoB,CACxBD,GACL,QAAQ,KAAK,UAAW,GAAGC,CAAI,CACjC,EACA,KAAM,IAAIA,IAAoB,CAC5B,QAAQ,KAAK,SAAU,GAAGA,CAAI,CAChC,EACA,MAAO,IAAIA,IAAoB,CAC7B,QAAQ,MAAM,UAAW,GAAGA,CAAI,CAClC,CACF,CACF,CAEA,SAASC,EAAUC,EAAkC,CAEnD,OAAO,OAAO,QAAY,KAAeA,aAAiB,OAC5D,CAEA,SAASC,EAAYC,EAAaC,EAA2B,CAC3D,GAAI,CACF,OAAOD,EAAG,QAAQC,CAAQ,CAC5B,MAAQ,CACN,MAAO,EACT,CACF,CAEA,SAASC,EAAoBC,EAA4BF,EAAkC,CACzF,IAAIG,EAA0BD,EAE9B,KAAOC,GAAK,CACV,GAAIP,EAAUO,CAAG,GAAKL,EAAYK,EAAKH,CAAQ,EAAG,OAAOG,EACzDA,EAAMP,EAAUO,CAAG,EAAIA,EAAI,cAAgB,IAC7C,CAEA,OAAO,IACT,CAEA,SAASC,EAAwBC,EAAyB,CACxD,OAAQC,GAAa,CAEnB,IAAMC,EAAUF,EAAK,QAAQ,MAAM,EAEnC,QAAWG,KAASD,EAAS,CAC3B,IAAME,EAAUR,EAAoBK,EAAE,OAAQE,EAAM,QAAQ,EAC5D,GAAKC,IAELD,EAAM,QAAQF,EAAGG,CAAO,EAEpBD,EAAM,MAAM,CACd,IAAME,EAAML,EAAK,QAAQ,QAAQG,CAAK,EAClCE,GAAO,GAAGL,EAAK,QAAQ,OAAOK,EAAK,CAAC,CAC1C,CACF,CACF,CACF,CAEA,SAASC,EAAsBC,EAAwB,CAIrD,OAAIA,aAAgB,SAAiBA,EAAK,iBAAmBA,EACtDA,CACT,CAIO,SAASC,EAAWC,EAAuB,CAAC,EAAS,CAC1D,IAAMF,EAA8BE,EAAQ,MAAQ,SAC9CC,EAAStB,EAAa,CAAC,CAACqB,EAAQ,KAAK,EAErCE,EAAO,IAAI,IACXC,EAAY,IAAI,IAEhBC,EAAkB,IAAI,IAE5B,SAASC,EAAGC,EAAcpB,EAAkBqB,EAA2BC,EAAkB,CAAC,EAAa,CACrG,IAAMC,EAAU,CAAC,CAACD,EAAK,QACjBE,EAAU,CAAC,CAACF,EAAK,QAEjBG,EAAWP,EAAgB,IAAIE,CAAI,EACzC,GAAIK,EACF,OAAAA,EAAS,QAAQ,KAAK,CAAE,SAAAzB,EAAU,QAAAqB,EAAS,KAAM,CAAC,CAACC,EAAK,IAAK,CAAC,EAEvD,IAAM,CACX,IAAMZ,EAAMe,EAAS,QAAQ,UAAWnB,GAAMA,EAAE,WAAaN,GAAYM,EAAE,UAAYe,CAAO,EAC1FX,GAAO,GAAGe,EAAS,QAAQ,OAAOf,EAAK,CAAC,EAGxCe,EAAS,QAAQ,SAAW,IAC9Bb,EAAK,oBAAoBQ,EAAMK,EAAS,SAAU,CAAE,QAASA,EAAS,OAAQ,CAAC,EAC/EP,EAAgB,OAAOE,CAAI,EAE/B,EAGF,IAAMf,EAA0B,CAC9B,QAAAkB,EACA,QAAAC,EACA,QAAS,CAAC,CAAE,SAAAxB,EAAU,QAAAqB,EAAS,KAAM,CAAC,CAACC,EAAK,IAAK,CAAC,EAClD,SAAU,IAAM,CAAC,CACnB,EAEMI,EAAWtB,EAAwBC,CAAI,EAC7C,OAAAA,EAAK,SAAWqB,EAEhBR,EAAgB,IAAIE,EAAMf,CAAI,EAE9BO,EAAK,iBAAiBQ,EAAMM,EAAU,CAAE,QAAAH,EAAS,QAAAC,CAAQ,CAAC,EAGnD,IAAM,CACX,IAAMrB,EAAMe,EAAgB,IAAIE,CAAI,EACpC,GAAI,CAACjB,EAAK,OAEV,IAAMO,EAAMP,EAAI,QAAQ,UAAWG,GAAMA,EAAE,WAAaN,GAAYM,EAAE,UAAYe,CAAO,EACrFX,GAAO,GAAGP,EAAI,QAAQ,OAAOO,EAAK,CAAC,EAEnCP,EAAI,QAAQ,SAAW,IACzBS,EAAK,oBAAoBQ,EAAMjB,EAAI,SAAU,CAAE,QAASA,EAAI,OAAQ,CAAC,EACrEe,EAAgB,OAAOE,CAAI,EAE/B,CACF,CAEA,SAASO,EAAK5B,EAAa6B,EAAcC,EAAkB,CACzD,IAAMC,EAAK,IAAI,YAAYF,EAAM,CAAE,OAAAC,EAAQ,QAAS,EAAK,CAAC,EAC1D9B,EAAG,cAAc+B,CAAE,CACrB,CAEA,SAASC,EAASC,EAA4B,CAC5ChB,EAAK,IAAIgB,EAAI,IAAKA,CAAG,CACvB,CAEA,SAASC,EAAWC,EAAgB,CAClClB,EAAK,OAAOkB,CAAG,CACjB,CAEA,SAASC,EAAMD,EAAgBE,EAAoB,CACjD,IAAMJ,EAAMhB,EAAK,IAAIkB,CAAG,EAExB,GADI,CAACF,GACDf,EAAU,IAAIiB,CAAG,EAAG,OAExB,IAAMG,EAAOL,EAAI,KAAKM,CAAG,EACzBrB,EAAU,IAAIiB,EAAKG,CAAI,CACzB,CAEA,SAASE,EAAQL,EAAgB,CAC/B,IAAMG,EAAOpB,EAAU,IAAIiB,CAAG,EACzBG,IACLA,EAAK,QAAQ,EACbpB,EAAU,OAAOiB,CAAG,EACtB,CAEA,SAASM,EAASJ,EAAoB,CACpC,QAAWF,KAAOlB,EAAK,KAAK,EAAGmB,EAAMD,CAAG,CAC1C,CAEA,SAASO,GAAa,CACpB,QAAWP,KAAOjB,EAAU,KAAK,EAAGsB,EAAQL,CAAG,CACjD,CAEA,IAAIQ,EAAoC,KAExC,SAASC,EAAQC,EAA2BhC,EAAgB,CAC1D,OAAI8B,EAAiB,IAAM,CAAC,GAE5BA,EAAW,IAAI,iBAAkBG,GAAe,CAGhD,CAAC,EAEDH,EAAS,QAAQ/B,EAAsBiC,CAAY,EAAG,CACpD,QAAS,GACT,UAAW,GACX,WAAY,EACd,CAAC,EAEM,IAAME,EAAc,EAC7B,CAEA,SAASA,GAAgB,CAClBJ,IACLA,EAAS,WAAW,EACpBA,EAAW,KACb,CAEA,SAASK,GAAU,CACjBD,EAAc,EACdL,EAAW,EAEX,OAAW,CAACrB,EAAMf,CAAI,IAAKa,EAAgB,QAAQ,EACjDN,EAAK,oBAAoBQ,EAAMf,EAAK,SAAU,CAAE,QAASA,EAAK,OAAQ,CAAC,EAGzEa,EAAgB,MAAM,EACtBF,EAAK,MAAM,EACXC,EAAU,MAAM,CAClB,CAEA,SAAS+B,GAAY,CACnB,OAAOjC,CACT,CAEA,IAAMuB,EAAY,CAChB,GAAAnB,EACA,KAAAQ,EACA,SAAAI,EACA,WAAAE,EACA,MAAAE,EACA,QAAAI,EACA,SAAAC,EACA,WAAAC,EACA,QAAAE,EACA,cAAAG,EACA,QAAAC,EACA,UAAAC,CACF,EAEA,OAAOV,CACT,CAIA,IAAIW,EAAyB,KAEtB,SAASC,EAAiBpC,EAAuB,CAAC,EAAS,CAChE,OAAImC,IACJA,EAAYpC,EAAW,CAAE,UAAW,GAAM,GAAGC,CAAQ,CAAC,GAE9BA,EAAQ,WAAa,KACtB,OAAO,SAAa,MACrC,SAAS,aAAe,UAC1B,SAAS,iBACP,mBACA,IAAM,CACJmC,GAAW,SAAS,CACtB,EACA,CAAE,KAAM,EAAK,CACf,EAEAA,EAAU,SAAS,GAIhBA,EACT,CC1WA,SAASE,EAAgBC,EAAwB,CAC/C,OAAOA,EAAO,KAAK,EAAE,QAAQ,OAAQ,EAAE,CACzC,CAEA,SAASC,EAAcC,EAA+B,CAGpD,OAAOH,EAAgBG,EAAO,MAAQA,EAAO,QAAQ,CACvD,CAEA,SAASC,GAAeD,EAA+B,CAErD,OADWA,EAAO,SAAW,IAAI,KAAK,GAC1B,QACd,CAOA,SAASE,GAAkBJ,EAAgBK,EAAiBC,EAAyB,CACnF,MAAO,GAAGN,CAAM,aAAaK,CAAO,IAAIC,CAAO,gBACjD,CAEA,IAAMC,GAA4C,CAChD,WAAY,UACd,EAEO,SAASC,EAAuBC,EAAgBP,EAAsC,CAC3F,IAAMF,EAASC,EAAcC,CAAM,EAC7BI,EAAUH,GAAeD,CAAM,EAE/BG,EAAUE,GAAeE,CAAG,EAClC,OAAKJ,EAEED,GAAkBJ,EAAQK,EAASC,CAAO,EAF5B,IAGvB,CCTA,IAAMI,GAAmB,+BAEzB,SAASC,GAAQC,EAA6CC,EAAoC,CAChG,OAAQD,EAAAC,KAAAD,EAAAC,GAAiB,CAAE,IAAAA,EAAK,OAAQ,MAAO,EACjD,CAEA,SAASC,GAAeC,EAAuB,CAC7C,OAAOA,EAAE,SAAW,SAAWA,EAAE,SAAW,OAC9C,CAEA,SAASC,GAAQC,EAAqB,CACpC,OAAOA,aAAe,MAAQA,EAAM,IAAI,MAAM,OAAOA,CAAG,CAAC,CAC3D,CAEA,SAASC,EAAiBC,EAAoC,CAC5D,IAAMC,GAAKD,GAAS,IAAI,KAAK,EAC7B,GAAKC,EACL,OAAOA,EAAE,QAAQ,OAAQ,EAAE,CAC7B,CAEA,SAASC,GAAcC,EAAwC,CAC7D,IAAMC,EAAWL,EAAiBI,EAAQ,QAAQ,QAAQ,GAAKZ,GACzDc,GAAWF,EAAQ,QAAQ,SAAWA,EAAQ,SAAS,KAAK,GAAKA,EAAQ,QAEzEG,EAAqB,CAAE,SAAAF,EAAU,QAAAC,CAAQ,EAEzCE,EAAOR,EAAiBI,EAAQ,QAAQ,IAAI,EAClD,OAAII,IAAMD,EAAI,KAAOC,GAEdD,CACT,CAMA,SAASE,GAAmBC,EAAcC,EAA+C,CACvF,IAAMC,EACAF,GAAO,OAAOA,GAAQ,SACTA,EACD,SAAWA,EAEpBA,EAGT,GAAI,CAACE,GAAa,OAAOA,GAAc,SACrC,MAAM,IAAI,MAAM,iCAAiCD,CAAW,EAAE,EAGhE,IAAME,EAAMD,EAEZ,GAAI,OAAOC,EAAI,KAAQ,UAAY,OAAOA,EAAI,MAAS,WACrD,MAAM,IAAI,MAAM,iCAAiCF,CAAW,EAAE,EAIhE,GAAIE,EAAI,MAAQF,EACd,MAAM,IAAI,MAAM,kCAAkCA,CAAW,WAAWE,EAAI,GAAG,GAAG,EAGpF,OAAOA,CACT,CAEO,SAASC,EAAcV,EAAuC,CACnE,IAAMW,EAAQX,EAAQ,OAAS,GACzBY,EAAOZ,EAAQ,MAAQ,GAGvBa,EAAWb,EAAQ,MAAQ,KAK3Bc,EACJd,EAAQ,MACRe,EAAW,CACT,MAAAJ,EACA,UAAW,EACb,CAAC,EAEGK,EAASF,EAAK,UAAU,EACxBG,EAASlB,GAAcC,CAAO,EAE9BV,EAA8C,CAAC,EAC/C4B,EAAsB,CAAC,EAEzBC,EAAoC,KAExC,SAASC,KAAOC,EAAiB,CAC1BV,GACLK,EAAO,MAAM,kBAAmB,GAAGK,CAAI,CACzC,CAEA,SAASC,KAAYD,EAAiB,CACpCL,EAAO,MAAM,kBAAmB,GAAGK,CAAI,CACzC,CAEA,SAASE,EAAMhC,EAAgBiC,EAAwB,CACrD,QAASC,EAAIP,EAAM,OAAS,EAAGO,GAAK,EAAGA,IAAK,CAC1C,IAAMC,EAAQR,EAAMO,CAAC,EACrB,GAAKC,GACDA,EAAM,MAAQnC,EAAK,CACrB2B,EAAM,OAAOO,EAAG,CAAC,EACjB,GAAI,CACFC,EAAM,GAAGF,CAAE,CACb,OAASG,EAAG,CACVL,EAAS,uBAAwB/B,EAAKoC,CAAC,CACzC,CACF,CACF,CACF,CAEA,SAASC,EAAcrC,EAAgB,CACrC,IAAMiC,EAAKlC,EAAQC,CAAG,EACtB,GAAKiC,EAEL,IAAI,CACFA,EAAG,UAAU,UAAU,CACzB,OAASG,EAAG,CACVL,EAAS,uBAAwB/B,EAAKoC,CAAC,CACzC,CAEA,OAAOH,EAAG,SACV,OAAOA,EAAG,IACV,OAAOA,EAAG,MACV,OAAOA,EAAG,QAEVA,EAAG,OAAS,OACd,CAEA,eAAeK,EAAKtC,EAA6C,CAC/D,IAAMiC,EAAKnC,GAAQC,EAASC,CAAG,EAG/B,GADIiC,EAAG,SAAW,SACdA,EAAG,SAAW,QAAS,OAAOA,EAElC,GAAIA,EAAG,SAAW,WAAaA,EAAG,QAAS,OAAOA,EAAG,QAErD,IAAMM,EAAaC,EAAuBxC,EAAK0B,CAAM,EACrD,GAAI,CAACa,EACH,OAAAN,EAAG,OAAS,QACZA,EAAG,MAAQ,IAAI,MAAM,uBAAuBjC,CAAG,EAAE,EACjDgC,EAAMhC,EAAKiC,CAAE,EACNA,EAGTA,EAAG,OAAS,UACZJ,EAAI,SAAU7B,EAAK,KAAMuC,CAAU,EAEnC,IAAME,GAAwC,SAAY,CACxD,GAAI,CACF,IAAM1B,EAAe,MAAM,OAA0BwB,GAC/CrB,EAAMJ,GAAmBC,EAAKf,CAAG,EAEvC,OAAAiC,EAAG,IAAMf,EAEJe,EAAG,WACNA,EAAG,SAAWf,EAAI,KAAKK,CAAI,GAG7BU,EAAG,OAAS,QACZ,OAAOA,EAAG,MACV,OAAOA,EAAG,QAEVD,EAAMhC,EAAKiC,CAAE,EACNA,CACT,OAAS7B,EAAK,CACZ,OAAA6B,EAAG,OAAS,QACZA,EAAG,MAAQ9B,GAAQC,CAAG,EACtB,OAAO6B,EAAG,QAEVD,EAAMhC,EAAKiC,CAAE,EACNA,CACT,CACF,GAAG,EAEH,OAAAA,EAAG,QAAUQ,EACNA,CACT,CAEA,eAAeC,EAAO1C,EAA6C,CACjE,OAAA6B,EAAI,WAAY7B,CAAG,EACnBqC,EAAcrC,CAAG,EACVsC,EAAKtC,CAAG,CACjB,CAEA,SAAS2C,EAAK3C,EAAgB4C,EAAyC,CACrE,IAAMX,EAAKlC,EAAQC,CAAG,EACtB,GAAIiC,GAAMhC,GAAegC,CAAE,EAAG,CAC5B,GAAI,CACFW,EAAGX,CAAE,CACP,OAASG,EAAG,CACVL,EAAS,uBAAwB/B,EAAKoC,CAAC,CACzC,CACA,MACF,CACAT,EAAM,KAAK,CAAE,IAAA3B,EAAK,GAAA4C,CAAG,CAAC,CACxB,CAEA,SAASC,EAAgBC,EAAmB,SAAU,CACpD,IAAMC,EAAOC,EAAyBF,CAAI,EAC1C,QAAW9C,KAAO+C,EAAWT,EAAKtC,CAAG,CACvC,CAEA,SAASiD,GAAgB,CAClBC,EAAU,IACXtB,IAEJA,EAAW,IAAI,iBAAkBuB,GAAc,CAC7C,QAAWC,KAAKD,EACd,QAAWE,KAAQ,MAAM,KAAKD,EAAE,UAAU,EAClCC,aAAgB,aACtBR,EAAgBQ,CAAI,CAG1B,CAAC,EAEDzB,EAAS,QAAQ,SAAS,gBAAiB,CAAE,UAAW,GAAM,QAAS,EAAK,CAAC,GAC/E,CAEA,SAAS0B,GAAe,CACtB1B,GAAU,WAAW,EACrBA,EAAW,IACb,CAEA,SAAS2B,EAAQC,EAAiC,CAChD3B,EAAI,WAAW,EAEfyB,EAAa,EAEb,QAAWrB,KAAM,OAAO,OAAOlC,CAAO,EACpC,GAAI,CACFkC,EAAG,UAAU,UAAU,CACzB,OAASG,EAAG,CACVL,EAAS,wBAAyBE,EAAG,IAAKG,CAAC,CAC7C,CAIF,GAAId,EACF,GAAI,CACFC,EAAK,QAAQ,CACf,OAASa,EAAG,CACVL,EAAS,sBAAuBK,CAAC,CACnC,CAGF,QAAWqB,KAAK,OAAO,KAAK1D,CAAO,EAAG,OAAOA,EAAQ0D,CAAC,EACtD9B,EAAM,OAAS,EAEX,CAAC6B,GAAM,YAAc,OAAO,OAAW,KACzC,OAAO,OAAO,eAElB,CAEA,IAAME,EAAwB,CAC5B,QAASjD,EAAQ,QACjB,OAAAiB,EACA,KAAAH,EACA,MAAAH,EACA,QAAArB,EACA,KAAAuC,EACA,KAAAK,EACA,OAAAD,EACA,QAAAa,CACF,EAEA,GAAI,OAAO,OAAW,IAAa,CACjC,IAAMI,EAAU,OAAO,qBACvB,GAAI,MAAM,QAAQA,CAAO,GAAKA,EAAQ,OAAS,EAAG,CAChD,IAAMC,EAA2BD,EAAQ,OAAO,EAAGA,EAAQ,MAAM,EACjE,OAAW,CAAC3D,EAAK4C,CAAE,IAAKgB,EAAOF,EAAQ,KAAK1D,EAAK4C,CAAE,CACrD,CACF,CAEA,OAAIvB,GAAQ6B,EAAU,IACpBL,EAAgB,SAAS,MAAQ,QAAQ,EACzCI,EAAc,GAGTS,CACT,CC1SA,SAASG,GAAqBC,EAAqD,CACjF,OACE,OAAOA,GAAO,UACdA,IAAO,MACP,OAAQA,EAAuC,mBAAsB,UAEzE,CAEA,SAASC,GAAcC,EAAmC,CACxD,OAAO,MAAM,QAAQA,CAAK,GAAKA,EAAM,MAAOC,GAAM,OAAOA,GAAM,QAAQ,CACzE,CAEA,SAASC,GAAkBJ,EAAmD,CAC5E,GAAI,OAAOA,GAAO,UAAYA,IAAO,KAAM,MAAO,GAElD,IAAMK,EAASL,EAAgC,WAC/C,GAAI,OAAOK,GAAU,UAAYA,IAAU,KAAM,MAAO,GAExD,IAAMC,EAAID,EACV,OAAO,OAAOC,EAAE,QAAW,UAAY,OAAOA,EAAE,MAAS,UAC3D,CAEA,SAASC,GACPC,EACmF,CACnF,OAAI,OAAOA,GAAS,UAAYA,IAAS,KAAa,GAC/C,OAAQA,EAAwC,kBAAqB,UAC9E,CAGA,SAASC,GAAsBT,EAAuB,CAEpD,GAAID,GAAqBC,CAAE,EAAG,CAC5B,IAAMU,EAAQV,EAAG,kBAAkB,EACnC,GAAIC,GAAcS,CAAK,EAAG,OAAOA,CACnC,CAGA,GAAIN,GAAkBJ,CAAE,EAAG,CACzB,IAAMW,EAAgB,CAAC,EACvB,QAASC,EAAI,EAAGA,EAAIZ,EAAG,WAAW,OAAQY,IAAK,CAC7C,IAAMC,EAAOb,EAAG,WAAW,KAAKY,CAAC,EAC7BC,GAAQ,OAAOA,EAAK,MAAS,UAAYA,EAAK,MAAMF,EAAI,KAAKE,EAAK,IAAI,CAC5E,CACA,OAAOF,CACT,CAEA,MAAO,CAAC,CACV,CAOA,SAASG,GAAyBC,EAA+B,CAC/D,IAAMC,GAAQD,EAAE,aAAa,MAAM,GAAK,IAAI,KAAK,EACjD,GAAIC,GAAQA,IAAS,SAAU,MAAO,GAEtC,IAAMC,GAAOF,EAAE,aAAa,KAAK,GAAK,IAAI,KAAK,EAC/C,OAAKE,EAEEA,EAAI,SAAS,eAAe,EAFlB,EAGnB,CAEA,SAASC,EAAmBhB,EAAoC,CAC9D,GAAI,OAAOA,GAAU,SAAU,OAC/B,IAAMC,EAAID,EAAM,KAAK,EACrB,OAAOC,GAAQ,MACjB,CAEA,SAASgB,EAAajB,EAAgBkB,EAA4B,CAChE,GAAI,OAAOlB,GAAU,SAAU,OAAOkB,EACtC,IAAMjB,EAAID,EAAM,KAAK,EAAE,YAAY,EACnC,OAAIC,IAAM,IAAMA,IAAM,QAAUA,IAAM,KAAOA,IAAM,OAASA,IAAM,KAAa,GAC3EA,IAAM,SAAWA,IAAM,KAAOA,IAAM,MAAQA,IAAM,MAAc,GAC7DiB,CACT,CAWA,SAASC,GAAiBN,EAA0C,CAGlE,IAAMO,EAAMP,EAAsD,SAAW,CAAC,EAExEQ,EAAQJ,EAAaG,EAAG,WAAY,EAAK,EACzCE,EAAOL,EAAaG,EAAG,UAAW,EAAI,EAEtCG,EAAWP,EAAmBI,EAAG,aAAa,EAC9CI,EAAUR,EAAmBI,EAAG,YAAY,EAC5CK,EAAOT,EAAmBI,EAAG,SAAS,EAGtCM,EAAiC,CAAC,EACxC,OAAIH,IAAUG,EAAO,SAAWH,GAC5BC,IAASE,EAAO,QAAUF,GAC1BC,IAAMC,EAAO,KAAOD,GAEjB,CAAE,MAAAJ,EAAO,KAAAC,EAAM,OAAAI,CAAO,CAC/B,CAEO,SAASC,EAAkBrB,EAAmB,SAA8B,CACjF,GAAI,CAACD,GAAoBC,CAAI,EAAG,MAAO,CAAC,EAExC,IAAMsB,EAAU,MAAM,KAAKtB,EAAK,iBAAiB,QAAQ,CAAC,EACpDuB,EAA6B,CAAC,EAEpC,QAAWC,KAAUF,EAAS,CAE5B,GADI,EAAEE,aAAkB,oBACpB,CAAClB,GAAyBkB,CAAM,EAAG,SAEvC,IAAMC,EAAY,IAAI,IAEtB,QAAWC,KAAWzB,GAAsBuB,CAAM,EAAG,CACnD,IAAMG,EAAOC,EAAuBF,CAAO,EACvCG,EAAYF,CAAI,GAAGF,EAAU,IAAIE,CAAI,CAC3C,CAEAJ,EAAO,KAAK,CACV,GAAIC,EACJ,cAAe,MAAM,KAAKC,CAAS,EACnC,aAAcZ,GAAiBW,CAAM,CACvC,CAAC,CACH,CAEA,OAAOD,CACT,CCvIA,IAAMO,GAAkD,SAEvD,UAAqB,CAIpB,GAHI,CAACC,EAAU,GAGX,OAAO,gBAAiB,OAE5B,IAAMC,EAAUC,EAAkB,QAAQ,EACpCC,EAAUF,EAAQ,CAAC,EAGnBG,EAAQD,GAAS,aAAa,OAAS,GACvCE,EAAOF,GAAS,aAAa,MAAQ,GACrCG,EAASH,GAAS,aAAa,QAAU,CAAC,EAE1CI,EAAOC,EAAiB,CAAE,KAAM,SAAU,MAAAJ,CAAM,CAAC,EACjDK,EAAUC,EAAc,CAC5B,QAASX,GACT,KAAAQ,EACA,MAAAH,EACA,KAAAC,EACA,OAAAC,CACF,CAAC,EAGD,OAAO,gBAAkBG,EAGzB,IAAME,EAAY,IAAI,IACtB,QAAWC,KAAQX,EACjB,QAAWY,KAAKD,EAAK,cAAeD,EAAU,IAAIE,CAAC,EAIrD,QAAWC,KAAOH,EAChBF,EAAQ,KAAKK,CAAG,EAAE,MAAM,IAAM,CAE9B,CAAC,CAEL,GAAG","names":["isModuleKey","value","normalizeAttributeName","name","hasQuerySelectorAll","collectModuleKeysFromDOM","root","found","elements","el","attr","normalized","isBrowser","createLogger","debug","args","isElement","value","safeMatches","el","selector","findClosestMatching","target","cur","createDelegatedListener","info","e","entries","entry","matched","idx","resolveObserverTarget","root","createCore","options","logger","defs","instances","listenersByType","on","type","handler","opts","capture","passive","existing","listener","emit","name","detail","ev","register","def","unregister","key","mount","_root","inst","api","unmount","mountAll","unmountAll","observer","observe","observedRoot","_mutations","stopObserving","destroy","getLogger","singleton","getCoreSingleton","normalizeOrigin","origin","resolveOrigin","config","resolveVersion","makeEsmImportPath","pkgName","version","PACKAGE_BY_KEY","getImportPathForModule","key","DEFAULT_REGISTRY","stateOf","modules","key","isReadyOrError","s","toError","err","normalizeUrlBase","value","v","resolveConfig","options","registry","version","out","base","toModuleDefinition","mod","expectedKey","candidate","def","createRuntime","debug","auto","ownsCore","core","createCore","logger","config","queue","observer","log","args","logError","flush","st","i","entry","e","destroyModule","load","importPath","getImportPathForModule","promise","reload","push","cb","autoLoadFromDOM","root","keys","collectModuleKeysFromDOM","startObserver","isBrowser","mutations","m","node","stopObserver","destroy","opts","k","runtime","globalQ","items","hasGetAttributeNames","el","isStringArray","value","v","hasAttributesLike","attrs","a","hasQuerySelectorAll","root","getAttributeNamesSafe","maybe","out","i","attr","isAttributesLoaderScript","s","type","src","pickNonEmptyString","parseBoolean","fallback","readLoaderConfig","ds","debug","auto","registry","version","base","config","findLoaderScripts","scripts","result","script","requested","rawName","name","normalizeAttributeName","isModuleKey","VERSION","isBrowser","loaders","findLoaderScripts","primary","debug","auto","config","core","getCoreSingleton","runtime","createRuntime","requested","info","k","key"]}
@@ -1,201 +0,0 @@
1
- 'use strict';
2
-
3
- Object.defineProperty(exports, '__esModule', { value: true });
4
-
5
- // src/core/index.ts
6
- function createLogger(debug = false) {
7
- return {
8
- debug: (...args) => {
9
- if (!debug) return;
10
- console.warn("[debug]", ...args);
11
- },
12
- warn: (...args) => {
13
- console.warn("[warn]", ...args);
14
- },
15
- error: (...args) => {
16
- console.error("[error]", ...args);
17
- }
18
- };
19
- }
20
- function isElement(value) {
21
- return typeof Element !== "undefined" && value instanceof Element;
22
- }
23
- function safeMatches(el, selector) {
24
- try {
25
- return el.matches(selector);
26
- } catch {
27
- return false;
28
- }
29
- }
30
- function findClosestMatching(target, selector) {
31
- let cur = target;
32
- while (cur) {
33
- if (isElement(cur) && safeMatches(cur, selector)) return cur;
34
- cur = isElement(cur) ? cur.parentElement : null;
35
- }
36
- return null;
37
- }
38
- function createDelegatedListener(info) {
39
- return (e) => {
40
- const entries = info.entries.slice();
41
- for (const entry of entries) {
42
- const matched = findClosestMatching(e.target, entry.selector);
43
- if (!matched) continue;
44
- entry.handler(e, matched);
45
- if (entry.once) {
46
- const idx = info.entries.indexOf(entry);
47
- if (idx >= 0) info.entries.splice(idx, 1);
48
- }
49
- }
50
- };
51
- }
52
- function resolveObserverTarget(root) {
53
- if (root instanceof Document) return root.documentElement ?? root;
54
- return root;
55
- }
56
- function createCore(options = {}) {
57
- const root = options.root ?? document;
58
- const logger = createLogger(!!options.debug);
59
- const defs = /* @__PURE__ */ new Map();
60
- const instances = /* @__PURE__ */ new Map();
61
- const listenersByType = /* @__PURE__ */ new Map();
62
- function on(type, selector, handler, opts = {}) {
63
- const capture = !!opts.capture;
64
- const passive = !!opts.passive;
65
- const existing = listenersByType.get(type);
66
- if (existing) {
67
- existing.entries.push({ selector, handler, once: !!opts.once });
68
- return () => {
69
- const idx = existing.entries.findIndex((e) => e.selector === selector && e.handler === handler);
70
- if (idx >= 0) existing.entries.splice(idx, 1);
71
- if (existing.entries.length === 0) {
72
- root.removeEventListener(type, existing.listener, { capture: existing.capture });
73
- listenersByType.delete(type);
74
- }
75
- };
76
- }
77
- const info = {
78
- capture,
79
- passive,
80
- entries: [{ selector, handler, once: !!opts.once }],
81
- listener: () => {
82
- }
83
- };
84
- const listener = createDelegatedListener(info);
85
- info.listener = listener;
86
- listenersByType.set(type, info);
87
- root.addEventListener(type, listener, { capture, passive });
88
- return () => {
89
- const cur = listenersByType.get(type);
90
- if (!cur) return;
91
- const idx = cur.entries.findIndex((e) => e.selector === selector && e.handler === handler);
92
- if (idx >= 0) cur.entries.splice(idx, 1);
93
- if (cur.entries.length === 0) {
94
- root.removeEventListener(type, cur.listener, { capture: cur.capture });
95
- listenersByType.delete(type);
96
- }
97
- };
98
- }
99
- function emit(el, name, detail) {
100
- const ev = new CustomEvent(name, { detail, bubbles: true });
101
- el.dispatchEvent(ev);
102
- }
103
- function register(def) {
104
- defs.set(def.key, def);
105
- }
106
- function unregister(key) {
107
- defs.delete(key);
108
- }
109
- function mount(key, _root) {
110
- const def = defs.get(key);
111
- if (!def) return;
112
- if (instances.has(key)) return;
113
- const inst = def.init(api);
114
- instances.set(key, inst);
115
- }
116
- function unmount(key) {
117
- const inst = instances.get(key);
118
- if (!inst) return;
119
- inst.destroy();
120
- instances.delete(key);
121
- }
122
- function mountAll(_root) {
123
- for (const key of defs.keys()) mount(key);
124
- }
125
- function unmountAll() {
126
- for (const key of instances.keys()) unmount(key);
127
- }
128
- let observer = null;
129
- function observe(observedRoot = root) {
130
- if (observer) return () => {
131
- };
132
- observer = new MutationObserver((_mutations) => {
133
- });
134
- observer.observe(resolveObserverTarget(observedRoot), {
135
- subtree: true,
136
- childList: true,
137
- attributes: false
138
- });
139
- return () => stopObserving();
140
- }
141
- function stopObserving() {
142
- if (!observer) return;
143
- observer.disconnect();
144
- observer = null;
145
- }
146
- function destroy() {
147
- stopObserving();
148
- unmountAll();
149
- for (const [type, info] of listenersByType.entries()) {
150
- root.removeEventListener(type, info.listener, { capture: info.capture });
151
- }
152
- listenersByType.clear();
153
- defs.clear();
154
- instances.clear();
155
- }
156
- function getLogger() {
157
- return logger;
158
- }
159
- const api = {
160
- on,
161
- emit,
162
- register,
163
- unregister,
164
- mount,
165
- unmount,
166
- mountAll,
167
- unmountAll,
168
- observe,
169
- stopObserving,
170
- destroy,
171
- getLogger
172
- };
173
- return api;
174
- }
175
- var singleton = null;
176
- function getCoreSingleton(options = {}) {
177
- if (singleton) return singleton;
178
- singleton = createCore({ ...options });
179
- const shouldAutoMount = options.autoMount ?? true;
180
- if (shouldAutoMount && typeof document !== "undefined") {
181
- if (document.readyState === "loading") {
182
- document.addEventListener(
183
- "DOMContentLoaded",
184
- () => {
185
- singleton?.mountAll();
186
- },
187
- { once: true }
188
- );
189
- } else {
190
- singleton.mountAll();
191
- }
192
- }
193
- return singleton;
194
- }
195
- var core_default = createCore;
196
-
197
- exports.createCore = createCore;
198
- exports.default = core_default;
199
- exports.getCoreSingleton = getCoreSingleton;
200
- //# sourceMappingURL=index.cjs.map
201
- //# sourceMappingURL=index.cjs.map
@@ -1 +0,0 @@
1
- {"version":3,"sources":["../../src/core/index.ts"],"names":[],"mappings":";;;;;AAqHA,SAAS,YAAA,CAAa,QAAQ,KAAA,EAAmB;AAC/C,EAAA,OAAO;AAAA,IACL,KAAA,EAAO,IAAI,IAAA,KAAoB;AAC7B,MAAA,IAAI,CAAC,KAAA,EAAO;AACZ,MAAA,OAAA,CAAQ,IAAA,CAAK,SAAA,EAAW,GAAG,IAAI,CAAA;AAAA,IACjC,CAAA;AAAA,IACA,IAAA,EAAM,IAAI,IAAA,KAAoB;AAC5B,MAAA,OAAA,CAAQ,IAAA,CAAK,QAAA,EAAU,GAAG,IAAI,CAAA;AAAA,IAChC,CAAA;AAAA,IACA,KAAA,EAAO,IAAI,IAAA,KAAoB;AAC7B,MAAA,OAAA,CAAQ,KAAA,CAAM,SAAA,EAAW,GAAG,IAAI,CAAA;AAAA,IAClC;AAAA,GACF;AACF;AAEA,SAAS,UAAU,KAAA,EAAkC;AAEnD,EAAA,OAAO,OAAO,OAAA,KAAY,WAAA,IAAe,KAAA,YAAiB,OAAA;AAC5D;AAEA,SAAS,WAAA,CAAY,IAAa,QAAA,EAA2B;AAC3D,EAAA,IAAI;AACF,IAAA,OAAO,EAAA,CAAG,QAAQ,QAAQ,CAAA;AAAA,EAC5B,CAAA,CAAA,MAAQ;AACN,IAAA,OAAO,KAAA;AAAA,EACT;AACF;AAEA,SAAS,mBAAA,CAAoB,QAA4B,QAAA,EAAkC;AACzF,EAAA,IAAI,GAAA,GAA0B,MAAA;AAE9B,EAAA,OAAO,GAAA,EAAK;AACV,IAAA,IAAI,UAAU,GAAG,CAAA,IAAK,YAAY,GAAA,EAAK,QAAQ,GAAG,OAAO,GAAA;AACzD,IAAA,GAAA,GAAM,SAAA,CAAU,GAAG,CAAA,GAAI,GAAA,CAAI,aAAA,GAAgB,IAAA;AAAA,EAC7C;AAEA,EAAA,OAAO,IAAA;AACT;AAEA,SAAS,wBAAwB,IAAA,EAAyB;AACxD,EAAA,OAAO,CAAC,CAAA,KAAa;AAEnB,IAAA,MAAM,OAAA,GAAU,IAAA,CAAK,OAAA,CAAQ,KAAA,EAAM;AAEnC,IAAA,KAAA,MAAW,SAAS,OAAA,EAAS;AAC3B,MAAA,MAAM,OAAA,GAAU,mBAAA,CAAoB,CAAA,CAAE,MAAA,EAAQ,MAAM,QAAQ,CAAA;AAC5D,MAAA,IAAI,CAAC,OAAA,EAAS;AAEd,MAAA,KAAA,CAAM,OAAA,CAAQ,GAAG,OAAO,CAAA;AAExB,MAAA,IAAI,MAAM,IAAA,EAAM;AACd,QAAA,MAAM,GAAA,GAAM,IAAA,CAAK,OAAA,CAAQ,OAAA,CAAQ,KAAK,CAAA;AACtC,QAAA,IAAI,OAAO,CAAA,EAAG,IAAA,CAAK,OAAA,CAAQ,MAAA,CAAO,KAAK,CAAC,CAAA;AAAA,MAC1C;AAAA,IACF;AAAA,EACF,CAAA;AACF;AAEA,SAAS,sBAAsB,IAAA,EAAwB;AAIrD,EAAA,IAAI,IAAA,YAAgB,QAAA,EAAU,OAAO,IAAA,CAAK,eAAA,IAAmB,IAAA;AAC7D,EAAA,OAAO,IAAA;AACT;AAIO,SAAS,UAAA,CAAW,OAAA,GAAuB,EAAC,EAAS;AAC1D,EAAA,MAAM,IAAA,GAA8B,QAAQ,IAAA,IAAQ,QAAA;AACpD,EAAA,MAAM,MAAA,GAAS,YAAA,CAAa,CAAC,CAAC,QAAQ,KAAK,CAAA;AAE3C,EAAA,MAAM,IAAA,uBAAW,GAAA,EAAsC;AACvD,EAAA,MAAM,SAAA,uBAAgB,GAAA,EAAoC;AAE1D,EAAA,MAAM,eAAA,uBAAsB,GAAA,EAA+B;AAE3D,EAAA,SAAS,GAAG,IAAA,EAAc,QAAA,EAAkB,OAAA,EAA2B,IAAA,GAAkB,EAAC,EAAa;AACrG,IAAA,MAAM,OAAA,GAAU,CAAC,CAAC,IAAA,CAAK,OAAA;AACvB,IAAA,MAAM,OAAA,GAAU,CAAC,CAAC,IAAA,CAAK,OAAA;AAEvB,IAAA,MAAM,QAAA,GAAW,eAAA,CAAgB,GAAA,CAAI,IAAI,CAAA;AACzC,IAAA,IAAI,QAAA,EAAU;AACZ,MAAA,QAAA,CAAS,OAAA,CAAQ,IAAA,CAAK,EAAE,QAAA,EAAU,OAAA,EAAS,MAAM,CAAC,CAAC,IAAA,CAAK,IAAA,EAAM,CAAA;AAE9D,MAAA,OAAO,MAAM;AACX,QAAA,MAAM,GAAA,GAAM,QAAA,CAAS,OAAA,CAAQ,SAAA,CAAU,CAAC,CAAA,KAAM,CAAA,CAAE,QAAA,KAAa,QAAA,IAAY,CAAA,CAAE,OAAA,KAAY,OAAO,CAAA;AAC9F,QAAA,IAAI,OAAO,CAAA,EAAG,QAAA,CAAS,OAAA,CAAQ,MAAA,CAAO,KAAK,CAAC,CAAA;AAG5C,QAAA,IAAI,QAAA,CAAS,OAAA,CAAQ,MAAA,KAAW,CAAA,EAAG;AACjC,UAAA,IAAA,CAAK,mBAAA,CAAoB,MAAM,QAAA,CAAS,QAAA,EAAU,EAAE,OAAA,EAAS,QAAA,CAAS,SAAS,CAAA;AAC/E,UAAA,eAAA,CAAgB,OAAO,IAAI,CAAA;AAAA,QAC7B;AAAA,MACF,CAAA;AAAA,IACF;AAEA,IAAA,MAAM,IAAA,GAA0B;AAAA,MAC9B,OAAA;AAAA,MACA,OAAA;AAAA,MACA,OAAA,EAAS,CAAC,EAAE,QAAA,EAAU,OAAA,EAAS,MAAM,CAAC,CAAC,IAAA,CAAK,IAAA,EAAM,CAAA;AAAA,MAClD,UAAU,MAAM;AAAA,MAAC;AAAA,KACnB;AAEA,IAAA,MAAM,QAAA,GAAW,wBAAwB,IAAI,CAAA;AAC7C,IAAA,IAAA,CAAK,QAAA,GAAW,QAAA;AAEhB,IAAA,eAAA,CAAgB,GAAA,CAAI,MAAM,IAAI,CAAA;AAE9B,IAAA,IAAA,CAAK,iBAAiB,IAAA,EAAM,QAAA,EAAU,EAAE,OAAA,EAAS,SAAS,CAAA;AAG1D,IAAA,OAAO,MAAM;AACX,MAAA,MAAM,GAAA,GAAM,eAAA,CAAgB,GAAA,CAAI,IAAI,CAAA;AACpC,MAAA,IAAI,CAAC,GAAA,EAAK;AAEV,MAAA,MAAM,GAAA,GAAM,GAAA,CAAI,OAAA,CAAQ,SAAA,CAAU,CAAC,CAAA,KAAM,CAAA,CAAE,QAAA,KAAa,QAAA,IAAY,CAAA,CAAE,OAAA,KAAY,OAAO,CAAA;AACzF,MAAA,IAAI,OAAO,CAAA,EAAG,GAAA,CAAI,OAAA,CAAQ,MAAA,CAAO,KAAK,CAAC,CAAA;AAEvC,MAAA,IAAI,GAAA,CAAI,OAAA,CAAQ,MAAA,KAAW,CAAA,EAAG;AAC5B,QAAA,IAAA,CAAK,mBAAA,CAAoB,MAAM,GAAA,CAAI,QAAA,EAAU,EAAE,OAAA,EAAS,GAAA,CAAI,SAAS,CAAA;AACrE,QAAA,eAAA,CAAgB,OAAO,IAAI,CAAA;AAAA,MAC7B;AAAA,IACF,CAAA;AAAA,EACF;AAEA,EAAA,SAAS,IAAA,CAAK,EAAA,EAAa,IAAA,EAAc,MAAA,EAAkB;AACzD,IAAA,MAAM,EAAA,GAAK,IAAI,WAAA,CAAY,IAAA,EAAM,EAAE,MAAA,EAAQ,OAAA,EAAS,MAAM,CAAA;AAC1D,IAAA,EAAA,CAAG,cAAc,EAAE,CAAA;AAAA,EACrB;AAEA,EAAA,SAAS,SAAS,GAAA,EAA4B;AAC5C,IAAA,IAAA,CAAK,GAAA,CAAI,GAAA,CAAI,GAAA,EAAK,GAAG,CAAA;AAAA,EACvB;AAEA,EAAA,SAAS,WAAW,GAAA,EAAgB;AAClC,IAAA,IAAA,CAAK,OAAO,GAAG,CAAA;AAAA,EACjB;AAEA,EAAA,SAAS,KAAA,CAAM,KAAgB,KAAA,EAAoB;AACjD,IAAA,MAAM,GAAA,GAAM,IAAA,CAAK,GAAA,CAAI,GAAG,CAAA;AACxB,IAAA,IAAI,CAAC,GAAA,EAAK;AACV,IAAA,IAAI,SAAA,CAAU,GAAA,CAAI,GAAG,CAAA,EAAG;AAExB,IAAA,MAAM,IAAA,GAAO,GAAA,CAAI,IAAA,CAAK,GAAG,CAAA;AACzB,IAAA,SAAA,CAAU,GAAA,CAAI,KAAK,IAAI,CAAA;AAAA,EACzB;AAEA,EAAA,SAAS,QAAQ,GAAA,EAAgB;AAC/B,IAAA,MAAM,IAAA,GAAO,SAAA,CAAU,GAAA,CAAI,GAAG,CAAA;AAC9B,IAAA,IAAI,CAAC,IAAA,EAAM;AACX,IAAA,IAAA,CAAK,OAAA,EAAQ;AACb,IAAA,SAAA,CAAU,OAAO,GAAG,CAAA;AAAA,EACtB;AAEA,EAAA,SAAS,SAAS,KAAA,EAAoB;AACpC,IAAA,KAAA,MAAW,GAAA,IAAO,IAAA,CAAK,IAAA,EAAK,QAAS,GAAG,CAAA;AAAA,EAC1C;AAEA,EAAA,SAAS,UAAA,GAAa;AACpB,IAAA,KAAA,MAAW,GAAA,IAAO,SAAA,CAAU,IAAA,EAAK,UAAW,GAAG,CAAA;AAAA,EACjD;AAEA,EAAA,IAAI,QAAA,GAAoC,IAAA;AAExC,EAAA,SAAS,OAAA,CAAQ,eAA2B,IAAA,EAAgB;AAC1D,IAAA,IAAI,QAAA,SAAiB,MAAM;AAAA,IAAC,CAAA;AAE5B,IAAA,QAAA,GAAW,IAAI,gBAAA,CAAiB,CAAC,UAAA,KAAe;AAAA,IAGhD,CAAC,CAAA;AAED,IAAA,QAAA,CAAS,OAAA,CAAQ,qBAAA,CAAsB,YAAY,CAAA,EAAG;AAAA,MACpD,OAAA,EAAS,IAAA;AAAA,MACT,SAAA,EAAW,IAAA;AAAA,MACX,UAAA,EAAY;AAAA,KACb,CAAA;AAED,IAAA,OAAO,MAAM,aAAA,EAAc;AAAA,EAC7B;AAEA,EAAA,SAAS,aAAA,GAAgB;AACvB,IAAA,IAAI,CAAC,QAAA,EAAU;AACf,IAAA,QAAA,CAAS,UAAA,EAAW;AACpB,IAAA,QAAA,GAAW,IAAA;AAAA,EACb;AAEA,EAAA,SAAS,OAAA,GAAU;AACjB,IAAA,aAAA,EAAc;AACd,IAAA,UAAA,EAAW;AAEX,IAAA,KAAA,MAAW,CAAC,IAAA,EAAM,IAAI,CAAA,IAAK,eAAA,CAAgB,SAAQ,EAAG;AACpD,MAAA,IAAA,CAAK,mBAAA,CAAoB,MAAM,IAAA,CAAK,QAAA,EAAU,EAAE,OAAA,EAAS,IAAA,CAAK,SAAS,CAAA;AAAA,IACzE;AAEA,IAAA,eAAA,CAAgB,KAAA,EAAM;AACtB,IAAA,IAAA,CAAK,KAAA,EAAM;AACX,IAAA,SAAA,CAAU,KAAA,EAAM;AAAA,EAClB;AAEA,EAAA,SAAS,SAAA,GAAY;AACnB,IAAA,OAAO,MAAA;AAAA,EACT;AAEA,EAAA,MAAM,GAAA,GAAY;AAAA,IAChB,EAAA;AAAA,IACA,IAAA;AAAA,IACA,QAAA;AAAA,IACA,UAAA;AAAA,IACA,KAAA;AAAA,IACA,OAAA;AAAA,IACA,QAAA;AAAA,IACA,UAAA;AAAA,IACA,OAAA;AAAA,IACA,aAAA;AAAA,IACA,OAAA;AAAA,IACA;AAAA,GACF;AAEA,EAAA,OAAO,GAAA;AACT;AAIA,IAAI,SAAA,GAAyB,IAAA;AAEtB,SAAS,gBAAA,CAAiB,OAAA,GAAuB,EAAC,EAAS;AAChE,EAAA,IAAI,WAAW,OAAO,SAAA;AACtB,EAAA,SAAA,GAAY,WAAW,EAAmB,GAAG,SAAS,CAAA;AAEtD,EAAA,MAAM,eAAA,GAAkB,QAAQ,SAAA,IAAa,IAAA;AAC7C,EAAA,IAAI,eAAA,IAAmB,OAAO,QAAA,KAAa,WAAA,EAAa;AACtD,IAAA,IAAI,QAAA,CAAS,eAAe,SAAA,EAAW;AACrC,MAAA,QAAA,CAAS,gBAAA;AAAA,QACP,kBAAA;AAAA,QACA,MAAM;AACJ,UAAA,SAAA,EAAW,QAAA,EAAS;AAAA,QACtB,CAAA;AAAA,QACA,EAAE,MAAM,IAAA;AAAK,OACf;AAAA,IACF,CAAA,MAAO;AACL,MAAA,SAAA,CAAU,QAAA,EAAS;AAAA,IACrB;AAAA,EACF;AAEA,EAAA,OAAO,SAAA;AACT;AAEA,IAAO,YAAA,GAAQ","file":"index.cjs","sourcesContent":["/* --------------------------------------------------------------------------\n * AdLib Attributes · Core\n *\n * Primitives partagées utilisées par le runtime et les modules d’attributs :\n * - délégation d’événements (listeners uniques sur une racine)\n * - registre de modules (définitions + instances)\n * - cycle de vie (mount/unmount/destroy)\n * - observation DOM (signal de changements, orchestration pilotée par le runtime)\n * -------------------------------------------------------------------------- */\n\nexport type Disposer = () => void;\nexport type Cleanup = void | Disposer;\n\nexport type CoreLogger = {\n debug: (...args: unknown[]) => void;\n warn: (...args: unknown[]) => void;\n error: (...args: unknown[]) => void;\n};\n\nexport type CoreOptions = {\n /** Root document/shadow root to bind listeners & observer (defaults to document). */\n root?: Document | ShadowRoot;\n /** Enable debug logs (printed as console.warn with \"[debug]\"). */\n debug?: boolean;\n /** Auto-mount modules on DOMContentLoaded when using singleton. Default: true. */\n autoMount?: boolean;\n};\n\nexport type DelegatedHandler = (e: Event, matched: Element) => void;\n\nexport type OnOptions = {\n /** If true, this delegated handler will run once then auto-unsubscribe. */\n once?: boolean;\n /** Capture phase for the underlying listener (per event type, first call wins). */\n capture?: boolean;\n /** Passive flag for the underlying listener (per event type, first call wins). */\n passive?: boolean;\n};\n\nexport interface Core {\n /**\n * Event delegation: listen on root and invoke handler when an ancestor matches selector.\n * Returns a disposer to remove this specific handler.\n */\n on: (type: string, selector: string, handler: DelegatedHandler, options?: OnOptions) => Disposer;\n\n /** Emit a CustomEvent from a given element. */\n emit: (el: Element, name: string, detail?: unknown) => void;\n\n /** Register a module definition. */\n register: (def: AdLibModuleDefinition) => void;\n\n /** Unregister a module definition by key. */\n unregister: (key: ModuleKey) => void;\n\n /** Mount a module by key, optionally on a given root. */\n mount: (key: ModuleKey, root?: ParentNode) => void;\n\n /** Unmount a module instance by key. */\n unmount: (key: ModuleKey) => void;\n\n /** Mount all registered modules. */\n mountAll: (root?: ParentNode) => void;\n\n /** Unmount all mounted modules. */\n unmountAll: () => void;\n\n /**\n * Observe dynamic DOM changes on a given root.\n *\n * Rôle :\n * - fournir un signal de changement DOM (ajouts/retraits de nœuds)\n * - permettre au runtime d’orchestrer un rescan/remount si nécessaire\n *\n * Retourne un disposer pour arrêter l’observation.\n */\n observe: (root?: ParentNode) => Disposer;\n\n /** Stop observing dynamic DOM changes. */\n stopObserving: () => void;\n\n /** Destroy core: unmount all, remove listeners, disconnect observer. */\n destroy: () => void;\n\n /** Core logger (debug/warn/error). */\n getLogger: () => CoreLogger;\n}\n\n/** Module key type (ex: 'ad-click'). */\nexport type ModuleKey = `ad-${string}`;\n\nexport interface AdLibModuleInstance {\n key: ModuleKey;\n destroy(): void;\n restart?(options?: { rescan?: boolean }): void;\n}\n\nexport interface AdLibModuleDefinition {\n key: ModuleKey;\n init(core: Core): AdLibModuleInstance;\n}\n\n/* --------------------------------- Internals -------------------------------- */\n\ntype DelegatedEntry = {\n selector: string;\n handler: DelegatedHandler;\n once: boolean;\n};\n\ntype EventListenerInfo = {\n capture: boolean;\n passive: boolean;\n listener: (e: Event) => void;\n entries: DelegatedEntry[];\n};\n\nfunction createLogger(debug = false): CoreLogger {\n return {\n debug: (...args: unknown[]) => {\n if (!debug) return;\n console.warn('[debug]', ...args);\n },\n warn: (...args: unknown[]) => {\n console.warn('[warn]', ...args);\n },\n error: (...args: unknown[]) => {\n console.error('[error]', ...args);\n },\n };\n}\n\nfunction isElement(value: unknown): value is Element {\n // Garde-fou typé : vérifie l’existence de Element (tests / environnements non DOM).\n return typeof Element !== 'undefined' && value instanceof Element;\n}\n\nfunction safeMatches(el: Element, selector: string): boolean {\n try {\n return el.matches(selector);\n } catch {\n return false;\n }\n}\n\nfunction findClosestMatching(target: EventTarget | null, selector: string): Element | null {\n let cur: EventTarget | null = target;\n\n while (cur) {\n if (isElement(cur) && safeMatches(cur, selector)) return cur;\n cur = isElement(cur) ? cur.parentElement : null;\n }\n\n return null;\n}\n\nfunction createDelegatedListener(info: EventListenerInfo) {\n return (e: Event) => {\n // Copie défensive : la liste peut être modifiée par un handler \"once\".\n const entries = info.entries.slice();\n\n for (const entry of entries) {\n const matched = findClosestMatching(e.target, entry.selector);\n if (!matched) continue;\n\n entry.handler(e, matched);\n\n if (entry.once) {\n const idx = info.entries.indexOf(entry);\n if (idx >= 0) info.entries.splice(idx, 1);\n }\n }\n };\n}\n\nfunction resolveObserverTarget(root: ParentNode): Node {\n // MutationObserver attend un Node.\n // - Document => document.documentElement si disponible, sinon le document lui-même\n // - ShadowRoot / Element => observe directement\n if (root instanceof Document) return root.documentElement ?? root;\n return root as unknown as Node;\n}\n\n/* ---------------------------------- Core ---------------------------------- */\n\nexport function createCore(options: CoreOptions = {}): Core {\n const root: Document | ShadowRoot = options.root ?? document;\n const logger = createLogger(!!options.debug);\n\n const defs = new Map<ModuleKey, AdLibModuleDefinition>();\n const instances = new Map<ModuleKey, AdLibModuleInstance>();\n\n const listenersByType = new Map<string, EventListenerInfo>();\n\n function on(type: string, selector: string, handler: DelegatedHandler, opts: OnOptions = {}): Disposer {\n const capture = !!opts.capture;\n const passive = !!opts.passive;\n\n const existing = listenersByType.get(type);\n if (existing) {\n existing.entries.push({ selector, handler, once: !!opts.once });\n\n return () => {\n const idx = existing.entries.findIndex((e) => e.selector === selector && e.handler === handler);\n if (idx >= 0) existing.entries.splice(idx, 1);\n\n // ✅ Si c'était le dernier handler, on retire le listener racine et on nettoie la map\n if (existing.entries.length === 0) {\n root.removeEventListener(type, existing.listener, { capture: existing.capture });\n listenersByType.delete(type);\n }\n };\n }\n\n const info: EventListenerInfo = {\n capture,\n passive,\n entries: [{ selector, handler, once: !!opts.once }],\n listener: () => {},\n };\n\n const listener = createDelegatedListener(info);\n info.listener = listener;\n\n listenersByType.set(type, info);\n\n root.addEventListener(type, listener, { capture, passive });\n\n // ✅ Disposer “handler-level” (pas “type-level”)\n return () => {\n const cur = listenersByType.get(type);\n if (!cur) return;\n\n const idx = cur.entries.findIndex((e) => e.selector === selector && e.handler === handler);\n if (idx >= 0) cur.entries.splice(idx, 1);\n\n if (cur.entries.length === 0) {\n root.removeEventListener(type, cur.listener, { capture: cur.capture });\n listenersByType.delete(type);\n }\n };\n }\n\n function emit(el: Element, name: string, detail?: unknown) {\n const ev = new CustomEvent(name, { detail, bubbles: true });\n el.dispatchEvent(ev);\n }\n\n function register(def: AdLibModuleDefinition) {\n defs.set(def.key, def);\n }\n\n function unregister(key: ModuleKey) {\n defs.delete(key);\n }\n\n function mount(key: ModuleKey, _root?: ParentNode) {\n const def = defs.get(key);\n if (!def) return;\n if (instances.has(key)) return;\n\n const inst = def.init(api);\n instances.set(key, inst);\n }\n\n function unmount(key: ModuleKey) {\n const inst = instances.get(key);\n if (!inst) return;\n inst.destroy();\n instances.delete(key);\n }\n\n function mountAll(_root?: ParentNode) {\n for (const key of defs.keys()) mount(key);\n }\n\n function unmountAll() {\n for (const key of instances.keys()) unmount(key);\n }\n\n let observer: MutationObserver | null = null;\n\n function observe(observedRoot: ParentNode = root): Disposer {\n if (observer) return () => {};\n\n observer = new MutationObserver((_mutations) => {\n // Signal DOM : le runtime est responsable de décider quoi charger / recharger.\n // Le core garantit uniquement une observation stable et désinscriptible.\n });\n\n observer.observe(resolveObserverTarget(observedRoot), {\n subtree: true,\n childList: true,\n attributes: false,\n });\n\n return () => stopObserving();\n }\n\n function stopObserving() {\n if (!observer) return;\n observer.disconnect();\n observer = null;\n }\n\n function destroy() {\n stopObserving();\n unmountAll();\n\n for (const [type, info] of listenersByType.entries()) {\n root.removeEventListener(type, info.listener, { capture: info.capture });\n }\n\n listenersByType.clear();\n defs.clear();\n instances.clear();\n }\n\n function getLogger() {\n return logger;\n }\n\n const api: Core = {\n on,\n emit,\n register,\n unregister,\n mount,\n unmount,\n mountAll,\n unmountAll,\n observe,\n stopObserving,\n destroy,\n getLogger,\n };\n\n return api;\n}\n\n/* ----------------------------- Singleton helpers ---------------------------- */\n\nlet singleton: Core | null = null;\n\nexport function getCoreSingleton(options: CoreOptions = {}): Core {\n if (singleton) return singleton;\n singleton = createCore({ autoMount: true, ...options });\n\n const shouldAutoMount = options.autoMount ?? true;\n if (shouldAutoMount && typeof document !== 'undefined') {\n if (document.readyState === 'loading') {\n document.addEventListener(\n 'DOMContentLoaded',\n () => {\n singleton?.mountAll();\n },\n { once: true }\n );\n } else {\n singleton.mountAll();\n }\n }\n\n return singleton;\n}\n\nexport default createCore;"]}