@devwareng/vanilla-ts 1.2.125 → 1.2.126

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/dist/index.cjs CHANGED
@@ -1,2 +1,2 @@
1
- "use strict";var fe=Object.create;var L=Object.defineProperty;var ge=Object.getOwnPropertyDescriptor;var he=Object.getOwnPropertyNames;var Se=Object.getPrototypeOf,Te=Object.prototype.hasOwnProperty;var Ee=(t,e)=>{for(var n in e)L(t,n,{get:e[n],enumerable:!0})},Z=(t,e,n,r)=>{if(e&&typeof e=="object"||typeof e=="function")for(let o of he(e))!Te.call(t,o)&&o!==n&&L(t,o,{get:()=>e[o],enumerable:!(r=ge(e,o))||r.enumerable});return t};var p=(t,e,n)=>(n=t!=null?fe(Se(t)):{},Z(e||!t||!t.__esModule?L(n,"default",{value:t,enumerable:!0}):n,t)),ye=t=>Z(L({},"__esModule",{value:!0}),t);var Ae={};Ee(Ae,{TSRouter:()=>x,createEffect:()=>G,createSignal:()=>Q,html:()=>R,loadPyFiles:()=>J,mapper:()=>ee,renderChildRoutes:()=>W,useAnchorSingle:()=>N,useInitialDOM:()=>z,useTSAnchorMount:()=>V,useTSAuth:()=>U,useTSCollection:()=>F,useTSComponent:()=>E,useTSElementEach:()=>y,useTSElements:()=>k,useTSEvent:()=>H,useTSEventAll:()=>$,useTSExtractParams:()=>O,useTSLazy:()=>Y,useTSMetaData:()=>q,useTSNavigate:()=>j,useTSOutlet:()=>B,useTSParams:()=>T,useTSPurifier:()=>C,useTSSelect:()=>_,useTSloadBrython:()=>X});module.exports=ye(Ae);function ve(t){return(t==null?"":String(t)).replace(/<\s*(script|iframe|object|embed|link|style)[^>]*>.*?<\s*\/\s*\1\s*>/gi,"").replace(/<\s*(script|iframe|object|embed|link|style)[^>]*>/gi,"").replace(/\son\w+\s*=\s*(['"]).*?\1/gi,"").replace(/\s(href|src)\s*=\s*(['"])\s*javascript:[^'"]*\2/gi,"")}function R(t,...e){return t.reduce((n,r,o)=>{let s=o<e.length?ve(e[o]):"";return n+r+s},"")}function w(){let t=new Set;document.querySelectorAll("*").forEach(e=>{let n=e.tagName.toLowerCase();n.includes("-")&&t.add(n)}),t.forEach(e=>{customElements.get(e)||customElements.define(e,class extends HTMLElement{connectedCallback(){this.innerHTML=`<div style="padding:10px;background:#eee;">${e} (Auto)</div>`}})})}var Le=t=>t.replace(/<\/?(script|iframe|object|embed|link|meta|style)[^>]*>/gi,"").replace(/\s+on[a-z]+\s*=\s*("[^"]*"|'[^']*'|[^\s>]+)/gi,"").replace(/\s+(href|src)\s*=\s*(['"]?)\s*javascript:[^'"\s>]*/gi,""),ee=t=>t?.map(e=>Le(e)).join("")??"";var b=p(require("dompurify"),1),C=(t,e)=>{let r={...{ADD_TAGS:["my-custom-tag"]},...e};return typeof t=="string"?b.default.sanitize(t,r):b.default.sanitize(t.innerHTML,r)};var H=(t,e,n)=>{if(typeof t=="string"){let r=document.getElementById(t);r?r.addEventListener(e,n):console.warn(`Element with id '${t}' not found.`)}else t===document?document.addEventListener(e,n):console.warn("Invalid id parameter provided.")};var te=require("zustand/vanilla"),D=p(require("dompurify"),1);function we(t,e){let n=[],r=t.replace(/:[^/]+/g,a=>(n.push(a.slice(1)),"([^/]+)")),o=new RegExp(`^${r}$`),s=e.match(o),i={};return s&&n.forEach((a,c)=>{i[a]=D.default.sanitize(s[c+1]??"")}),i}function Me(t){let e={},n=new URLSearchParams(t);for(let[r,o]of n.entries())e[r]=D.default.sanitize(o);return e}var T=(0,te.createStore)((t,e)=>({params:{},query:{},setFromPattern:n=>{let r=window.location.pathname,o=we(n,r),s=Me(window.location.search);t({params:o,query:s})},getParam:n=>e().params[n],getQuery:n=>e().query[n]}));function O(t){let e=T.getState();e.setFromPattern(t);let n=e.params,r=e.query;return{...n,...r}}var $=(t,e,n)=>{let r=document.querySelectorAll(t);return r.forEach(o=>{o.addEventListener(e,n)}),()=>{r.forEach(o=>{o.removeEventListener(e,n)})}};var M=p(require("dompurify"),1),k=(t,e,n)=>{let r={USE_PROFILES:{svg:!0,html:!0},ALLOWED_TAGS:["svg","path","circle","rect","line","polyline","polygon","g","main","div","h1","h2","h3","h4","h5","h6","p","button","span","a","img","input","ul","li","i"],ALLOWED_ATTR:["class","id","href","src","alt","fill","stroke","stroke-width","viewBox","xmlns","d","x","y","cx","cy","r","width","height"],FORBID_TAGS:["script","iframe"],ALLOWED_URI_REGEXP:/^(?:(?:https?|mailto|tel|ftp):|[^a-z]|[a-z+.\-]+(?:[^a-z+.\-:]|$))/i,...n};M.default.addHook("uponSanitizeElement",(s,i)=>{let a=i.tagName.toLowerCase();a.includes("-")&&(i.allowedTags[a]=!0)}),M.default.addHook("uponSanitizeAttribute",(s,i)=>{i.attrName&&i.attrName.toLowerCase().startsWith("on")&&(i.keepAttr=!1)});let o=M.default.sanitize(e,r);t.innerHTML!==o&&(t.innerHTML=o)};var ne=p(require("dompurify"),1),P=null,z=(t,e)=>{if(typeof document>"u")return;let n=document.getElementById(t);if(!n)return;let r=n.innerHTML,o=ne.default.sanitize(r);if(P!==null&&o!==P){let s=document.createElement("div");e(s),n.innerHTML=P}else P=o,e(n)};var I=p(require("dompurify"),1);typeof window<"u"&&!window.__anchorSinglePopstateHandlerAttached&&(window.addEventListener("popstate",t=>{let e=t.state;e?.scrollPosition!==void 0&&window.scrollTo(0,e.scrollPosition)}),window.__anchorSinglePopstateHandlerAttached=!0);var N=(t,e,n,r="",o=null)=>{if(!t)return;let s=I.default.sanitize(e,{ALLOWED_URI_REGEXP:/^(https?:|\/)/}),i=I.default.sanitize(n,{USE_PROFILES:{html:!1}});t.setAttribute("href",s),t.setAttribute("aria-label",i),r&&(t.className=r.trim()),o&&t.replaceChildren(o),typeof window<"u"&&t.addEventListener("click",a=>{a.preventDefault();let d=a.currentTarget.getAttribute("href");if(d){let u=window.scrollY;window.scrollTo(0,0),window.history.pushState({scrollPosition:u},"",d),dispatchEvent(new PopStateEvent("popstate"))}})};var h=p(require("dompurify"),1);var re=(t="'self' 'nonce-rAnd0m123' 'unsafe-inline' 'unsafe-eval'",e="'self' 'nonce-rAnd0m123'",n="'none'",r="'self' https://fonts.googleapis.com https://fonts.gstatic.com",o="'self' https://blogger.googleusercontent.com",s=["'self'","https://fonts.googleapis.com","https://fonts.gstatic.com","https://www.google.com/maps/"],i="'self' https://www.youtube.com",a="'self'",c="/csp-report",d=!1)=>{let u=()=>{try{let l=document.querySelector('meta[http-equiv="Content-Security-Policy"]');l||(l=document.createElement("meta"),l.setAttribute("http-equiv","Content-Security-Policy"),document.head.appendChild(l));let f=d?`report-uri ${c};`:"";l.setAttribute("content",`default-src 'self'; script-src ${t}; style-src ${e}; object-src ${n}; font-src ${r}; img-src ${o}; connect-src ${s.join(" ")}; frame-src ${i}; base-uri ${a}; ${f}`)}catch(l){console.error("Error adding CSP meta element:",l)}};document.readyState==="loading"?document.addEventListener("DOMContentLoaded",u):u()};var q=(t,e)=>{let n={name:h.default.sanitize(t.name||""),description:h.default.sanitize(t.description||"Default description"),author:h.default.sanitize(t.author||"")},r=m=>{n.name=h.default.sanitize(m),l("name",n.name)},o=m=>{n.description=h.default.sanitize(m),l("description",n.description)},s=m=>{n.author=h.default.sanitize(m),l("author",n.author)},i=()=>n.name,a=()=>n.description,c=()=>n.author,d=()=>n,u=(m,v)=>{let S=document.createElement("meta");S.setAttribute("name",m),S.setAttribute("content",v),document.head.appendChild(S)},l=(m,v)=>{let S=document.querySelector(`meta[name="${m}"]`);S?S.setAttribute("content",v):u(m,v)},f=()=>{l("name",n.name),l("description",n.description),l("author",n.author)};return e&&re(e.scriptSrc,e.styleSrc,e.objectSrc,Array.isArray(e.connectSrc)?e.connectSrc.join(" "):e.connectSrc,e.reportOnly!==void 0?String(e.reportOnly):void 0),f(),{setName:r,setDescription:o,setAuthor:s,getName:i,getDescription:a,getAuthor:c,getAllMetaData:d,appendMetaTagsToHead:f}};var oe=p(require("dompurify"),1),E=(t,e,n,r,o)=>{let s=`#${t}`,i=e.querySelectorAll(s);if(i.length===0)throw new Error(`[useTSComponent] No element found with id '${t}' in the given parent.`);if(i.length>1)throw new Error(`[useTSComponent] Duplicate id '${t}' detected. Found ${i.length} elements.`);let a=i[0];a.innerHTML=oe.default.sanitize(a.innerHTML,{USE_PROFILES:{html:!0}}),n(a,r,o)};var F=(t,e,n,r=[])=>{let o=new Set;t.forEach((s,i)=>{if(o.has(s)){console.warn(`[useTSCollection] Duplicate ID in collection array: "${s}" \u2014 skipping.`);return}o.add(s);let a=e.querySelectorAll(`#${s}`);if(a.length>1){console.warn(`[useTSCollection] Duplicate ID in DOM: "${s}" (${a.length} elements found) \u2014 skipping component mount.`);return}let c=n[i],d=Array.isArray(r)?r[i]:void 0;typeof c=="function"?E(s,e,c,d):console.warn(`[useTSCollection] No valid component function found for ID: "${s}"`)})};var _=(t,e)=>{let r=(e??document).querySelectorAll(t);if(r.length===0)return process.env.NODE_ENV!=="production"&&console.warn(`[useTSSelect] No element found for selector: '${t}'`),null;if(t.startsWith("#")&&r.length>1){if(process.env.NODE_ENV!=="production")throw new Error(`[useTSSelect] Duplicate ID detected: '${t}'. Found ${r.length} elements with this ID.`);return r[0]}return r.length>1&&process.env.NODE_ENV!=="production"&&console.warn(`[useTSSelect] Multiple elements found for selector: '${t}'. Returning the first one.`),r[0]};var se=require("jwt-decode"),U=(t,e)=>{let n=localStorage.getItem("token");if(!n)return window.location.href=e,null;try{let r=(0,se.jwtDecode)(n),o=Date.now()/1e3;return r.exp&&r.exp<o&&(console.error("Token has expired"),window.localStorage.removeItem("token"),window.location.href=e),null}catch(r){return console.error("Invalid token:",r),window.location.href=e,null}};var y=(t,e,n)=>{t.forEach(r=>{e.forEach(o=>{r.addEventListener(o,s=>{n(r,s)})})})};var j=()=>({back:()=>window.history.back(),forward:()=>window.history.forward()});var B=(t,e)=>{let n=document.querySelector(`#${t}`)||document.querySelector(`.${t}`);if(!n)return;let r=window.location.pathname.replace(/\/$/,"");for(let o of e){let s=o.path.replace(/\/$/,"");if(r===s||r.startsWith(`${s}/`)){o.component(n);break}}};function W(t,e){let n=window.location.pathname.replace(/\/$/,"");e.routes.forEach(r=>{r.children?.length&&r.children.forEach(o=>{let s=o.path.replace(/\/$/,"");if(n===s||n.startsWith(`${s}/`)){let i=t.querySelector(`#${o.outlet}`)||t.querySelector(`.${o.outlet}`);i instanceof HTMLElement&&o.element&&o.element(i)}})})}var ie=require("zustand/vanilla");function Q(t){let e=(0,ie.createStore)(()=>({value:t})),n=new Set;return{get:()=>e.getState().value,set:r=>{e.setState({value:r}),n.forEach(o=>o(r))},subscribe:r=>(n.add(r),r(e.getState().value),()=>n.delete(r))}}function G(t){let e=t();typeof e=="function"&&e()}var ae=()=>{let t=document.querySelectorAll('a[href^="#"]');y(t,["click"],(e,n)=>{n.preventDefault();let r=e.getAttribute("href")?.substring(1),o=r?document.getElementById(r):null;o&&o.scrollIntoView({behavior:"smooth",block:"start"})})};var ce=require("lodash-es"),A=t=>t;typeof window<"u"&&typeof document<"u"&&(A=t=>{let e=document.createElement("div");return e.innerText=t,e.innerHTML});var Pe=(0,ce.debounce)(t=>{(t?Array.isArray(t)?t:t instanceof HTMLAnchorElement?[t]:Array.from(t):Array.from(document.querySelectorAll("a"))).forEach(n=>{if(!n||n.dataset.anchorEnhanced==="true")return;n.dataset.anchorEnhanced="true";let r=n.getAttribute("href")||"#",o=A(r);n.setAttribute("href",o);let s=n.getAttribute("class")||"";n.setAttribute("class",A(s));let i=n.getAttribute("aria-label");i&&n.setAttribute("aria-label",A(i));let a=n.querySelector(":scope > *");a&&(n.innerHTML="",n.appendChild(a));let c=n.getAttribute("href")||"";if(!c.startsWith("#")){try{if(new URL(c,window.location.href).origin!==window.location.origin)return}catch{return}n.addEventListener("click",d=>{d.preventDefault();try{let u=new URL(c,window.location.href);window.history.pushState({},"",u.pathname+u.search+u.hash),window.dispatchEvent(new PopStateEvent("popstate"))}catch(u){console.error("Invalid URL in anchor:",c,u)}})}})},50),le=t=>{Pe(t)};var ue=()=>{let t=document.querySelectorAll("a");return le(t)};var V=()=>{ue(),ae()};var X=async()=>{let t="https://cdn.jsdelivr.net/npm/brython@3/brython.min.js",e="https://cdn.jsdelivr.net/npm/brython@3/brython_stdlib.js",n=r=>new Promise((o,s)=>{let i=document.createElement("script");i.src=r,i.onload=()=>o(),i.onerror=()=>s(new Error(`Failed to load ${r}`)),document.head.appendChild(i)});await n(t),await n(e),typeof window.brython=="function"?window.brython():console.error("Brython did not load correctly.")},J=t=>new Promise((e,n)=>{let r=document.createElement("script");r.type="text/python",r.src=`/src/python/${t}`,r.onload=()=>e(),r.onerror=()=>n(new Error(`Failed to load ${t}`)),document.body.appendChild(r)});function Y(t){let e=null;return async(n,r)=>{try{if(!e){let o=await t();e=o.default||o}if(typeof e=="function")return e(n,r);if(e instanceof HTMLElement){n?.appendChild(e);return}if(e&&typeof e.render=="function")return e.render(n,r);console.warn("useTSLazy: Unsupported module type",e)}catch(o){console.error("useTSLazy failed:",o)}}}var K=p(require("dompurify"),1);var me=require("zustand/vanilla"),pe=p(require("dompurify"),1),g=(0,me.createStore)(t=>({params:{},query:{},setParams:e=>t(()=>({params:de(e)})),setQuery:e=>t(()=>({query:de(e)}))}));function de(t){let e={};for(let n in t)e[n]=pe.default.sanitize(t[n]);return e}var x=class{constructor(e,n){this.routes=[];this.routes=e,this.expectedParams=new Set(n),window.addEventListener("popstate",this.handlePopState.bind(this)),this.handlePopState()}handlePopState(){let e=window.location.pathname,n=window.location.search,r=this.parseQueryParams(n),o=this.findMatchingRoute(e,this.routes);if(o){if(o.routeto){this.navigate(o.routeto);return}let s=this.filterAndSanitizeParams(o.params);g.getState().setParams(s),g.getState().setQuery(r);let i=document.createElement("div");if(o.element?.(i,s,r),o.children){let a=e.slice(o.path.length),c=i.querySelector("#child");c&&this.renderChildren(o.children,a,c,s,r)}}else{let s=this.findMatchingRoute("*",this.routes);if(s){let i=this.filterAndSanitizeParams(s.params);g.getState().setParams(i),g.getState().setQuery(r);let a=document.createElement("div");s.element?.(a,i,r)}}}renderChildren(e,n,r,o,s){if(!e||e.length===0){let a=r.querySelector("#child");a&&a.remove();return}let i=this.findMatchingRoute(n,e);if(i){let a=document.createElement("div");a.id="child";let c={...o,...i.params},d=this.filterAndSanitizeParams(c);if(g.getState().setParams(d),g.getState().setQuery(s),i.element?.(a,d,s),r.appendChild(a),i.children){let u=n.slice(i.path.length);this.renderChildren(i.children,u,a,d,s)}}}parseQueryParams(e){let n={},r=new URLSearchParams(e);for(let[o,s]of r.entries())this.expectedParams.has(o)&&(n[o]=K.default.sanitize(s));return n}findMatchingRoute(e,n,r={}){for(let o of n){let s=o.path;if(s==="*")return o;{let a=[],c=s.replace(/:[^\s/]+/g,l=>(a.push(l.substring(1)),"([^\\s/]+)")),d=new RegExp(`^${c}(?:/|$)`),u=e.match(d);if(u){let l={...r};if(a.forEach((f,m)=>{l[f]=u[m+1]??""}),o.children){let f=e.slice(u[0].length),m=this.findMatchingRoute(f,o.children,l);if(m)return m}return{...o,params:l}}}}}filterAndSanitizeParams(e){if(!e)return{};let n={};for(let r in e)this.expectedParams.has(r)&&(n[r]=K.default.sanitize(e[r]??""));return n}navigate(e){history.pushState(null,"",e),this.handlePopState()}addRoute(e){this.routes.push(e)}};typeof window<"u"&&(window.addEventListener("popstate",()=>{w()}),document.addEventListener("DOMContentLoaded",w));0&&(module.exports={TSRouter,createEffect,createSignal,html,loadPyFiles,mapper,renderChildRoutes,useAnchorSingle,useInitialDOM,useTSAnchorMount,useTSAuth,useTSCollection,useTSComponent,useTSElementEach,useTSElements,useTSEvent,useTSEventAll,useTSExtractParams,useTSLazy,useTSMetaData,useTSNavigate,useTSOutlet,useTSParams,useTSPurifier,useTSSelect,useTSloadBrython});
1
+ "use strict";var fe=Object.create;var L=Object.defineProperty;var ge=Object.getOwnPropertyDescriptor;var he=Object.getOwnPropertyNames;var Se=Object.getPrototypeOf,Ee=Object.prototype.hasOwnProperty;var Te=(t,e)=>{for(var n in e)L(t,n,{get:e[n],enumerable:!0})},Z=(t,e,n,r)=>{if(e&&typeof e=="object"||typeof e=="function")for(let o of he(e))!Ee.call(t,o)&&o!==n&&L(t,o,{get:()=>e[o],enumerable:!(r=ge(e,o))||r.enumerable});return t};var p=(t,e,n)=>(n=t!=null?fe(Se(t)):{},Z(e||!t||!t.__esModule?L(n,"default",{value:t,enumerable:!0}):n,t)),ye=t=>Z(L({},"__esModule",{value:!0}),t);var Ae={};Te(Ae,{TSRouter:()=>x,createEffect:()=>G,createSignal:()=>Q,html:()=>R,loadPyFiles:()=>J,mapper:()=>ee,renderChildRoutes:()=>W,useAnchorSingle:()=>I,useInitialDOM:()=>z,useTSAnchorMount:()=>V,useTSAuth:()=>U,useTSCollection:()=>F,useTSComponent:()=>T,useTSElementEach:()=>y,useTSElements:()=>$,useTSEvent:()=>H,useTSEventAll:()=>k,useTSExtractParams:()=>O,useTSLazy:()=>Y,useTSMetaData:()=>N,useTSNavigate:()=>j,useTSOutlet:()=>B,useTSParams:()=>E,useTSPurifier:()=>C,useTSSelect:()=>_,useTSloadBrython:()=>X});module.exports=ye(Ae);function ve(t){return(t==null?"":String(t)).replace(/<\s*(script|iframe|object|embed|link|style)[^>]*>.*?<\s*\/\s*\1\s*>/gi,"").replace(/<\s*(script|iframe|object|embed|link|style)[^>]*>/gi,"").replace(/\son\w+\s*=\s*(['"]).*?\1/gi,"").replace(/\s(href|src)\s*=\s*(['"])\s*javascript:[^'"]*\2/gi,"")}function R(t,...e){return t.reduce((n,r,o)=>{let s=o<e.length?ve(e[o]):"";return n+r+s},"")}function w(){let t=new Set;document.querySelectorAll("*").forEach(e=>{let n=e.tagName.toLowerCase();n.includes("-")&&t.add(n)}),t.forEach(e=>{customElements.get(e)||customElements.define(e,class extends HTMLElement{connectedCallback(){this.innerHTML=`<div style="padding:10px;background:#eee;">${e} (Auto)</div>`}})})}var Le=t=>t.replace(/<\/?(script|iframe|object|embed|link|meta|style)[^>]*>/gi,"").replace(/\s+on[a-z]+\s*=\s*("[^"]*"|'[^']*'|[^\s>]+)/gi,"").replace(/\s+(href|src)\s*=\s*(['"]?)\s*javascript:[^'"\s>]*/gi,""),ee=t=>t?.map(e=>Le(e)).join("")??"";var b=p(require("dompurify"),1),C=(t,e)=>{let r={...{ADD_TAGS:["my-custom-tag"]},...e};return typeof t=="string"?b.default.sanitize(t,r):b.default.sanitize(t.innerHTML,r)};var H=(t,e,n)=>{if(typeof t=="string"){let r=document.getElementById(t);r?r.addEventListener(e,n):console.warn(`Element with id '${t}' not found.`)}else t===document?document.addEventListener(e,n):console.warn("Invalid id parameter provided.")};var te=require("zustand/vanilla"),D=p(require("dompurify"),1);function we(t,e){let n=[],r=t.replace(/:[^/]+/g,a=>(n.push(a.slice(1)),"([^/]+)")),o=new RegExp(`^${r}$`),s=e.match(o),i={};return s&&n.forEach((a,c)=>{i[a]=D.default.sanitize(s[c+1]??"")}),i}function Me(t){let e={},n=new URLSearchParams(t);for(let[r,o]of n.entries())e[r]=D.default.sanitize(o);return e}var E=(0,te.createStore)((t,e)=>({params:{},query:{},setFromPattern:n=>{let r=window.location.pathname,o=we(n,r),s=Me(window.location.search);t({params:o,query:s})},getParam:n=>e().params[n],getQuery:n=>e().query[n]}));function O(t){let e=E.getState();e.setFromPattern(t);let n=e.params,r=e.query;return{...n,...r}}var k=(t,e,n)=>{let r=document.querySelectorAll(t);return r.forEach(o=>{o.addEventListener(e,n)}),()=>{r.forEach(o=>{o.removeEventListener(e,n)})}};var M=p(require("dompurify"),1),$=(t,e,n,r={})=>{let o={USE_PROFILES:{svg:!0,html:!0},ALLOWED_TAGS:["svg","path","circle","rect","line","polyline","polygon","g","main","div","h1","h2","h3","h4","h5","h6","p","button","span","a","img","input","ul","li","i"],ALLOWED_ATTR:["class","id","href","src","alt","fill","stroke","stroke-width","viewBox","xmlns","d","x","y","cx","cy","r","width","height","data-onclick","data-onchange"],FORBID_TAGS:["script","iframe"],ALLOWED_URI_REGEXP:/^(?:(?:https?|mailto|tel|ftp):|[^a-z]|[a-z+.\-]+(?:[^a-z+.\-:]|$))/i,...n};M.default.addHook("uponSanitizeElement",(i,a)=>{let c=a.tagName.toLowerCase();c.includes("-")&&(a.allowedTags[c]=!0)}),M.default.addHook("uponSanitizeAttribute",(i,a)=>{a.attrName&&a.attrName.toLowerCase().startsWith("on")&&(a.keepAttr=!1)});let s=M.default.sanitize(e,o);t.innerHTML=s,t.querySelectorAll("[data-onclick]").forEach(i=>{let a=i.dataset.onclick;r[a]&&i.addEventListener("click",r[a])}),t.querySelectorAll("[data-onchange]").forEach(i=>{let a=i.dataset.onchange;r[a]&&i.addEventListener("change",r[a])})};var ne=p(require("dompurify"),1),P=null,z=(t,e)=>{if(typeof document>"u")return;let n=document.getElementById(t);if(!n)return;let r=n.innerHTML,o=ne.default.sanitize(r);if(P!==null&&o!==P){let s=document.createElement("div");e(s),n.innerHTML=P}else P=o,e(n)};var q=p(require("dompurify"),1);typeof window<"u"&&!window.__anchorSinglePopstateHandlerAttached&&(window.addEventListener("popstate",t=>{let e=t.state;e?.scrollPosition!==void 0&&window.scrollTo(0,e.scrollPosition)}),window.__anchorSinglePopstateHandlerAttached=!0);var I=(t,e,n,r="",o=null)=>{if(!t)return;let s=q.default.sanitize(e,{ALLOWED_URI_REGEXP:/^(https?:|\/)/}),i=q.default.sanitize(n,{USE_PROFILES:{html:!1}});t.setAttribute("href",s),t.setAttribute("aria-label",i),r&&(t.className=r.trim()),o&&t.replaceChildren(o),typeof window<"u"&&t.addEventListener("click",a=>{a.preventDefault();let d=a.currentTarget.getAttribute("href");if(d){let u=window.scrollY;window.scrollTo(0,0),window.history.pushState({scrollPosition:u},"",d),dispatchEvent(new PopStateEvent("popstate"))}})};var h=p(require("dompurify"),1);var re=(t="'self' 'nonce-rAnd0m123' 'unsafe-inline' 'unsafe-eval'",e="'self' 'nonce-rAnd0m123'",n="'none'",r="'self' https://fonts.googleapis.com https://fonts.gstatic.com",o="'self' https://blogger.googleusercontent.com",s=["'self'","https://fonts.googleapis.com","https://fonts.gstatic.com","https://www.google.com/maps/"],i="'self' https://www.youtube.com",a="'self'",c="/csp-report",d=!1)=>{let u=()=>{try{let l=document.querySelector('meta[http-equiv="Content-Security-Policy"]');l||(l=document.createElement("meta"),l.setAttribute("http-equiv","Content-Security-Policy"),document.head.appendChild(l));let f=d?`report-uri ${c};`:"";l.setAttribute("content",`default-src 'self'; script-src ${t}; style-src ${e}; object-src ${n}; font-src ${r}; img-src ${o}; connect-src ${s.join(" ")}; frame-src ${i}; base-uri ${a}; ${f}`)}catch(l){console.error("Error adding CSP meta element:",l)}};document.readyState==="loading"?document.addEventListener("DOMContentLoaded",u):u()};var N=(t,e)=>{let n={name:h.default.sanitize(t.name||""),description:h.default.sanitize(t.description||"Default description"),author:h.default.sanitize(t.author||"")},r=m=>{n.name=h.default.sanitize(m),l("name",n.name)},o=m=>{n.description=h.default.sanitize(m),l("description",n.description)},s=m=>{n.author=h.default.sanitize(m),l("author",n.author)},i=()=>n.name,a=()=>n.description,c=()=>n.author,d=()=>n,u=(m,v)=>{let S=document.createElement("meta");S.setAttribute("name",m),S.setAttribute("content",v),document.head.appendChild(S)},l=(m,v)=>{let S=document.querySelector(`meta[name="${m}"]`);S?S.setAttribute("content",v):u(m,v)},f=()=>{l("name",n.name),l("description",n.description),l("author",n.author)};return e&&re(e.scriptSrc,e.styleSrc,e.objectSrc,Array.isArray(e.connectSrc)?e.connectSrc.join(" "):e.connectSrc,e.reportOnly!==void 0?String(e.reportOnly):void 0),f(),{setName:r,setDescription:o,setAuthor:s,getName:i,getDescription:a,getAuthor:c,getAllMetaData:d,appendMetaTagsToHead:f}};var oe=p(require("dompurify"),1),T=(t,e,n,r,o)=>{let s=`#${t}`,i=e.querySelectorAll(s);if(i.length===0)throw new Error(`[useTSComponent] No element found with id '${t}' in the given parent.`);if(i.length>1)throw new Error(`[useTSComponent] Duplicate id '${t}' detected. Found ${i.length} elements.`);let a=i[0];a.innerHTML=oe.default.sanitize(a.innerHTML,{USE_PROFILES:{html:!0}}),n(a,r,o)};var F=(t,e,n,r=[])=>{let o=new Set;t.forEach((s,i)=>{if(o.has(s)){console.warn(`[useTSCollection] Duplicate ID in collection array: "${s}" \u2014 skipping.`);return}o.add(s);let a=e.querySelectorAll(`#${s}`);if(a.length>1){console.warn(`[useTSCollection] Duplicate ID in DOM: "${s}" (${a.length} elements found) \u2014 skipping component mount.`);return}let c=n[i],d=Array.isArray(r)?r[i]:void 0;typeof c=="function"?T(s,e,c,d):console.warn(`[useTSCollection] No valid component function found for ID: "${s}"`)})};var _=(t,e)=>{let r=(e??document).querySelectorAll(t);if(r.length===0)return process.env.NODE_ENV!=="production"&&console.warn(`[useTSSelect] No element found for selector: '${t}'`),null;if(t.startsWith("#")&&r.length>1){if(process.env.NODE_ENV!=="production")throw new Error(`[useTSSelect] Duplicate ID detected: '${t}'. Found ${r.length} elements with this ID.`);return r[0]}return r.length>1&&process.env.NODE_ENV!=="production"&&console.warn(`[useTSSelect] Multiple elements found for selector: '${t}'. Returning the first one.`),r[0]};var se=require("jwt-decode"),U=(t,e)=>{let n=localStorage.getItem("token");if(!n)return window.location.href=e,null;try{let r=(0,se.jwtDecode)(n),o=Date.now()/1e3;return r.exp&&r.exp<o&&(console.error("Token has expired"),window.localStorage.removeItem("token"),window.location.href=e),null}catch(r){return console.error("Invalid token:",r),window.location.href=e,null}};var y=(t,e,n)=>{t.forEach(r=>{e.forEach(o=>{r.addEventListener(o,s=>{n(r,s)})})})};var j=()=>({back:()=>window.history.back(),forward:()=>window.history.forward()});var B=(t,e)=>{let n=document.querySelector(`#${t}`)||document.querySelector(`.${t}`);if(!n)return;let r=window.location.pathname.replace(/\/$/,"");for(let o of e){let s=o.path.replace(/\/$/,"");if(r===s||r.startsWith(`${s}/`)){o.component(n);break}}};function W(t,e){let n=window.location.pathname.replace(/\/$/,"");e.routes.forEach(r=>{r.children?.length&&r.children.forEach(o=>{let s=o.path.replace(/\/$/,"");if(n===s||n.startsWith(`${s}/`)){let i=t.querySelector(`#${o.outlet}`)||t.querySelector(`.${o.outlet}`);i instanceof HTMLElement&&o.element&&o.element(i)}})})}var ie=require("zustand/vanilla");function Q(t){let e=(0,ie.createStore)(()=>({value:t})),n=new Set;return{get:()=>e.getState().value,set:r=>{e.setState({value:r}),n.forEach(o=>o(r))},subscribe:r=>(n.add(r),r(e.getState().value),()=>n.delete(r))}}function G(t){let e=t();typeof e=="function"&&e()}var ae=()=>{let t=document.querySelectorAll('a[href^="#"]');y(t,["click"],(e,n)=>{n.preventDefault();let r=e.getAttribute("href")?.substring(1),o=r?document.getElementById(r):null;o&&o.scrollIntoView({behavior:"smooth",block:"start"})})};var ce=require("lodash-es"),A=t=>t;typeof window<"u"&&typeof document<"u"&&(A=t=>{let e=document.createElement("div");return e.innerText=t,e.innerHTML});var Pe=(0,ce.debounce)(t=>{(t?Array.isArray(t)?t:t instanceof HTMLAnchorElement?[t]:Array.from(t):Array.from(document.querySelectorAll("a"))).forEach(n=>{if(!n||n.dataset.anchorEnhanced==="true")return;n.dataset.anchorEnhanced="true";let r=n.getAttribute("href")||"#",o=A(r);n.setAttribute("href",o);let s=n.getAttribute("class")||"";n.setAttribute("class",A(s));let i=n.getAttribute("aria-label");i&&n.setAttribute("aria-label",A(i));let a=n.querySelector(":scope > *");a&&(n.innerHTML="",n.appendChild(a));let c=n.getAttribute("href")||"";if(!c.startsWith("#")){try{if(new URL(c,window.location.href).origin!==window.location.origin)return}catch{return}n.addEventListener("click",d=>{d.preventDefault();try{let u=new URL(c,window.location.href);window.history.pushState({},"",u.pathname+u.search+u.hash),window.dispatchEvent(new PopStateEvent("popstate"))}catch(u){console.error("Invalid URL in anchor:",c,u)}})}})},50),le=t=>{Pe(t)};var ue=()=>{let t=document.querySelectorAll("a");return le(t)};var V=()=>{ue(),ae()};var X=async()=>{let t="https://cdn.jsdelivr.net/npm/brython@3/brython.min.js",e="https://cdn.jsdelivr.net/npm/brython@3/brython_stdlib.js",n=r=>new Promise((o,s)=>{let i=document.createElement("script");i.src=r,i.onload=()=>o(),i.onerror=()=>s(new Error(`Failed to load ${r}`)),document.head.appendChild(i)});await n(t),await n(e),typeof window.brython=="function"?window.brython():console.error("Brython did not load correctly.")},J=t=>new Promise((e,n)=>{let r=document.createElement("script");r.type="text/python",r.src=`/src/python/${t}`,r.onload=()=>e(),r.onerror=()=>n(new Error(`Failed to load ${t}`)),document.body.appendChild(r)});function Y(t){let e=null;return async(n,r)=>{try{if(!e){let o=await t();e=o.default||o}if(typeof e=="function")return e(n,r);if(e instanceof HTMLElement){n?.appendChild(e);return}if(e&&typeof e.render=="function")return e.render(n,r);console.warn("useTSLazy: Unsupported module type",e)}catch(o){console.error("useTSLazy failed:",o)}}}var K=p(require("dompurify"),1);var me=require("zustand/vanilla"),pe=p(require("dompurify"),1),g=(0,me.createStore)(t=>({params:{},query:{},setParams:e=>t(()=>({params:de(e)})),setQuery:e=>t(()=>({query:de(e)}))}));function de(t){let e={};for(let n in t)e[n]=pe.default.sanitize(t[n]);return e}var x=class{constructor(e,n){this.routes=[];this.routes=e,this.expectedParams=new Set(n),window.addEventListener("popstate",this.handlePopState.bind(this)),this.handlePopState()}handlePopState(){let e=window.location.pathname,n=window.location.search,r=this.parseQueryParams(n),o=this.findMatchingRoute(e,this.routes);if(o){if(o.routeto){this.navigate(o.routeto);return}let s=this.filterAndSanitizeParams(o.params);g.getState().setParams(s),g.getState().setQuery(r);let i=document.createElement("div");if(o.element?.(i,s,r),o.children){let a=e.slice(o.path.length),c=i.querySelector("#child");c&&this.renderChildren(o.children,a,c,s,r)}}else{let s=this.findMatchingRoute("*",this.routes);if(s){let i=this.filterAndSanitizeParams(s.params);g.getState().setParams(i),g.getState().setQuery(r);let a=document.createElement("div");s.element?.(a,i,r)}}}renderChildren(e,n,r,o,s){if(!e||e.length===0){let a=r.querySelector("#child");a&&a.remove();return}let i=this.findMatchingRoute(n,e);if(i){let a=document.createElement("div");a.id="child";let c={...o,...i.params},d=this.filterAndSanitizeParams(c);if(g.getState().setParams(d),g.getState().setQuery(s),i.element?.(a,d,s),r.appendChild(a),i.children){let u=n.slice(i.path.length);this.renderChildren(i.children,u,a,d,s)}}}parseQueryParams(e){let n={},r=new URLSearchParams(e);for(let[o,s]of r.entries())this.expectedParams.has(o)&&(n[o]=K.default.sanitize(s));return n}findMatchingRoute(e,n,r={}){for(let o of n){let s=o.path;if(s==="*")return o;{let a=[],c=s.replace(/:[^\s/]+/g,l=>(a.push(l.substring(1)),"([^\\s/]+)")),d=new RegExp(`^${c}(?:/|$)`),u=e.match(d);if(u){let l={...r};if(a.forEach((f,m)=>{l[f]=u[m+1]??""}),o.children){let f=e.slice(u[0].length),m=this.findMatchingRoute(f,o.children,l);if(m)return m}return{...o,params:l}}}}}filterAndSanitizeParams(e){if(!e)return{};let n={};for(let r in e)this.expectedParams.has(r)&&(n[r]=K.default.sanitize(e[r]??""));return n}navigate(e){history.pushState(null,"",e),this.handlePopState()}addRoute(e){this.routes.push(e)}};typeof window<"u"&&(window.addEventListener("popstate",()=>{w()}),document.addEventListener("DOMContentLoaded",w));0&&(module.exports={TSRouter,createEffect,createSignal,html,loadPyFiles,mapper,renderChildRoutes,useAnchorSingle,useInitialDOM,useTSAnchorMount,useTSAuth,useTSCollection,useTSComponent,useTSElementEach,useTSElements,useTSEvent,useTSEventAll,useTSExtractParams,useTSLazy,useTSMetaData,useTSNavigate,useTSOutlet,useTSParams,useTSPurifier,useTSSelect,useTSloadBrython});
2
2
  //# sourceMappingURL=index.cjs.map
@@ -1 +1 @@
1
- {"version":3,"sources":["../index.mts","../src/define/html.ts","../src/define/auto-register.ts","../src/func/index.ts","../src/hooks/useTSPurifier.ts","../src/hooks/useTSEvent.ts","../src/hooks/useTSParams.ts","../src/hooks/useTSExtract.ts","../src/hooks/useTSAllElements.ts","../src/hooks/useTSElements.ts","../src/hooks/useIntialDOM.ts","../src/hooks/useTSAnchorSingle.ts","../src/hooks/useTSMetaData.ts","../src/hooks/useTSCSP.ts","../src/hooks/useTSComponent.ts","../src/hooks/useTSCollection.ts","../src/hooks/useTSSelect.ts","../src/hooks/useTSAuth.ts","../src/hooks/useTSForEach.ts","../src/hooks/useTSNavigate.ts","../src/hooks/useTSOutlet.ts","../src/hooks/useReactivity.ts","../src/hooks/useTSHashAnchor.ts","../src/hooks/useTSAnchor.ts","../src/hooks/useTSNoReload.ts","../src/hooks/useTSAnchorMount.ts","../src/hooks/useTSInitializedBrython.ts","../src/hooks/useTSLazy.ts","../src/routes/class/Router.class.ts","../src/store/useTSParam.store.ts"],"sourcesContent":["import { autoRegister } from './src/define';\r\n\r\nexport { html } from './src/define';\r\nexport { mapper } from './src/func'\r\nexport { createEffect, createSignal, renderChildRoutes, useTSLazy, useTSOutlet, useTSloadBrython, loadPyFiles, useTSNavigate, useTSMetaData, useTSSelect, useTSCollection, useTSComponent, useTSAuth, useTSElementEach, useInitialDOM, useAnchorSingle, useTSPurifier, useTSEvent, useTSExtractParams, useTSParams, useTSEventAll, useTSElements, useTSAnchorMount } from \"./src/hooks\"\r\nexport { TSRouter } from \"./src/routes/class/Router.class\";\r\n\r\nif (typeof window !== 'undefined') {\r\n window.addEventListener('popstate', () => {\r\n autoRegister();\r\n });\r\n document.addEventListener('DOMContentLoaded', autoRegister);\r\n}\r\n\r\n","function sanitize(input: unknown): string {\r\n // Always convert to string first\r\n const str = input === null || input === undefined ? \"\" : String(input);\r\n\r\n return str\r\n // remove <script>, <iframe>, <object>, <embed>, <link>, <style> blocks\r\n .replace(/<\\s*(script|iframe|object|embed|link|style)[^>]*>.*?<\\s*\\/\\s*\\1\\s*>/gi, \"\")\r\n // remove opening dangerous tags without closing\r\n .replace(/<\\s*(script|iframe|object|embed|link|style)[^>]*>/gi, \"\")\r\n // strip inline event handlers like onclick=, onerror=, etc.\r\n .replace(/\\son\\w+\\s*=\\s*(['\"]).*?\\1/gi, \"\")\r\n // block javascript: URLs\r\n .replace(/\\s(href|src)\\s*=\\s*(['\"])\\s*javascript:[^'\"]*\\2/gi, \"\");\r\n}\r\n\r\nexport function html(strings: TemplateStringsArray, ...values: unknown[]): string {\r\n return strings.reduce((result, str, i) => {\r\n const safeValue = i < values.length ? sanitize(values[i]) : \"\";\r\n return result + str + safeValue;\r\n }, \"\");\r\n}\r\n","// auto-register-runtime.ts\r\nfunction autoRegister() {\r\n const allTags = new Set<string>();\r\n document.querySelectorAll('*').forEach((el) => {\r\n const tagName = el.tagName.toLowerCase();\r\n if (!tagName.includes('-')) return; // Only register custom tags with a dash\r\n allTags.add(tagName);\r\n });\r\n\r\n allTags.forEach(tag => {\r\n if (!customElements.get(tag)) {\r\n customElements.define(tag, class extends HTMLElement {\r\n connectedCallback() {\r\n this.innerHTML = `<div style=\"padding:10px;background:#eee;\">${tag} (Auto)</div>`;\r\n }\r\n });\r\n }\r\n });\r\n}\r\n\r\n\r\nexport { autoRegister };","// ✅ sanitize HTML but allow harmless tags\r\nconst sanitizeHtml = (str: string) => {\r\n return str\r\n // remove <script>, <iframe>, <object>, <embed>, <link>, <meta>, <style>\r\n .replace(/<\\/?(script|iframe|object|embed|link|meta|style)[^>]*>/gi, \"\")\r\n // remove any attribute that starts with \"on\" (onerror, onclick, etc.)\r\n .replace(/\\s+on[a-z]+\\s*=\\s*(\"[^\"]*\"|'[^']*'|[^\\s>]+)/gi, \"\")\r\n // block javascript: in href/src\r\n .replace(/\\s+(href|src)\\s*=\\s*(['\"]?)\\s*javascript:[^'\"\\s>]*/gi, \"\")\r\n}\r\n\r\n// ✅ mapper with sanitization\r\nconst mapper = (arr: string[] | undefined) =>\r\n arr?.map((item) => sanitizeHtml(item)).join(\"\") ?? \"\"\r\n\r\nexport { mapper }\r\n","import DOMPurify from \"dompurify\";\r\nimport type { Config } from \"dompurify\";\r\n\r\ntype TSPurifier = (input: string | HTMLElement, config?: Config) => string;\r\n\r\nexport const useTSPurifier: TSPurifier = (\r\n input,\r\n config?\r\n) => {\r\n const defaultConfig: Config = {\r\n ADD_TAGS: [\"my-custom-tag\"],\r\n };\r\n\r\n const mergedConfig: Config = { ...defaultConfig, ...config };\r\n\r\n if (typeof input === \"string\") {\r\n return DOMPurify.sanitize(input, mergedConfig);\r\n } else {\r\n return DOMPurify.sanitize(input.innerHTML, mergedConfig);\r\n }\r\n};\r\n","type TSEvent = (\r\n id: string | Document,\r\n eventType: keyof HTMLElementEventMap,\r\n handler: (event: HTMLElementEventMap[keyof HTMLElementEventMap]) => void\r\n) => void;\r\n\r\nexport const useTSEvent: TSEvent = (\r\n id,\r\n eventType,\r\n handler\r\n) => {\r\n if (typeof id === 'string') {\r\n const element = document.getElementById(id);\r\n if (element) {\r\n element.addEventListener(\r\n eventType,\r\n handler as EventListenerOrEventListenerObject\r\n );\r\n } else {\r\n console.warn(`Element with id '${id}' not found.`);\r\n }\r\n } else if (id === document) {\r\n document.addEventListener(\r\n eventType,\r\n handler as EventListenerOrEventListenerObject\r\n );\r\n } else {\r\n console.warn(`Invalid id parameter provided.`);\r\n }\r\n};\r\n","// utils/hooks/useTSParams.ts\r\nimport { createStore } from 'zustand/vanilla';\r\nimport DOMPurify from 'dompurify';\r\n\r\ntype ParamStore = {\r\n params: Record<string, string>;\r\n query: Record<string, string>;\r\n setFromPattern: (pattern: MustURL) => void;\r\n getParam: (key: string) => string | undefined;\r\n getQuery: (key: string) => string | undefined;\r\n};\r\n\r\ntype MustURL = `/${string}`;\r\n\r\nfunction extractPatternParams(pattern: MustURL, path: string): Record<string, string> {\r\n const paramNames: string[] = [];\r\n const regexPattern = pattern.replace(/:[^/]+/g, (match) => {\r\n paramNames.push(match.slice(1));\r\n return '([^/]+)';\r\n });\r\n\r\n const regex = new RegExp(`^${regexPattern}$`);\r\n const match = path.match(regex);\r\n const result: Record<string, string> = {};\r\n\r\n if (match) {\r\n paramNames.forEach((name, i) => {\r\n result[name] = DOMPurify.sanitize(match[i + 1] ?? '');\r\n });\r\n }\r\n\r\n return result;\r\n}\r\n\r\nfunction extractQueryParams(search: MustURL): Record<string, string> {\r\n const result: Record<string, string> = {};\r\n const urlSearchParams = new URLSearchParams(search);\r\n\r\n for (const [key, value] of urlSearchParams.entries()) {\r\n result[key] = DOMPurify.sanitize(value);\r\n }\r\n\r\n return result;\r\n}\r\n\r\nexport const useTSParams = createStore<ParamStore>((set, get) => ({\r\n params: {},\r\n query: {},\r\n setFromPattern: (pattern: MustURL) => {\r\n const path = window.location.pathname;\r\n const params = extractPatternParams(pattern, path);\r\n const query = extractQueryParams(window.location.search as MustURL);\r\n set({ params, query });\r\n },\r\n getParam: (key: string) => get().params[key],\r\n getQuery: (key: string) => get().query[key],\r\n}));\r\n","import { useTSParams } from './useTSParams';\r\n\r\ntype MustURL = `/${string}`;\r\n\r\nexport function useTSExtractParams(pattern: MustURL) {\r\n const store = useTSParams.getState();\r\n\r\n // Populate internal param/query store\r\n store.setFromPattern(pattern);\r\n\r\n const params = store.params;\r\n const query = store.query;\r\n\r\n return { ...params, ...query };\r\n}\r\n","export const useTSEventAll = <T extends Event>(\r\n selector: string,\r\n eventType: keyof HTMLElementEventMap,\r\n handler: (event: T) => void\r\n) => {\r\n const elements = document.querySelectorAll(selector);\r\n elements.forEach(element => {\r\n element.addEventListener(eventType, handler as EventListener);\r\n });\r\n\r\n return () => {\r\n elements.forEach(element => {\r\n element.removeEventListener(eventType, handler as EventListener);\r\n });\r\n };\r\n};\r\n\r\nexport const useTSEventSelectAll = <T extends Event>(\r\n selectors: string[],\r\n eventType: keyof HTMLElementEventMap,\r\n handler: (event: T) => void\r\n) => {\r\n const elements: NodeListOf<HTMLElement>[] = [];\r\n\r\n selectors.forEach(selector => {\r\n const selectedElements = document.querySelectorAll(\r\n selector\r\n ) as NodeListOf<HTMLElement>;\r\n selectedElements.forEach(element => {\r\n element.addEventListener(eventType, handler as EventListener);\r\n });\r\n elements.push(selectedElements);\r\n });\r\n\r\n return () => {\r\n elements.forEach(nodeList => {\r\n nodeList.forEach(element => {\r\n element.removeEventListener(eventType, handler as EventListener);\r\n });\r\n });\r\n };\r\n};\r\n","import DOMPurify, { Config } from \"dompurify\";\r\n\r\ntype TSElements = (\r\n htmlElement: HTMLElement,\r\n element: string,\r\n config?: Config\r\n) => void;\r\n\r\nexport const useTSElements: TSElements = (htmlElement, element, config) => {\r\n const defaultConfig: Config = {\r\n USE_PROFILES: { svg: true, html: true },\r\n ALLOWED_TAGS: [\r\n \"svg\", \"path\", \"circle\", \"rect\", \"line\", \"polyline\", \"polygon\", \"g\",\r\n \"main\", \"div\", \"h1\", \"h2\", \"h3\", \"h4\", \"h5\", \"h6\",\r\n \"p\", \"button\", \"span\", \"a\", \"img\", \"input\", \"ul\", \"li\", \"i\"\r\n ],\r\n ALLOWED_ATTR: [\r\n \"class\", \"id\", \"href\", \"src\", \"alt\", \"fill\", \"stroke\", \"stroke-width\",\r\n \"viewBox\", \"xmlns\", \"d\", \"x\", \"y\", \"cx\", \"cy\", \"r\", \"width\", \"height\"\r\n ],\r\n FORBID_TAGS: [\"script\", \"iframe\"],\r\n ALLOWED_URI_REGEXP:\r\n /^(?:(?:https?|mailto|tel|ftp):|[^a-z]|[a-z+.\\-]+(?:[^a-z+.\\-:]|$))/i,\r\n ...config,\r\n };\r\n\r\n // ✅ Allow custom elements dynamically\r\n DOMPurify.addHook(\"uponSanitizeElement\", (node, data) => {\r\n const tagName = data.tagName.toLowerCase();\r\n if (tagName.includes(\"-\")) {\r\n data.allowedTags[tagName] = true;\r\n }\r\n });\r\n\r\n // ✅ Strip dangerous event handlers\r\n DOMPurify.addHook(\"uponSanitizeAttribute\", (node, data) => {\r\n if (data.attrName && data.attrName.toLowerCase().startsWith(\"on\")) {\r\n data.keepAttr = false;\r\n }\r\n });\r\n\r\n const sanitizedContent = DOMPurify.sanitize(element, defaultConfig);\r\n\r\n if (htmlElement.innerHTML !== sanitizedContent) {\r\n htmlElement.innerHTML = sanitizedContent;\r\n }\r\n};\r\n\r\n","import DOMPurify from \"dompurify\"\r\n\r\nlet previousHTML: string | null = null\r\n\r\ntype TSInitialDOM = (id: string, mount: (el: HTMLElement) => void) => void;\r\n\r\nexport const useInitialDOM: TSInitialDOM = (id, mount) => {\r\n // SSR guard\r\n if (typeof document === \"undefined\") return\r\n\r\n const targetElement = document.getElementById(id)\r\n if (!targetElement) return\r\n\r\n const currentHTML = targetElement.innerHTML\r\n const sanitizedHTML = DOMPurify.sanitize(currentHTML)\r\n\r\n if (previousHTML !== null && sanitizedHTML !== previousHTML) {\r\n // DOM changed externally — reset and remount in a temp container\r\n const fallbackEl = document.createElement(\"div\")\r\n mount(fallbackEl)\r\n targetElement.innerHTML = previousHTML\r\n } else {\r\n // First time or same sanitized DOM — mount to target\r\n previousHTML = sanitizedHTML\r\n mount(targetElement)\r\n }\r\n}\r\n","import DOMPurify from \"dompurify\";\r\n\r\ndeclare global {\r\n interface Window {\r\n __anchorSinglePopstateHandlerAttached?: boolean;\r\n }\r\n}\r\n\r\ntype AnchorSingle = (\r\n element: HTMLAnchorElement | null,\r\n href: string,\r\n ariaLabel: string,\r\n className?: string,\r\n childElement?: HTMLElement | null\r\n) => void;\r\n\r\n// Attach popstate listener only in the browser\r\nif (typeof window !== \"undefined\" && !window.__anchorSinglePopstateHandlerAttached) {\r\n window.addEventListener(\"popstate\", (e) => {\r\n const state = e.state as { scrollPosition?: number };\r\n if (state?.scrollPosition !== undefined) {\r\n window.scrollTo(0, state.scrollPosition);\r\n }\r\n });\r\n window.__anchorSinglePopstateHandlerAttached = true;\r\n}\r\n\r\nexport const useAnchorSingle: AnchorSingle = (\r\n element,\r\n href,\r\n ariaLabel,\r\n className = \"\",\r\n childElement = null\r\n) => {\r\n if (!element) return;\r\n\r\n // Sanitize string inputs\r\n const sanitizedHref = DOMPurify.sanitize(href, { ALLOWED_URI_REGEXP: /^(https?:|\\/)/ });\r\n const sanitizedAriaLabel = DOMPurify.sanitize(ariaLabel, { USE_PROFILES: { html: false } });\r\n\r\n element.setAttribute(\"href\", sanitizedHref);\r\n element.setAttribute(\"aria-label\", sanitizedAriaLabel);\r\n\r\n if (className) {\r\n element.className = className.trim();\r\n }\r\n\r\n if (childElement) {\r\n element.replaceChildren(childElement);\r\n }\r\n\r\n // Event binding only in browser\r\n if (typeof window !== \"undefined\") {\r\n element.addEventListener(\"click\", (e) => {\r\n e.preventDefault();\r\n const target = e.currentTarget as HTMLAnchorElement;\r\n const hrefAttr = target.getAttribute(\"href\");\r\n if (hrefAttr) {\r\n const scrollPosition = window.scrollY;\r\n window.scrollTo(0, 0);\r\n window.history.pushState({ scrollPosition }, \"\", hrefAttr);\r\n dispatchEvent(new PopStateEvent(\"popstate\"));\r\n }\r\n });\r\n }\r\n};\r\n","import DOMPurify from \"dompurify\";\r\nimport { useTSCSP } from \"./useTSCSP\";\r\n\r\ntype SEOConfig = {\r\n name?: string;\r\n description?: string;\r\n author?: string;\r\n}\r\n\r\ntype CSPConfig = {\r\n scriptSrc?: string;\r\n styleSrc?: string;\r\n objectSrc?: string;\r\n connectSrc?: string[];\r\n reportOnly?: boolean;\r\n}\r\n\r\ntype SEOHandler = {\r\n setName: (name: string) => void;\r\n setDescription: (description: string) => void;\r\n setAuthor: (author: string) => void;\r\n getName: () => string;\r\n getDescription: () => string;\r\n getAuthor: () => string;\r\n getAllMetaData: () => SEOConfig;\r\n appendMetaTagsToHead: () => void;\r\n}\r\n\r\nexport const useTSMetaData = (\r\n config: SEOConfig,\r\n cspConfig?: CSPConfig\r\n): SEOHandler => {\r\n let metaData: SEOConfig = {\r\n name: DOMPurify.sanitize(config.name || \"\"),\r\n description: DOMPurify.sanitize(\r\n config.description || \"Default description\"\r\n ),\r\n author: DOMPurify.sanitize(config.author || \"\"),\r\n };\r\n\r\n const setName = (name: string): void => {\r\n metaData.name = DOMPurify.sanitize(name);\r\n updateMetaTag(\"name\", metaData.name);\r\n };\r\n\r\n const setDescription = (description: string): void => {\r\n metaData.description = DOMPurify.sanitize(description);\r\n updateMetaTag(\"description\", metaData.description);\r\n };\r\n\r\n const setAuthor = (author: string): void => {\r\n metaData.author = DOMPurify.sanitize(author);\r\n updateMetaTag(\"author\", metaData.author);\r\n };\r\n\r\n const getName = (): string => {\r\n return metaData.name!;\r\n };\r\n\r\n const getDescription = (): string => {\r\n return metaData.description!;\r\n };\r\n\r\n const getAuthor = (): string => {\r\n return metaData.author!;\r\n };\r\n\r\n const getAllMetaData = (): SEOConfig => {\r\n return metaData;\r\n };\r\n\r\n const createMetaTag = (name: string, content: string) => {\r\n const metaTag = document.createElement(\"meta\");\r\n metaTag.setAttribute(\"name\", name);\r\n metaTag.setAttribute(\"content\", content);\r\n document.head.appendChild(metaTag);\r\n };\r\n\r\n const updateMetaTag = (name: string, content: string) => {\r\n let metaTag = document.querySelector(`meta[name=\"${name}\"]`);\r\n if (metaTag) {\r\n metaTag.setAttribute(\"content\", content);\r\n } else {\r\n createMetaTag(name, content);\r\n }\r\n };\r\n\r\n const appendMetaTagsToHead = () => {\r\n updateMetaTag(\"name\", metaData.name!);\r\n updateMetaTag(\"description\", metaData.description!);\r\n updateMetaTag(\"author\", metaData.author!);\r\n };\r\n\r\n // Integrate with useTSCSP for CSP enforcement\r\n if (cspConfig) {\r\n useTSCSP(\r\n cspConfig.scriptSrc,\r\n cspConfig.styleSrc,\r\n cspConfig.objectSrc,\r\n Array.isArray(cspConfig.connectSrc) ? cspConfig.connectSrc.join(\" \") : cspConfig.connectSrc,\r\n cspConfig.reportOnly !== undefined ? String(cspConfig.reportOnly) : undefined\r\n );\r\n }\r\n\r\n appendMetaTagsToHead();\r\n\r\n return {\r\n setName,\r\n setDescription,\r\n setAuthor,\r\n getName,\r\n getDescription,\r\n getAuthor,\r\n getAllMetaData,\r\n appendMetaTagsToHead,\r\n };\r\n};\r\n","export const useTSCSP = (\r\n scriptSrc = `'self' 'nonce-rAnd0m123' 'unsafe-inline' 'unsafe-eval'`,\r\n styleSrc = \"'self' 'nonce-rAnd0m123'\", // Use nonce for inline styles\r\n objectSrc = \"'none'\",\r\n fontSrc = \"'self' https://fonts.googleapis.com https://fonts.gstatic.com\",\r\n imgSrc = \"'self' https://blogger.googleusercontent.com\",\r\n connectSrc = [\r\n \"'self'\",\r\n \"https://fonts.googleapis.com\",\r\n \"https://fonts.gstatic.com\",\r\n \"https://www.google.com/maps/\",\r\n ],\r\n frameSrc = \"'self' https://www.youtube.com\", // Add frame-src for embedding\r\n baseUri = \"'self'\",\r\n reportUri = \"/csp-report\",\r\n reportOnly = false\r\n) => {\r\n const addOrUpdateCSPMeta = () => {\r\n try {\r\n let metaElement = document.querySelector(\r\n 'meta[http-equiv=\"Content-Security-Policy\"]'\r\n );\r\n if (!metaElement) {\r\n metaElement = document.createElement(\"meta\");\r\n metaElement.setAttribute(\"http-equiv\", \"Content-Security-Policy\");\r\n document.head.appendChild(metaElement);\r\n }\r\n\r\n const reportUriDirective = reportOnly ? `report-uri ${reportUri};` : \"\";\r\n metaElement.setAttribute(\r\n \"content\",\r\n `default-src 'self'; script-src ${scriptSrc}; style-src ${styleSrc}; object-src ${objectSrc}; font-src ${fontSrc}; img-src ${imgSrc}; connect-src ${connectSrc.join(\r\n \" \"\r\n )}; frame-src ${frameSrc}; base-uri ${baseUri}; ${reportUriDirective}`\r\n );\r\n } catch (error) {\r\n console.error(\"Error adding CSP meta element:\", error);\r\n }\r\n };\r\n\r\n if (document.readyState === \"loading\") {\r\n document.addEventListener(\"DOMContentLoaded\", addOrUpdateCSPMeta);\r\n } else {\r\n addOrUpdateCSPMeta();\r\n }\r\n};\r\n","import DOMPurify from \"dompurify\";\r\n\r\ntype TSComponent = (\r\n id: string,\r\n parent: HTMLElement,\r\n element: Function,\r\n params?: any,\r\n params2?: any\r\n) => void;\r\n\r\nexport const useTSComponent: TSComponent = (\r\n id,\r\n parent,\r\n element,\r\n params,\r\n params2\r\n) => {\r\n const selector = `#${id}`;\r\n const matches = parent.querySelectorAll<HTMLElement>(selector);\r\n\r\n // 1. Missing element check\r\n if (matches.length === 0) {\r\n throw new Error(`[useTSComponent] No element found with id '${id}' in the given parent.`);\r\n }\r\n\r\n // 2. Duplicate ID check\r\n if (matches.length > 1) {\r\n throw new Error(`[useTSComponent] Duplicate id '${id}' detected. Found ${matches.length} elements.`);\r\n }\r\n\r\n const target = matches[0];\r\n\r\n // 3. Sanitize the target’s existing HTML content\r\n target.innerHTML = DOMPurify.sanitize(target.innerHTML, { USE_PROFILES: { html: true } });\r\n\r\n // 4. Call the component function with the target\r\n element(target, params, params2);\r\n};\r\n","import { useTSComponent } from \"./useTSComponent\";\r\n\r\ntype TSCollection = (\r\n collections: string[],\r\n DOM: HTMLElement,\r\n elements: Function[],\r\n params?: any[]\r\n) => void;\r\n\r\nexport const useTSCollection: TSCollection = (\r\n collections,\r\n DOM,\r\n elements,\r\n params = []\r\n) => {\r\n const seenIds = new Set<string>();\r\n\r\n collections.forEach((id, index) => {\r\n // Check for duplicate IDs in the collection list itself\r\n if (seenIds.has(id)) {\r\n console.warn(`[useTSCollection] Duplicate ID in collection array: \"${id}\" — skipping.`);\r\n return;\r\n }\r\n seenIds.add(id);\r\n\r\n // Check for duplicates already in DOM\r\n const matches = DOM.querySelectorAll(`#${id}`);\r\n if (matches.length > 1) {\r\n console.warn(\r\n `[useTSCollection] Duplicate ID in DOM: \"${id}\" (${matches.length} elements found) — skipping component mount.`\r\n );\r\n return;\r\n }\r\n\r\n const elementFn = elements[index];\r\n const param = Array.isArray(params) ? params[index] : undefined;\r\n\r\n if (typeof elementFn === \"function\") {\r\n useTSComponent(id, DOM, elementFn, param);\r\n } else {\r\n console.warn(`[useTSCollection] No valid component function found for ID: \"${id}\"`);\r\n }\r\n });\r\n};\r\n","type TSSelect = <T extends Element = HTMLElement>(\r\n selector: string,\r\n scope?: HTMLElement\r\n) => T | null;\r\n\r\nconst useTSSelect: TSSelect = <T extends Element = HTMLElement>(\r\n selector: string,\r\n scope?: HTMLElement\r\n): T | null => {\r\n const root = scope ?? document;\r\n const elements = root.querySelectorAll<T>(selector);\r\n\r\n if (elements.length === 0) {\r\n if (process.env.NODE_ENV !== \"production\") {\r\n console.warn(`[useTSSelect] No element found for selector: '${selector}'`);\r\n }\r\n return null;\r\n }\r\n\r\n if (selector.startsWith(\"#\") && elements.length > 1) {\r\n if (process.env.NODE_ENV !== \"production\") {\r\n throw new Error(\r\n `[useTSSelect] Duplicate ID detected: '${selector}'. Found ${elements.length} elements with this ID.`\r\n );\r\n }\r\n return elements[0]; // fallback: just return first\r\n }\r\n\r\n if (elements.length > 1) {\r\n if (process.env.NODE_ENV !== \"production\") {\r\n console.warn(\r\n `[useTSSelect] Multiple elements found for selector: '${selector}'. Returning the first one.`\r\n );\r\n }\r\n }\r\n\r\n return elements[0];\r\n};\r\n\r\nexport { useTSSelect };\r\n","import { jwtDecode } from \"jwt-decode\";\r\n\r\nexport const useTSAuth = (_Component: HTMLElement | void, loginUrl: string) => {\r\n const token = localStorage.getItem(\"token\");\r\n\r\n if (!token) {\r\n // Redirect to login page if token is missing\r\n window.location.href = loginUrl;\r\n return null; // Return null when redirecting\r\n }\r\n\r\n try {\r\n const decodedToken: any = jwtDecode(token);\r\n\r\n // Example: Check if the token has expired\r\n const currentTime = Date.now() / 1000;\r\n if (decodedToken.exp && decodedToken.exp < currentTime) {\r\n console.error(\"Token has expired\");\r\n window.localStorage.removeItem(\"token\");\r\n window.location.href = loginUrl;\r\n return null; // Return null when redirecting\r\n }\r\n\r\n // If the user is authenticated, return the component\r\n return null;\r\n } catch (error) {\r\n console.error(\"Invalid token:\", error);\r\n // Redirect to login page if token decoding fails\r\n window.location.href = loginUrl;\r\n return null; // Return null when redirecting\r\n }\r\n};\r\n","\r\ntype TSElementEach = (\r\n elements: NodeListOf<HTMLElement> | HTMLElement[],\r\n events: (keyof HTMLElementEventMap)[],\r\n callback: (element: HTMLElement, event: Event) => void\r\n) => void;\r\n\r\nexport const useTSElementEach: TSElementEach = (\r\n elements,\r\n events,\r\n callback\r\n) => {\r\n elements.forEach(element => {\r\n events.forEach(eventType => {\r\n element.addEventListener(eventType, event => {\r\n callback(element, event);\r\n });\r\n });\r\n });\r\n};\r\n","export const useTSNavigate = () => {\r\n const back = () => window.history.back();\r\n const forward = () => window.history.forward();\r\n\r\n return {\r\n back,\r\n forward,\r\n };\r\n};\r\n","// types.ts\r\nexport type OutletComponent = (DOM: HTMLElement) => void;\r\n\r\nexport type ChildRoute = {\r\n path: string;\r\n outlet: string;\r\n element: OutletComponent;\r\n};\r\n\r\nexport type Route = {\r\n path: string;\r\n element: (DOM: HTMLElement) => void;\r\n children?: ChildRoute[];\r\n};\r\n\r\n// You don't actually need to import the class TSRouter type.\r\n// Instead, export a cleaner interface with routes.\r\nexport interface RouterInstance {\r\n routes: Route[];\r\n}\r\n\r\n\r\ntype OutletOptions = {\r\n path: string;\r\n component: OutletComponent;\r\n};\r\n\r\nexport const useTSOutlet = (\r\n selector: string,\r\n outlets: OutletOptions[]\r\n): void => {\r\n const outletDOM = document.querySelector<HTMLElement>(`#${selector}`)\r\n || document.querySelector<HTMLElement>(`.${selector}`);\r\n\r\n if (!outletDOM) return;\r\n\r\n const currentPath = window.location.pathname.replace(/\\/$/, \"\");\r\n\r\n for (const outlet of outlets) {\r\n const base = outlet.path.replace(/\\/$/, \"\");\r\n\r\n // Match exact or nested path (e.g., /openai/child/1)\r\n if (currentPath === base || currentPath.startsWith(`${base}/`)) {\r\n outlet.component(outletDOM);\r\n break;\r\n }\r\n }\r\n};\r\n\r\n\r\nexport function renderChildRoutes(DOM: HTMLElement, router: RouterInstance): void {\r\n const pathname = window.location.pathname.replace(/\\/$/, \"\");\r\n\r\n router.routes.forEach((route) => {\r\n if (!route.children?.length) return;\r\n\r\n route.children.forEach((child) => {\r\n const childPath = child.path.replace(/\\/$/, \"\");\r\n\r\n if (pathname === childPath || pathname.startsWith(`${childPath}/`)) {\r\n const outlet = DOM.querySelector(`#${child.outlet}`)\r\n || DOM.querySelector(`.${child.outlet}`);\r\n if (outlet instanceof HTMLElement && child.element) {\r\n child.element(outlet);\r\n }\r\n }\r\n });\r\n });\r\n}","// useTSReactivity.ts\r\nimport { createStore } from 'zustand/vanilla';\r\n\r\ntype Listener<T> = (value: T) => void;\r\n\r\ninterface Signal<T> {\r\n get: () => T;\r\n set: (newValue: T) => void;\r\n subscribe: (listener: Listener<T>) => () => void;\r\n}\r\n\r\nexport function createSignal<T>(initialValue: T): Signal<T> {\r\n const store = createStore<{ value: T }>(() => ({ value: initialValue }));\r\n const listeners = new Set<Listener<T>>();\r\n\r\n return {\r\n get: () => store.getState().value,\r\n set: (newValue: T) => {\r\n store.setState({ value: newValue });\r\n listeners.forEach((listener) => listener(newValue));\r\n },\r\n subscribe: (listener: Listener<T>) => {\r\n listeners.add(listener);\r\n listener(store.getState().value); // Trigger immediately\r\n return () => listeners.delete(listener);\r\n },\r\n };\r\n}\r\n\r\ntype CleanupFn = () => void;\r\n\r\nexport function createEffect(effectFn: () => void | CleanupFn): void {\r\n const cleanup = effectFn();\r\n\r\n // Optional: return a way to dispose the effect manually\r\n if (typeof cleanup === 'function') {\r\n // You may store this and call it later if needed\r\n cleanup();\r\n }\r\n}\r\n","import { useTSElementEach } from './useTSForEach';\r\n\r\n\r\nconst useTSHashAnchor = () => {\r\n const links = document.querySelectorAll<HTMLAnchorElement>('a[href^=\"#\"]');\r\n\r\n useTSElementEach(\r\n links,\r\n ['click'],\r\n (element, e) => {\r\n e.preventDefault();\r\n const targetId = element.getAttribute('href')?.substring(1);\r\n const targetElement = targetId ? document.getElementById(targetId) : null;\r\n\r\n if (targetElement) {\r\n targetElement.scrollIntoView({\r\n behavior: 'smooth',\r\n block: 'start'\r\n });\r\n }\r\n }\r\n );\r\n}\r\n\r\nexport { useTSHashAnchor }","import { debounce } from 'lodash-es';\r\n\r\nlet sanitizeInput = (input: string): string => input;\r\n\r\nif (typeof window !== 'undefined' && typeof document !== 'undefined') {\r\n sanitizeInput = (input: string): string => {\r\n const element = document.createElement(\"div\");\r\n element.innerText = input;\r\n return element.innerHTML;\r\n };\r\n}\r\n\r\ntype AnchorInput =\r\n | NodeListOf<HTMLAnchorElement>\r\n | HTMLAnchorElement[]\r\n | HTMLAnchorElement\r\n | null\r\n | undefined;\r\n\r\nconst _enhanceAnchors = debounce((anchors: AnchorInput) => {\r\n const resolvedAnchors: HTMLAnchorElement[] = (() => {\r\n if (!anchors) return Array.from(document.querySelectorAll(\"a\"));\r\n if (Array.isArray(anchors)) return anchors;\r\n if (anchors instanceof HTMLAnchorElement) return [anchors];\r\n return Array.from(anchors);\r\n })();\r\n\r\n resolvedAnchors.forEach(anchor => {\r\n if (!anchor || anchor.dataset.anchorEnhanced === 'true') return;\r\n anchor.dataset.anchorEnhanced = 'true';\r\n\r\n // Sanitize attributes\r\n const originalHref = anchor.getAttribute(\"href\") || \"#\";\r\n const sanitizedHref = sanitizeInput(originalHref);\r\n anchor.setAttribute(\"href\", sanitizedHref);\r\n\r\n const originalClassName = anchor.getAttribute(\"class\") || \"\";\r\n anchor.setAttribute(\"class\", sanitizeInput(originalClassName));\r\n\r\n const ariaLabel = anchor.getAttribute(\"aria-label\");\r\n if (ariaLabel) {\r\n anchor.setAttribute(\"aria-label\", sanitizeInput(ariaLabel));\r\n }\r\n\r\n // Keep child elements safe (optional — you can remove this block if not needed)\r\n const child = anchor.querySelector(\":scope > *\") as HTMLElement;\r\n if (child) {\r\n anchor.innerHTML = \"\";\r\n anchor.appendChild(child);\r\n }\r\n\r\n // Skip attaching click listener if:\r\n // - It's a hash link (in-page navigation)\r\n // - It's an external link\r\n const href = anchor.getAttribute(\"href\") || \"\";\r\n if (href.startsWith(\"#\")) return; // Let browser handle hash scrolling normally\r\n\r\n try {\r\n const url = new URL(href, window.location.href);\r\n if (url.origin !== window.location.origin) return; // external link\r\n } catch {\r\n return; // invalid URL — skip\r\n }\r\n\r\n // Intercept same-origin navigation for SPA\r\n anchor.addEventListener(\"click\", (e: MouseEvent) => {\r\n e.preventDefault();\r\n try {\r\n const url = new URL(href, window.location.href);\r\n window.history.pushState({}, \"\", url.pathname + url.search + url.hash);\r\n window.dispatchEvent(new PopStateEvent(\"popstate\"));\r\n } catch (err) {\r\n console.error(\"Invalid URL in anchor:\", href, err);\r\n }\r\n });\r\n });\r\n}, 50);\r\n\r\nexport const useAnchor = (anchors?: AnchorInput): void => {\r\n _enhanceAnchors(anchors);\r\n};\r\n","import { useAnchor } from './useTSAnchor';\r\n\r\nconst useTSNoReload = () => {\r\n const a = document.querySelectorAll(\"a\") as NodeListOf<HTMLAnchorElement>;\r\n return useAnchor(a);\r\n}\r\n\r\nexport { useTSNoReload };","import { useTSHashAnchor } from \"./useTSHashAnchor\";\r\nimport { useTSNoReload } from \"./useTSNoReload\";\r\n\r\nconst useTSAnchorMount = () => {\r\n useTSNoReload();\r\n useTSHashAnchor();\r\n};\r\n\r\nexport { useTSAnchorMount };","// src/loadBrython.ts\r\ntype LoadBrython = (src: string) => Promise<void>;\r\n\r\ndeclare global {\r\n interface Window {\r\n brython: Function;\r\n }\r\n}\r\n\r\nconst useTSloadBrython = async () => {\r\n const brythonJS = \"https://cdn.jsdelivr.net/npm/brython@3/brython.min.js\";\r\n const brythonStdlib = \"https://cdn.jsdelivr.net/npm/brython@3/brython_stdlib.js\";\r\n\r\n // Utility function to load a script\r\n const loadScript: LoadBrython = (src) => {\r\n return new Promise((resolve, reject) => {\r\n const script = document.createElement(\"script\");\r\n script.src = src;\r\n script.onload = () => resolve();\r\n script.onerror = () => reject(new Error(`Failed to load ${src}`));\r\n document.head.appendChild(script);\r\n });\r\n };\r\n\r\n // Load both scripts sequentially\r\n await loadScript(brythonJS);\r\n await loadScript(brythonStdlib);\r\n\r\n // Call brython() after scripts are loaded\r\n if (typeof window.brython === \"function\") {\r\n window.brython();\r\n } else {\r\n console.error(\"Brython did not load correctly.\");\r\n }\r\n};\r\n\r\ntype RequirePy = `${string}.py`;\r\n\r\ntype LoadPy = (src: RequirePy) => Promise<void>;\r\n\r\nconst loadPyFiles: LoadPy = (src) =>\r\n new Promise((resolve, reject) => {\r\n const script = document.createElement(\"script\");\r\n script.type = \"text/python\";\r\n script.src = `/src/python/${src}`;\r\n script.onload = () => resolve();\r\n script.onerror = () => reject(new Error(`Failed to load ${src}`));\r\n document.body.appendChild(script);\r\n });\r\n\r\nexport { useTSloadBrython, loadPyFiles };\r\n","export function useTSLazy(factory: () => Promise<any>) {\r\n let cached: any | null = null;\r\n\r\n return async (el?: HTMLElement, props?: any) => {\r\n try {\r\n if (!cached) {\r\n const mod = await factory();\r\n cached = mod.default || mod;\r\n }\r\n\r\n // If it's a component function (Vanilla TS style)\r\n if (typeof cached === \"function\") {\r\n return cached(el, props);\r\n }\r\n\r\n // If it's already an HTMLElement\r\n if (cached instanceof HTMLElement) {\r\n el?.appendChild(cached);\r\n return;\r\n }\r\n\r\n // If it's a plain object with render()\r\n if (cached && typeof cached.render === \"function\") {\r\n return cached.render(el, props);\r\n }\r\n\r\n console.warn(\"useTSLazy: Unsupported module type\", cached);\r\n } catch (err) {\r\n console.error(\"useTSLazy failed:\", err);\r\n }\r\n };\r\n}\r\n","import DOMPurify from \"dompurify\";\r\nimport { tsParamsStore } from \"../../store\";\r\n\r\ntype RouteCallback = (\r\n errorElement?: HTMLElement,\r\n params?: Record<string, string>,\r\n query?: Record<string, string>\r\n) => void;\r\n\r\ninterface RouteConfig {\r\n path: string;\r\n routeto?: string;\r\n element: RouteCallback;\r\n errorElement?: RouteCallback;\r\n children?: RouteConfig[];\r\n params?: Record<string, string>;\r\n}\r\n\r\nexport class TSRouter {\r\n private routes: RouteConfig[] = [];\r\n private expectedParams: Set<string>;\r\n\r\n constructor(routes: RouteConfig[], expectedParams: string[]) {\r\n this.routes = routes;\r\n this.expectedParams = new Set(expectedParams);\r\n window.addEventListener(\"popstate\", this.handlePopState.bind(this));\r\n this.handlePopState(); // Initial load\r\n }\r\n\r\n private handlePopState() {\r\n const currentPath = window.location.pathname;\r\n const currentSearch = window.location.search;\r\n const queryParams = this.parseQueryParams(currentSearch);\r\n\r\n const matchingRoute = this.findMatchingRoute(currentPath, this.routes);\r\n\r\n if (matchingRoute) {\r\n if (matchingRoute.routeto) {\r\n this.navigate(matchingRoute.routeto);\r\n return;\r\n }\r\n\r\n const sanitizedParams = this.filterAndSanitizeParams(matchingRoute.params);\r\n tsParamsStore.getState().setParams(sanitizedParams);\r\n tsParamsStore.getState().setQuery(queryParams);\r\n\r\n const errorElement = document.createElement(\"div\");\r\n\r\n matchingRoute.element?.(errorElement, sanitizedParams, queryParams);\r\n\r\n if (matchingRoute.children) {\r\n const nestedPath = currentPath.slice(matchingRoute.path.length);\r\n const childElement = errorElement.querySelector(\"#child\") as HTMLDivElement;\r\n if (childElement) {\r\n this.renderChildren(\r\n matchingRoute.children,\r\n nestedPath,\r\n childElement,\r\n sanitizedParams,\r\n queryParams\r\n );\r\n }\r\n }\r\n } else {\r\n const notFoundRoute = this.findMatchingRoute(\"*\", this.routes);\r\n if (notFoundRoute) {\r\n const fallbackParams = this.filterAndSanitizeParams(notFoundRoute.params);\r\n tsParamsStore.getState().setParams(fallbackParams);\r\n tsParamsStore.getState().setQuery(queryParams);\r\n\r\n const errorElement = document.createElement(\"div\");\r\n notFoundRoute.element?.(errorElement, fallbackParams, queryParams);\r\n }\r\n }\r\n }\r\n\r\n private renderChildren(\r\n children: RouteConfig[] | undefined,\r\n nestedPath: string,\r\n parentElement: HTMLElement,\r\n parentParams: Record<string, string>,\r\n queryParams: Record<string, string>\r\n ) {\r\n if (!children || children.length === 0) {\r\n const childElement = parentElement.querySelector(\"#child\") as HTMLDivElement;\r\n if (childElement) childElement.remove();\r\n return;\r\n }\r\n\r\n const matchingChild = this.findMatchingRoute(nestedPath, children);\r\n if (matchingChild) {\r\n const childElement = document.createElement(\"div\");\r\n childElement.id = \"child\";\r\n const mergedParams = { ...parentParams, ...matchingChild.params };\r\n const sanitizedParams = this.filterAndSanitizeParams(mergedParams);\r\n\r\n tsParamsStore.getState().setParams(sanitizedParams);\r\n tsParamsStore.getState().setQuery(queryParams);\r\n\r\n matchingChild.element?.(childElement, sanitizedParams, queryParams);\r\n parentElement.appendChild(childElement);\r\n\r\n if (matchingChild.children) {\r\n const nextNestedPath = nestedPath.slice(matchingChild.path.length);\r\n this.renderChildren(\r\n matchingChild.children,\r\n nextNestedPath,\r\n childElement,\r\n sanitizedParams,\r\n queryParams\r\n );\r\n }\r\n }\r\n }\r\n\r\n private parseQueryParams(search: string): Record<string, string> {\r\n const queryParams: Record<string, string> = {};\r\n const urlSearchParams = new URLSearchParams(search);\r\n\r\n for (const [key, value] of urlSearchParams.entries()) {\r\n if (this.expectedParams.has(key)) {\r\n queryParams[key] = DOMPurify.sanitize(value);\r\n }\r\n }\r\n\r\n return queryParams;\r\n }\r\n\r\n private findMatchingRoute(\r\n path: string,\r\n routes: RouteConfig[],\r\n inheritedParams: Record<string, string> = {}\r\n ): RouteConfig | undefined {\r\n for (const route of routes) {\r\n const routePath = route.path;\r\n const isDefaultRoute = routePath === \"*\";\r\n\r\n if (!isDefaultRoute) {\r\n const paramNames: string[] = [];\r\n const regexPattern = routePath.replace(/:[^\\s/]+/g, match => {\r\n paramNames.push(match.substring(1));\r\n return \"([^\\\\s/]+)\";\r\n });\r\n\r\n const regex = new RegExp(`^${regexPattern}(?:/|$)`);\r\n const match = path.match(regex);\r\n\r\n if (match) {\r\n const params: Record<string, string> = { ...inheritedParams };\r\n paramNames.forEach((name, index) => {\r\n params[name] = match[index + 1] ?? \"\";\r\n });\r\n\r\n if (route.children) {\r\n const nestedPath = path.slice(match[0].length);\r\n const matchingChild = this.findMatchingRoute(\r\n nestedPath,\r\n route.children,\r\n params\r\n );\r\n if (matchingChild) return matchingChild;\r\n }\r\n\r\n return { ...route, params };\r\n }\r\n } else {\r\n return route;\r\n }\r\n }\r\n\r\n return undefined;\r\n }\r\n\r\n private filterAndSanitizeParams(\r\n params?: Record<string, string>\r\n ): Record<string, string> {\r\n if (!params) return {};\r\n const sanitizedParams: Record<string, string> = {};\r\n for (const key in params) {\r\n if (this.expectedParams.has(key)) {\r\n sanitizedParams[key] = DOMPurify.sanitize(params[key] ?? \"\");\r\n }\r\n }\r\n return sanitizedParams;\r\n }\r\n\r\n navigate(path: string) {\r\n history.pushState(null, \"\", path);\r\n this.handlePopState();\r\n }\r\n\r\n addRoute(route: RouteConfig) {\r\n this.routes.push(route);\r\n }\r\n}\r\n","import { createStore } from \"zustand/vanilla\";\r\nimport DOMPurify from \"dompurify\";\r\n\r\ninterface TSParamsState {\r\n params: Record<string, string>;\r\n query: Record<string, string>;\r\n setParams: (params: Record<string, string>) => void;\r\n setQuery: (query: Record<string, string>) => void;\r\n}\r\n\r\nexport const tsParamsStore = createStore<TSParamsState>((set) => ({\r\n params: {},\r\n query: {},\r\n setParams: (params) =>\r\n set(() => ({\r\n params: sanitize(params),\r\n })),\r\n setQuery: (query) =>\r\n set(() => ({\r\n query: sanitize(query),\r\n })),\r\n}));\r\n\r\nfunction sanitize(obj: Record<string, string>): Record<string, string> {\r\n const output: Record<string, string> = {};\r\n for (const key in obj) {\r\n output[key] = DOMPurify.sanitize(obj[key]);\r\n }\r\n return output;\r\n}\r\n"],"mappings":"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","names":["index_exports","__export","TSRouter","createEffect","createSignal","html","loadPyFiles","mapper","renderChildRoutes","useAnchorSingle","useInitialDOM","useTSAnchorMount","useTSAuth","useTSCollection","useTSComponent","useTSElementEach","useTSElements","useTSEvent","useTSEventAll","useTSExtractParams","useTSLazy","useTSMetaData","useTSNavigate","useTSOutlet","useTSParams","useTSPurifier","useTSSelect","useTSloadBrython","__toCommonJS","sanitize","input","html","strings","values","result","str","i","safeValue","autoRegister","allTags","el","tagName","tag","sanitizeHtml","str","mapper","arr","item","import_dompurify","useTSPurifier","input","config","mergedConfig","DOMPurify","useTSEvent","id","eventType","handler","element","import_vanilla","import_dompurify","extractPatternParams","pattern","path","paramNames","regexPattern","match","regex","result","name","i","DOMPurify","extractQueryParams","search","urlSearchParams","key","value","useTSParams","set","get","params","query","useTSExtractParams","pattern","store","useTSParams","params","query","useTSEventAll","selector","eventType","handler","elements","element","import_dompurify","useTSElements","htmlElement","element","config","defaultConfig","DOMPurify","node","data","tagName","sanitizedContent","import_dompurify","previousHTML","useInitialDOM","id","mount","targetElement","currentHTML","sanitizedHTML","DOMPurify","fallbackEl","import_dompurify","e","state","useAnchorSingle","element","href","ariaLabel","className","childElement","sanitizedHref","DOMPurify","sanitizedAriaLabel","hrefAttr","scrollPosition","import_dompurify","useTSCSP","scriptSrc","styleSrc","objectSrc","fontSrc","imgSrc","connectSrc","frameSrc","baseUri","reportUri","reportOnly","addOrUpdateCSPMeta","metaElement","reportUriDirective","error","useTSMetaData","config","cspConfig","metaData","DOMPurify","setName","name","updateMetaTag","setDescription","description","setAuthor","author","getName","getDescription","getAuthor","getAllMetaData","createMetaTag","content","metaTag","appendMetaTagsToHead","useTSCSP","import_dompurify","useTSComponent","id","parent","element","params","params2","selector","matches","target","DOMPurify","useTSCollection","collections","DOM","elements","params","seenIds","id","index","matches","elementFn","param","useTSComponent","useTSSelect","selector","scope","elements","import_jwt_decode","useTSAuth","_Component","loginUrl","token","decodedToken","currentTime","error","useTSElementEach","elements","events","callback","element","eventType","event","useTSNavigate","useTSOutlet","selector","outlets","outletDOM","currentPath","outlet","base","renderChildRoutes","DOM","router","pathname","route","child","childPath","import_vanilla","createSignal","initialValue","store","listeners","newValue","listener","createEffect","effectFn","cleanup","useTSHashAnchor","links","useTSElementEach","element","e","targetId","targetElement","import_lodash_es","sanitizeInput","input","element","_enhanceAnchors","anchors","anchor","originalHref","sanitizedHref","originalClassName","ariaLabel","child","href","e","url","err","useAnchor","useTSNoReload","a","useAnchor","useTSAnchorMount","useTSNoReload","useTSHashAnchor","useTSloadBrython","brythonJS","brythonStdlib","loadScript","src","resolve","reject","script","loadPyFiles","useTSLazy","factory","cached","el","props","mod","err","import_dompurify","import_vanilla","import_dompurify","tsParamsStore","set","params","sanitize","query","obj","output","key","DOMPurify","TSRouter","routes","expectedParams","currentPath","currentSearch","queryParams","matchingRoute","sanitizedParams","tsParamsStore","errorElement","nestedPath","childElement","notFoundRoute","fallbackParams","children","parentElement","parentParams","matchingChild","mergedParams","nextNestedPath","search","urlSearchParams","key","value","DOMPurify","path","inheritedParams","route","routePath","paramNames","regexPattern","match","regex","params","name","index","autoRegister"]}
1
+ {"version":3,"sources":["../index.mts","../src/define/html.ts","../src/define/auto-register.ts","../src/func/index.ts","../src/hooks/useTSPurifier.ts","../src/hooks/useTSEvent.ts","../src/hooks/useTSParams.ts","../src/hooks/useTSExtract.ts","../src/hooks/useTSAllElements.ts","../src/hooks/useTSElements.ts","../src/hooks/useIntialDOM.ts","../src/hooks/useTSAnchorSingle.ts","../src/hooks/useTSMetaData.ts","../src/hooks/useTSCSP.ts","../src/hooks/useTSComponent.ts","../src/hooks/useTSCollection.ts","../src/hooks/useTSSelect.ts","../src/hooks/useTSAuth.ts","../src/hooks/useTSForEach.ts","../src/hooks/useTSNavigate.ts","../src/hooks/useTSOutlet.ts","../src/hooks/useReactivity.ts","../src/hooks/useTSHashAnchor.ts","../src/hooks/useTSAnchor.ts","../src/hooks/useTSNoReload.ts","../src/hooks/useTSAnchorMount.ts","../src/hooks/useTSInitializedBrython.ts","../src/hooks/useTSLazy.ts","../src/routes/class/Router.class.ts","../src/store/useTSParam.store.ts"],"sourcesContent":["import { autoRegister } from './src/define';\r\n\r\nexport { html } from './src/define';\r\nexport { mapper } from './src/func'\r\nexport { createEffect, createSignal, renderChildRoutes, useTSLazy, useTSOutlet, useTSloadBrython, loadPyFiles, useTSNavigate, useTSMetaData, useTSSelect, useTSCollection, useTSComponent, useTSAuth, useTSElementEach, useInitialDOM, useAnchorSingle, useTSPurifier, useTSEvent, useTSExtractParams, useTSParams, useTSEventAll, useTSElements, useTSAnchorMount } from \"./src/hooks\"\r\nexport { TSRouter } from \"./src/routes/class/Router.class\";\r\n\r\nif (typeof window !== 'undefined') {\r\n window.addEventListener('popstate', () => {\r\n autoRegister();\r\n });\r\n document.addEventListener('DOMContentLoaded', autoRegister);\r\n}\r\n\r\n","function sanitize(input: unknown): string {\r\n // Always convert to string first\r\n const str = input === null || input === undefined ? \"\" : String(input);\r\n\r\n return str\r\n // remove <script>, <iframe>, <object>, <embed>, <link>, <style> blocks\r\n .replace(/<\\s*(script|iframe|object|embed|link|style)[^>]*>.*?<\\s*\\/\\s*\\1\\s*>/gi, \"\")\r\n // remove opening dangerous tags without closing\r\n .replace(/<\\s*(script|iframe|object|embed|link|style)[^>]*>/gi, \"\")\r\n // strip inline event handlers like onclick=, onerror=, etc.\r\n .replace(/\\son\\w+\\s*=\\s*(['\"]).*?\\1/gi, \"\")\r\n // block javascript: URLs\r\n .replace(/\\s(href|src)\\s*=\\s*(['\"])\\s*javascript:[^'\"]*\\2/gi, \"\");\r\n}\r\n\r\nexport function html(strings: TemplateStringsArray, ...values: unknown[]): string {\r\n return strings.reduce((result, str, i) => {\r\n const safeValue = i < values.length ? sanitize(values[i]) : \"\";\r\n return result + str + safeValue;\r\n }, \"\");\r\n}\r\n","// auto-register-runtime.ts\r\nfunction autoRegister() {\r\n const allTags = new Set<string>();\r\n document.querySelectorAll('*').forEach((el) => {\r\n const tagName = el.tagName.toLowerCase();\r\n if (!tagName.includes('-')) return; // Only register custom tags with a dash\r\n allTags.add(tagName);\r\n });\r\n\r\n allTags.forEach(tag => {\r\n if (!customElements.get(tag)) {\r\n customElements.define(tag, class extends HTMLElement {\r\n connectedCallback() {\r\n this.innerHTML = `<div style=\"padding:10px;background:#eee;\">${tag} (Auto)</div>`;\r\n }\r\n });\r\n }\r\n });\r\n}\r\n\r\n\r\nexport { autoRegister };","// ✅ sanitize HTML but allow harmless tags\r\nconst sanitizeHtml = (str: string) => {\r\n return str\r\n // remove <script>, <iframe>, <object>, <embed>, <link>, <meta>, <style>\r\n .replace(/<\\/?(script|iframe|object|embed|link|meta|style)[^>]*>/gi, \"\")\r\n // remove any attribute that starts with \"on\" (onerror, onclick, etc.)\r\n .replace(/\\s+on[a-z]+\\s*=\\s*(\"[^\"]*\"|'[^']*'|[^\\s>]+)/gi, \"\")\r\n // block javascript: in href/src\r\n .replace(/\\s+(href|src)\\s*=\\s*(['\"]?)\\s*javascript:[^'\"\\s>]*/gi, \"\")\r\n}\r\n\r\n// ✅ mapper with sanitization\r\nconst mapper = (arr: string[] | undefined) =>\r\n arr?.map((item) => sanitizeHtml(item)).join(\"\") ?? \"\"\r\n\r\nexport { mapper }\r\n","import DOMPurify from \"dompurify\";\r\nimport type { Config } from \"dompurify\";\r\n\r\ntype TSPurifier = (input: string | HTMLElement, config?: Config) => string;\r\n\r\nexport const useTSPurifier: TSPurifier = (\r\n input,\r\n config?\r\n) => {\r\n const defaultConfig: Config = {\r\n ADD_TAGS: [\"my-custom-tag\"],\r\n };\r\n\r\n const mergedConfig: Config = { ...defaultConfig, ...config };\r\n\r\n if (typeof input === \"string\") {\r\n return DOMPurify.sanitize(input, mergedConfig);\r\n } else {\r\n return DOMPurify.sanitize(input.innerHTML, mergedConfig);\r\n }\r\n};\r\n","type TSEvent = (\r\n id: string | Document,\r\n eventType: keyof HTMLElementEventMap,\r\n handler: (event: HTMLElementEventMap[keyof HTMLElementEventMap]) => void\r\n) => void;\r\n\r\nexport const useTSEvent: TSEvent = (\r\n id,\r\n eventType,\r\n handler\r\n) => {\r\n if (typeof id === 'string') {\r\n const element = document.getElementById(id);\r\n if (element) {\r\n element.addEventListener(\r\n eventType,\r\n handler as EventListenerOrEventListenerObject\r\n );\r\n } else {\r\n console.warn(`Element with id '${id}' not found.`);\r\n }\r\n } else if (id === document) {\r\n document.addEventListener(\r\n eventType,\r\n handler as EventListenerOrEventListenerObject\r\n );\r\n } else {\r\n console.warn(`Invalid id parameter provided.`);\r\n }\r\n};\r\n","// utils/hooks/useTSParams.ts\r\nimport { createStore } from 'zustand/vanilla';\r\nimport DOMPurify from 'dompurify';\r\n\r\ntype ParamStore = {\r\n params: Record<string, string>;\r\n query: Record<string, string>;\r\n setFromPattern: (pattern: MustURL) => void;\r\n getParam: (key: string) => string | undefined;\r\n getQuery: (key: string) => string | undefined;\r\n};\r\n\r\ntype MustURL = `/${string}`;\r\n\r\nfunction extractPatternParams(pattern: MustURL, path: string): Record<string, string> {\r\n const paramNames: string[] = [];\r\n const regexPattern = pattern.replace(/:[^/]+/g, (match) => {\r\n paramNames.push(match.slice(1));\r\n return '([^/]+)';\r\n });\r\n\r\n const regex = new RegExp(`^${regexPattern}$`);\r\n const match = path.match(regex);\r\n const result: Record<string, string> = {};\r\n\r\n if (match) {\r\n paramNames.forEach((name, i) => {\r\n result[name] = DOMPurify.sanitize(match[i + 1] ?? '');\r\n });\r\n }\r\n\r\n return result;\r\n}\r\n\r\nfunction extractQueryParams(search: MustURL): Record<string, string> {\r\n const result: Record<string, string> = {};\r\n const urlSearchParams = new URLSearchParams(search);\r\n\r\n for (const [key, value] of urlSearchParams.entries()) {\r\n result[key] = DOMPurify.sanitize(value);\r\n }\r\n\r\n return result;\r\n}\r\n\r\nexport const useTSParams = createStore<ParamStore>((set, get) => ({\r\n params: {},\r\n query: {},\r\n setFromPattern: (pattern: MustURL) => {\r\n const path = window.location.pathname;\r\n const params = extractPatternParams(pattern, path);\r\n const query = extractQueryParams(window.location.search as MustURL);\r\n set({ params, query });\r\n },\r\n getParam: (key: string) => get().params[key],\r\n getQuery: (key: string) => get().query[key],\r\n}));\r\n","import { useTSParams } from './useTSParams';\r\n\r\ntype MustURL = `/${string}`;\r\n\r\nexport function useTSExtractParams(pattern: MustURL) {\r\n const store = useTSParams.getState();\r\n\r\n // Populate internal param/query store\r\n store.setFromPattern(pattern);\r\n\r\n const params = store.params;\r\n const query = store.query;\r\n\r\n return { ...params, ...query };\r\n}\r\n","export const useTSEventAll = <T extends Event>(\r\n selector: string,\r\n eventType: keyof HTMLElementEventMap,\r\n handler: (event: T) => void\r\n) => {\r\n const elements = document.querySelectorAll(selector);\r\n elements.forEach(element => {\r\n element.addEventListener(eventType, handler as EventListener);\r\n });\r\n\r\n return () => {\r\n elements.forEach(element => {\r\n element.removeEventListener(eventType, handler as EventListener);\r\n });\r\n };\r\n};\r\n\r\nexport const useTSEventSelectAll = <T extends Event>(\r\n selectors: string[],\r\n eventType: keyof HTMLElementEventMap,\r\n handler: (event: T) => void\r\n) => {\r\n const elements: NodeListOf<HTMLElement>[] = [];\r\n\r\n selectors.forEach(selector => {\r\n const selectedElements = document.querySelectorAll(\r\n selector\r\n ) as NodeListOf<HTMLElement>;\r\n selectedElements.forEach(element => {\r\n element.addEventListener(eventType, handler as EventListener);\r\n });\r\n elements.push(selectedElements);\r\n });\r\n\r\n return () => {\r\n elements.forEach(nodeList => {\r\n nodeList.forEach(element => {\r\n element.removeEventListener(eventType, handler as EventListener);\r\n });\r\n });\r\n };\r\n};\r\n","import DOMPurify, { Config } from \"dompurify\";\r\n\r\ntype EventHandlers = Record<string, EventListener>;\r\n\r\ntype TSElements = (\r\n htmlElement: HTMLElement,\r\n element: string,\r\n config?: Config,\r\n handlers?: EventHandlers\r\n) => void;\r\n\r\nexport const useTSElements: TSElements = (\r\n htmlElement,\r\n element,\r\n config,\r\n handlers = {}\r\n) => {\r\n const defaultConfig: Config = {\r\n USE_PROFILES: { svg: true, html: true },\r\n ALLOWED_TAGS: [\r\n \"svg\", \"path\", \"circle\", \"rect\", \"line\", \"polyline\", \"polygon\", \"g\",\r\n \"main\", \"div\", \"h1\", \"h2\", \"h3\", \"h4\", \"h5\", \"h6\",\r\n \"p\", \"button\", \"span\", \"a\", \"img\", \"input\", \"ul\", \"li\", \"i\"\r\n ],\r\n ALLOWED_ATTR: [\r\n \"class\", \"id\", \"href\", \"src\", \"alt\", \"fill\", \"stroke\", \"stroke-width\",\r\n \"viewBox\", \"xmlns\", \"d\", \"x\", \"y\", \"cx\", \"cy\", \"r\", \"width\", \"height\",\r\n \"data-onclick\", \"data-onchange\" // ✅ allow safe declarative events\r\n ],\r\n FORBID_TAGS: [\"script\", \"iframe\"],\r\n ALLOWED_URI_REGEXP:\r\n /^(?:(?:https?|mailto|tel|ftp):|[^a-z]|[a-z+.\\-]+(?:[^a-z+.\\-:]|$))/i,\r\n ...config,\r\n };\r\n\r\n // ✅ Allow custom elements dynamically\r\n DOMPurify.addHook(\"uponSanitizeElement\", (node, data) => {\r\n const tagName = data.tagName.toLowerCase();\r\n if (tagName.includes(\"-\")) {\r\n data.allowedTags[tagName] = true;\r\n }\r\n });\r\n\r\n // ✅ Strip dangerous event handlers (`onclick`, etc.)\r\n DOMPurify.addHook(\"uponSanitizeAttribute\", (node, data) => {\r\n if (data.attrName && data.attrName.toLowerCase().startsWith(\"on\")) {\r\n data.keepAttr = false;\r\n }\r\n });\r\n\r\n const sanitizedContent = DOMPurify.sanitize(element, defaultConfig);\r\n htmlElement.innerHTML = sanitizedContent;\r\n\r\n // ✅ Bind safe declarative events from `data-*`\r\n htmlElement.querySelectorAll<HTMLElement>(\"[data-onclick]\").forEach((el) => {\r\n const key = el.dataset.onclick!;\r\n if (handlers[key]) {\r\n el.addEventListener(\"click\", handlers[key]);\r\n }\r\n });\r\n\r\n htmlElement.querySelectorAll<HTMLElement>(\"[data-onchange]\").forEach((el) => {\r\n const key = el.dataset.onchange!;\r\n if (handlers[key]) {\r\n el.addEventListener(\"change\", handlers[key]);\r\n }\r\n });\r\n};\r\n","import DOMPurify from \"dompurify\"\r\n\r\nlet previousHTML: string | null = null\r\n\r\ntype TSInitialDOM = (id: string, mount: (el: HTMLElement) => void) => void;\r\n\r\nexport const useInitialDOM: TSInitialDOM = (id, mount) => {\r\n // SSR guard\r\n if (typeof document === \"undefined\") return\r\n\r\n const targetElement = document.getElementById(id)\r\n if (!targetElement) return\r\n\r\n const currentHTML = targetElement.innerHTML\r\n const sanitizedHTML = DOMPurify.sanitize(currentHTML)\r\n\r\n if (previousHTML !== null && sanitizedHTML !== previousHTML) {\r\n // DOM changed externally — reset and remount in a temp container\r\n const fallbackEl = document.createElement(\"div\")\r\n mount(fallbackEl)\r\n targetElement.innerHTML = previousHTML\r\n } else {\r\n // First time or same sanitized DOM — mount to target\r\n previousHTML = sanitizedHTML\r\n mount(targetElement)\r\n }\r\n}\r\n","import DOMPurify from \"dompurify\";\r\n\r\ndeclare global {\r\n interface Window {\r\n __anchorSinglePopstateHandlerAttached?: boolean;\r\n }\r\n}\r\n\r\ntype AnchorSingle = (\r\n element: HTMLAnchorElement | null,\r\n href: string,\r\n ariaLabel: string,\r\n className?: string,\r\n childElement?: HTMLElement | null\r\n) => void;\r\n\r\n// Attach popstate listener only in the browser\r\nif (typeof window !== \"undefined\" && !window.__anchorSinglePopstateHandlerAttached) {\r\n window.addEventListener(\"popstate\", (e) => {\r\n const state = e.state as { scrollPosition?: number };\r\n if (state?.scrollPosition !== undefined) {\r\n window.scrollTo(0, state.scrollPosition);\r\n }\r\n });\r\n window.__anchorSinglePopstateHandlerAttached = true;\r\n}\r\n\r\nexport const useAnchorSingle: AnchorSingle = (\r\n element,\r\n href,\r\n ariaLabel,\r\n className = \"\",\r\n childElement = null\r\n) => {\r\n if (!element) return;\r\n\r\n // Sanitize string inputs\r\n const sanitizedHref = DOMPurify.sanitize(href, { ALLOWED_URI_REGEXP: /^(https?:|\\/)/ });\r\n const sanitizedAriaLabel = DOMPurify.sanitize(ariaLabel, { USE_PROFILES: { html: false } });\r\n\r\n element.setAttribute(\"href\", sanitizedHref);\r\n element.setAttribute(\"aria-label\", sanitizedAriaLabel);\r\n\r\n if (className) {\r\n element.className = className.trim();\r\n }\r\n\r\n if (childElement) {\r\n element.replaceChildren(childElement);\r\n }\r\n\r\n // Event binding only in browser\r\n if (typeof window !== \"undefined\") {\r\n element.addEventListener(\"click\", (e) => {\r\n e.preventDefault();\r\n const target = e.currentTarget as HTMLAnchorElement;\r\n const hrefAttr = target.getAttribute(\"href\");\r\n if (hrefAttr) {\r\n const scrollPosition = window.scrollY;\r\n window.scrollTo(0, 0);\r\n window.history.pushState({ scrollPosition }, \"\", hrefAttr);\r\n dispatchEvent(new PopStateEvent(\"popstate\"));\r\n }\r\n });\r\n }\r\n};\r\n","import DOMPurify from \"dompurify\";\r\nimport { useTSCSP } from \"./useTSCSP\";\r\n\r\ntype SEOConfig = {\r\n name?: string;\r\n description?: string;\r\n author?: string;\r\n}\r\n\r\ntype CSPConfig = {\r\n scriptSrc?: string;\r\n styleSrc?: string;\r\n objectSrc?: string;\r\n connectSrc?: string[];\r\n reportOnly?: boolean;\r\n}\r\n\r\ntype SEOHandler = {\r\n setName: (name: string) => void;\r\n setDescription: (description: string) => void;\r\n setAuthor: (author: string) => void;\r\n getName: () => string;\r\n getDescription: () => string;\r\n getAuthor: () => string;\r\n getAllMetaData: () => SEOConfig;\r\n appendMetaTagsToHead: () => void;\r\n}\r\n\r\nexport const useTSMetaData = (\r\n config: SEOConfig,\r\n cspConfig?: CSPConfig\r\n): SEOHandler => {\r\n let metaData: SEOConfig = {\r\n name: DOMPurify.sanitize(config.name || \"\"),\r\n description: DOMPurify.sanitize(\r\n config.description || \"Default description\"\r\n ),\r\n author: DOMPurify.sanitize(config.author || \"\"),\r\n };\r\n\r\n const setName = (name: string): void => {\r\n metaData.name = DOMPurify.sanitize(name);\r\n updateMetaTag(\"name\", metaData.name);\r\n };\r\n\r\n const setDescription = (description: string): void => {\r\n metaData.description = DOMPurify.sanitize(description);\r\n updateMetaTag(\"description\", metaData.description);\r\n };\r\n\r\n const setAuthor = (author: string): void => {\r\n metaData.author = DOMPurify.sanitize(author);\r\n updateMetaTag(\"author\", metaData.author);\r\n };\r\n\r\n const getName = (): string => {\r\n return metaData.name!;\r\n };\r\n\r\n const getDescription = (): string => {\r\n return metaData.description!;\r\n };\r\n\r\n const getAuthor = (): string => {\r\n return metaData.author!;\r\n };\r\n\r\n const getAllMetaData = (): SEOConfig => {\r\n return metaData;\r\n };\r\n\r\n const createMetaTag = (name: string, content: string) => {\r\n const metaTag = document.createElement(\"meta\");\r\n metaTag.setAttribute(\"name\", name);\r\n metaTag.setAttribute(\"content\", content);\r\n document.head.appendChild(metaTag);\r\n };\r\n\r\n const updateMetaTag = (name: string, content: string) => {\r\n let metaTag = document.querySelector(`meta[name=\"${name}\"]`);\r\n if (metaTag) {\r\n metaTag.setAttribute(\"content\", content);\r\n } else {\r\n createMetaTag(name, content);\r\n }\r\n };\r\n\r\n const appendMetaTagsToHead = () => {\r\n updateMetaTag(\"name\", metaData.name!);\r\n updateMetaTag(\"description\", metaData.description!);\r\n updateMetaTag(\"author\", metaData.author!);\r\n };\r\n\r\n // Integrate with useTSCSP for CSP enforcement\r\n if (cspConfig) {\r\n useTSCSP(\r\n cspConfig.scriptSrc,\r\n cspConfig.styleSrc,\r\n cspConfig.objectSrc,\r\n Array.isArray(cspConfig.connectSrc) ? cspConfig.connectSrc.join(\" \") : cspConfig.connectSrc,\r\n cspConfig.reportOnly !== undefined ? String(cspConfig.reportOnly) : undefined\r\n );\r\n }\r\n\r\n appendMetaTagsToHead();\r\n\r\n return {\r\n setName,\r\n setDescription,\r\n setAuthor,\r\n getName,\r\n getDescription,\r\n getAuthor,\r\n getAllMetaData,\r\n appendMetaTagsToHead,\r\n };\r\n};\r\n","export const useTSCSP = (\r\n scriptSrc = `'self' 'nonce-rAnd0m123' 'unsafe-inline' 'unsafe-eval'`,\r\n styleSrc = \"'self' 'nonce-rAnd0m123'\", // Use nonce for inline styles\r\n objectSrc = \"'none'\",\r\n fontSrc = \"'self' https://fonts.googleapis.com https://fonts.gstatic.com\",\r\n imgSrc = \"'self' https://blogger.googleusercontent.com\",\r\n connectSrc = [\r\n \"'self'\",\r\n \"https://fonts.googleapis.com\",\r\n \"https://fonts.gstatic.com\",\r\n \"https://www.google.com/maps/\",\r\n ],\r\n frameSrc = \"'self' https://www.youtube.com\", // Add frame-src for embedding\r\n baseUri = \"'self'\",\r\n reportUri = \"/csp-report\",\r\n reportOnly = false\r\n) => {\r\n const addOrUpdateCSPMeta = () => {\r\n try {\r\n let metaElement = document.querySelector(\r\n 'meta[http-equiv=\"Content-Security-Policy\"]'\r\n );\r\n if (!metaElement) {\r\n metaElement = document.createElement(\"meta\");\r\n metaElement.setAttribute(\"http-equiv\", \"Content-Security-Policy\");\r\n document.head.appendChild(metaElement);\r\n }\r\n\r\n const reportUriDirective = reportOnly ? `report-uri ${reportUri};` : \"\";\r\n metaElement.setAttribute(\r\n \"content\",\r\n `default-src 'self'; script-src ${scriptSrc}; style-src ${styleSrc}; object-src ${objectSrc}; font-src ${fontSrc}; img-src ${imgSrc}; connect-src ${connectSrc.join(\r\n \" \"\r\n )}; frame-src ${frameSrc}; base-uri ${baseUri}; ${reportUriDirective}`\r\n );\r\n } catch (error) {\r\n console.error(\"Error adding CSP meta element:\", error);\r\n }\r\n };\r\n\r\n if (document.readyState === \"loading\") {\r\n document.addEventListener(\"DOMContentLoaded\", addOrUpdateCSPMeta);\r\n } else {\r\n addOrUpdateCSPMeta();\r\n }\r\n};\r\n","import DOMPurify from \"dompurify\";\r\n\r\ntype TSComponent = (\r\n id: string,\r\n parent: HTMLElement,\r\n element: Function,\r\n params?: any,\r\n params2?: any\r\n) => void;\r\n\r\nexport const useTSComponent: TSComponent = (\r\n id,\r\n parent,\r\n element,\r\n params,\r\n params2\r\n) => {\r\n const selector = `#${id}`;\r\n const matches = parent.querySelectorAll<HTMLElement>(selector);\r\n\r\n // 1. Missing element check\r\n if (matches.length === 0) {\r\n throw new Error(`[useTSComponent] No element found with id '${id}' in the given parent.`);\r\n }\r\n\r\n // 2. Duplicate ID check\r\n if (matches.length > 1) {\r\n throw new Error(`[useTSComponent] Duplicate id '${id}' detected. Found ${matches.length} elements.`);\r\n }\r\n\r\n const target = matches[0];\r\n\r\n // 3. Sanitize the target’s existing HTML content\r\n target.innerHTML = DOMPurify.sanitize(target.innerHTML, { USE_PROFILES: { html: true } });\r\n\r\n // 4. Call the component function with the target\r\n element(target, params, params2);\r\n};\r\n","import { useTSComponent } from \"./useTSComponent\";\r\n\r\ntype TSCollection = (\r\n collections: string[],\r\n DOM: HTMLElement,\r\n elements: Function[],\r\n params?: any[]\r\n) => void;\r\n\r\nexport const useTSCollection: TSCollection = (\r\n collections,\r\n DOM,\r\n elements,\r\n params = []\r\n) => {\r\n const seenIds = new Set<string>();\r\n\r\n collections.forEach((id, index) => {\r\n // Check for duplicate IDs in the collection list itself\r\n if (seenIds.has(id)) {\r\n console.warn(`[useTSCollection] Duplicate ID in collection array: \"${id}\" — skipping.`);\r\n return;\r\n }\r\n seenIds.add(id);\r\n\r\n // Check for duplicates already in DOM\r\n const matches = DOM.querySelectorAll(`#${id}`);\r\n if (matches.length > 1) {\r\n console.warn(\r\n `[useTSCollection] Duplicate ID in DOM: \"${id}\" (${matches.length} elements found) — skipping component mount.`\r\n );\r\n return;\r\n }\r\n\r\n const elementFn = elements[index];\r\n const param = Array.isArray(params) ? params[index] : undefined;\r\n\r\n if (typeof elementFn === \"function\") {\r\n useTSComponent(id, DOM, elementFn, param);\r\n } else {\r\n console.warn(`[useTSCollection] No valid component function found for ID: \"${id}\"`);\r\n }\r\n });\r\n};\r\n","type TSSelect = <T extends Element = HTMLElement>(\r\n selector: string,\r\n scope?: HTMLElement\r\n) => T | null;\r\n\r\nconst useTSSelect: TSSelect = <T extends Element = HTMLElement>(\r\n selector: string,\r\n scope?: HTMLElement\r\n): T | null => {\r\n const root = scope ?? document;\r\n const elements = root.querySelectorAll<T>(selector);\r\n\r\n if (elements.length === 0) {\r\n if (process.env.NODE_ENV !== \"production\") {\r\n console.warn(`[useTSSelect] No element found for selector: '${selector}'`);\r\n }\r\n return null;\r\n }\r\n\r\n if (selector.startsWith(\"#\") && elements.length > 1) {\r\n if (process.env.NODE_ENV !== \"production\") {\r\n throw new Error(\r\n `[useTSSelect] Duplicate ID detected: '${selector}'. Found ${elements.length} elements with this ID.`\r\n );\r\n }\r\n return elements[0]; // fallback: just return first\r\n }\r\n\r\n if (elements.length > 1) {\r\n if (process.env.NODE_ENV !== \"production\") {\r\n console.warn(\r\n `[useTSSelect] Multiple elements found for selector: '${selector}'. Returning the first one.`\r\n );\r\n }\r\n }\r\n\r\n return elements[0];\r\n};\r\n\r\nexport { useTSSelect };\r\n","import { jwtDecode } from \"jwt-decode\";\r\n\r\nexport const useTSAuth = (_Component: HTMLElement | void, loginUrl: string) => {\r\n const token = localStorage.getItem(\"token\");\r\n\r\n if (!token) {\r\n // Redirect to login page if token is missing\r\n window.location.href = loginUrl;\r\n return null; // Return null when redirecting\r\n }\r\n\r\n try {\r\n const decodedToken: any = jwtDecode(token);\r\n\r\n // Example: Check if the token has expired\r\n const currentTime = Date.now() / 1000;\r\n if (decodedToken.exp && decodedToken.exp < currentTime) {\r\n console.error(\"Token has expired\");\r\n window.localStorage.removeItem(\"token\");\r\n window.location.href = loginUrl;\r\n return null; // Return null when redirecting\r\n }\r\n\r\n // If the user is authenticated, return the component\r\n return null;\r\n } catch (error) {\r\n console.error(\"Invalid token:\", error);\r\n // Redirect to login page if token decoding fails\r\n window.location.href = loginUrl;\r\n return null; // Return null when redirecting\r\n }\r\n};\r\n","\r\ntype TSElementEach = (\r\n elements: NodeListOf<HTMLElement> | HTMLElement[],\r\n events: (keyof HTMLElementEventMap)[],\r\n callback: (element: HTMLElement, event: Event) => void\r\n) => void;\r\n\r\nexport const useTSElementEach: TSElementEach = (\r\n elements,\r\n events,\r\n callback\r\n) => {\r\n elements.forEach(element => {\r\n events.forEach(eventType => {\r\n element.addEventListener(eventType, event => {\r\n callback(element, event);\r\n });\r\n });\r\n });\r\n};\r\n","export const useTSNavigate = () => {\r\n const back = () => window.history.back();\r\n const forward = () => window.history.forward();\r\n\r\n return {\r\n back,\r\n forward,\r\n };\r\n};\r\n","// types.ts\r\nexport type OutletComponent = (DOM: HTMLElement) => void;\r\n\r\nexport type ChildRoute = {\r\n path: string;\r\n outlet: string;\r\n element: OutletComponent;\r\n};\r\n\r\nexport type Route = {\r\n path: string;\r\n element: (DOM: HTMLElement) => void;\r\n children?: ChildRoute[];\r\n};\r\n\r\n// You don't actually need to import the class TSRouter type.\r\n// Instead, export a cleaner interface with routes.\r\nexport interface RouterInstance {\r\n routes: Route[];\r\n}\r\n\r\n\r\ntype OutletOptions = {\r\n path: string;\r\n component: OutletComponent;\r\n};\r\n\r\nexport const useTSOutlet = (\r\n selector: string,\r\n outlets: OutletOptions[]\r\n): void => {\r\n const outletDOM = document.querySelector<HTMLElement>(`#${selector}`)\r\n || document.querySelector<HTMLElement>(`.${selector}`);\r\n\r\n if (!outletDOM) return;\r\n\r\n const currentPath = window.location.pathname.replace(/\\/$/, \"\");\r\n\r\n for (const outlet of outlets) {\r\n const base = outlet.path.replace(/\\/$/, \"\");\r\n\r\n // Match exact or nested path (e.g., /openai/child/1)\r\n if (currentPath === base || currentPath.startsWith(`${base}/`)) {\r\n outlet.component(outletDOM);\r\n break;\r\n }\r\n }\r\n};\r\n\r\n\r\nexport function renderChildRoutes(DOM: HTMLElement, router: RouterInstance): void {\r\n const pathname = window.location.pathname.replace(/\\/$/, \"\");\r\n\r\n router.routes.forEach((route) => {\r\n if (!route.children?.length) return;\r\n\r\n route.children.forEach((child) => {\r\n const childPath = child.path.replace(/\\/$/, \"\");\r\n\r\n if (pathname === childPath || pathname.startsWith(`${childPath}/`)) {\r\n const outlet = DOM.querySelector(`#${child.outlet}`)\r\n || DOM.querySelector(`.${child.outlet}`);\r\n if (outlet instanceof HTMLElement && child.element) {\r\n child.element(outlet);\r\n }\r\n }\r\n });\r\n });\r\n}","// useTSReactivity.ts\r\nimport { createStore } from 'zustand/vanilla';\r\n\r\ntype Listener<T> = (value: T) => void;\r\n\r\ninterface Signal<T> {\r\n get: () => T;\r\n set: (newValue: T) => void;\r\n subscribe: (listener: Listener<T>) => () => void;\r\n}\r\n\r\nexport function createSignal<T>(initialValue: T): Signal<T> {\r\n const store = createStore<{ value: T }>(() => ({ value: initialValue }));\r\n const listeners = new Set<Listener<T>>();\r\n\r\n return {\r\n get: () => store.getState().value,\r\n set: (newValue: T) => {\r\n store.setState({ value: newValue });\r\n listeners.forEach((listener) => listener(newValue));\r\n },\r\n subscribe: (listener: Listener<T>) => {\r\n listeners.add(listener);\r\n listener(store.getState().value); // Trigger immediately\r\n return () => listeners.delete(listener);\r\n },\r\n };\r\n}\r\n\r\ntype CleanupFn = () => void;\r\n\r\nexport function createEffect(effectFn: () => void | CleanupFn): void {\r\n const cleanup = effectFn();\r\n\r\n // Optional: return a way to dispose the effect manually\r\n if (typeof cleanup === 'function') {\r\n // You may store this and call it later if needed\r\n cleanup();\r\n }\r\n}\r\n","import { useTSElementEach } from './useTSForEach';\r\n\r\n\r\nconst useTSHashAnchor = () => {\r\n const links = document.querySelectorAll<HTMLAnchorElement>('a[href^=\"#\"]');\r\n\r\n useTSElementEach(\r\n links,\r\n ['click'],\r\n (element, e) => {\r\n e.preventDefault();\r\n const targetId = element.getAttribute('href')?.substring(1);\r\n const targetElement = targetId ? document.getElementById(targetId) : null;\r\n\r\n if (targetElement) {\r\n targetElement.scrollIntoView({\r\n behavior: 'smooth',\r\n block: 'start'\r\n });\r\n }\r\n }\r\n );\r\n}\r\n\r\nexport { useTSHashAnchor }","import { debounce } from 'lodash-es';\r\n\r\nlet sanitizeInput = (input: string): string => input;\r\n\r\nif (typeof window !== 'undefined' && typeof document !== 'undefined') {\r\n sanitizeInput = (input: string): string => {\r\n const element = document.createElement(\"div\");\r\n element.innerText = input;\r\n return element.innerHTML;\r\n };\r\n}\r\n\r\ntype AnchorInput =\r\n | NodeListOf<HTMLAnchorElement>\r\n | HTMLAnchorElement[]\r\n | HTMLAnchorElement\r\n | null\r\n | undefined;\r\n\r\nconst _enhanceAnchors = debounce((anchors: AnchorInput) => {\r\n const resolvedAnchors: HTMLAnchorElement[] = (() => {\r\n if (!anchors) return Array.from(document.querySelectorAll(\"a\"));\r\n if (Array.isArray(anchors)) return anchors;\r\n if (anchors instanceof HTMLAnchorElement) return [anchors];\r\n return Array.from(anchors);\r\n })();\r\n\r\n resolvedAnchors.forEach(anchor => {\r\n if (!anchor || anchor.dataset.anchorEnhanced === 'true') return;\r\n anchor.dataset.anchorEnhanced = 'true';\r\n\r\n // Sanitize attributes\r\n const originalHref = anchor.getAttribute(\"href\") || \"#\";\r\n const sanitizedHref = sanitizeInput(originalHref);\r\n anchor.setAttribute(\"href\", sanitizedHref);\r\n\r\n const originalClassName = anchor.getAttribute(\"class\") || \"\";\r\n anchor.setAttribute(\"class\", sanitizeInput(originalClassName));\r\n\r\n const ariaLabel = anchor.getAttribute(\"aria-label\");\r\n if (ariaLabel) {\r\n anchor.setAttribute(\"aria-label\", sanitizeInput(ariaLabel));\r\n }\r\n\r\n // Keep child elements safe (optional — you can remove this block if not needed)\r\n const child = anchor.querySelector(\":scope > *\") as HTMLElement;\r\n if (child) {\r\n anchor.innerHTML = \"\";\r\n anchor.appendChild(child);\r\n }\r\n\r\n // Skip attaching click listener if:\r\n // - It's a hash link (in-page navigation)\r\n // - It's an external link\r\n const href = anchor.getAttribute(\"href\") || \"\";\r\n if (href.startsWith(\"#\")) return; // Let browser handle hash scrolling normally\r\n\r\n try {\r\n const url = new URL(href, window.location.href);\r\n if (url.origin !== window.location.origin) return; // external link\r\n } catch {\r\n return; // invalid URL — skip\r\n }\r\n\r\n // Intercept same-origin navigation for SPA\r\n anchor.addEventListener(\"click\", (e: MouseEvent) => {\r\n e.preventDefault();\r\n try {\r\n const url = new URL(href, window.location.href);\r\n window.history.pushState({}, \"\", url.pathname + url.search + url.hash);\r\n window.dispatchEvent(new PopStateEvent(\"popstate\"));\r\n } catch (err) {\r\n console.error(\"Invalid URL in anchor:\", href, err);\r\n }\r\n });\r\n });\r\n}, 50);\r\n\r\nexport const useAnchor = (anchors?: AnchorInput): void => {\r\n _enhanceAnchors(anchors);\r\n};\r\n","import { useAnchor } from './useTSAnchor';\r\n\r\nconst useTSNoReload = () => {\r\n const a = document.querySelectorAll(\"a\") as NodeListOf<HTMLAnchorElement>;\r\n return useAnchor(a);\r\n}\r\n\r\nexport { useTSNoReload };","import { useTSHashAnchor } from \"./useTSHashAnchor\";\r\nimport { useTSNoReload } from \"./useTSNoReload\";\r\n\r\nconst useTSAnchorMount = () => {\r\n useTSNoReload();\r\n useTSHashAnchor();\r\n};\r\n\r\nexport { useTSAnchorMount };","// src/loadBrython.ts\r\ntype LoadBrython = (src: string) => Promise<void>;\r\n\r\ndeclare global {\r\n interface Window {\r\n brython: Function;\r\n }\r\n}\r\n\r\nconst useTSloadBrython = async () => {\r\n const brythonJS = \"https://cdn.jsdelivr.net/npm/brython@3/brython.min.js\";\r\n const brythonStdlib = \"https://cdn.jsdelivr.net/npm/brython@3/brython_stdlib.js\";\r\n\r\n // Utility function to load a script\r\n const loadScript: LoadBrython = (src) => {\r\n return new Promise((resolve, reject) => {\r\n const script = document.createElement(\"script\");\r\n script.src = src;\r\n script.onload = () => resolve();\r\n script.onerror = () => reject(new Error(`Failed to load ${src}`));\r\n document.head.appendChild(script);\r\n });\r\n };\r\n\r\n // Load both scripts sequentially\r\n await loadScript(brythonJS);\r\n await loadScript(brythonStdlib);\r\n\r\n // Call brython() after scripts are loaded\r\n if (typeof window.brython === \"function\") {\r\n window.brython();\r\n } else {\r\n console.error(\"Brython did not load correctly.\");\r\n }\r\n};\r\n\r\ntype RequirePy = `${string}.py`;\r\n\r\ntype LoadPy = (src: RequirePy) => Promise<void>;\r\n\r\nconst loadPyFiles: LoadPy = (src) =>\r\n new Promise((resolve, reject) => {\r\n const script = document.createElement(\"script\");\r\n script.type = \"text/python\";\r\n script.src = `/src/python/${src}`;\r\n script.onload = () => resolve();\r\n script.onerror = () => reject(new Error(`Failed to load ${src}`));\r\n document.body.appendChild(script);\r\n });\r\n\r\nexport { useTSloadBrython, loadPyFiles };\r\n","export function useTSLazy(factory: () => Promise<any>) {\r\n let cached: any | null = null;\r\n\r\n return async (el?: HTMLElement, props?: any) => {\r\n try {\r\n if (!cached) {\r\n const mod = await factory();\r\n cached = mod.default || mod;\r\n }\r\n\r\n // If it's a component function (Vanilla TS style)\r\n if (typeof cached === \"function\") {\r\n return cached(el, props);\r\n }\r\n\r\n // If it's already an HTMLElement\r\n if (cached instanceof HTMLElement) {\r\n el?.appendChild(cached);\r\n return;\r\n }\r\n\r\n // If it's a plain object with render()\r\n if (cached && typeof cached.render === \"function\") {\r\n return cached.render(el, props);\r\n }\r\n\r\n console.warn(\"useTSLazy: Unsupported module type\", cached);\r\n } catch (err) {\r\n console.error(\"useTSLazy failed:\", err);\r\n }\r\n };\r\n}\r\n","import DOMPurify from \"dompurify\";\r\nimport { tsParamsStore } from \"../../store\";\r\n\r\ntype RouteCallback = (\r\n errorElement?: HTMLElement,\r\n params?: Record<string, string>,\r\n query?: Record<string, string>\r\n) => void;\r\n\r\ninterface RouteConfig {\r\n path: string;\r\n routeto?: string;\r\n element: RouteCallback;\r\n errorElement?: RouteCallback;\r\n children?: RouteConfig[];\r\n params?: Record<string, string>;\r\n}\r\n\r\nexport class TSRouter {\r\n private routes: RouteConfig[] = [];\r\n private expectedParams: Set<string>;\r\n\r\n constructor(routes: RouteConfig[], expectedParams: string[]) {\r\n this.routes = routes;\r\n this.expectedParams = new Set(expectedParams);\r\n window.addEventListener(\"popstate\", this.handlePopState.bind(this));\r\n this.handlePopState(); // Initial load\r\n }\r\n\r\n private handlePopState() {\r\n const currentPath = window.location.pathname;\r\n const currentSearch = window.location.search;\r\n const queryParams = this.parseQueryParams(currentSearch);\r\n\r\n const matchingRoute = this.findMatchingRoute(currentPath, this.routes);\r\n\r\n if (matchingRoute) {\r\n if (matchingRoute.routeto) {\r\n this.navigate(matchingRoute.routeto);\r\n return;\r\n }\r\n\r\n const sanitizedParams = this.filterAndSanitizeParams(matchingRoute.params);\r\n tsParamsStore.getState().setParams(sanitizedParams);\r\n tsParamsStore.getState().setQuery(queryParams);\r\n\r\n const errorElement = document.createElement(\"div\");\r\n\r\n matchingRoute.element?.(errorElement, sanitizedParams, queryParams);\r\n\r\n if (matchingRoute.children) {\r\n const nestedPath = currentPath.slice(matchingRoute.path.length);\r\n const childElement = errorElement.querySelector(\"#child\") as HTMLDivElement;\r\n if (childElement) {\r\n this.renderChildren(\r\n matchingRoute.children,\r\n nestedPath,\r\n childElement,\r\n sanitizedParams,\r\n queryParams\r\n );\r\n }\r\n }\r\n } else {\r\n const notFoundRoute = this.findMatchingRoute(\"*\", this.routes);\r\n if (notFoundRoute) {\r\n const fallbackParams = this.filterAndSanitizeParams(notFoundRoute.params);\r\n tsParamsStore.getState().setParams(fallbackParams);\r\n tsParamsStore.getState().setQuery(queryParams);\r\n\r\n const errorElement = document.createElement(\"div\");\r\n notFoundRoute.element?.(errorElement, fallbackParams, queryParams);\r\n }\r\n }\r\n }\r\n\r\n private renderChildren(\r\n children: RouteConfig[] | undefined,\r\n nestedPath: string,\r\n parentElement: HTMLElement,\r\n parentParams: Record<string, string>,\r\n queryParams: Record<string, string>\r\n ) {\r\n if (!children || children.length === 0) {\r\n const childElement = parentElement.querySelector(\"#child\") as HTMLDivElement;\r\n if (childElement) childElement.remove();\r\n return;\r\n }\r\n\r\n const matchingChild = this.findMatchingRoute(nestedPath, children);\r\n if (matchingChild) {\r\n const childElement = document.createElement(\"div\");\r\n childElement.id = \"child\";\r\n const mergedParams = { ...parentParams, ...matchingChild.params };\r\n const sanitizedParams = this.filterAndSanitizeParams(mergedParams);\r\n\r\n tsParamsStore.getState().setParams(sanitizedParams);\r\n tsParamsStore.getState().setQuery(queryParams);\r\n\r\n matchingChild.element?.(childElement, sanitizedParams, queryParams);\r\n parentElement.appendChild(childElement);\r\n\r\n if (matchingChild.children) {\r\n const nextNestedPath = nestedPath.slice(matchingChild.path.length);\r\n this.renderChildren(\r\n matchingChild.children,\r\n nextNestedPath,\r\n childElement,\r\n sanitizedParams,\r\n queryParams\r\n );\r\n }\r\n }\r\n }\r\n\r\n private parseQueryParams(search: string): Record<string, string> {\r\n const queryParams: Record<string, string> = {};\r\n const urlSearchParams = new URLSearchParams(search);\r\n\r\n for (const [key, value] of urlSearchParams.entries()) {\r\n if (this.expectedParams.has(key)) {\r\n queryParams[key] = DOMPurify.sanitize(value);\r\n }\r\n }\r\n\r\n return queryParams;\r\n }\r\n\r\n private findMatchingRoute(\r\n path: string,\r\n routes: RouteConfig[],\r\n inheritedParams: Record<string, string> = {}\r\n ): RouteConfig | undefined {\r\n for (const route of routes) {\r\n const routePath = route.path;\r\n const isDefaultRoute = routePath === \"*\";\r\n\r\n if (!isDefaultRoute) {\r\n const paramNames: string[] = [];\r\n const regexPattern = routePath.replace(/:[^\\s/]+/g, match => {\r\n paramNames.push(match.substring(1));\r\n return \"([^\\\\s/]+)\";\r\n });\r\n\r\n const regex = new RegExp(`^${regexPattern}(?:/|$)`);\r\n const match = path.match(regex);\r\n\r\n if (match) {\r\n const params: Record<string, string> = { ...inheritedParams };\r\n paramNames.forEach((name, index) => {\r\n params[name] = match[index + 1] ?? \"\";\r\n });\r\n\r\n if (route.children) {\r\n const nestedPath = path.slice(match[0].length);\r\n const matchingChild = this.findMatchingRoute(\r\n nestedPath,\r\n route.children,\r\n params\r\n );\r\n if (matchingChild) return matchingChild;\r\n }\r\n\r\n return { ...route, params };\r\n }\r\n } else {\r\n return route;\r\n }\r\n }\r\n\r\n return undefined;\r\n }\r\n\r\n private filterAndSanitizeParams(\r\n params?: Record<string, string>\r\n ): Record<string, string> {\r\n if (!params) return {};\r\n const sanitizedParams: Record<string, string> = {};\r\n for (const key in params) {\r\n if (this.expectedParams.has(key)) {\r\n sanitizedParams[key] = DOMPurify.sanitize(params[key] ?? \"\");\r\n }\r\n }\r\n return sanitizedParams;\r\n }\r\n\r\n navigate(path: string) {\r\n history.pushState(null, \"\", path);\r\n this.handlePopState();\r\n }\r\n\r\n addRoute(route: RouteConfig) {\r\n this.routes.push(route);\r\n }\r\n}\r\n","import { createStore } from \"zustand/vanilla\";\r\nimport DOMPurify from \"dompurify\";\r\n\r\ninterface TSParamsState {\r\n params: Record<string, string>;\r\n query: Record<string, string>;\r\n setParams: (params: Record<string, string>) => void;\r\n setQuery: (query: Record<string, string>) => void;\r\n}\r\n\r\nexport const tsParamsStore = createStore<TSParamsState>((set) => ({\r\n params: {},\r\n query: {},\r\n setParams: (params) =>\r\n set(() => ({\r\n params: sanitize(params),\r\n })),\r\n setQuery: (query) =>\r\n set(() => ({\r\n query: sanitize(query),\r\n })),\r\n}));\r\n\r\nfunction sanitize(obj: Record<string, string>): Record<string, string> {\r\n const output: Record<string, string> = {};\r\n for (const key in obj) {\r\n output[key] = DOMPurify.sanitize(obj[key]);\r\n }\r\n return output;\r\n}\r\n"],"mappings":"skBAAA,IAAAA,GAAA,GAAAC,GAAAD,GAAA,cAAAE,EAAA,iBAAAC,EAAA,iBAAAC,EAAA,SAAAC,EAAA,gBAAAC,EAAA,WAAAC,GAAA,sBAAAC,EAAA,oBAAAC,EAAA,kBAAAC,EAAA,qBAAAC,EAAA,cAAAC,EAAA,oBAAAC,EAAA,mBAAAC,EAAA,qBAAAC,EAAA,kBAAAC,EAAA,eAAAC,EAAA,kBAAAC,EAAA,uBAAAC,EAAA,cAAAC,EAAA,kBAAAC,EAAA,kBAAAC,EAAA,gBAAAC,EAAA,gBAAAC,EAAA,kBAAAC,EAAA,gBAAAC,EAAA,qBAAAC,IAAA,eAAAC,GAAA5B,ICAA,SAAS6B,GAASC,EAAwB,CAItC,OAFYA,GAAU,KAA8B,GAAK,OAAOA,CAAK,GAIhE,QAAQ,wEAAyE,EAAE,EAEnF,QAAQ,sDAAuD,EAAE,EAEjE,QAAQ,8BAA+B,EAAE,EAEzC,QAAQ,oDAAqD,EAAE,CACxE,CAEO,SAASC,EAAKC,KAAkCC,EAA2B,CAC9E,OAAOD,EAAQ,OAAO,CAACE,EAAQC,EAAKC,IAAM,CACtC,IAAMC,EAAYD,EAAIH,EAAO,OAASJ,GAASI,EAAOG,CAAC,CAAC,EAAI,GAC5D,OAAOF,EAASC,EAAME,CAC1B,EAAG,EAAE,CACT,CCnBA,SAASC,GAAe,CACpB,IAAMC,EAAU,IAAI,IACpB,SAAS,iBAAiB,GAAG,EAAE,QAASC,GAAO,CAC3C,IAAMC,EAAUD,EAAG,QAAQ,YAAY,EAClCC,EAAQ,SAAS,GAAG,GACzBF,EAAQ,IAAIE,CAAO,CACvB,CAAC,EAEDF,EAAQ,QAAQG,GAAO,CACd,eAAe,IAAIA,CAAG,GACvB,eAAe,OAAOA,EAAK,cAAc,WAAY,CACjD,mBAAoB,CAChB,KAAK,UAAY,8CAA8CA,CAAG,eACtE,CACJ,CAAC,CAET,CAAC,CACL,CCjBA,IAAMC,GAAgBC,GACXA,EAEF,QAAQ,2DAA4D,EAAE,EAEtE,QAAQ,gDAAiD,EAAE,EAE3D,QAAQ,uDAAwD,EAAE,EAIrEC,GAAUC,GACZA,GAAK,IAAKC,GAASJ,GAAaI,CAAI,CAAC,EAAE,KAAK,EAAE,GAAK,GCbvD,IAAAC,EAAsB,0BAKTC,EAA4B,CACvCC,EACAC,IACG,CAKH,IAAMC,EAAuB,CAAE,GAJD,CAC5B,SAAU,CAAC,eAAe,CAC5B,EAEiD,GAAGD,CAAO,EAE3D,OAAI,OAAOD,GAAU,SACZ,EAAAG,QAAU,SAASH,EAAOE,CAAY,EAEtC,EAAAC,QAAU,SAASH,EAAM,UAAWE,CAAY,CAE3D,ECdO,IAAME,EAAsB,CACjCC,EACAC,EACAC,IACG,CACH,GAAI,OAAOF,GAAO,SAAU,CAC1B,IAAMG,EAAU,SAAS,eAAeH,CAAE,EACtCG,EACFA,EAAQ,iBACNF,EACAC,CACF,EAEA,QAAQ,KAAK,oBAAoBF,CAAE,cAAc,CAErD,MAAWA,IAAO,SAChB,SAAS,iBACPC,EACAC,CACF,EAEA,QAAQ,KAAK,gCAAgC,CAEjD,EC5BA,IAAAE,GAA4B,2BAC5BC,EAAsB,0BAYtB,SAASC,GAAqBC,EAAkBC,EAAsC,CAClF,IAAMC,EAAuB,CAAC,EACxBC,EAAeH,EAAQ,QAAQ,UAAYI,IAC7CF,EAAW,KAAKE,EAAM,MAAM,CAAC,CAAC,EACvB,UACV,EAEKC,EAAQ,IAAI,OAAO,IAAIF,CAAY,GAAG,EACtCC,EAAQH,EAAK,MAAMI,CAAK,EACxBC,EAAiC,CAAC,EAExC,OAAIF,GACAF,EAAW,QAAQ,CAACK,EAAMC,IAAM,CAC5BF,EAAOC,CAAI,EAAI,EAAAE,QAAU,SAASL,EAAMI,EAAI,CAAC,GAAK,EAAE,CACxD,CAAC,EAGEF,CACX,CAEA,SAASI,GAAmBC,EAAyC,CACjE,IAAML,EAAiC,CAAC,EAClCM,EAAkB,IAAI,gBAAgBD,CAAM,EAElD,OAAW,CAACE,EAAKC,CAAK,IAAKF,EAAgB,QAAQ,EAC/CN,EAAOO,CAAG,EAAI,EAAAJ,QAAU,SAASK,CAAK,EAG1C,OAAOR,CACX,CAEO,IAAMS,KAAc,gBAAwB,CAACC,EAAKC,KAAS,CAC9D,OAAQ,CAAC,EACT,MAAO,CAAC,EACR,eAAiBjB,GAAqB,CAClC,IAAMC,EAAO,OAAO,SAAS,SACvBiB,EAASnB,GAAqBC,EAASC,CAAI,EAC3CkB,EAAQT,GAAmB,OAAO,SAAS,MAAiB,EAClEM,EAAI,CAAE,OAAAE,EAAQ,MAAAC,CAAM,CAAC,CACzB,EACA,SAAWN,GAAgBI,EAAI,EAAE,OAAOJ,CAAG,EAC3C,SAAWA,GAAgBI,EAAI,EAAE,MAAMJ,CAAG,CAC9C,EAAE,ECpDK,SAASO,EAAmBC,EAAkB,CACjD,IAAMC,EAAQC,EAAY,SAAS,EAGnCD,EAAM,eAAeD,CAAO,EAE5B,IAAMG,EAASF,EAAM,OACfG,EAAQH,EAAM,MAEpB,MAAO,CAAE,GAAGE,EAAQ,GAAGC,CAAM,CACjC,CCdO,IAAMC,EAAgB,CAC3BC,EACAC,EACAC,IACG,CACH,IAAMC,EAAW,SAAS,iBAAiBH,CAAQ,EACnD,OAAAG,EAAS,QAAQC,GAAW,CAC1BA,EAAQ,iBAAiBH,EAAWC,CAAwB,CAC9D,CAAC,EAEM,IAAM,CACXC,EAAS,QAAQC,GAAW,CAC1BA,EAAQ,oBAAoBH,EAAWC,CAAwB,CACjE,CAAC,CACH,CACF,ECfA,IAAAG,EAAkC,0BAWrBC,EAA4B,CACvCC,EACAC,EACAC,EACAC,EAAW,CAAC,IACT,CACH,IAAMC,EAAwB,CAC5B,aAAc,CAAE,IAAK,GAAM,KAAM,EAAK,EACtC,aAAc,CACZ,MAAO,OAAQ,SAAU,OAAQ,OAAQ,WAAY,UAAW,IAChE,OAAQ,MAAO,KAAM,KAAM,KAAM,KAAM,KAAM,KAC7C,IAAK,SAAU,OAAQ,IAAK,MAAO,QAAS,KAAM,KAAM,GAC1D,EACA,aAAc,CACZ,QAAS,KAAM,OAAQ,MAAO,MAAO,OAAQ,SAAU,eACvD,UAAW,QAAS,IAAK,IAAK,IAAK,KAAM,KAAM,IAAK,QAAS,SAC7D,eAAgB,eAClB,EACA,YAAa,CAAC,SAAU,QAAQ,EAChC,mBACE,sEACF,GAAGF,CACL,EAGA,EAAAG,QAAU,QAAQ,sBAAuB,CAACC,EAAMC,IAAS,CACvD,IAAMC,EAAUD,EAAK,QAAQ,YAAY,EACrCC,EAAQ,SAAS,GAAG,IACtBD,EAAK,YAAYC,CAAO,EAAI,GAEhC,CAAC,EAGD,EAAAH,QAAU,QAAQ,wBAAyB,CAACC,EAAMC,IAAS,CACrDA,EAAK,UAAYA,EAAK,SAAS,YAAY,EAAE,WAAW,IAAI,IAC9DA,EAAK,SAAW,GAEpB,CAAC,EAED,IAAME,EAAmB,EAAAJ,QAAU,SAASJ,EAASG,CAAa,EAClEJ,EAAY,UAAYS,EAGxBT,EAAY,iBAA8B,gBAAgB,EAAE,QAASU,GAAO,CAC1E,IAAMC,EAAMD,EAAG,QAAQ,QACnBP,EAASQ,CAAG,GACdD,EAAG,iBAAiB,QAASP,EAASQ,CAAG,CAAC,CAE9C,CAAC,EAEDX,EAAY,iBAA8B,iBAAiB,EAAE,QAASU,GAAO,CAC3E,IAAMC,EAAMD,EAAG,QAAQ,SACnBP,EAASQ,CAAG,GACdD,EAAG,iBAAiB,SAAUP,EAASQ,CAAG,CAAC,CAE/C,CAAC,CACH,ECnEA,IAAAC,GAAsB,0BAElBC,EAA8B,KAIrBC,EAA8B,CAACC,EAAIC,IAAU,CAExD,GAAI,OAAO,SAAa,IAAa,OAErC,IAAMC,EAAgB,SAAS,eAAeF,CAAE,EAChD,GAAI,CAACE,EAAe,OAEpB,IAAMC,EAAcD,EAAc,UAC5BE,EAAgB,GAAAC,QAAU,SAASF,CAAW,EAEpD,GAAIL,IAAiB,MAAQM,IAAkBN,EAAc,CAE3D,IAAMQ,EAAa,SAAS,cAAc,KAAK,EAC/CL,EAAMK,CAAU,EAChBJ,EAAc,UAAYJ,CAC5B,MAEEA,EAAeM,EACfH,EAAMC,CAAa,CAEvB,EC1BA,IAAAK,EAAsB,0BAiBlB,OAAO,OAAW,KAAe,CAAC,OAAO,wCAC3C,OAAO,iBAAiB,WAAaC,GAAM,CACzC,IAAMC,EAAQD,EAAE,MACZC,GAAO,iBAAmB,QAC5B,OAAO,SAAS,EAAGA,EAAM,cAAc,CAE3C,CAAC,EACD,OAAO,sCAAwC,IAG1C,IAAMC,EAAgC,CAC3CC,EACAC,EACAC,EACAC,EAAY,GACZC,EAAe,OACZ,CACH,GAAI,CAACJ,EAAS,OAGd,IAAMK,EAAgB,EAAAC,QAAU,SAASL,EAAM,CAAE,mBAAoB,eAAgB,CAAC,EAChFM,EAAqB,EAAAD,QAAU,SAASJ,EAAW,CAAE,aAAc,CAAE,KAAM,EAAM,CAAE,CAAC,EAE1FF,EAAQ,aAAa,OAAQK,CAAa,EAC1CL,EAAQ,aAAa,aAAcO,CAAkB,EAEjDJ,IACFH,EAAQ,UAAYG,EAAU,KAAK,GAGjCC,GACFJ,EAAQ,gBAAgBI,CAAY,EAIlC,OAAO,OAAW,KACpBJ,EAAQ,iBAAiB,QAAUH,GAAM,CACvCA,EAAE,eAAe,EAEjB,IAAMW,EADSX,EAAE,cACO,aAAa,MAAM,EAC3C,GAAIW,EAAU,CACZ,IAAMC,EAAiB,OAAO,QAC9B,OAAO,SAAS,EAAG,CAAC,EACpB,OAAO,QAAQ,UAAU,CAAE,eAAAA,CAAe,EAAG,GAAID,CAAQ,EACzD,cAAc,IAAI,cAAc,UAAU,CAAC,CAC7C,CACF,CAAC,CAEL,ECjEA,IAAAE,EAAsB,0BCAf,IAAMC,GAAW,CACtBC,EAAY,yDACZC,EAAW,2BACXC,EAAY,SACZC,EAAU,gEACVC,EAAS,+CACTC,EAAa,CACX,SACA,+BACA,4BACA,8BACF,EACAC,EAAW,iCACXC,EAAU,SACVC,EAAY,cACZC,EAAa,KACV,CACH,IAAMC,EAAqB,IAAM,CAC/B,GAAI,CACF,IAAIC,EAAc,SAAS,cACzB,4CACF,EACKA,IACHA,EAAc,SAAS,cAAc,MAAM,EAC3CA,EAAY,aAAa,aAAc,yBAAyB,EAChE,SAAS,KAAK,YAAYA,CAAW,GAGvC,IAAMC,EAAqBH,EAAa,cAAcD,CAAS,IAAM,GACrEG,EAAY,aACV,UACA,kCAAkCX,CAAS,eAAeC,CAAQ,gBAAgBC,CAAS,cAAcC,CAAO,aAAaC,CAAM,iBAAiBC,EAAW,KAC7J,GACF,CAAC,eAAeC,CAAQ,cAAcC,CAAO,KAAKK,CAAkB,EACtE,CACF,OAASC,EAAO,CACd,QAAQ,MAAM,iCAAkCA,CAAK,CACvD,CACF,EAEI,SAAS,aAAe,UAC1B,SAAS,iBAAiB,mBAAoBH,CAAkB,EAEhEA,EAAmB,CAEvB,EDjBO,IAAMI,EAAgB,CAC3BC,EACAC,IACe,CACf,IAAIC,EAAsB,CACxB,KAAM,EAAAC,QAAU,SAASH,EAAO,MAAQ,EAAE,EAC1C,YAAa,EAAAG,QAAU,SACrBH,EAAO,aAAe,qBACxB,EACA,OAAQ,EAAAG,QAAU,SAASH,EAAO,QAAU,EAAE,CAChD,EAEMI,EAAWC,GAAuB,CACtCH,EAAS,KAAO,EAAAC,QAAU,SAASE,CAAI,EACvCC,EAAc,OAAQJ,EAAS,IAAI,CACrC,EAEMK,EAAkBC,GAA8B,CACpDN,EAAS,YAAc,EAAAC,QAAU,SAASK,CAAW,EACrDF,EAAc,cAAeJ,EAAS,WAAW,CACnD,EAEMO,EAAaC,GAAyB,CAC1CR,EAAS,OAAS,EAAAC,QAAU,SAASO,CAAM,EAC3CJ,EAAc,SAAUJ,EAAS,MAAM,CACzC,EAEMS,EAAU,IACPT,EAAS,KAGZU,EAAiB,IACdV,EAAS,YAGZW,EAAY,IACTX,EAAS,OAGZY,EAAiB,IACdZ,EAGHa,EAAgB,CAACV,EAAcW,IAAoB,CACvD,IAAMC,EAAU,SAAS,cAAc,MAAM,EAC7CA,EAAQ,aAAa,OAAQZ,CAAI,EACjCY,EAAQ,aAAa,UAAWD,CAAO,EACvC,SAAS,KAAK,YAAYC,CAAO,CACnC,EAEMX,EAAgB,CAACD,EAAcW,IAAoB,CACvD,IAAIC,EAAU,SAAS,cAAc,cAAcZ,CAAI,IAAI,EACvDY,EACFA,EAAQ,aAAa,UAAWD,CAAO,EAEvCD,EAAcV,EAAMW,CAAO,CAE/B,EAEME,EAAuB,IAAM,CACjCZ,EAAc,OAAQJ,EAAS,IAAK,EACpCI,EAAc,cAAeJ,EAAS,WAAY,EAClDI,EAAc,SAAUJ,EAAS,MAAO,CAC1C,EAGA,OAAID,GACFkB,GACElB,EAAU,UACVA,EAAU,SACVA,EAAU,UACV,MAAM,QAAQA,EAAU,UAAU,EAAIA,EAAU,WAAW,KAAK,GAAG,EAAIA,EAAU,WACjFA,EAAU,aAAe,OAAY,OAAOA,EAAU,UAAU,EAAI,MACtE,EAGFiB,EAAqB,EAEd,CACL,QAAAd,EACA,eAAAG,EACA,UAAAE,EACA,QAAAE,EACA,eAAAC,EACA,UAAAC,EACA,eAAAC,EACA,qBAAAI,CACF,CACF,EEpHA,IAAAE,GAAsB,0BAUTC,EAA8B,CACzCC,EACAC,EACAC,EACAC,EACAC,IACG,CACH,IAAMC,EAAW,IAAIL,CAAE,GACjBM,EAAUL,EAAO,iBAA8BI,CAAQ,EAG7D,GAAIC,EAAQ,SAAW,EACrB,MAAM,IAAI,MAAM,8CAA8CN,CAAE,wBAAwB,EAI1F,GAAIM,EAAQ,OAAS,EACnB,MAAM,IAAI,MAAM,kCAAkCN,CAAE,qBAAqBM,EAAQ,MAAM,YAAY,EAGrG,IAAMC,EAASD,EAAQ,CAAC,EAGxBC,EAAO,UAAY,GAAAC,QAAU,SAASD,EAAO,UAAW,CAAE,aAAc,CAAE,KAAM,EAAK,CAAE,CAAC,EAGxFL,EAAQK,EAAQJ,EAAQC,CAAO,CACjC,EC5BO,IAAMK,EAAgC,CAC3CC,EACAC,EACAC,EACAC,EAAS,CAAC,IACP,CACH,IAAMC,EAAU,IAAI,IAEpBJ,EAAY,QAAQ,CAACK,EAAIC,IAAU,CAEjC,GAAIF,EAAQ,IAAIC,CAAE,EAAG,CACnB,QAAQ,KAAK,wDAAwDA,CAAE,oBAAe,EACtF,MACF,CACAD,EAAQ,IAAIC,CAAE,EAGd,IAAME,EAAUN,EAAI,iBAAiB,IAAII,CAAE,EAAE,EAC7C,GAAIE,EAAQ,OAAS,EAAG,CACtB,QAAQ,KACN,2CAA2CF,CAAE,MAAME,EAAQ,MAAM,mDACnE,EACA,MACF,CAEA,IAAMC,EAAYN,EAASI,CAAK,EAC1BG,EAAQ,MAAM,QAAQN,CAAM,EAAIA,EAAOG,CAAK,EAAI,OAElD,OAAOE,GAAc,WACvBE,EAAeL,EAAIJ,EAAKO,EAAWC,CAAK,EAExC,QAAQ,KAAK,gEAAgEJ,CAAE,GAAG,CAEtF,CAAC,CACH,ECtCA,IAAMM,EAAwB,CAC1BC,EACAC,IACW,CAEX,IAAMC,GADOD,GAAS,UACA,iBAAoBD,CAAQ,EAElD,GAAIE,EAAS,SAAW,EACpB,OAAI,QAAQ,IAAI,WAAa,cACzB,QAAQ,KAAK,iDAAiDF,CAAQ,GAAG,EAEtE,KAGX,GAAIA,EAAS,WAAW,GAAG,GAAKE,EAAS,OAAS,EAAG,CACjD,GAAI,QAAQ,IAAI,WAAa,aACzB,MAAM,IAAI,MACN,yCAAyCF,CAAQ,YAAYE,EAAS,MAAM,yBAChF,EAEJ,OAAOA,EAAS,CAAC,CACrB,CAEA,OAAIA,EAAS,OAAS,GACd,QAAQ,IAAI,WAAa,cACzB,QAAQ,KACJ,wDAAwDF,CAAQ,6BACpE,EAIDE,EAAS,CAAC,CACrB,ECrCA,IAAAC,GAA0B,sBAEbC,EAAY,CAACC,EAAgCC,IAAqB,CAC7E,IAAMC,EAAQ,aAAa,QAAQ,OAAO,EAE1C,GAAI,CAACA,EAEH,cAAO,SAAS,KAAOD,EAChB,KAGT,GAAI,CACF,IAAME,KAAoB,cAAUD,CAAK,EAGnCE,EAAc,KAAK,IAAI,EAAI,IACjC,OAAID,EAAa,KAAOA,EAAa,IAAMC,IACzC,QAAQ,MAAM,mBAAmB,EACjC,OAAO,aAAa,WAAW,OAAO,EACtC,OAAO,SAAS,KAAOH,GAChB,IAKX,OAASI,EAAO,CACd,eAAQ,MAAM,iBAAkBA,CAAK,EAErC,OAAO,SAAS,KAAOJ,EAChB,IACT,CACF,ECxBO,IAAMK,EAAkC,CAC7CC,EACAC,EACAC,IACG,CACHF,EAAS,QAAQG,GAAW,CAC1BF,EAAO,QAAQG,GAAa,CAC1BD,EAAQ,iBAAiBC,EAAWC,GAAS,CAC3CH,EAASC,EAASE,CAAK,CACzB,CAAC,CACH,CAAC,CACH,CAAC,CACH,ECnBO,IAAMC,EAAgB,KAIlB,CACH,KAJS,IAAM,OAAO,QAAQ,KAAK,EAKnC,QAJY,IAAM,OAAO,QAAQ,QAAQ,CAK7C,GCoBG,IAAMC,EAAc,CACvBC,EACAC,IACO,CACP,IAAMC,EAAY,SAAS,cAA2B,IAAIF,CAAQ,EAAE,GAC7D,SAAS,cAA2B,IAAIA,CAAQ,EAAE,EAEzD,GAAI,CAACE,EAAW,OAEhB,IAAMC,EAAc,OAAO,SAAS,SAAS,QAAQ,MAAO,EAAE,EAE9D,QAAWC,KAAUH,EAAS,CAC1B,IAAMI,EAAOD,EAAO,KAAK,QAAQ,MAAO,EAAE,EAG1C,GAAID,IAAgBE,GAAQF,EAAY,WAAW,GAAGE,CAAI,GAAG,EAAG,CAC5DD,EAAO,UAAUF,CAAS,EAC1B,KACJ,CACJ,CACJ,EAGO,SAASI,EAAkBC,EAAkBC,EAA8B,CAC9E,IAAMC,EAAW,OAAO,SAAS,SAAS,QAAQ,MAAO,EAAE,EAE3DD,EAAO,OAAO,QAASE,GAAU,CACxBA,EAAM,UAAU,QAErBA,EAAM,SAAS,QAASC,GAAU,CAC9B,IAAMC,EAAYD,EAAM,KAAK,QAAQ,MAAO,EAAE,EAE9C,GAAIF,IAAaG,GAAaH,EAAS,WAAW,GAAGG,CAAS,GAAG,EAAG,CAChE,IAAMR,EAASG,EAAI,cAAc,IAAII,EAAM,MAAM,EAAE,GAC5CJ,EAAI,cAAc,IAAII,EAAM,MAAM,EAAE,EACvCP,aAAkB,aAAeO,EAAM,SACvCA,EAAM,QAAQP,CAAM,CAE5B,CACJ,CAAC,CACL,CAAC,CACL,CCnEA,IAAAS,GAA4B,2BAUrB,SAASC,EAAgBC,EAA4B,CACxD,IAAMC,KAAQ,gBAA0B,KAAO,CAAE,MAAOD,CAAa,EAAE,EACjEE,EAAY,IAAI,IAEtB,MAAO,CACH,IAAK,IAAMD,EAAM,SAAS,EAAE,MAC5B,IAAME,GAAgB,CAClBF,EAAM,SAAS,CAAE,MAAOE,CAAS,CAAC,EAClCD,EAAU,QAASE,GAAaA,EAASD,CAAQ,CAAC,CACtD,EACA,UAAYC,IACRF,EAAU,IAAIE,CAAQ,EACtBA,EAASH,EAAM,SAAS,EAAE,KAAK,EACxB,IAAMC,EAAU,OAAOE,CAAQ,EAE9C,CACJ,CAIO,SAASC,EAAaC,EAAwC,CACjE,IAAMC,EAAUD,EAAS,EAGrB,OAAOC,GAAY,YAEnBA,EAAQ,CAEhB,CCpCA,IAAMC,GAAkB,IAAM,CAC1B,IAAMC,EAAQ,SAAS,iBAAoC,cAAc,EAEzEC,EACID,EACA,CAAC,OAAO,EACR,CAACE,EAASC,IAAM,CACZA,EAAE,eAAe,EACjB,IAAMC,EAAWF,EAAQ,aAAa,MAAM,GAAG,UAAU,CAAC,EACpDG,EAAgBD,EAAW,SAAS,eAAeA,CAAQ,EAAI,KAEjEC,GACAA,EAAc,eAAe,CACzB,SAAU,SACV,MAAO,OACX,CAAC,CAET,CACJ,CACJ,ECtBA,IAAAC,GAAyB,qBAErBC,EAAiBC,GAA0BA,EAE3C,OAAO,OAAW,KAAe,OAAO,SAAa,MACvDD,EAAiBC,GAA0B,CACzC,IAAMC,EAAU,SAAS,cAAc,KAAK,EAC5C,OAAAA,EAAQ,UAAYD,EACbC,EAAQ,SACjB,GAUF,IAAMC,MAAkB,aAAUC,GAAyB,EAElDA,EACD,MAAM,QAAQA,CAAO,EAAUA,EAC/BA,aAAmB,kBAA0B,CAACA,CAAO,EAClD,MAAM,KAAKA,CAAO,EAHJ,MAAM,KAAK,SAAS,iBAAiB,GAAG,CAAC,GAMhD,QAAQC,GAAU,CAChC,GAAI,CAACA,GAAUA,EAAO,QAAQ,iBAAmB,OAAQ,OACzDA,EAAO,QAAQ,eAAiB,OAGhC,IAAMC,EAAeD,EAAO,aAAa,MAAM,GAAK,IAC9CE,EAAgBP,EAAcM,CAAY,EAChDD,EAAO,aAAa,OAAQE,CAAa,EAEzC,IAAMC,EAAoBH,EAAO,aAAa,OAAO,GAAK,GAC1DA,EAAO,aAAa,QAASL,EAAcQ,CAAiB,CAAC,EAE7D,IAAMC,EAAYJ,EAAO,aAAa,YAAY,EAC9CI,GACFJ,EAAO,aAAa,aAAcL,EAAcS,CAAS,CAAC,EAI5D,IAAMC,EAAQL,EAAO,cAAc,YAAY,EAC3CK,IACFL,EAAO,UAAY,GACnBA,EAAO,YAAYK,CAAK,GAM1B,IAAMC,EAAON,EAAO,aAAa,MAAM,GAAK,GAC5C,GAAI,CAAAM,EAAK,WAAW,GAAG,EAEvB,IAAI,CAEF,GADY,IAAI,IAAIA,EAAM,OAAO,SAAS,IAAI,EACtC,SAAW,OAAO,SAAS,OAAQ,MAC7C,MAAQ,CACN,MACF,CAGAN,EAAO,iBAAiB,QAAUO,GAAkB,CAClDA,EAAE,eAAe,EACjB,GAAI,CACF,IAAMC,EAAM,IAAI,IAAIF,EAAM,OAAO,SAAS,IAAI,EAC9C,OAAO,QAAQ,UAAU,CAAC,EAAG,GAAIE,EAAI,SAAWA,EAAI,OAASA,EAAI,IAAI,EACrE,OAAO,cAAc,IAAI,cAAc,UAAU,CAAC,CACpD,OAASC,EAAK,CACZ,QAAQ,MAAM,yBAA0BH,EAAMG,CAAG,CACnD,CACF,CAAC,EACH,CAAC,CACH,EAAG,EAAE,EAEQC,GAAaX,GAAgC,CACxDD,GAAgBC,CAAO,CACzB,EC9EA,IAAMY,GAAgB,IAAM,CACxB,IAAMC,EAAI,SAAS,iBAAiB,GAAG,EACvC,OAAOC,GAAUD,CAAC,CACtB,ECFA,IAAME,EAAmB,IAAM,CAC3BC,GAAc,EACdC,GAAgB,CACpB,ECGA,IAAMC,EAAmB,SAAY,CACjC,IAAMC,EAAY,wDACZC,EAAgB,2DAGhBC,EAA2BC,GACtB,IAAI,QAAQ,CAACC,EAASC,IAAW,CACpC,IAAMC,EAAS,SAAS,cAAc,QAAQ,EAC9CA,EAAO,IAAMH,EACbG,EAAO,OAAS,IAAMF,EAAQ,EAC9BE,EAAO,QAAU,IAAMD,EAAO,IAAI,MAAM,kBAAkBF,CAAG,EAAE,CAAC,EAChE,SAAS,KAAK,YAAYG,CAAM,CACpC,CAAC,EAIL,MAAMJ,EAAWF,CAAS,EAC1B,MAAME,EAAWD,CAAa,EAG1B,OAAO,OAAO,SAAY,WAC1B,OAAO,QAAQ,EAEf,QAAQ,MAAM,iCAAiC,CAEvD,EAMMM,EAAuBJ,GACzB,IAAI,QAAQ,CAACC,EAASC,IAAW,CAC7B,IAAMC,EAAS,SAAS,cAAc,QAAQ,EAC9CA,EAAO,KAAO,cACdA,EAAO,IAAM,eAAeH,CAAG,GAC/BG,EAAO,OAAS,IAAMF,EAAQ,EAC9BE,EAAO,QAAU,IAAMD,EAAO,IAAI,MAAM,kBAAkBF,CAAG,EAAE,CAAC,EAChE,SAAS,KAAK,YAAYG,CAAM,CACpC,CAAC,EChDE,SAASE,EAAUC,EAA6B,CACnD,IAAIC,EAAqB,KAEzB,MAAO,OAAOC,EAAkBC,IAAgB,CAC5C,GAAI,CACA,GAAI,CAACF,EAAQ,CACT,IAAMG,EAAM,MAAMJ,EAAQ,EAC1BC,EAASG,EAAI,SAAWA,CAC5B,CAGA,GAAI,OAAOH,GAAW,WAClB,OAAOA,EAAOC,EAAIC,CAAK,EAI3B,GAAIF,aAAkB,YAAa,CAC/BC,GAAI,YAAYD,CAAM,EACtB,MACJ,CAGA,GAAIA,GAAU,OAAOA,EAAO,QAAW,WACnC,OAAOA,EAAO,OAAOC,EAAIC,CAAK,EAGlC,QAAQ,KAAK,qCAAsCF,CAAM,CAC7D,OAASI,EAAK,CACV,QAAQ,MAAM,oBAAqBA,CAAG,CAC1C,CACJ,CACJ,CC/BA,IAAAC,EAAsB,0BCAtB,IAAAC,GAA4B,2BAC5BC,GAAsB,0BASTC,KAAgB,gBAA4BC,IAAS,CAC9D,OAAQ,CAAC,EACT,MAAO,CAAC,EACR,UAAYC,GACRD,EAAI,KAAO,CACP,OAAQE,GAASD,CAAM,CAC3B,EAAE,EACN,SAAWE,GACPH,EAAI,KAAO,CACP,MAAOE,GAASC,CAAK,CACzB,EAAE,CACV,EAAE,EAEF,SAASD,GAASE,EAAqD,CACnE,IAAMC,EAAiC,CAAC,EACxC,QAAWC,KAAOF,EACdC,EAAOC,CAAG,EAAI,GAAAC,QAAU,SAASH,EAAIE,CAAG,CAAC,EAE7C,OAAOD,CACX,CDXO,IAAMG,EAAN,KAAe,CAIpB,YAAYC,EAAuBC,EAA0B,CAH7D,KAAQ,OAAwB,CAAC,EAI/B,KAAK,OAASD,EACd,KAAK,eAAiB,IAAI,IAAIC,CAAc,EAC5C,OAAO,iBAAiB,WAAY,KAAK,eAAe,KAAK,IAAI,CAAC,EAClE,KAAK,eAAe,CACtB,CAEQ,gBAAiB,CACvB,IAAMC,EAAc,OAAO,SAAS,SAC9BC,EAAgB,OAAO,SAAS,OAChCC,EAAc,KAAK,iBAAiBD,CAAa,EAEjDE,EAAgB,KAAK,kBAAkBH,EAAa,KAAK,MAAM,EAErE,GAAIG,EAAe,CACjB,GAAIA,EAAc,QAAS,CACzB,KAAK,SAASA,EAAc,OAAO,EACnC,MACF,CAEA,IAAMC,EAAkB,KAAK,wBAAwBD,EAAc,MAAM,EACzEE,EAAc,SAAS,EAAE,UAAUD,CAAe,EAClDC,EAAc,SAAS,EAAE,SAASH,CAAW,EAE7C,IAAMI,EAAe,SAAS,cAAc,KAAK,EAIjD,GAFAH,EAAc,UAAUG,EAAcF,EAAiBF,CAAW,EAE9DC,EAAc,SAAU,CAC1B,IAAMI,EAAaP,EAAY,MAAMG,EAAc,KAAK,MAAM,EACxDK,EAAeF,EAAa,cAAc,QAAQ,EACpDE,GACF,KAAK,eACHL,EAAc,SACdI,EACAC,EACAJ,EACAF,CACF,CAEJ,CACF,KAAO,CACL,IAAMO,EAAgB,KAAK,kBAAkB,IAAK,KAAK,MAAM,EAC7D,GAAIA,EAAe,CACjB,IAAMC,EAAiB,KAAK,wBAAwBD,EAAc,MAAM,EACxEJ,EAAc,SAAS,EAAE,UAAUK,CAAc,EACjDL,EAAc,SAAS,EAAE,SAASH,CAAW,EAE7C,IAAMI,EAAe,SAAS,cAAc,KAAK,EACjDG,EAAc,UAAUH,EAAcI,EAAgBR,CAAW,CACnE,CACF,CACF,CAEQ,eACNS,EACAJ,EACAK,EACAC,EACAX,EACA,CACA,GAAI,CAACS,GAAYA,EAAS,SAAW,EAAG,CACtC,IAAMH,EAAeI,EAAc,cAAc,QAAQ,EACrDJ,GAAcA,EAAa,OAAO,EACtC,MACF,CAEA,IAAMM,EAAgB,KAAK,kBAAkBP,EAAYI,CAAQ,EACjE,GAAIG,EAAe,CACjB,IAAMN,EAAe,SAAS,cAAc,KAAK,EACjDA,EAAa,GAAK,QAClB,IAAMO,EAAe,CAAE,GAAGF,EAAc,GAAGC,EAAc,MAAO,EAC1DV,EAAkB,KAAK,wBAAwBW,CAAY,EAQjE,GANAV,EAAc,SAAS,EAAE,UAAUD,CAAe,EAClDC,EAAc,SAAS,EAAE,SAASH,CAAW,EAE7CY,EAAc,UAAUN,EAAcJ,EAAiBF,CAAW,EAClEU,EAAc,YAAYJ,CAAY,EAElCM,EAAc,SAAU,CAC1B,IAAME,EAAiBT,EAAW,MAAMO,EAAc,KAAK,MAAM,EACjE,KAAK,eACHA,EAAc,SACdE,EACAR,EACAJ,EACAF,CACF,CACF,CACF,CACF,CAEQ,iBAAiBe,EAAwC,CAC/D,IAAMf,EAAsC,CAAC,EACvCgB,EAAkB,IAAI,gBAAgBD,CAAM,EAElD,OAAW,CAACE,EAAKC,CAAK,IAAKF,EAAgB,QAAQ,EAC7C,KAAK,eAAe,IAAIC,CAAG,IAC7BjB,EAAYiB,CAAG,EAAI,EAAAE,QAAU,SAASD,CAAK,GAI/C,OAAOlB,CACT,CAEQ,kBACNoB,EACAxB,EACAyB,EAA0C,CAAC,EAClB,CACzB,QAAWC,KAAS1B,EAAQ,CAC1B,IAAM2B,EAAYD,EAAM,KAGxB,GAFuBC,IAAc,IA+BnC,OAAOD,EA7BY,CACnB,IAAME,EAAuB,CAAC,EACxBC,EAAeF,EAAU,QAAQ,YAAaG,IAClDF,EAAW,KAAKE,EAAM,UAAU,CAAC,CAAC,EAC3B,aACR,EAEKC,EAAQ,IAAI,OAAO,IAAIF,CAAY,SAAS,EAC5CC,EAAQN,EAAK,MAAMO,CAAK,EAE9B,GAAID,EAAO,CACT,IAAME,EAAiC,CAAE,GAAGP,CAAgB,EAK5D,GAJAG,EAAW,QAAQ,CAACK,EAAMC,IAAU,CAClCF,EAAOC,CAAI,EAAIH,EAAMI,EAAQ,CAAC,GAAK,EACrC,CAAC,EAEGR,EAAM,SAAU,CAClB,IAAMjB,EAAae,EAAK,MAAMM,EAAM,CAAC,EAAE,MAAM,EACvCd,EAAgB,KAAK,kBACzBP,EACAiB,EAAM,SACNM,CACF,EACA,GAAIhB,EAAe,OAAOA,CAC5B,CAEA,MAAO,CAAE,GAAGU,EAAO,OAAAM,CAAO,CAC5B,CACF,CAGF,CAGF,CAEQ,wBACNA,EACwB,CACxB,GAAI,CAACA,EAAQ,MAAO,CAAC,EACrB,IAAM1B,EAA0C,CAAC,EACjD,QAAWe,KAAOW,EACZ,KAAK,eAAe,IAAIX,CAAG,IAC7Bf,EAAgBe,CAAG,EAAI,EAAAE,QAAU,SAASS,EAAOX,CAAG,GAAK,EAAE,GAG/D,OAAOf,CACT,CAEA,SAASkB,EAAc,CACrB,QAAQ,UAAU,KAAM,GAAIA,CAAI,EAChC,KAAK,eAAe,CACtB,CAEA,SAASE,EAAoB,CAC3B,KAAK,OAAO,KAAKA,CAAK,CACxB,CACF,E5B3LI,OAAO,OAAW,MAClB,OAAO,iBAAiB,WAAY,IAAM,CACtCS,EAAa,CACjB,CAAC,EACD,SAAS,iBAAiB,mBAAoBA,CAAY","names":["index_exports","__export","TSRouter","createEffect","createSignal","html","loadPyFiles","mapper","renderChildRoutes","useAnchorSingle","useInitialDOM","useTSAnchorMount","useTSAuth","useTSCollection","useTSComponent","useTSElementEach","useTSElements","useTSEvent","useTSEventAll","useTSExtractParams","useTSLazy","useTSMetaData","useTSNavigate","useTSOutlet","useTSParams","useTSPurifier","useTSSelect","useTSloadBrython","__toCommonJS","sanitize","input","html","strings","values","result","str","i","safeValue","autoRegister","allTags","el","tagName","tag","sanitizeHtml","str","mapper","arr","item","import_dompurify","useTSPurifier","input","config","mergedConfig","DOMPurify","useTSEvent","id","eventType","handler","element","import_vanilla","import_dompurify","extractPatternParams","pattern","path","paramNames","regexPattern","match","regex","result","name","i","DOMPurify","extractQueryParams","search","urlSearchParams","key","value","useTSParams","set","get","params","query","useTSExtractParams","pattern","store","useTSParams","params","query","useTSEventAll","selector","eventType","handler","elements","element","import_dompurify","useTSElements","htmlElement","element","config","handlers","defaultConfig","DOMPurify","node","data","tagName","sanitizedContent","el","key","import_dompurify","previousHTML","useInitialDOM","id","mount","targetElement","currentHTML","sanitizedHTML","DOMPurify","fallbackEl","import_dompurify","e","state","useAnchorSingle","element","href","ariaLabel","className","childElement","sanitizedHref","DOMPurify","sanitizedAriaLabel","hrefAttr","scrollPosition","import_dompurify","useTSCSP","scriptSrc","styleSrc","objectSrc","fontSrc","imgSrc","connectSrc","frameSrc","baseUri","reportUri","reportOnly","addOrUpdateCSPMeta","metaElement","reportUriDirective","error","useTSMetaData","config","cspConfig","metaData","DOMPurify","setName","name","updateMetaTag","setDescription","description","setAuthor","author","getName","getDescription","getAuthor","getAllMetaData","createMetaTag","content","metaTag","appendMetaTagsToHead","useTSCSP","import_dompurify","useTSComponent","id","parent","element","params","params2","selector","matches","target","DOMPurify","useTSCollection","collections","DOM","elements","params","seenIds","id","index","matches","elementFn","param","useTSComponent","useTSSelect","selector","scope","elements","import_jwt_decode","useTSAuth","_Component","loginUrl","token","decodedToken","currentTime","error","useTSElementEach","elements","events","callback","element","eventType","event","useTSNavigate","useTSOutlet","selector","outlets","outletDOM","currentPath","outlet","base","renderChildRoutes","DOM","router","pathname","route","child","childPath","import_vanilla","createSignal","initialValue","store","listeners","newValue","listener","createEffect","effectFn","cleanup","useTSHashAnchor","links","useTSElementEach","element","e","targetId","targetElement","import_lodash_es","sanitizeInput","input","element","_enhanceAnchors","anchors","anchor","originalHref","sanitizedHref","originalClassName","ariaLabel","child","href","e","url","err","useAnchor","useTSNoReload","a","useAnchor","useTSAnchorMount","useTSNoReload","useTSHashAnchor","useTSloadBrython","brythonJS","brythonStdlib","loadScript","src","resolve","reject","script","loadPyFiles","useTSLazy","factory","cached","el","props","mod","err","import_dompurify","import_vanilla","import_dompurify","tsParamsStore","set","params","sanitize","query","obj","output","key","DOMPurify","TSRouter","routes","expectedParams","currentPath","currentSearch","queryParams","matchingRoute","sanitizedParams","tsParamsStore","errorElement","nestedPath","childElement","notFoundRoute","fallbackParams","children","parentElement","parentParams","matchingChild","mergedParams","nextNestedPath","search","urlSearchParams","key","value","DOMPurify","path","inheritedParams","route","routePath","paramNames","regexPattern","match","regex","params","name","index","autoRegister"]}
package/dist/index.d.cts CHANGED
@@ -28,7 +28,8 @@ declare const useTSParams: zustand_vanilla.StoreApi<ParamStore>;
28
28
 
29
29
  declare const useTSEventAll: <T extends Event>(selector: string, eventType: keyof HTMLElementEventMap, handler: (event: T) => void) => () => void;
30
30
 
31
- type TSElements = (htmlElement: HTMLElement, element: string, config?: Config) => void;
31
+ type EventHandlers = Record<string, EventListener>;
32
+ type TSElements = (htmlElement: HTMLElement, element: string, config?: Config, handlers?: EventHandlers) => void;
32
33
  declare const useTSElements: TSElements;
33
34
 
34
35
  type TSInitialDOM = (id: string, mount: (el: HTMLElement) => void) => void;
package/dist/index.d.ts CHANGED
@@ -28,7 +28,8 @@ declare const useTSParams: zustand_vanilla.StoreApi<ParamStore>;
28
28
 
29
29
  declare const useTSEventAll: <T extends Event>(selector: string, eventType: keyof HTMLElementEventMap, handler: (event: T) => void) => () => void;
30
30
 
31
- type TSElements = (htmlElement: HTMLElement, element: string, config?: Config) => void;
31
+ type EventHandlers = Record<string, EventListener>;
32
+ type TSElements = (htmlElement: HTMLElement, element: string, config?: Config, handlers?: EventHandlers) => void;
32
33
  declare const useTSElements: TSElements;
33
34
 
34
35
  type TSInitialDOM = (id: string, mount: (el: HTMLElement) => void) => void;
package/dist/index.js CHANGED
@@ -1,2 +1,2 @@
1
- function ne(n){return(n==null?"":String(n)).replace(/<\s*(script|iframe|object|embed|link|style)[^>]*>.*?<\s*\/\s*\1\s*>/gi,"").replace(/<\s*(script|iframe|object|embed|link|style)[^>]*>/gi,"").replace(/\son\w+\s*=\s*(['"]).*?\1/gi,"").replace(/\s(href|src)\s*=\s*(['"])\s*javascript:[^'"]*\2/gi,"")}function A(n,...e){return n.reduce((t,r,o)=>{let s=o<e.length?ne(e[o]):"";return t+r+s},"")}function T(){let n=new Set;document.querySelectorAll("*").forEach(e=>{let t=e.tagName.toLowerCase();t.includes("-")&&n.add(t)}),n.forEach(e=>{customElements.get(e)||customElements.define(e,class extends HTMLElement{connectedCallback(){this.innerHTML=`<div style="padding:10px;background:#eee;">${e} (Auto)</div>`}})})}var re=n=>n.replace(/<\/?(script|iframe|object|embed|link|meta|style)[^>]*>/gi,"").replace(/\s+on[a-z]+\s*=\s*("[^"]*"|'[^']*'|[^\s>]+)/gi,"").replace(/\s+(href|src)\s*=\s*(['"]?)\s*javascript:[^'"\s>]*/gi,""),oe=n=>n?.map(e=>re(e)).join("")??"";import x from"dompurify";var R=(n,e)=>{let r={...{ADD_TAGS:["my-custom-tag"]},...e};return typeof n=="string"?x.sanitize(n,r):x.sanitize(n.innerHTML,r)};var b=(n,e,t)=>{if(typeof n=="string"){let r=document.getElementById(n);r?r.addEventListener(e,t):console.warn(`Element with id '${n}' not found.`)}else n===document?document.addEventListener(e,t):console.warn("Invalid id parameter provided.")};import{createStore as se}from"zustand/vanilla";import C from"dompurify";function ie(n,e){let t=[],r=n.replace(/:[^/]+/g,a=>(t.push(a.slice(1)),"([^/]+)")),o=new RegExp(`^${r}$`),s=e.match(o),i={};return s&&t.forEach((a,c)=>{i[a]=C.sanitize(s[c+1]??"")}),i}function ae(n){let e={},t=new URLSearchParams(n);for(let[r,o]of t.entries())e[r]=C.sanitize(o);return e}var E=se((n,e)=>({params:{},query:{},setFromPattern:t=>{let r=window.location.pathname,o=ie(t,r),s=ae(window.location.search);n({params:o,query:s})},getParam:t=>e().params[t],getQuery:t=>e().query[t]}));function H(n){let e=E.getState();e.setFromPattern(n);let t=e.params,r=e.query;return{...t,...r}}var D=(n,e,t)=>{let r=document.querySelectorAll(n);return r.forEach(o=>{o.addEventListener(e,t)}),()=>{r.forEach(o=>{o.removeEventListener(e,t)})}};import M from"dompurify";var O=(n,e,t)=>{let r={USE_PROFILES:{svg:!0,html:!0},ALLOWED_TAGS:["svg","path","circle","rect","line","polyline","polygon","g","main","div","h1","h2","h3","h4","h5","h6","p","button","span","a","img","input","ul","li","i"],ALLOWED_ATTR:["class","id","href","src","alt","fill","stroke","stroke-width","viewBox","xmlns","d","x","y","cx","cy","r","width","height"],FORBID_TAGS:["script","iframe"],ALLOWED_URI_REGEXP:/^(?:(?:https?|mailto|tel|ftp):|[^a-z]|[a-z+.\-]+(?:[^a-z+.\-:]|$))/i,...t};M.addHook("uponSanitizeElement",(s,i)=>{let a=i.tagName.toLowerCase();a.includes("-")&&(i.allowedTags[a]=!0)}),M.addHook("uponSanitizeAttribute",(s,i)=>{i.attrName&&i.attrName.toLowerCase().startsWith("on")&&(i.keepAttr=!1)});let o=M.sanitize(e,r);n.innerHTML!==o&&(n.innerHTML=o)};import ce from"dompurify";var y=null,$=(n,e)=>{if(typeof document>"u")return;let t=document.getElementById(n);if(!t)return;let r=t.innerHTML,o=ce.sanitize(r);if(y!==null&&o!==y){let s=document.createElement("div");e(s),t.innerHTML=y}else y=o,e(t)};import k from"dompurify";typeof window<"u"&&!window.__anchorSinglePopstateHandlerAttached&&(window.addEventListener("popstate",n=>{let e=n.state;e?.scrollPosition!==void 0&&window.scrollTo(0,e.scrollPosition)}),window.__anchorSinglePopstateHandlerAttached=!0);var z=(n,e,t,r="",o=null)=>{if(!n)return;let s=k.sanitize(e,{ALLOWED_URI_REGEXP:/^(https?:|\/)/}),i=k.sanitize(t,{USE_PROFILES:{html:!1}});n.setAttribute("href",s),n.setAttribute("aria-label",i),r&&(n.className=r.trim()),o&&n.replaceChildren(o),typeof window<"u"&&n.addEventListener("click",a=>{a.preventDefault();let d=a.currentTarget.getAttribute("href");if(d){let u=window.scrollY;window.scrollTo(0,0),window.history.pushState({scrollPosition:u},"",d),dispatchEvent(new PopStateEvent("popstate"))}})};import h from"dompurify";var I=(n="'self' 'nonce-rAnd0m123' 'unsafe-inline' 'unsafe-eval'",e="'self' 'nonce-rAnd0m123'",t="'none'",r="'self' https://fonts.googleapis.com https://fonts.gstatic.com",o="'self' https://blogger.googleusercontent.com",s=["'self'","https://fonts.googleapis.com","https://fonts.gstatic.com","https://www.google.com/maps/"],i="'self' https://www.youtube.com",a="'self'",c="/csp-report",d=!1)=>{let u=()=>{try{let l=document.querySelector('meta[http-equiv="Content-Security-Policy"]');l||(l=document.createElement("meta"),l.setAttribute("http-equiv","Content-Security-Policy"),document.head.appendChild(l));let p=d?`report-uri ${c};`:"";l.setAttribute("content",`default-src 'self'; script-src ${n}; style-src ${e}; object-src ${t}; font-src ${r}; img-src ${o}; connect-src ${s.join(" ")}; frame-src ${i}; base-uri ${a}; ${p}`)}catch(l){console.error("Error adding CSP meta element:",l)}};document.readyState==="loading"?document.addEventListener("DOMContentLoaded",u):u()};var N=(n,e)=>{let t={name:h.sanitize(n.name||""),description:h.sanitize(n.description||"Default description"),author:h.sanitize(n.author||"")},r=m=>{t.name=h.sanitize(m),l("name",t.name)},o=m=>{t.description=h.sanitize(m),l("description",t.description)},s=m=>{t.author=h.sanitize(m),l("author",t.author)},i=()=>t.name,a=()=>t.description,c=()=>t.author,d=()=>t,u=(m,S)=>{let g=document.createElement("meta");g.setAttribute("name",m),g.setAttribute("content",S),document.head.appendChild(g)},l=(m,S)=>{let g=document.querySelector(`meta[name="${m}"]`);g?g.setAttribute("content",S):u(m,S)},p=()=>{l("name",t.name),l("description",t.description),l("author",t.author)};return e&&I(e.scriptSrc,e.styleSrc,e.objectSrc,Array.isArray(e.connectSrc)?e.connectSrc.join(" "):e.connectSrc,e.reportOnly!==void 0?String(e.reportOnly):void 0),p(),{setName:r,setDescription:o,setAuthor:s,getName:i,getDescription:a,getAuthor:c,getAllMetaData:d,appendMetaTagsToHead:p}};import le from"dompurify";var v=(n,e,t,r,o)=>{let s=`#${n}`,i=e.querySelectorAll(s);if(i.length===0)throw new Error(`[useTSComponent] No element found with id '${n}' in the given parent.`);if(i.length>1)throw new Error(`[useTSComponent] Duplicate id '${n}' detected. Found ${i.length} elements.`);let a=i[0];a.innerHTML=le.sanitize(a.innerHTML,{USE_PROFILES:{html:!0}}),t(a,r,o)};var q=(n,e,t,r=[])=>{let o=new Set;n.forEach((s,i)=>{if(o.has(s)){console.warn(`[useTSCollection] Duplicate ID in collection array: "${s}" \u2014 skipping.`);return}o.add(s);let a=e.querySelectorAll(`#${s}`);if(a.length>1){console.warn(`[useTSCollection] Duplicate ID in DOM: "${s}" (${a.length} elements found) \u2014 skipping component mount.`);return}let c=t[i],d=Array.isArray(r)?r[i]:void 0;typeof c=="function"?v(s,e,c,d):console.warn(`[useTSCollection] No valid component function found for ID: "${s}"`)})};var F=(n,e)=>{let r=(e??document).querySelectorAll(n);if(r.length===0)return process.env.NODE_ENV!=="production"&&console.warn(`[useTSSelect] No element found for selector: '${n}'`),null;if(n.startsWith("#")&&r.length>1){if(process.env.NODE_ENV!=="production")throw new Error(`[useTSSelect] Duplicate ID detected: '${n}'. Found ${r.length} elements with this ID.`);return r[0]}return r.length>1&&process.env.NODE_ENV!=="production"&&console.warn(`[useTSSelect] Multiple elements found for selector: '${n}'. Returning the first one.`),r[0]};import{jwtDecode as ue}from"jwt-decode";var _=(n,e)=>{let t=localStorage.getItem("token");if(!t)return window.location.href=e,null;try{let r=ue(t),o=Date.now()/1e3;return r.exp&&r.exp<o&&(console.error("Token has expired"),window.localStorage.removeItem("token"),window.location.href=e),null}catch(r){return console.error("Invalid token:",r),window.location.href=e,null}};var L=(n,e,t)=>{n.forEach(r=>{e.forEach(o=>{r.addEventListener(o,s=>{t(r,s)})})})};var U=()=>({back:()=>window.history.back(),forward:()=>window.history.forward()});var j=(n,e)=>{let t=document.querySelector(`#${n}`)||document.querySelector(`.${n}`);if(!t)return;let r=window.location.pathname.replace(/\/$/,"");for(let o of e){let s=o.path.replace(/\/$/,"");if(r===s||r.startsWith(`${s}/`)){o.component(t);break}}};function B(n,e){let t=window.location.pathname.replace(/\/$/,"");e.routes.forEach(r=>{r.children?.length&&r.children.forEach(o=>{let s=o.path.replace(/\/$/,"");if(t===s||t.startsWith(`${s}/`)){let i=n.querySelector(`#${o.outlet}`)||n.querySelector(`.${o.outlet}`);i instanceof HTMLElement&&o.element&&o.element(i)}})})}import{createStore as de}from"zustand/vanilla";function W(n){let e=de(()=>({value:n})),t=new Set;return{get:()=>e.getState().value,set:r=>{e.setState({value:r}),t.forEach(o=>o(r))},subscribe:r=>(t.add(r),r(e.getState().value),()=>t.delete(r))}}function Q(n){let e=n();typeof e=="function"&&e()}var G=()=>{let n=document.querySelectorAll('a[href^="#"]');L(n,["click"],(e,t)=>{t.preventDefault();let r=e.getAttribute("href")?.substring(1),o=r?document.getElementById(r):null;o&&o.scrollIntoView({behavior:"smooth",block:"start"})})};import{debounce as me}from"lodash-es";var w=n=>n;typeof window<"u"&&typeof document<"u"&&(w=n=>{let e=document.createElement("div");return e.innerText=n,e.innerHTML});var pe=me(n=>{(n?Array.isArray(n)?n:n instanceof HTMLAnchorElement?[n]:Array.from(n):Array.from(document.querySelectorAll("a"))).forEach(t=>{if(!t||t.dataset.anchorEnhanced==="true")return;t.dataset.anchorEnhanced="true";let r=t.getAttribute("href")||"#",o=w(r);t.setAttribute("href",o);let s=t.getAttribute("class")||"";t.setAttribute("class",w(s));let i=t.getAttribute("aria-label");i&&t.setAttribute("aria-label",w(i));let a=t.querySelector(":scope > *");a&&(t.innerHTML="",t.appendChild(a));let c=t.getAttribute("href")||"";if(!c.startsWith("#")){try{if(new URL(c,window.location.href).origin!==window.location.origin)return}catch{return}t.addEventListener("click",d=>{d.preventDefault();try{let u=new URL(c,window.location.href);window.history.pushState({},"",u.pathname+u.search+u.hash),window.dispatchEvent(new PopStateEvent("popstate"))}catch(u){console.error("Invalid URL in anchor:",c,u)}})}})},50),V=n=>{pe(n)};var X=()=>{let n=document.querySelectorAll("a");return V(n)};var J=()=>{X(),G()};var Y=async()=>{let n="https://cdn.jsdelivr.net/npm/brython@3/brython.min.js",e="https://cdn.jsdelivr.net/npm/brython@3/brython_stdlib.js",t=r=>new Promise((o,s)=>{let i=document.createElement("script");i.src=r,i.onload=()=>o(),i.onerror=()=>s(new Error(`Failed to load ${r}`)),document.head.appendChild(i)});await t(n),await t(e),typeof window.brython=="function"?window.brython():console.error("Brython did not load correctly.")},K=n=>new Promise((e,t)=>{let r=document.createElement("script");r.type="text/python",r.src=`/src/python/${n}`,r.onload=()=>e(),r.onerror=()=>t(new Error(`Failed to load ${n}`)),document.body.appendChild(r)});function Z(n){let e=null;return async(t,r)=>{try{if(!e){let o=await n();e=o.default||o}if(typeof e=="function")return e(t,r);if(e instanceof HTMLElement){t?.appendChild(e);return}if(e&&typeof e.render=="function")return e.render(t,r);console.warn("useTSLazy: Unsupported module type",e)}catch(o){console.error("useTSLazy failed:",o)}}}import te from"dompurify";import{createStore as fe}from"zustand/vanilla";import ge from"dompurify";var f=fe(n=>({params:{},query:{},setParams:e=>n(()=>({params:ee(e)})),setQuery:e=>n(()=>({query:ee(e)}))}));function ee(n){let e={};for(let t in n)e[t]=ge.sanitize(n[t]);return e}var P=class{constructor(e,t){this.routes=[];this.routes=e,this.expectedParams=new Set(t),window.addEventListener("popstate",this.handlePopState.bind(this)),this.handlePopState()}handlePopState(){let e=window.location.pathname,t=window.location.search,r=this.parseQueryParams(t),o=this.findMatchingRoute(e,this.routes);if(o){if(o.routeto){this.navigate(o.routeto);return}let s=this.filterAndSanitizeParams(o.params);f.getState().setParams(s),f.getState().setQuery(r);let i=document.createElement("div");if(o.element?.(i,s,r),o.children){let a=e.slice(o.path.length),c=i.querySelector("#child");c&&this.renderChildren(o.children,a,c,s,r)}}else{let s=this.findMatchingRoute("*",this.routes);if(s){let i=this.filterAndSanitizeParams(s.params);f.getState().setParams(i),f.getState().setQuery(r);let a=document.createElement("div");s.element?.(a,i,r)}}}renderChildren(e,t,r,o,s){if(!e||e.length===0){let a=r.querySelector("#child");a&&a.remove();return}let i=this.findMatchingRoute(t,e);if(i){let a=document.createElement("div");a.id="child";let c={...o,...i.params},d=this.filterAndSanitizeParams(c);if(f.getState().setParams(d),f.getState().setQuery(s),i.element?.(a,d,s),r.appendChild(a),i.children){let u=t.slice(i.path.length);this.renderChildren(i.children,u,a,d,s)}}}parseQueryParams(e){let t={},r=new URLSearchParams(e);for(let[o,s]of r.entries())this.expectedParams.has(o)&&(t[o]=te.sanitize(s));return t}findMatchingRoute(e,t,r={}){for(let o of t){let s=o.path;if(s==="*")return o;{let a=[],c=s.replace(/:[^\s/]+/g,l=>(a.push(l.substring(1)),"([^\\s/]+)")),d=new RegExp(`^${c}(?:/|$)`),u=e.match(d);if(u){let l={...r};if(a.forEach((p,m)=>{l[p]=u[m+1]??""}),o.children){let p=e.slice(u[0].length),m=this.findMatchingRoute(p,o.children,l);if(m)return m}return{...o,params:l}}}}}filterAndSanitizeParams(e){if(!e)return{};let t={};for(let r in e)this.expectedParams.has(r)&&(t[r]=te.sanitize(e[r]??""));return t}navigate(e){history.pushState(null,"",e),this.handlePopState()}addRoute(e){this.routes.push(e)}};typeof window<"u"&&(window.addEventListener("popstate",()=>{T()}),document.addEventListener("DOMContentLoaded",T));export{P as TSRouter,Q as createEffect,W as createSignal,A as html,K as loadPyFiles,oe as mapper,B as renderChildRoutes,z as useAnchorSingle,$ as useInitialDOM,J as useTSAnchorMount,_ as useTSAuth,q as useTSCollection,v as useTSComponent,L as useTSElementEach,O as useTSElements,b as useTSEvent,D as useTSEventAll,H as useTSExtractParams,Z as useTSLazy,N as useTSMetaData,U as useTSNavigate,j as useTSOutlet,E as useTSParams,R as useTSPurifier,F as useTSSelect,Y as useTSloadBrython};
1
+ function ne(n){return(n==null?"":String(n)).replace(/<\s*(script|iframe|object|embed|link|style)[^>]*>.*?<\s*\/\s*\1\s*>/gi,"").replace(/<\s*(script|iframe|object|embed|link|style)[^>]*>/gi,"").replace(/\son\w+\s*=\s*(['"]).*?\1/gi,"").replace(/\s(href|src)\s*=\s*(['"])\s*javascript:[^'"]*\2/gi,"")}function A(n,...e){return n.reduce((t,r,o)=>{let s=o<e.length?ne(e[o]):"";return t+r+s},"")}function E(){let n=new Set;document.querySelectorAll("*").forEach(e=>{let t=e.tagName.toLowerCase();t.includes("-")&&n.add(t)}),n.forEach(e=>{customElements.get(e)||customElements.define(e,class extends HTMLElement{connectedCallback(){this.innerHTML=`<div style="padding:10px;background:#eee;">${e} (Auto)</div>`}})})}var re=n=>n.replace(/<\/?(script|iframe|object|embed|link|meta|style)[^>]*>/gi,"").replace(/\s+on[a-z]+\s*=\s*("[^"]*"|'[^']*'|[^\s>]+)/gi,"").replace(/\s+(href|src)\s*=\s*(['"]?)\s*javascript:[^'"\s>]*/gi,""),oe=n=>n?.map(e=>re(e)).join("")??"";import x from"dompurify";var R=(n,e)=>{let r={...{ADD_TAGS:["my-custom-tag"]},...e};return typeof n=="string"?x.sanitize(n,r):x.sanitize(n.innerHTML,r)};var b=(n,e,t)=>{if(typeof n=="string"){let r=document.getElementById(n);r?r.addEventListener(e,t):console.warn(`Element with id '${n}' not found.`)}else n===document?document.addEventListener(e,t):console.warn("Invalid id parameter provided.")};import{createStore as se}from"zustand/vanilla";import C from"dompurify";function ie(n,e){let t=[],r=n.replace(/:[^/]+/g,a=>(t.push(a.slice(1)),"([^/]+)")),o=new RegExp(`^${r}$`),s=e.match(o),i={};return s&&t.forEach((a,c)=>{i[a]=C.sanitize(s[c+1]??"")}),i}function ae(n){let e={},t=new URLSearchParams(n);for(let[r,o]of t.entries())e[r]=C.sanitize(o);return e}var T=se((n,e)=>({params:{},query:{},setFromPattern:t=>{let r=window.location.pathname,o=ie(t,r),s=ae(window.location.search);n({params:o,query:s})},getParam:t=>e().params[t],getQuery:t=>e().query[t]}));function H(n){let e=T.getState();e.setFromPattern(n);let t=e.params,r=e.query;return{...t,...r}}var D=(n,e,t)=>{let r=document.querySelectorAll(n);return r.forEach(o=>{o.addEventListener(e,t)}),()=>{r.forEach(o=>{o.removeEventListener(e,t)})}};import M from"dompurify";var O=(n,e,t,r={})=>{let o={USE_PROFILES:{svg:!0,html:!0},ALLOWED_TAGS:["svg","path","circle","rect","line","polyline","polygon","g","main","div","h1","h2","h3","h4","h5","h6","p","button","span","a","img","input","ul","li","i"],ALLOWED_ATTR:["class","id","href","src","alt","fill","stroke","stroke-width","viewBox","xmlns","d","x","y","cx","cy","r","width","height","data-onclick","data-onchange"],FORBID_TAGS:["script","iframe"],ALLOWED_URI_REGEXP:/^(?:(?:https?|mailto|tel|ftp):|[^a-z]|[a-z+.\-]+(?:[^a-z+.\-:]|$))/i,...t};M.addHook("uponSanitizeElement",(i,a)=>{let c=a.tagName.toLowerCase();c.includes("-")&&(a.allowedTags[c]=!0)}),M.addHook("uponSanitizeAttribute",(i,a)=>{a.attrName&&a.attrName.toLowerCase().startsWith("on")&&(a.keepAttr=!1)});let s=M.sanitize(e,o);n.innerHTML=s,n.querySelectorAll("[data-onclick]").forEach(i=>{let a=i.dataset.onclick;r[a]&&i.addEventListener("click",r[a])}),n.querySelectorAll("[data-onchange]").forEach(i=>{let a=i.dataset.onchange;r[a]&&i.addEventListener("change",r[a])})};import ce from"dompurify";var y=null,k=(n,e)=>{if(typeof document>"u")return;let t=document.getElementById(n);if(!t)return;let r=t.innerHTML,o=ce.sanitize(r);if(y!==null&&o!==y){let s=document.createElement("div");e(s),t.innerHTML=y}else y=o,e(t)};import $ from"dompurify";typeof window<"u"&&!window.__anchorSinglePopstateHandlerAttached&&(window.addEventListener("popstate",n=>{let e=n.state;e?.scrollPosition!==void 0&&window.scrollTo(0,e.scrollPosition)}),window.__anchorSinglePopstateHandlerAttached=!0);var z=(n,e,t,r="",o=null)=>{if(!n)return;let s=$.sanitize(e,{ALLOWED_URI_REGEXP:/^(https?:|\/)/}),i=$.sanitize(t,{USE_PROFILES:{html:!1}});n.setAttribute("href",s),n.setAttribute("aria-label",i),r&&(n.className=r.trim()),o&&n.replaceChildren(o),typeof window<"u"&&n.addEventListener("click",a=>{a.preventDefault();let d=a.currentTarget.getAttribute("href");if(d){let u=window.scrollY;window.scrollTo(0,0),window.history.pushState({scrollPosition:u},"",d),dispatchEvent(new PopStateEvent("popstate"))}})};import h from"dompurify";var q=(n="'self' 'nonce-rAnd0m123' 'unsafe-inline' 'unsafe-eval'",e="'self' 'nonce-rAnd0m123'",t="'none'",r="'self' https://fonts.googleapis.com https://fonts.gstatic.com",o="'self' https://blogger.googleusercontent.com",s=["'self'","https://fonts.googleapis.com","https://fonts.gstatic.com","https://www.google.com/maps/"],i="'self' https://www.youtube.com",a="'self'",c="/csp-report",d=!1)=>{let u=()=>{try{let l=document.querySelector('meta[http-equiv="Content-Security-Policy"]');l||(l=document.createElement("meta"),l.setAttribute("http-equiv","Content-Security-Policy"),document.head.appendChild(l));let p=d?`report-uri ${c};`:"";l.setAttribute("content",`default-src 'self'; script-src ${n}; style-src ${e}; object-src ${t}; font-src ${r}; img-src ${o}; connect-src ${s.join(" ")}; frame-src ${i}; base-uri ${a}; ${p}`)}catch(l){console.error("Error adding CSP meta element:",l)}};document.readyState==="loading"?document.addEventListener("DOMContentLoaded",u):u()};var I=(n,e)=>{let t={name:h.sanitize(n.name||""),description:h.sanitize(n.description||"Default description"),author:h.sanitize(n.author||"")},r=m=>{t.name=h.sanitize(m),l("name",t.name)},o=m=>{t.description=h.sanitize(m),l("description",t.description)},s=m=>{t.author=h.sanitize(m),l("author",t.author)},i=()=>t.name,a=()=>t.description,c=()=>t.author,d=()=>t,u=(m,S)=>{let g=document.createElement("meta");g.setAttribute("name",m),g.setAttribute("content",S),document.head.appendChild(g)},l=(m,S)=>{let g=document.querySelector(`meta[name="${m}"]`);g?g.setAttribute("content",S):u(m,S)},p=()=>{l("name",t.name),l("description",t.description),l("author",t.author)};return e&&q(e.scriptSrc,e.styleSrc,e.objectSrc,Array.isArray(e.connectSrc)?e.connectSrc.join(" "):e.connectSrc,e.reportOnly!==void 0?String(e.reportOnly):void 0),p(),{setName:r,setDescription:o,setAuthor:s,getName:i,getDescription:a,getAuthor:c,getAllMetaData:d,appendMetaTagsToHead:p}};import le from"dompurify";var v=(n,e,t,r,o)=>{let s=`#${n}`,i=e.querySelectorAll(s);if(i.length===0)throw new Error(`[useTSComponent] No element found with id '${n}' in the given parent.`);if(i.length>1)throw new Error(`[useTSComponent] Duplicate id '${n}' detected. Found ${i.length} elements.`);let a=i[0];a.innerHTML=le.sanitize(a.innerHTML,{USE_PROFILES:{html:!0}}),t(a,r,o)};var N=(n,e,t,r=[])=>{let o=new Set;n.forEach((s,i)=>{if(o.has(s)){console.warn(`[useTSCollection] Duplicate ID in collection array: "${s}" \u2014 skipping.`);return}o.add(s);let a=e.querySelectorAll(`#${s}`);if(a.length>1){console.warn(`[useTSCollection] Duplicate ID in DOM: "${s}" (${a.length} elements found) \u2014 skipping component mount.`);return}let c=t[i],d=Array.isArray(r)?r[i]:void 0;typeof c=="function"?v(s,e,c,d):console.warn(`[useTSCollection] No valid component function found for ID: "${s}"`)})};var F=(n,e)=>{let r=(e??document).querySelectorAll(n);if(r.length===0)return process.env.NODE_ENV!=="production"&&console.warn(`[useTSSelect] No element found for selector: '${n}'`),null;if(n.startsWith("#")&&r.length>1){if(process.env.NODE_ENV!=="production")throw new Error(`[useTSSelect] Duplicate ID detected: '${n}'. Found ${r.length} elements with this ID.`);return r[0]}return r.length>1&&process.env.NODE_ENV!=="production"&&console.warn(`[useTSSelect] Multiple elements found for selector: '${n}'. Returning the first one.`),r[0]};import{jwtDecode as ue}from"jwt-decode";var _=(n,e)=>{let t=localStorage.getItem("token");if(!t)return window.location.href=e,null;try{let r=ue(t),o=Date.now()/1e3;return r.exp&&r.exp<o&&(console.error("Token has expired"),window.localStorage.removeItem("token"),window.location.href=e),null}catch(r){return console.error("Invalid token:",r),window.location.href=e,null}};var L=(n,e,t)=>{n.forEach(r=>{e.forEach(o=>{r.addEventListener(o,s=>{t(r,s)})})})};var U=()=>({back:()=>window.history.back(),forward:()=>window.history.forward()});var j=(n,e)=>{let t=document.querySelector(`#${n}`)||document.querySelector(`.${n}`);if(!t)return;let r=window.location.pathname.replace(/\/$/,"");for(let o of e){let s=o.path.replace(/\/$/,"");if(r===s||r.startsWith(`${s}/`)){o.component(t);break}}};function B(n,e){let t=window.location.pathname.replace(/\/$/,"");e.routes.forEach(r=>{r.children?.length&&r.children.forEach(o=>{let s=o.path.replace(/\/$/,"");if(t===s||t.startsWith(`${s}/`)){let i=n.querySelector(`#${o.outlet}`)||n.querySelector(`.${o.outlet}`);i instanceof HTMLElement&&o.element&&o.element(i)}})})}import{createStore as de}from"zustand/vanilla";function W(n){let e=de(()=>({value:n})),t=new Set;return{get:()=>e.getState().value,set:r=>{e.setState({value:r}),t.forEach(o=>o(r))},subscribe:r=>(t.add(r),r(e.getState().value),()=>t.delete(r))}}function Q(n){let e=n();typeof e=="function"&&e()}var G=()=>{let n=document.querySelectorAll('a[href^="#"]');L(n,["click"],(e,t)=>{t.preventDefault();let r=e.getAttribute("href")?.substring(1),o=r?document.getElementById(r):null;o&&o.scrollIntoView({behavior:"smooth",block:"start"})})};import{debounce as me}from"lodash-es";var w=n=>n;typeof window<"u"&&typeof document<"u"&&(w=n=>{let e=document.createElement("div");return e.innerText=n,e.innerHTML});var pe=me(n=>{(n?Array.isArray(n)?n:n instanceof HTMLAnchorElement?[n]:Array.from(n):Array.from(document.querySelectorAll("a"))).forEach(t=>{if(!t||t.dataset.anchorEnhanced==="true")return;t.dataset.anchorEnhanced="true";let r=t.getAttribute("href")||"#",o=w(r);t.setAttribute("href",o);let s=t.getAttribute("class")||"";t.setAttribute("class",w(s));let i=t.getAttribute("aria-label");i&&t.setAttribute("aria-label",w(i));let a=t.querySelector(":scope > *");a&&(t.innerHTML="",t.appendChild(a));let c=t.getAttribute("href")||"";if(!c.startsWith("#")){try{if(new URL(c,window.location.href).origin!==window.location.origin)return}catch{return}t.addEventListener("click",d=>{d.preventDefault();try{let u=new URL(c,window.location.href);window.history.pushState({},"",u.pathname+u.search+u.hash),window.dispatchEvent(new PopStateEvent("popstate"))}catch(u){console.error("Invalid URL in anchor:",c,u)}})}})},50),V=n=>{pe(n)};var X=()=>{let n=document.querySelectorAll("a");return V(n)};var J=()=>{X(),G()};var Y=async()=>{let n="https://cdn.jsdelivr.net/npm/brython@3/brython.min.js",e="https://cdn.jsdelivr.net/npm/brython@3/brython_stdlib.js",t=r=>new Promise((o,s)=>{let i=document.createElement("script");i.src=r,i.onload=()=>o(),i.onerror=()=>s(new Error(`Failed to load ${r}`)),document.head.appendChild(i)});await t(n),await t(e),typeof window.brython=="function"?window.brython():console.error("Brython did not load correctly.")},K=n=>new Promise((e,t)=>{let r=document.createElement("script");r.type="text/python",r.src=`/src/python/${n}`,r.onload=()=>e(),r.onerror=()=>t(new Error(`Failed to load ${n}`)),document.body.appendChild(r)});function Z(n){let e=null;return async(t,r)=>{try{if(!e){let o=await n();e=o.default||o}if(typeof e=="function")return e(t,r);if(e instanceof HTMLElement){t?.appendChild(e);return}if(e&&typeof e.render=="function")return e.render(t,r);console.warn("useTSLazy: Unsupported module type",e)}catch(o){console.error("useTSLazy failed:",o)}}}import te from"dompurify";import{createStore as fe}from"zustand/vanilla";import ge from"dompurify";var f=fe(n=>({params:{},query:{},setParams:e=>n(()=>({params:ee(e)})),setQuery:e=>n(()=>({query:ee(e)}))}));function ee(n){let e={};for(let t in n)e[t]=ge.sanitize(n[t]);return e}var P=class{constructor(e,t){this.routes=[];this.routes=e,this.expectedParams=new Set(t),window.addEventListener("popstate",this.handlePopState.bind(this)),this.handlePopState()}handlePopState(){let e=window.location.pathname,t=window.location.search,r=this.parseQueryParams(t),o=this.findMatchingRoute(e,this.routes);if(o){if(o.routeto){this.navigate(o.routeto);return}let s=this.filterAndSanitizeParams(o.params);f.getState().setParams(s),f.getState().setQuery(r);let i=document.createElement("div");if(o.element?.(i,s,r),o.children){let a=e.slice(o.path.length),c=i.querySelector("#child");c&&this.renderChildren(o.children,a,c,s,r)}}else{let s=this.findMatchingRoute("*",this.routes);if(s){let i=this.filterAndSanitizeParams(s.params);f.getState().setParams(i),f.getState().setQuery(r);let a=document.createElement("div");s.element?.(a,i,r)}}}renderChildren(e,t,r,o,s){if(!e||e.length===0){let a=r.querySelector("#child");a&&a.remove();return}let i=this.findMatchingRoute(t,e);if(i){let a=document.createElement("div");a.id="child";let c={...o,...i.params},d=this.filterAndSanitizeParams(c);if(f.getState().setParams(d),f.getState().setQuery(s),i.element?.(a,d,s),r.appendChild(a),i.children){let u=t.slice(i.path.length);this.renderChildren(i.children,u,a,d,s)}}}parseQueryParams(e){let t={},r=new URLSearchParams(e);for(let[o,s]of r.entries())this.expectedParams.has(o)&&(t[o]=te.sanitize(s));return t}findMatchingRoute(e,t,r={}){for(let o of t){let s=o.path;if(s==="*")return o;{let a=[],c=s.replace(/:[^\s/]+/g,l=>(a.push(l.substring(1)),"([^\\s/]+)")),d=new RegExp(`^${c}(?:/|$)`),u=e.match(d);if(u){let l={...r};if(a.forEach((p,m)=>{l[p]=u[m+1]??""}),o.children){let p=e.slice(u[0].length),m=this.findMatchingRoute(p,o.children,l);if(m)return m}return{...o,params:l}}}}}filterAndSanitizeParams(e){if(!e)return{};let t={};for(let r in e)this.expectedParams.has(r)&&(t[r]=te.sanitize(e[r]??""));return t}navigate(e){history.pushState(null,"",e),this.handlePopState()}addRoute(e){this.routes.push(e)}};typeof window<"u"&&(window.addEventListener("popstate",()=>{E()}),document.addEventListener("DOMContentLoaded",E));export{P as TSRouter,Q as createEffect,W as createSignal,A as html,K as loadPyFiles,oe as mapper,B as renderChildRoutes,z as useAnchorSingle,k as useInitialDOM,J as useTSAnchorMount,_ as useTSAuth,N as useTSCollection,v as useTSComponent,L as useTSElementEach,O as useTSElements,b as useTSEvent,D as useTSEventAll,H as useTSExtractParams,Z as useTSLazy,I as useTSMetaData,U as useTSNavigate,j as useTSOutlet,T as useTSParams,R as useTSPurifier,F as useTSSelect,Y as useTSloadBrython};
2
2
  //# sourceMappingURL=index.js.map
package/dist/index.js.map CHANGED
@@ -1 +1 @@
1
- {"version":3,"sources":["../src/define/html.ts","../src/define/auto-register.ts","../src/func/index.ts","../src/hooks/useTSPurifier.ts","../src/hooks/useTSEvent.ts","../src/hooks/useTSParams.ts","../src/hooks/useTSExtract.ts","../src/hooks/useTSAllElements.ts","../src/hooks/useTSElements.ts","../src/hooks/useIntialDOM.ts","../src/hooks/useTSAnchorSingle.ts","../src/hooks/useTSMetaData.ts","../src/hooks/useTSCSP.ts","../src/hooks/useTSComponent.ts","../src/hooks/useTSCollection.ts","../src/hooks/useTSSelect.ts","../src/hooks/useTSAuth.ts","../src/hooks/useTSForEach.ts","../src/hooks/useTSNavigate.ts","../src/hooks/useTSOutlet.ts","../src/hooks/useReactivity.ts","../src/hooks/useTSHashAnchor.ts","../src/hooks/useTSAnchor.ts","../src/hooks/useTSNoReload.ts","../src/hooks/useTSAnchorMount.ts","../src/hooks/useTSInitializedBrython.ts","../src/hooks/useTSLazy.ts","../src/routes/class/Router.class.ts","../src/store/useTSParam.store.ts","../index.mts"],"sourcesContent":["function sanitize(input: unknown): string {\r\n // Always convert to string first\r\n const str = input === null || input === undefined ? \"\" : String(input);\r\n\r\n return str\r\n // remove <script>, <iframe>, <object>, <embed>, <link>, <style> blocks\r\n .replace(/<\\s*(script|iframe|object|embed|link|style)[^>]*>.*?<\\s*\\/\\s*\\1\\s*>/gi, \"\")\r\n // remove opening dangerous tags without closing\r\n .replace(/<\\s*(script|iframe|object|embed|link|style)[^>]*>/gi, \"\")\r\n // strip inline event handlers like onclick=, onerror=, etc.\r\n .replace(/\\son\\w+\\s*=\\s*(['\"]).*?\\1/gi, \"\")\r\n // block javascript: URLs\r\n .replace(/\\s(href|src)\\s*=\\s*(['\"])\\s*javascript:[^'\"]*\\2/gi, \"\");\r\n}\r\n\r\nexport function html(strings: TemplateStringsArray, ...values: unknown[]): string {\r\n return strings.reduce((result, str, i) => {\r\n const safeValue = i < values.length ? sanitize(values[i]) : \"\";\r\n return result + str + safeValue;\r\n }, \"\");\r\n}\r\n","// auto-register-runtime.ts\r\nfunction autoRegister() {\r\n const allTags = new Set<string>();\r\n document.querySelectorAll('*').forEach((el) => {\r\n const tagName = el.tagName.toLowerCase();\r\n if (!tagName.includes('-')) return; // Only register custom tags with a dash\r\n allTags.add(tagName);\r\n });\r\n\r\n allTags.forEach(tag => {\r\n if (!customElements.get(tag)) {\r\n customElements.define(tag, class extends HTMLElement {\r\n connectedCallback() {\r\n this.innerHTML = `<div style=\"padding:10px;background:#eee;\">${tag} (Auto)</div>`;\r\n }\r\n });\r\n }\r\n });\r\n}\r\n\r\n\r\nexport { autoRegister };","// ✅ sanitize HTML but allow harmless tags\r\nconst sanitizeHtml = (str: string) => {\r\n return str\r\n // remove <script>, <iframe>, <object>, <embed>, <link>, <meta>, <style>\r\n .replace(/<\\/?(script|iframe|object|embed|link|meta|style)[^>]*>/gi, \"\")\r\n // remove any attribute that starts with \"on\" (onerror, onclick, etc.)\r\n .replace(/\\s+on[a-z]+\\s*=\\s*(\"[^\"]*\"|'[^']*'|[^\\s>]+)/gi, \"\")\r\n // block javascript: in href/src\r\n .replace(/\\s+(href|src)\\s*=\\s*(['\"]?)\\s*javascript:[^'\"\\s>]*/gi, \"\")\r\n}\r\n\r\n// ✅ mapper with sanitization\r\nconst mapper = (arr: string[] | undefined) =>\r\n arr?.map((item) => sanitizeHtml(item)).join(\"\") ?? \"\"\r\n\r\nexport { mapper }\r\n","import DOMPurify from \"dompurify\";\r\nimport type { Config } from \"dompurify\";\r\n\r\ntype TSPurifier = (input: string | HTMLElement, config?: Config) => string;\r\n\r\nexport const useTSPurifier: TSPurifier = (\r\n input,\r\n config?\r\n) => {\r\n const defaultConfig: Config = {\r\n ADD_TAGS: [\"my-custom-tag\"],\r\n };\r\n\r\n const mergedConfig: Config = { ...defaultConfig, ...config };\r\n\r\n if (typeof input === \"string\") {\r\n return DOMPurify.sanitize(input, mergedConfig);\r\n } else {\r\n return DOMPurify.sanitize(input.innerHTML, mergedConfig);\r\n }\r\n};\r\n","type TSEvent = (\r\n id: string | Document,\r\n eventType: keyof HTMLElementEventMap,\r\n handler: (event: HTMLElementEventMap[keyof HTMLElementEventMap]) => void\r\n) => void;\r\n\r\nexport const useTSEvent: TSEvent = (\r\n id,\r\n eventType,\r\n handler\r\n) => {\r\n if (typeof id === 'string') {\r\n const element = document.getElementById(id);\r\n if (element) {\r\n element.addEventListener(\r\n eventType,\r\n handler as EventListenerOrEventListenerObject\r\n );\r\n } else {\r\n console.warn(`Element with id '${id}' not found.`);\r\n }\r\n } else if (id === document) {\r\n document.addEventListener(\r\n eventType,\r\n handler as EventListenerOrEventListenerObject\r\n );\r\n } else {\r\n console.warn(`Invalid id parameter provided.`);\r\n }\r\n};\r\n","// utils/hooks/useTSParams.ts\r\nimport { createStore } from 'zustand/vanilla';\r\nimport DOMPurify from 'dompurify';\r\n\r\ntype ParamStore = {\r\n params: Record<string, string>;\r\n query: Record<string, string>;\r\n setFromPattern: (pattern: MustURL) => void;\r\n getParam: (key: string) => string | undefined;\r\n getQuery: (key: string) => string | undefined;\r\n};\r\n\r\ntype MustURL = `/${string}`;\r\n\r\nfunction extractPatternParams(pattern: MustURL, path: string): Record<string, string> {\r\n const paramNames: string[] = [];\r\n const regexPattern = pattern.replace(/:[^/]+/g, (match) => {\r\n paramNames.push(match.slice(1));\r\n return '([^/]+)';\r\n });\r\n\r\n const regex = new RegExp(`^${regexPattern}$`);\r\n const match = path.match(regex);\r\n const result: Record<string, string> = {};\r\n\r\n if (match) {\r\n paramNames.forEach((name, i) => {\r\n result[name] = DOMPurify.sanitize(match[i + 1] ?? '');\r\n });\r\n }\r\n\r\n return result;\r\n}\r\n\r\nfunction extractQueryParams(search: MustURL): Record<string, string> {\r\n const result: Record<string, string> = {};\r\n const urlSearchParams = new URLSearchParams(search);\r\n\r\n for (const [key, value] of urlSearchParams.entries()) {\r\n result[key] = DOMPurify.sanitize(value);\r\n }\r\n\r\n return result;\r\n}\r\n\r\nexport const useTSParams = createStore<ParamStore>((set, get) => ({\r\n params: {},\r\n query: {},\r\n setFromPattern: (pattern: MustURL) => {\r\n const path = window.location.pathname;\r\n const params = extractPatternParams(pattern, path);\r\n const query = extractQueryParams(window.location.search as MustURL);\r\n set({ params, query });\r\n },\r\n getParam: (key: string) => get().params[key],\r\n getQuery: (key: string) => get().query[key],\r\n}));\r\n","import { useTSParams } from './useTSParams';\r\n\r\ntype MustURL = `/${string}`;\r\n\r\nexport function useTSExtractParams(pattern: MustURL) {\r\n const store = useTSParams.getState();\r\n\r\n // Populate internal param/query store\r\n store.setFromPattern(pattern);\r\n\r\n const params = store.params;\r\n const query = store.query;\r\n\r\n return { ...params, ...query };\r\n}\r\n","export const useTSEventAll = <T extends Event>(\r\n selector: string,\r\n eventType: keyof HTMLElementEventMap,\r\n handler: (event: T) => void\r\n) => {\r\n const elements = document.querySelectorAll(selector);\r\n elements.forEach(element => {\r\n element.addEventListener(eventType, handler as EventListener);\r\n });\r\n\r\n return () => {\r\n elements.forEach(element => {\r\n element.removeEventListener(eventType, handler as EventListener);\r\n });\r\n };\r\n};\r\n\r\nexport const useTSEventSelectAll = <T extends Event>(\r\n selectors: string[],\r\n eventType: keyof HTMLElementEventMap,\r\n handler: (event: T) => void\r\n) => {\r\n const elements: NodeListOf<HTMLElement>[] = [];\r\n\r\n selectors.forEach(selector => {\r\n const selectedElements = document.querySelectorAll(\r\n selector\r\n ) as NodeListOf<HTMLElement>;\r\n selectedElements.forEach(element => {\r\n element.addEventListener(eventType, handler as EventListener);\r\n });\r\n elements.push(selectedElements);\r\n });\r\n\r\n return () => {\r\n elements.forEach(nodeList => {\r\n nodeList.forEach(element => {\r\n element.removeEventListener(eventType, handler as EventListener);\r\n });\r\n });\r\n };\r\n};\r\n","import DOMPurify, { Config } from \"dompurify\";\r\n\r\ntype TSElements = (\r\n htmlElement: HTMLElement,\r\n element: string,\r\n config?: Config\r\n) => void;\r\n\r\nexport const useTSElements: TSElements = (htmlElement, element, config) => {\r\n const defaultConfig: Config = {\r\n USE_PROFILES: { svg: true, html: true },\r\n ALLOWED_TAGS: [\r\n \"svg\", \"path\", \"circle\", \"rect\", \"line\", \"polyline\", \"polygon\", \"g\",\r\n \"main\", \"div\", \"h1\", \"h2\", \"h3\", \"h4\", \"h5\", \"h6\",\r\n \"p\", \"button\", \"span\", \"a\", \"img\", \"input\", \"ul\", \"li\", \"i\"\r\n ],\r\n ALLOWED_ATTR: [\r\n \"class\", \"id\", \"href\", \"src\", \"alt\", \"fill\", \"stroke\", \"stroke-width\",\r\n \"viewBox\", \"xmlns\", \"d\", \"x\", \"y\", \"cx\", \"cy\", \"r\", \"width\", \"height\"\r\n ],\r\n FORBID_TAGS: [\"script\", \"iframe\"],\r\n ALLOWED_URI_REGEXP:\r\n /^(?:(?:https?|mailto|tel|ftp):|[^a-z]|[a-z+.\\-]+(?:[^a-z+.\\-:]|$))/i,\r\n ...config,\r\n };\r\n\r\n // ✅ Allow custom elements dynamically\r\n DOMPurify.addHook(\"uponSanitizeElement\", (node, data) => {\r\n const tagName = data.tagName.toLowerCase();\r\n if (tagName.includes(\"-\")) {\r\n data.allowedTags[tagName] = true;\r\n }\r\n });\r\n\r\n // ✅ Strip dangerous event handlers\r\n DOMPurify.addHook(\"uponSanitizeAttribute\", (node, data) => {\r\n if (data.attrName && data.attrName.toLowerCase().startsWith(\"on\")) {\r\n data.keepAttr = false;\r\n }\r\n });\r\n\r\n const sanitizedContent = DOMPurify.sanitize(element, defaultConfig);\r\n\r\n if (htmlElement.innerHTML !== sanitizedContent) {\r\n htmlElement.innerHTML = sanitizedContent;\r\n }\r\n};\r\n\r\n","import DOMPurify from \"dompurify\"\r\n\r\nlet previousHTML: string | null = null\r\n\r\ntype TSInitialDOM = (id: string, mount: (el: HTMLElement) => void) => void;\r\n\r\nexport const useInitialDOM: TSInitialDOM = (id, mount) => {\r\n // SSR guard\r\n if (typeof document === \"undefined\") return\r\n\r\n const targetElement = document.getElementById(id)\r\n if (!targetElement) return\r\n\r\n const currentHTML = targetElement.innerHTML\r\n const sanitizedHTML = DOMPurify.sanitize(currentHTML)\r\n\r\n if (previousHTML !== null && sanitizedHTML !== previousHTML) {\r\n // DOM changed externally — reset and remount in a temp container\r\n const fallbackEl = document.createElement(\"div\")\r\n mount(fallbackEl)\r\n targetElement.innerHTML = previousHTML\r\n } else {\r\n // First time or same sanitized DOM — mount to target\r\n previousHTML = sanitizedHTML\r\n mount(targetElement)\r\n }\r\n}\r\n","import DOMPurify from \"dompurify\";\r\n\r\ndeclare global {\r\n interface Window {\r\n __anchorSinglePopstateHandlerAttached?: boolean;\r\n }\r\n}\r\n\r\ntype AnchorSingle = (\r\n element: HTMLAnchorElement | null,\r\n href: string,\r\n ariaLabel: string,\r\n className?: string,\r\n childElement?: HTMLElement | null\r\n) => void;\r\n\r\n// Attach popstate listener only in the browser\r\nif (typeof window !== \"undefined\" && !window.__anchorSinglePopstateHandlerAttached) {\r\n window.addEventListener(\"popstate\", (e) => {\r\n const state = e.state as { scrollPosition?: number };\r\n if (state?.scrollPosition !== undefined) {\r\n window.scrollTo(0, state.scrollPosition);\r\n }\r\n });\r\n window.__anchorSinglePopstateHandlerAttached = true;\r\n}\r\n\r\nexport const useAnchorSingle: AnchorSingle = (\r\n element,\r\n href,\r\n ariaLabel,\r\n className = \"\",\r\n childElement = null\r\n) => {\r\n if (!element) return;\r\n\r\n // Sanitize string inputs\r\n const sanitizedHref = DOMPurify.sanitize(href, { ALLOWED_URI_REGEXP: /^(https?:|\\/)/ });\r\n const sanitizedAriaLabel = DOMPurify.sanitize(ariaLabel, { USE_PROFILES: { html: false } });\r\n\r\n element.setAttribute(\"href\", sanitizedHref);\r\n element.setAttribute(\"aria-label\", sanitizedAriaLabel);\r\n\r\n if (className) {\r\n element.className = className.trim();\r\n }\r\n\r\n if (childElement) {\r\n element.replaceChildren(childElement);\r\n }\r\n\r\n // Event binding only in browser\r\n if (typeof window !== \"undefined\") {\r\n element.addEventListener(\"click\", (e) => {\r\n e.preventDefault();\r\n const target = e.currentTarget as HTMLAnchorElement;\r\n const hrefAttr = target.getAttribute(\"href\");\r\n if (hrefAttr) {\r\n const scrollPosition = window.scrollY;\r\n window.scrollTo(0, 0);\r\n window.history.pushState({ scrollPosition }, \"\", hrefAttr);\r\n dispatchEvent(new PopStateEvent(\"popstate\"));\r\n }\r\n });\r\n }\r\n};\r\n","import DOMPurify from \"dompurify\";\r\nimport { useTSCSP } from \"./useTSCSP\";\r\n\r\ntype SEOConfig = {\r\n name?: string;\r\n description?: string;\r\n author?: string;\r\n}\r\n\r\ntype CSPConfig = {\r\n scriptSrc?: string;\r\n styleSrc?: string;\r\n objectSrc?: string;\r\n connectSrc?: string[];\r\n reportOnly?: boolean;\r\n}\r\n\r\ntype SEOHandler = {\r\n setName: (name: string) => void;\r\n setDescription: (description: string) => void;\r\n setAuthor: (author: string) => void;\r\n getName: () => string;\r\n getDescription: () => string;\r\n getAuthor: () => string;\r\n getAllMetaData: () => SEOConfig;\r\n appendMetaTagsToHead: () => void;\r\n}\r\n\r\nexport const useTSMetaData = (\r\n config: SEOConfig,\r\n cspConfig?: CSPConfig\r\n): SEOHandler => {\r\n let metaData: SEOConfig = {\r\n name: DOMPurify.sanitize(config.name || \"\"),\r\n description: DOMPurify.sanitize(\r\n config.description || \"Default description\"\r\n ),\r\n author: DOMPurify.sanitize(config.author || \"\"),\r\n };\r\n\r\n const setName = (name: string): void => {\r\n metaData.name = DOMPurify.sanitize(name);\r\n updateMetaTag(\"name\", metaData.name);\r\n };\r\n\r\n const setDescription = (description: string): void => {\r\n metaData.description = DOMPurify.sanitize(description);\r\n updateMetaTag(\"description\", metaData.description);\r\n };\r\n\r\n const setAuthor = (author: string): void => {\r\n metaData.author = DOMPurify.sanitize(author);\r\n updateMetaTag(\"author\", metaData.author);\r\n };\r\n\r\n const getName = (): string => {\r\n return metaData.name!;\r\n };\r\n\r\n const getDescription = (): string => {\r\n return metaData.description!;\r\n };\r\n\r\n const getAuthor = (): string => {\r\n return metaData.author!;\r\n };\r\n\r\n const getAllMetaData = (): SEOConfig => {\r\n return metaData;\r\n };\r\n\r\n const createMetaTag = (name: string, content: string) => {\r\n const metaTag = document.createElement(\"meta\");\r\n metaTag.setAttribute(\"name\", name);\r\n metaTag.setAttribute(\"content\", content);\r\n document.head.appendChild(metaTag);\r\n };\r\n\r\n const updateMetaTag = (name: string, content: string) => {\r\n let metaTag = document.querySelector(`meta[name=\"${name}\"]`);\r\n if (metaTag) {\r\n metaTag.setAttribute(\"content\", content);\r\n } else {\r\n createMetaTag(name, content);\r\n }\r\n };\r\n\r\n const appendMetaTagsToHead = () => {\r\n updateMetaTag(\"name\", metaData.name!);\r\n updateMetaTag(\"description\", metaData.description!);\r\n updateMetaTag(\"author\", metaData.author!);\r\n };\r\n\r\n // Integrate with useTSCSP for CSP enforcement\r\n if (cspConfig) {\r\n useTSCSP(\r\n cspConfig.scriptSrc,\r\n cspConfig.styleSrc,\r\n cspConfig.objectSrc,\r\n Array.isArray(cspConfig.connectSrc) ? cspConfig.connectSrc.join(\" \") : cspConfig.connectSrc,\r\n cspConfig.reportOnly !== undefined ? String(cspConfig.reportOnly) : undefined\r\n );\r\n }\r\n\r\n appendMetaTagsToHead();\r\n\r\n return {\r\n setName,\r\n setDescription,\r\n setAuthor,\r\n getName,\r\n getDescription,\r\n getAuthor,\r\n getAllMetaData,\r\n appendMetaTagsToHead,\r\n };\r\n};\r\n","export const useTSCSP = (\r\n scriptSrc = `'self' 'nonce-rAnd0m123' 'unsafe-inline' 'unsafe-eval'`,\r\n styleSrc = \"'self' 'nonce-rAnd0m123'\", // Use nonce for inline styles\r\n objectSrc = \"'none'\",\r\n fontSrc = \"'self' https://fonts.googleapis.com https://fonts.gstatic.com\",\r\n imgSrc = \"'self' https://blogger.googleusercontent.com\",\r\n connectSrc = [\r\n \"'self'\",\r\n \"https://fonts.googleapis.com\",\r\n \"https://fonts.gstatic.com\",\r\n \"https://www.google.com/maps/\",\r\n ],\r\n frameSrc = \"'self' https://www.youtube.com\", // Add frame-src for embedding\r\n baseUri = \"'self'\",\r\n reportUri = \"/csp-report\",\r\n reportOnly = false\r\n) => {\r\n const addOrUpdateCSPMeta = () => {\r\n try {\r\n let metaElement = document.querySelector(\r\n 'meta[http-equiv=\"Content-Security-Policy\"]'\r\n );\r\n if (!metaElement) {\r\n metaElement = document.createElement(\"meta\");\r\n metaElement.setAttribute(\"http-equiv\", \"Content-Security-Policy\");\r\n document.head.appendChild(metaElement);\r\n }\r\n\r\n const reportUriDirective = reportOnly ? `report-uri ${reportUri};` : \"\";\r\n metaElement.setAttribute(\r\n \"content\",\r\n `default-src 'self'; script-src ${scriptSrc}; style-src ${styleSrc}; object-src ${objectSrc}; font-src ${fontSrc}; img-src ${imgSrc}; connect-src ${connectSrc.join(\r\n \" \"\r\n )}; frame-src ${frameSrc}; base-uri ${baseUri}; ${reportUriDirective}`\r\n );\r\n } catch (error) {\r\n console.error(\"Error adding CSP meta element:\", error);\r\n }\r\n };\r\n\r\n if (document.readyState === \"loading\") {\r\n document.addEventListener(\"DOMContentLoaded\", addOrUpdateCSPMeta);\r\n } else {\r\n addOrUpdateCSPMeta();\r\n }\r\n};\r\n","import DOMPurify from \"dompurify\";\r\n\r\ntype TSComponent = (\r\n id: string,\r\n parent: HTMLElement,\r\n element: Function,\r\n params?: any,\r\n params2?: any\r\n) => void;\r\n\r\nexport const useTSComponent: TSComponent = (\r\n id,\r\n parent,\r\n element,\r\n params,\r\n params2\r\n) => {\r\n const selector = `#${id}`;\r\n const matches = parent.querySelectorAll<HTMLElement>(selector);\r\n\r\n // 1. Missing element check\r\n if (matches.length === 0) {\r\n throw new Error(`[useTSComponent] No element found with id '${id}' in the given parent.`);\r\n }\r\n\r\n // 2. Duplicate ID check\r\n if (matches.length > 1) {\r\n throw new Error(`[useTSComponent] Duplicate id '${id}' detected. Found ${matches.length} elements.`);\r\n }\r\n\r\n const target = matches[0];\r\n\r\n // 3. Sanitize the target’s existing HTML content\r\n target.innerHTML = DOMPurify.sanitize(target.innerHTML, { USE_PROFILES: { html: true } });\r\n\r\n // 4. Call the component function with the target\r\n element(target, params, params2);\r\n};\r\n","import { useTSComponent } from \"./useTSComponent\";\r\n\r\ntype TSCollection = (\r\n collections: string[],\r\n DOM: HTMLElement,\r\n elements: Function[],\r\n params?: any[]\r\n) => void;\r\n\r\nexport const useTSCollection: TSCollection = (\r\n collections,\r\n DOM,\r\n elements,\r\n params = []\r\n) => {\r\n const seenIds = new Set<string>();\r\n\r\n collections.forEach((id, index) => {\r\n // Check for duplicate IDs in the collection list itself\r\n if (seenIds.has(id)) {\r\n console.warn(`[useTSCollection] Duplicate ID in collection array: \"${id}\" — skipping.`);\r\n return;\r\n }\r\n seenIds.add(id);\r\n\r\n // Check for duplicates already in DOM\r\n const matches = DOM.querySelectorAll(`#${id}`);\r\n if (matches.length > 1) {\r\n console.warn(\r\n `[useTSCollection] Duplicate ID in DOM: \"${id}\" (${matches.length} elements found) — skipping component mount.`\r\n );\r\n return;\r\n }\r\n\r\n const elementFn = elements[index];\r\n const param = Array.isArray(params) ? params[index] : undefined;\r\n\r\n if (typeof elementFn === \"function\") {\r\n useTSComponent(id, DOM, elementFn, param);\r\n } else {\r\n console.warn(`[useTSCollection] No valid component function found for ID: \"${id}\"`);\r\n }\r\n });\r\n};\r\n","type TSSelect = <T extends Element = HTMLElement>(\r\n selector: string,\r\n scope?: HTMLElement\r\n) => T | null;\r\n\r\nconst useTSSelect: TSSelect = <T extends Element = HTMLElement>(\r\n selector: string,\r\n scope?: HTMLElement\r\n): T | null => {\r\n const root = scope ?? document;\r\n const elements = root.querySelectorAll<T>(selector);\r\n\r\n if (elements.length === 0) {\r\n if (process.env.NODE_ENV !== \"production\") {\r\n console.warn(`[useTSSelect] No element found for selector: '${selector}'`);\r\n }\r\n return null;\r\n }\r\n\r\n if (selector.startsWith(\"#\") && elements.length > 1) {\r\n if (process.env.NODE_ENV !== \"production\") {\r\n throw new Error(\r\n `[useTSSelect] Duplicate ID detected: '${selector}'. Found ${elements.length} elements with this ID.`\r\n );\r\n }\r\n return elements[0]; // fallback: just return first\r\n }\r\n\r\n if (elements.length > 1) {\r\n if (process.env.NODE_ENV !== \"production\") {\r\n console.warn(\r\n `[useTSSelect] Multiple elements found for selector: '${selector}'. Returning the first one.`\r\n );\r\n }\r\n }\r\n\r\n return elements[0];\r\n};\r\n\r\nexport { useTSSelect };\r\n","import { jwtDecode } from \"jwt-decode\";\r\n\r\nexport const useTSAuth = (_Component: HTMLElement | void, loginUrl: string) => {\r\n const token = localStorage.getItem(\"token\");\r\n\r\n if (!token) {\r\n // Redirect to login page if token is missing\r\n window.location.href = loginUrl;\r\n return null; // Return null when redirecting\r\n }\r\n\r\n try {\r\n const decodedToken: any = jwtDecode(token);\r\n\r\n // Example: Check if the token has expired\r\n const currentTime = Date.now() / 1000;\r\n if (decodedToken.exp && decodedToken.exp < currentTime) {\r\n console.error(\"Token has expired\");\r\n window.localStorage.removeItem(\"token\");\r\n window.location.href = loginUrl;\r\n return null; // Return null when redirecting\r\n }\r\n\r\n // If the user is authenticated, return the component\r\n return null;\r\n } catch (error) {\r\n console.error(\"Invalid token:\", error);\r\n // Redirect to login page if token decoding fails\r\n window.location.href = loginUrl;\r\n return null; // Return null when redirecting\r\n }\r\n};\r\n","\r\ntype TSElementEach = (\r\n elements: NodeListOf<HTMLElement> | HTMLElement[],\r\n events: (keyof HTMLElementEventMap)[],\r\n callback: (element: HTMLElement, event: Event) => void\r\n) => void;\r\n\r\nexport const useTSElementEach: TSElementEach = (\r\n elements,\r\n events,\r\n callback\r\n) => {\r\n elements.forEach(element => {\r\n events.forEach(eventType => {\r\n element.addEventListener(eventType, event => {\r\n callback(element, event);\r\n });\r\n });\r\n });\r\n};\r\n","export const useTSNavigate = () => {\r\n const back = () => window.history.back();\r\n const forward = () => window.history.forward();\r\n\r\n return {\r\n back,\r\n forward,\r\n };\r\n};\r\n","// types.ts\r\nexport type OutletComponent = (DOM: HTMLElement) => void;\r\n\r\nexport type ChildRoute = {\r\n path: string;\r\n outlet: string;\r\n element: OutletComponent;\r\n};\r\n\r\nexport type Route = {\r\n path: string;\r\n element: (DOM: HTMLElement) => void;\r\n children?: ChildRoute[];\r\n};\r\n\r\n// You don't actually need to import the class TSRouter type.\r\n// Instead, export a cleaner interface with routes.\r\nexport interface RouterInstance {\r\n routes: Route[];\r\n}\r\n\r\n\r\ntype OutletOptions = {\r\n path: string;\r\n component: OutletComponent;\r\n};\r\n\r\nexport const useTSOutlet = (\r\n selector: string,\r\n outlets: OutletOptions[]\r\n): void => {\r\n const outletDOM = document.querySelector<HTMLElement>(`#${selector}`)\r\n || document.querySelector<HTMLElement>(`.${selector}`);\r\n\r\n if (!outletDOM) return;\r\n\r\n const currentPath = window.location.pathname.replace(/\\/$/, \"\");\r\n\r\n for (const outlet of outlets) {\r\n const base = outlet.path.replace(/\\/$/, \"\");\r\n\r\n // Match exact or nested path (e.g., /openai/child/1)\r\n if (currentPath === base || currentPath.startsWith(`${base}/`)) {\r\n outlet.component(outletDOM);\r\n break;\r\n }\r\n }\r\n};\r\n\r\n\r\nexport function renderChildRoutes(DOM: HTMLElement, router: RouterInstance): void {\r\n const pathname = window.location.pathname.replace(/\\/$/, \"\");\r\n\r\n router.routes.forEach((route) => {\r\n if (!route.children?.length) return;\r\n\r\n route.children.forEach((child) => {\r\n const childPath = child.path.replace(/\\/$/, \"\");\r\n\r\n if (pathname === childPath || pathname.startsWith(`${childPath}/`)) {\r\n const outlet = DOM.querySelector(`#${child.outlet}`)\r\n || DOM.querySelector(`.${child.outlet}`);\r\n if (outlet instanceof HTMLElement && child.element) {\r\n child.element(outlet);\r\n }\r\n }\r\n });\r\n });\r\n}","// useTSReactivity.ts\r\nimport { createStore } from 'zustand/vanilla';\r\n\r\ntype Listener<T> = (value: T) => void;\r\n\r\ninterface Signal<T> {\r\n get: () => T;\r\n set: (newValue: T) => void;\r\n subscribe: (listener: Listener<T>) => () => void;\r\n}\r\n\r\nexport function createSignal<T>(initialValue: T): Signal<T> {\r\n const store = createStore<{ value: T }>(() => ({ value: initialValue }));\r\n const listeners = new Set<Listener<T>>();\r\n\r\n return {\r\n get: () => store.getState().value,\r\n set: (newValue: T) => {\r\n store.setState({ value: newValue });\r\n listeners.forEach((listener) => listener(newValue));\r\n },\r\n subscribe: (listener: Listener<T>) => {\r\n listeners.add(listener);\r\n listener(store.getState().value); // Trigger immediately\r\n return () => listeners.delete(listener);\r\n },\r\n };\r\n}\r\n\r\ntype CleanupFn = () => void;\r\n\r\nexport function createEffect(effectFn: () => void | CleanupFn): void {\r\n const cleanup = effectFn();\r\n\r\n // Optional: return a way to dispose the effect manually\r\n if (typeof cleanup === 'function') {\r\n // You may store this and call it later if needed\r\n cleanup();\r\n }\r\n}\r\n","import { useTSElementEach } from './useTSForEach';\r\n\r\n\r\nconst useTSHashAnchor = () => {\r\n const links = document.querySelectorAll<HTMLAnchorElement>('a[href^=\"#\"]');\r\n\r\n useTSElementEach(\r\n links,\r\n ['click'],\r\n (element, e) => {\r\n e.preventDefault();\r\n const targetId = element.getAttribute('href')?.substring(1);\r\n const targetElement = targetId ? document.getElementById(targetId) : null;\r\n\r\n if (targetElement) {\r\n targetElement.scrollIntoView({\r\n behavior: 'smooth',\r\n block: 'start'\r\n });\r\n }\r\n }\r\n );\r\n}\r\n\r\nexport { useTSHashAnchor }","import { debounce } from 'lodash-es';\r\n\r\nlet sanitizeInput = (input: string): string => input;\r\n\r\nif (typeof window !== 'undefined' && typeof document !== 'undefined') {\r\n sanitizeInput = (input: string): string => {\r\n const element = document.createElement(\"div\");\r\n element.innerText = input;\r\n return element.innerHTML;\r\n };\r\n}\r\n\r\ntype AnchorInput =\r\n | NodeListOf<HTMLAnchorElement>\r\n | HTMLAnchorElement[]\r\n | HTMLAnchorElement\r\n | null\r\n | undefined;\r\n\r\nconst _enhanceAnchors = debounce((anchors: AnchorInput) => {\r\n const resolvedAnchors: HTMLAnchorElement[] = (() => {\r\n if (!anchors) return Array.from(document.querySelectorAll(\"a\"));\r\n if (Array.isArray(anchors)) return anchors;\r\n if (anchors instanceof HTMLAnchorElement) return [anchors];\r\n return Array.from(anchors);\r\n })();\r\n\r\n resolvedAnchors.forEach(anchor => {\r\n if (!anchor || anchor.dataset.anchorEnhanced === 'true') return;\r\n anchor.dataset.anchorEnhanced = 'true';\r\n\r\n // Sanitize attributes\r\n const originalHref = anchor.getAttribute(\"href\") || \"#\";\r\n const sanitizedHref = sanitizeInput(originalHref);\r\n anchor.setAttribute(\"href\", sanitizedHref);\r\n\r\n const originalClassName = anchor.getAttribute(\"class\") || \"\";\r\n anchor.setAttribute(\"class\", sanitizeInput(originalClassName));\r\n\r\n const ariaLabel = anchor.getAttribute(\"aria-label\");\r\n if (ariaLabel) {\r\n anchor.setAttribute(\"aria-label\", sanitizeInput(ariaLabel));\r\n }\r\n\r\n // Keep child elements safe (optional — you can remove this block if not needed)\r\n const child = anchor.querySelector(\":scope > *\") as HTMLElement;\r\n if (child) {\r\n anchor.innerHTML = \"\";\r\n anchor.appendChild(child);\r\n }\r\n\r\n // Skip attaching click listener if:\r\n // - It's a hash link (in-page navigation)\r\n // - It's an external link\r\n const href = anchor.getAttribute(\"href\") || \"\";\r\n if (href.startsWith(\"#\")) return; // Let browser handle hash scrolling normally\r\n\r\n try {\r\n const url = new URL(href, window.location.href);\r\n if (url.origin !== window.location.origin) return; // external link\r\n } catch {\r\n return; // invalid URL — skip\r\n }\r\n\r\n // Intercept same-origin navigation for SPA\r\n anchor.addEventListener(\"click\", (e: MouseEvent) => {\r\n e.preventDefault();\r\n try {\r\n const url = new URL(href, window.location.href);\r\n window.history.pushState({}, \"\", url.pathname + url.search + url.hash);\r\n window.dispatchEvent(new PopStateEvent(\"popstate\"));\r\n } catch (err) {\r\n console.error(\"Invalid URL in anchor:\", href, err);\r\n }\r\n });\r\n });\r\n}, 50);\r\n\r\nexport const useAnchor = (anchors?: AnchorInput): void => {\r\n _enhanceAnchors(anchors);\r\n};\r\n","import { useAnchor } from './useTSAnchor';\r\n\r\nconst useTSNoReload = () => {\r\n const a = document.querySelectorAll(\"a\") as NodeListOf<HTMLAnchorElement>;\r\n return useAnchor(a);\r\n}\r\n\r\nexport { useTSNoReload };","import { useTSHashAnchor } from \"./useTSHashAnchor\";\r\nimport { useTSNoReload } from \"./useTSNoReload\";\r\n\r\nconst useTSAnchorMount = () => {\r\n useTSNoReload();\r\n useTSHashAnchor();\r\n};\r\n\r\nexport { useTSAnchorMount };","// src/loadBrython.ts\r\ntype LoadBrython = (src: string) => Promise<void>;\r\n\r\ndeclare global {\r\n interface Window {\r\n brython: Function;\r\n }\r\n}\r\n\r\nconst useTSloadBrython = async () => {\r\n const brythonJS = \"https://cdn.jsdelivr.net/npm/brython@3/brython.min.js\";\r\n const brythonStdlib = \"https://cdn.jsdelivr.net/npm/brython@3/brython_stdlib.js\";\r\n\r\n // Utility function to load a script\r\n const loadScript: LoadBrython = (src) => {\r\n return new Promise((resolve, reject) => {\r\n const script = document.createElement(\"script\");\r\n script.src = src;\r\n script.onload = () => resolve();\r\n script.onerror = () => reject(new Error(`Failed to load ${src}`));\r\n document.head.appendChild(script);\r\n });\r\n };\r\n\r\n // Load both scripts sequentially\r\n await loadScript(brythonJS);\r\n await loadScript(brythonStdlib);\r\n\r\n // Call brython() after scripts are loaded\r\n if (typeof window.brython === \"function\") {\r\n window.brython();\r\n } else {\r\n console.error(\"Brython did not load correctly.\");\r\n }\r\n};\r\n\r\ntype RequirePy = `${string}.py`;\r\n\r\ntype LoadPy = (src: RequirePy) => Promise<void>;\r\n\r\nconst loadPyFiles: LoadPy = (src) =>\r\n new Promise((resolve, reject) => {\r\n const script = document.createElement(\"script\");\r\n script.type = \"text/python\";\r\n script.src = `/src/python/${src}`;\r\n script.onload = () => resolve();\r\n script.onerror = () => reject(new Error(`Failed to load ${src}`));\r\n document.body.appendChild(script);\r\n });\r\n\r\nexport { useTSloadBrython, loadPyFiles };\r\n","export function useTSLazy(factory: () => Promise<any>) {\r\n let cached: any | null = null;\r\n\r\n return async (el?: HTMLElement, props?: any) => {\r\n try {\r\n if (!cached) {\r\n const mod = await factory();\r\n cached = mod.default || mod;\r\n }\r\n\r\n // If it's a component function (Vanilla TS style)\r\n if (typeof cached === \"function\") {\r\n return cached(el, props);\r\n }\r\n\r\n // If it's already an HTMLElement\r\n if (cached instanceof HTMLElement) {\r\n el?.appendChild(cached);\r\n return;\r\n }\r\n\r\n // If it's a plain object with render()\r\n if (cached && typeof cached.render === \"function\") {\r\n return cached.render(el, props);\r\n }\r\n\r\n console.warn(\"useTSLazy: Unsupported module type\", cached);\r\n } catch (err) {\r\n console.error(\"useTSLazy failed:\", err);\r\n }\r\n };\r\n}\r\n","import DOMPurify from \"dompurify\";\r\nimport { tsParamsStore } from \"../../store\";\r\n\r\ntype RouteCallback = (\r\n errorElement?: HTMLElement,\r\n params?: Record<string, string>,\r\n query?: Record<string, string>\r\n) => void;\r\n\r\ninterface RouteConfig {\r\n path: string;\r\n routeto?: string;\r\n element: RouteCallback;\r\n errorElement?: RouteCallback;\r\n children?: RouteConfig[];\r\n params?: Record<string, string>;\r\n}\r\n\r\nexport class TSRouter {\r\n private routes: RouteConfig[] = [];\r\n private expectedParams: Set<string>;\r\n\r\n constructor(routes: RouteConfig[], expectedParams: string[]) {\r\n this.routes = routes;\r\n this.expectedParams = new Set(expectedParams);\r\n window.addEventListener(\"popstate\", this.handlePopState.bind(this));\r\n this.handlePopState(); // Initial load\r\n }\r\n\r\n private handlePopState() {\r\n const currentPath = window.location.pathname;\r\n const currentSearch = window.location.search;\r\n const queryParams = this.parseQueryParams(currentSearch);\r\n\r\n const matchingRoute = this.findMatchingRoute(currentPath, this.routes);\r\n\r\n if (matchingRoute) {\r\n if (matchingRoute.routeto) {\r\n this.navigate(matchingRoute.routeto);\r\n return;\r\n }\r\n\r\n const sanitizedParams = this.filterAndSanitizeParams(matchingRoute.params);\r\n tsParamsStore.getState().setParams(sanitizedParams);\r\n tsParamsStore.getState().setQuery(queryParams);\r\n\r\n const errorElement = document.createElement(\"div\");\r\n\r\n matchingRoute.element?.(errorElement, sanitizedParams, queryParams);\r\n\r\n if (matchingRoute.children) {\r\n const nestedPath = currentPath.slice(matchingRoute.path.length);\r\n const childElement = errorElement.querySelector(\"#child\") as HTMLDivElement;\r\n if (childElement) {\r\n this.renderChildren(\r\n matchingRoute.children,\r\n nestedPath,\r\n childElement,\r\n sanitizedParams,\r\n queryParams\r\n );\r\n }\r\n }\r\n } else {\r\n const notFoundRoute = this.findMatchingRoute(\"*\", this.routes);\r\n if (notFoundRoute) {\r\n const fallbackParams = this.filterAndSanitizeParams(notFoundRoute.params);\r\n tsParamsStore.getState().setParams(fallbackParams);\r\n tsParamsStore.getState().setQuery(queryParams);\r\n\r\n const errorElement = document.createElement(\"div\");\r\n notFoundRoute.element?.(errorElement, fallbackParams, queryParams);\r\n }\r\n }\r\n }\r\n\r\n private renderChildren(\r\n children: RouteConfig[] | undefined,\r\n nestedPath: string,\r\n parentElement: HTMLElement,\r\n parentParams: Record<string, string>,\r\n queryParams: Record<string, string>\r\n ) {\r\n if (!children || children.length === 0) {\r\n const childElement = parentElement.querySelector(\"#child\") as HTMLDivElement;\r\n if (childElement) childElement.remove();\r\n return;\r\n }\r\n\r\n const matchingChild = this.findMatchingRoute(nestedPath, children);\r\n if (matchingChild) {\r\n const childElement = document.createElement(\"div\");\r\n childElement.id = \"child\";\r\n const mergedParams = { ...parentParams, ...matchingChild.params };\r\n const sanitizedParams = this.filterAndSanitizeParams(mergedParams);\r\n\r\n tsParamsStore.getState().setParams(sanitizedParams);\r\n tsParamsStore.getState().setQuery(queryParams);\r\n\r\n matchingChild.element?.(childElement, sanitizedParams, queryParams);\r\n parentElement.appendChild(childElement);\r\n\r\n if (matchingChild.children) {\r\n const nextNestedPath = nestedPath.slice(matchingChild.path.length);\r\n this.renderChildren(\r\n matchingChild.children,\r\n nextNestedPath,\r\n childElement,\r\n sanitizedParams,\r\n queryParams\r\n );\r\n }\r\n }\r\n }\r\n\r\n private parseQueryParams(search: string): Record<string, string> {\r\n const queryParams: Record<string, string> = {};\r\n const urlSearchParams = new URLSearchParams(search);\r\n\r\n for (const [key, value] of urlSearchParams.entries()) {\r\n if (this.expectedParams.has(key)) {\r\n queryParams[key] = DOMPurify.sanitize(value);\r\n }\r\n }\r\n\r\n return queryParams;\r\n }\r\n\r\n private findMatchingRoute(\r\n path: string,\r\n routes: RouteConfig[],\r\n inheritedParams: Record<string, string> = {}\r\n ): RouteConfig | undefined {\r\n for (const route of routes) {\r\n const routePath = route.path;\r\n const isDefaultRoute = routePath === \"*\";\r\n\r\n if (!isDefaultRoute) {\r\n const paramNames: string[] = [];\r\n const regexPattern = routePath.replace(/:[^\\s/]+/g, match => {\r\n paramNames.push(match.substring(1));\r\n return \"([^\\\\s/]+)\";\r\n });\r\n\r\n const regex = new RegExp(`^${regexPattern}(?:/|$)`);\r\n const match = path.match(regex);\r\n\r\n if (match) {\r\n const params: Record<string, string> = { ...inheritedParams };\r\n paramNames.forEach((name, index) => {\r\n params[name] = match[index + 1] ?? \"\";\r\n });\r\n\r\n if (route.children) {\r\n const nestedPath = path.slice(match[0].length);\r\n const matchingChild = this.findMatchingRoute(\r\n nestedPath,\r\n route.children,\r\n params\r\n );\r\n if (matchingChild) return matchingChild;\r\n }\r\n\r\n return { ...route, params };\r\n }\r\n } else {\r\n return route;\r\n }\r\n }\r\n\r\n return undefined;\r\n }\r\n\r\n private filterAndSanitizeParams(\r\n params?: Record<string, string>\r\n ): Record<string, string> {\r\n if (!params) return {};\r\n const sanitizedParams: Record<string, string> = {};\r\n for (const key in params) {\r\n if (this.expectedParams.has(key)) {\r\n sanitizedParams[key] = DOMPurify.sanitize(params[key] ?? \"\");\r\n }\r\n }\r\n return sanitizedParams;\r\n }\r\n\r\n navigate(path: string) {\r\n history.pushState(null, \"\", path);\r\n this.handlePopState();\r\n }\r\n\r\n addRoute(route: RouteConfig) {\r\n this.routes.push(route);\r\n }\r\n}\r\n","import { createStore } from \"zustand/vanilla\";\r\nimport DOMPurify from \"dompurify\";\r\n\r\ninterface TSParamsState {\r\n params: Record<string, string>;\r\n query: Record<string, string>;\r\n setParams: (params: Record<string, string>) => void;\r\n setQuery: (query: Record<string, string>) => void;\r\n}\r\n\r\nexport const tsParamsStore = createStore<TSParamsState>((set) => ({\r\n params: {},\r\n query: {},\r\n setParams: (params) =>\r\n set(() => ({\r\n params: sanitize(params),\r\n })),\r\n setQuery: (query) =>\r\n set(() => ({\r\n query: sanitize(query),\r\n })),\r\n}));\r\n\r\nfunction sanitize(obj: Record<string, string>): Record<string, string> {\r\n const output: Record<string, string> = {};\r\n for (const key in obj) {\r\n output[key] = DOMPurify.sanitize(obj[key]);\r\n }\r\n return output;\r\n}\r\n","import { autoRegister } from './src/define';\r\n\r\nexport { html } from './src/define';\r\nexport { mapper } from './src/func'\r\nexport { createEffect, createSignal, renderChildRoutes, useTSLazy, useTSOutlet, useTSloadBrython, loadPyFiles, useTSNavigate, useTSMetaData, useTSSelect, useTSCollection, useTSComponent, useTSAuth, useTSElementEach, useInitialDOM, useAnchorSingle, useTSPurifier, useTSEvent, useTSExtractParams, useTSParams, useTSEventAll, useTSElements, useTSAnchorMount } from \"./src/hooks\"\r\nexport { TSRouter } from \"./src/routes/class/Router.class\";\r\n\r\nif (typeof window !== 'undefined') {\r\n window.addEventListener('popstate', () => {\r\n autoRegister();\r\n });\r\n document.addEventListener('DOMContentLoaded', autoRegister);\r\n}\r\n\r\n"],"mappings":"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","names":["sanitize","input","html","strings","values","result","str","i","safeValue","autoRegister","allTags","el","tagName","tag","sanitizeHtml","str","mapper","arr","item","DOMPurify","useTSPurifier","input","config","mergedConfig","useTSEvent","id","eventType","handler","element","createStore","DOMPurify","extractPatternParams","pattern","path","paramNames","regexPattern","match","regex","result","name","i","extractQueryParams","search","urlSearchParams","key","value","useTSParams","set","get","params","query","useTSExtractParams","pattern","store","useTSParams","params","query","useTSEventAll","selector","eventType","handler","elements","element","DOMPurify","useTSElements","htmlElement","element","config","defaultConfig","node","data","tagName","sanitizedContent","DOMPurify","previousHTML","useInitialDOM","id","mount","targetElement","currentHTML","sanitizedHTML","fallbackEl","DOMPurify","e","state","useAnchorSingle","element","href","ariaLabel","className","childElement","sanitizedHref","sanitizedAriaLabel","hrefAttr","scrollPosition","DOMPurify","useTSCSP","scriptSrc","styleSrc","objectSrc","fontSrc","imgSrc","connectSrc","frameSrc","baseUri","reportUri","reportOnly","addOrUpdateCSPMeta","metaElement","reportUriDirective","error","useTSMetaData","config","cspConfig","metaData","DOMPurify","setName","name","updateMetaTag","setDescription","description","setAuthor","author","getName","getDescription","getAuthor","getAllMetaData","createMetaTag","content","metaTag","appendMetaTagsToHead","useTSCSP","DOMPurify","useTSComponent","id","parent","element","params","params2","selector","matches","target","useTSCollection","collections","DOM","elements","params","seenIds","id","index","matches","elementFn","param","useTSComponent","useTSSelect","selector","scope","elements","jwtDecode","useTSAuth","_Component","loginUrl","token","decodedToken","currentTime","error","useTSElementEach","elements","events","callback","element","eventType","event","useTSNavigate","useTSOutlet","selector","outlets","outletDOM","currentPath","outlet","base","renderChildRoutes","DOM","router","pathname","route","child","childPath","createStore","createSignal","initialValue","store","listeners","newValue","listener","createEffect","effectFn","cleanup","useTSHashAnchor","links","useTSElementEach","element","e","targetId","targetElement","debounce","sanitizeInput","input","element","_enhanceAnchors","anchors","anchor","originalHref","sanitizedHref","originalClassName","ariaLabel","child","href","e","url","err","useAnchor","useTSNoReload","a","useAnchor","useTSAnchorMount","useTSNoReload","useTSHashAnchor","useTSloadBrython","brythonJS","brythonStdlib","loadScript","src","resolve","reject","script","loadPyFiles","useTSLazy","factory","cached","el","props","mod","err","DOMPurify","createStore","DOMPurify","tsParamsStore","set","params","sanitize","query","obj","output","key","TSRouter","routes","expectedParams","currentPath","currentSearch","queryParams","matchingRoute","sanitizedParams","tsParamsStore","errorElement","nestedPath","childElement","notFoundRoute","fallbackParams","children","parentElement","parentParams","matchingChild","mergedParams","nextNestedPath","search","urlSearchParams","key","value","DOMPurify","path","inheritedParams","route","routePath","paramNames","regexPattern","match","regex","params","name","index","autoRegister"]}
1
+ {"version":3,"sources":["../src/define/html.ts","../src/define/auto-register.ts","../src/func/index.ts","../src/hooks/useTSPurifier.ts","../src/hooks/useTSEvent.ts","../src/hooks/useTSParams.ts","../src/hooks/useTSExtract.ts","../src/hooks/useTSAllElements.ts","../src/hooks/useTSElements.ts","../src/hooks/useIntialDOM.ts","../src/hooks/useTSAnchorSingle.ts","../src/hooks/useTSMetaData.ts","../src/hooks/useTSCSP.ts","../src/hooks/useTSComponent.ts","../src/hooks/useTSCollection.ts","../src/hooks/useTSSelect.ts","../src/hooks/useTSAuth.ts","../src/hooks/useTSForEach.ts","../src/hooks/useTSNavigate.ts","../src/hooks/useTSOutlet.ts","../src/hooks/useReactivity.ts","../src/hooks/useTSHashAnchor.ts","../src/hooks/useTSAnchor.ts","../src/hooks/useTSNoReload.ts","../src/hooks/useTSAnchorMount.ts","../src/hooks/useTSInitializedBrython.ts","../src/hooks/useTSLazy.ts","../src/routes/class/Router.class.ts","../src/store/useTSParam.store.ts","../index.mts"],"sourcesContent":["function sanitize(input: unknown): string {\r\n // Always convert to string first\r\n const str = input === null || input === undefined ? \"\" : String(input);\r\n\r\n return str\r\n // remove <script>, <iframe>, <object>, <embed>, <link>, <style> blocks\r\n .replace(/<\\s*(script|iframe|object|embed|link|style)[^>]*>.*?<\\s*\\/\\s*\\1\\s*>/gi, \"\")\r\n // remove opening dangerous tags without closing\r\n .replace(/<\\s*(script|iframe|object|embed|link|style)[^>]*>/gi, \"\")\r\n // strip inline event handlers like onclick=, onerror=, etc.\r\n .replace(/\\son\\w+\\s*=\\s*(['\"]).*?\\1/gi, \"\")\r\n // block javascript: URLs\r\n .replace(/\\s(href|src)\\s*=\\s*(['\"])\\s*javascript:[^'\"]*\\2/gi, \"\");\r\n}\r\n\r\nexport function html(strings: TemplateStringsArray, ...values: unknown[]): string {\r\n return strings.reduce((result, str, i) => {\r\n const safeValue = i < values.length ? sanitize(values[i]) : \"\";\r\n return result + str + safeValue;\r\n }, \"\");\r\n}\r\n","// auto-register-runtime.ts\r\nfunction autoRegister() {\r\n const allTags = new Set<string>();\r\n document.querySelectorAll('*').forEach((el) => {\r\n const tagName = el.tagName.toLowerCase();\r\n if (!tagName.includes('-')) return; // Only register custom tags with a dash\r\n allTags.add(tagName);\r\n });\r\n\r\n allTags.forEach(tag => {\r\n if (!customElements.get(tag)) {\r\n customElements.define(tag, class extends HTMLElement {\r\n connectedCallback() {\r\n this.innerHTML = `<div style=\"padding:10px;background:#eee;\">${tag} (Auto)</div>`;\r\n }\r\n });\r\n }\r\n });\r\n}\r\n\r\n\r\nexport { autoRegister };","// ✅ sanitize HTML but allow harmless tags\r\nconst sanitizeHtml = (str: string) => {\r\n return str\r\n // remove <script>, <iframe>, <object>, <embed>, <link>, <meta>, <style>\r\n .replace(/<\\/?(script|iframe|object|embed|link|meta|style)[^>]*>/gi, \"\")\r\n // remove any attribute that starts with \"on\" (onerror, onclick, etc.)\r\n .replace(/\\s+on[a-z]+\\s*=\\s*(\"[^\"]*\"|'[^']*'|[^\\s>]+)/gi, \"\")\r\n // block javascript: in href/src\r\n .replace(/\\s+(href|src)\\s*=\\s*(['\"]?)\\s*javascript:[^'\"\\s>]*/gi, \"\")\r\n}\r\n\r\n// ✅ mapper with sanitization\r\nconst mapper = (arr: string[] | undefined) =>\r\n arr?.map((item) => sanitizeHtml(item)).join(\"\") ?? \"\"\r\n\r\nexport { mapper }\r\n","import DOMPurify from \"dompurify\";\r\nimport type { Config } from \"dompurify\";\r\n\r\ntype TSPurifier = (input: string | HTMLElement, config?: Config) => string;\r\n\r\nexport const useTSPurifier: TSPurifier = (\r\n input,\r\n config?\r\n) => {\r\n const defaultConfig: Config = {\r\n ADD_TAGS: [\"my-custom-tag\"],\r\n };\r\n\r\n const mergedConfig: Config = { ...defaultConfig, ...config };\r\n\r\n if (typeof input === \"string\") {\r\n return DOMPurify.sanitize(input, mergedConfig);\r\n } else {\r\n return DOMPurify.sanitize(input.innerHTML, mergedConfig);\r\n }\r\n};\r\n","type TSEvent = (\r\n id: string | Document,\r\n eventType: keyof HTMLElementEventMap,\r\n handler: (event: HTMLElementEventMap[keyof HTMLElementEventMap]) => void\r\n) => void;\r\n\r\nexport const useTSEvent: TSEvent = (\r\n id,\r\n eventType,\r\n handler\r\n) => {\r\n if (typeof id === 'string') {\r\n const element = document.getElementById(id);\r\n if (element) {\r\n element.addEventListener(\r\n eventType,\r\n handler as EventListenerOrEventListenerObject\r\n );\r\n } else {\r\n console.warn(`Element with id '${id}' not found.`);\r\n }\r\n } else if (id === document) {\r\n document.addEventListener(\r\n eventType,\r\n handler as EventListenerOrEventListenerObject\r\n );\r\n } else {\r\n console.warn(`Invalid id parameter provided.`);\r\n }\r\n};\r\n","// utils/hooks/useTSParams.ts\r\nimport { createStore } from 'zustand/vanilla';\r\nimport DOMPurify from 'dompurify';\r\n\r\ntype ParamStore = {\r\n params: Record<string, string>;\r\n query: Record<string, string>;\r\n setFromPattern: (pattern: MustURL) => void;\r\n getParam: (key: string) => string | undefined;\r\n getQuery: (key: string) => string | undefined;\r\n};\r\n\r\ntype MustURL = `/${string}`;\r\n\r\nfunction extractPatternParams(pattern: MustURL, path: string): Record<string, string> {\r\n const paramNames: string[] = [];\r\n const regexPattern = pattern.replace(/:[^/]+/g, (match) => {\r\n paramNames.push(match.slice(1));\r\n return '([^/]+)';\r\n });\r\n\r\n const regex = new RegExp(`^${regexPattern}$`);\r\n const match = path.match(regex);\r\n const result: Record<string, string> = {};\r\n\r\n if (match) {\r\n paramNames.forEach((name, i) => {\r\n result[name] = DOMPurify.sanitize(match[i + 1] ?? '');\r\n });\r\n }\r\n\r\n return result;\r\n}\r\n\r\nfunction extractQueryParams(search: MustURL): Record<string, string> {\r\n const result: Record<string, string> = {};\r\n const urlSearchParams = new URLSearchParams(search);\r\n\r\n for (const [key, value] of urlSearchParams.entries()) {\r\n result[key] = DOMPurify.sanitize(value);\r\n }\r\n\r\n return result;\r\n}\r\n\r\nexport const useTSParams = createStore<ParamStore>((set, get) => ({\r\n params: {},\r\n query: {},\r\n setFromPattern: (pattern: MustURL) => {\r\n const path = window.location.pathname;\r\n const params = extractPatternParams(pattern, path);\r\n const query = extractQueryParams(window.location.search as MustURL);\r\n set({ params, query });\r\n },\r\n getParam: (key: string) => get().params[key],\r\n getQuery: (key: string) => get().query[key],\r\n}));\r\n","import { useTSParams } from './useTSParams';\r\n\r\ntype MustURL = `/${string}`;\r\n\r\nexport function useTSExtractParams(pattern: MustURL) {\r\n const store = useTSParams.getState();\r\n\r\n // Populate internal param/query store\r\n store.setFromPattern(pattern);\r\n\r\n const params = store.params;\r\n const query = store.query;\r\n\r\n return { ...params, ...query };\r\n}\r\n","export const useTSEventAll = <T extends Event>(\r\n selector: string,\r\n eventType: keyof HTMLElementEventMap,\r\n handler: (event: T) => void\r\n) => {\r\n const elements = document.querySelectorAll(selector);\r\n elements.forEach(element => {\r\n element.addEventListener(eventType, handler as EventListener);\r\n });\r\n\r\n return () => {\r\n elements.forEach(element => {\r\n element.removeEventListener(eventType, handler as EventListener);\r\n });\r\n };\r\n};\r\n\r\nexport const useTSEventSelectAll = <T extends Event>(\r\n selectors: string[],\r\n eventType: keyof HTMLElementEventMap,\r\n handler: (event: T) => void\r\n) => {\r\n const elements: NodeListOf<HTMLElement>[] = [];\r\n\r\n selectors.forEach(selector => {\r\n const selectedElements = document.querySelectorAll(\r\n selector\r\n ) as NodeListOf<HTMLElement>;\r\n selectedElements.forEach(element => {\r\n element.addEventListener(eventType, handler as EventListener);\r\n });\r\n elements.push(selectedElements);\r\n });\r\n\r\n return () => {\r\n elements.forEach(nodeList => {\r\n nodeList.forEach(element => {\r\n element.removeEventListener(eventType, handler as EventListener);\r\n });\r\n });\r\n };\r\n};\r\n","import DOMPurify, { Config } from \"dompurify\";\r\n\r\ntype EventHandlers = Record<string, EventListener>;\r\n\r\ntype TSElements = (\r\n htmlElement: HTMLElement,\r\n element: string,\r\n config?: Config,\r\n handlers?: EventHandlers\r\n) => void;\r\n\r\nexport const useTSElements: TSElements = (\r\n htmlElement,\r\n element,\r\n config,\r\n handlers = {}\r\n) => {\r\n const defaultConfig: Config = {\r\n USE_PROFILES: { svg: true, html: true },\r\n ALLOWED_TAGS: [\r\n \"svg\", \"path\", \"circle\", \"rect\", \"line\", \"polyline\", \"polygon\", \"g\",\r\n \"main\", \"div\", \"h1\", \"h2\", \"h3\", \"h4\", \"h5\", \"h6\",\r\n \"p\", \"button\", \"span\", \"a\", \"img\", \"input\", \"ul\", \"li\", \"i\"\r\n ],\r\n ALLOWED_ATTR: [\r\n \"class\", \"id\", \"href\", \"src\", \"alt\", \"fill\", \"stroke\", \"stroke-width\",\r\n \"viewBox\", \"xmlns\", \"d\", \"x\", \"y\", \"cx\", \"cy\", \"r\", \"width\", \"height\",\r\n \"data-onclick\", \"data-onchange\" // ✅ allow safe declarative events\r\n ],\r\n FORBID_TAGS: [\"script\", \"iframe\"],\r\n ALLOWED_URI_REGEXP:\r\n /^(?:(?:https?|mailto|tel|ftp):|[^a-z]|[a-z+.\\-]+(?:[^a-z+.\\-:]|$))/i,\r\n ...config,\r\n };\r\n\r\n // ✅ Allow custom elements dynamically\r\n DOMPurify.addHook(\"uponSanitizeElement\", (node, data) => {\r\n const tagName = data.tagName.toLowerCase();\r\n if (tagName.includes(\"-\")) {\r\n data.allowedTags[tagName] = true;\r\n }\r\n });\r\n\r\n // ✅ Strip dangerous event handlers (`onclick`, etc.)\r\n DOMPurify.addHook(\"uponSanitizeAttribute\", (node, data) => {\r\n if (data.attrName && data.attrName.toLowerCase().startsWith(\"on\")) {\r\n data.keepAttr = false;\r\n }\r\n });\r\n\r\n const sanitizedContent = DOMPurify.sanitize(element, defaultConfig);\r\n htmlElement.innerHTML = sanitizedContent;\r\n\r\n // ✅ Bind safe declarative events from `data-*`\r\n htmlElement.querySelectorAll<HTMLElement>(\"[data-onclick]\").forEach((el) => {\r\n const key = el.dataset.onclick!;\r\n if (handlers[key]) {\r\n el.addEventListener(\"click\", handlers[key]);\r\n }\r\n });\r\n\r\n htmlElement.querySelectorAll<HTMLElement>(\"[data-onchange]\").forEach((el) => {\r\n const key = el.dataset.onchange!;\r\n if (handlers[key]) {\r\n el.addEventListener(\"change\", handlers[key]);\r\n }\r\n });\r\n};\r\n","import DOMPurify from \"dompurify\"\r\n\r\nlet previousHTML: string | null = null\r\n\r\ntype TSInitialDOM = (id: string, mount: (el: HTMLElement) => void) => void;\r\n\r\nexport const useInitialDOM: TSInitialDOM = (id, mount) => {\r\n // SSR guard\r\n if (typeof document === \"undefined\") return\r\n\r\n const targetElement = document.getElementById(id)\r\n if (!targetElement) return\r\n\r\n const currentHTML = targetElement.innerHTML\r\n const sanitizedHTML = DOMPurify.sanitize(currentHTML)\r\n\r\n if (previousHTML !== null && sanitizedHTML !== previousHTML) {\r\n // DOM changed externally — reset and remount in a temp container\r\n const fallbackEl = document.createElement(\"div\")\r\n mount(fallbackEl)\r\n targetElement.innerHTML = previousHTML\r\n } else {\r\n // First time or same sanitized DOM — mount to target\r\n previousHTML = sanitizedHTML\r\n mount(targetElement)\r\n }\r\n}\r\n","import DOMPurify from \"dompurify\";\r\n\r\ndeclare global {\r\n interface Window {\r\n __anchorSinglePopstateHandlerAttached?: boolean;\r\n }\r\n}\r\n\r\ntype AnchorSingle = (\r\n element: HTMLAnchorElement | null,\r\n href: string,\r\n ariaLabel: string,\r\n className?: string,\r\n childElement?: HTMLElement | null\r\n) => void;\r\n\r\n// Attach popstate listener only in the browser\r\nif (typeof window !== \"undefined\" && !window.__anchorSinglePopstateHandlerAttached) {\r\n window.addEventListener(\"popstate\", (e) => {\r\n const state = e.state as { scrollPosition?: number };\r\n if (state?.scrollPosition !== undefined) {\r\n window.scrollTo(0, state.scrollPosition);\r\n }\r\n });\r\n window.__anchorSinglePopstateHandlerAttached = true;\r\n}\r\n\r\nexport const useAnchorSingle: AnchorSingle = (\r\n element,\r\n href,\r\n ariaLabel,\r\n className = \"\",\r\n childElement = null\r\n) => {\r\n if (!element) return;\r\n\r\n // Sanitize string inputs\r\n const sanitizedHref = DOMPurify.sanitize(href, { ALLOWED_URI_REGEXP: /^(https?:|\\/)/ });\r\n const sanitizedAriaLabel = DOMPurify.sanitize(ariaLabel, { USE_PROFILES: { html: false } });\r\n\r\n element.setAttribute(\"href\", sanitizedHref);\r\n element.setAttribute(\"aria-label\", sanitizedAriaLabel);\r\n\r\n if (className) {\r\n element.className = className.trim();\r\n }\r\n\r\n if (childElement) {\r\n element.replaceChildren(childElement);\r\n }\r\n\r\n // Event binding only in browser\r\n if (typeof window !== \"undefined\") {\r\n element.addEventListener(\"click\", (e) => {\r\n e.preventDefault();\r\n const target = e.currentTarget as HTMLAnchorElement;\r\n const hrefAttr = target.getAttribute(\"href\");\r\n if (hrefAttr) {\r\n const scrollPosition = window.scrollY;\r\n window.scrollTo(0, 0);\r\n window.history.pushState({ scrollPosition }, \"\", hrefAttr);\r\n dispatchEvent(new PopStateEvent(\"popstate\"));\r\n }\r\n });\r\n }\r\n};\r\n","import DOMPurify from \"dompurify\";\r\nimport { useTSCSP } from \"./useTSCSP\";\r\n\r\ntype SEOConfig = {\r\n name?: string;\r\n description?: string;\r\n author?: string;\r\n}\r\n\r\ntype CSPConfig = {\r\n scriptSrc?: string;\r\n styleSrc?: string;\r\n objectSrc?: string;\r\n connectSrc?: string[];\r\n reportOnly?: boolean;\r\n}\r\n\r\ntype SEOHandler = {\r\n setName: (name: string) => void;\r\n setDescription: (description: string) => void;\r\n setAuthor: (author: string) => void;\r\n getName: () => string;\r\n getDescription: () => string;\r\n getAuthor: () => string;\r\n getAllMetaData: () => SEOConfig;\r\n appendMetaTagsToHead: () => void;\r\n}\r\n\r\nexport const useTSMetaData = (\r\n config: SEOConfig,\r\n cspConfig?: CSPConfig\r\n): SEOHandler => {\r\n let metaData: SEOConfig = {\r\n name: DOMPurify.sanitize(config.name || \"\"),\r\n description: DOMPurify.sanitize(\r\n config.description || \"Default description\"\r\n ),\r\n author: DOMPurify.sanitize(config.author || \"\"),\r\n };\r\n\r\n const setName = (name: string): void => {\r\n metaData.name = DOMPurify.sanitize(name);\r\n updateMetaTag(\"name\", metaData.name);\r\n };\r\n\r\n const setDescription = (description: string): void => {\r\n metaData.description = DOMPurify.sanitize(description);\r\n updateMetaTag(\"description\", metaData.description);\r\n };\r\n\r\n const setAuthor = (author: string): void => {\r\n metaData.author = DOMPurify.sanitize(author);\r\n updateMetaTag(\"author\", metaData.author);\r\n };\r\n\r\n const getName = (): string => {\r\n return metaData.name!;\r\n };\r\n\r\n const getDescription = (): string => {\r\n return metaData.description!;\r\n };\r\n\r\n const getAuthor = (): string => {\r\n return metaData.author!;\r\n };\r\n\r\n const getAllMetaData = (): SEOConfig => {\r\n return metaData;\r\n };\r\n\r\n const createMetaTag = (name: string, content: string) => {\r\n const metaTag = document.createElement(\"meta\");\r\n metaTag.setAttribute(\"name\", name);\r\n metaTag.setAttribute(\"content\", content);\r\n document.head.appendChild(metaTag);\r\n };\r\n\r\n const updateMetaTag = (name: string, content: string) => {\r\n let metaTag = document.querySelector(`meta[name=\"${name}\"]`);\r\n if (metaTag) {\r\n metaTag.setAttribute(\"content\", content);\r\n } else {\r\n createMetaTag(name, content);\r\n }\r\n };\r\n\r\n const appendMetaTagsToHead = () => {\r\n updateMetaTag(\"name\", metaData.name!);\r\n updateMetaTag(\"description\", metaData.description!);\r\n updateMetaTag(\"author\", metaData.author!);\r\n };\r\n\r\n // Integrate with useTSCSP for CSP enforcement\r\n if (cspConfig) {\r\n useTSCSP(\r\n cspConfig.scriptSrc,\r\n cspConfig.styleSrc,\r\n cspConfig.objectSrc,\r\n Array.isArray(cspConfig.connectSrc) ? cspConfig.connectSrc.join(\" \") : cspConfig.connectSrc,\r\n cspConfig.reportOnly !== undefined ? String(cspConfig.reportOnly) : undefined\r\n );\r\n }\r\n\r\n appendMetaTagsToHead();\r\n\r\n return {\r\n setName,\r\n setDescription,\r\n setAuthor,\r\n getName,\r\n getDescription,\r\n getAuthor,\r\n getAllMetaData,\r\n appendMetaTagsToHead,\r\n };\r\n};\r\n","export const useTSCSP = (\r\n scriptSrc = `'self' 'nonce-rAnd0m123' 'unsafe-inline' 'unsafe-eval'`,\r\n styleSrc = \"'self' 'nonce-rAnd0m123'\", // Use nonce for inline styles\r\n objectSrc = \"'none'\",\r\n fontSrc = \"'self' https://fonts.googleapis.com https://fonts.gstatic.com\",\r\n imgSrc = \"'self' https://blogger.googleusercontent.com\",\r\n connectSrc = [\r\n \"'self'\",\r\n \"https://fonts.googleapis.com\",\r\n \"https://fonts.gstatic.com\",\r\n \"https://www.google.com/maps/\",\r\n ],\r\n frameSrc = \"'self' https://www.youtube.com\", // Add frame-src for embedding\r\n baseUri = \"'self'\",\r\n reportUri = \"/csp-report\",\r\n reportOnly = false\r\n) => {\r\n const addOrUpdateCSPMeta = () => {\r\n try {\r\n let metaElement = document.querySelector(\r\n 'meta[http-equiv=\"Content-Security-Policy\"]'\r\n );\r\n if (!metaElement) {\r\n metaElement = document.createElement(\"meta\");\r\n metaElement.setAttribute(\"http-equiv\", \"Content-Security-Policy\");\r\n document.head.appendChild(metaElement);\r\n }\r\n\r\n const reportUriDirective = reportOnly ? `report-uri ${reportUri};` : \"\";\r\n metaElement.setAttribute(\r\n \"content\",\r\n `default-src 'self'; script-src ${scriptSrc}; style-src ${styleSrc}; object-src ${objectSrc}; font-src ${fontSrc}; img-src ${imgSrc}; connect-src ${connectSrc.join(\r\n \" \"\r\n )}; frame-src ${frameSrc}; base-uri ${baseUri}; ${reportUriDirective}`\r\n );\r\n } catch (error) {\r\n console.error(\"Error adding CSP meta element:\", error);\r\n }\r\n };\r\n\r\n if (document.readyState === \"loading\") {\r\n document.addEventListener(\"DOMContentLoaded\", addOrUpdateCSPMeta);\r\n } else {\r\n addOrUpdateCSPMeta();\r\n }\r\n};\r\n","import DOMPurify from \"dompurify\";\r\n\r\ntype TSComponent = (\r\n id: string,\r\n parent: HTMLElement,\r\n element: Function,\r\n params?: any,\r\n params2?: any\r\n) => void;\r\n\r\nexport const useTSComponent: TSComponent = (\r\n id,\r\n parent,\r\n element,\r\n params,\r\n params2\r\n) => {\r\n const selector = `#${id}`;\r\n const matches = parent.querySelectorAll<HTMLElement>(selector);\r\n\r\n // 1. Missing element check\r\n if (matches.length === 0) {\r\n throw new Error(`[useTSComponent] No element found with id '${id}' in the given parent.`);\r\n }\r\n\r\n // 2. Duplicate ID check\r\n if (matches.length > 1) {\r\n throw new Error(`[useTSComponent] Duplicate id '${id}' detected. Found ${matches.length} elements.`);\r\n }\r\n\r\n const target = matches[0];\r\n\r\n // 3. Sanitize the target’s existing HTML content\r\n target.innerHTML = DOMPurify.sanitize(target.innerHTML, { USE_PROFILES: { html: true } });\r\n\r\n // 4. Call the component function with the target\r\n element(target, params, params2);\r\n};\r\n","import { useTSComponent } from \"./useTSComponent\";\r\n\r\ntype TSCollection = (\r\n collections: string[],\r\n DOM: HTMLElement,\r\n elements: Function[],\r\n params?: any[]\r\n) => void;\r\n\r\nexport const useTSCollection: TSCollection = (\r\n collections,\r\n DOM,\r\n elements,\r\n params = []\r\n) => {\r\n const seenIds = new Set<string>();\r\n\r\n collections.forEach((id, index) => {\r\n // Check for duplicate IDs in the collection list itself\r\n if (seenIds.has(id)) {\r\n console.warn(`[useTSCollection] Duplicate ID in collection array: \"${id}\" — skipping.`);\r\n return;\r\n }\r\n seenIds.add(id);\r\n\r\n // Check for duplicates already in DOM\r\n const matches = DOM.querySelectorAll(`#${id}`);\r\n if (matches.length > 1) {\r\n console.warn(\r\n `[useTSCollection] Duplicate ID in DOM: \"${id}\" (${matches.length} elements found) — skipping component mount.`\r\n );\r\n return;\r\n }\r\n\r\n const elementFn = elements[index];\r\n const param = Array.isArray(params) ? params[index] : undefined;\r\n\r\n if (typeof elementFn === \"function\") {\r\n useTSComponent(id, DOM, elementFn, param);\r\n } else {\r\n console.warn(`[useTSCollection] No valid component function found for ID: \"${id}\"`);\r\n }\r\n });\r\n};\r\n","type TSSelect = <T extends Element = HTMLElement>(\r\n selector: string,\r\n scope?: HTMLElement\r\n) => T | null;\r\n\r\nconst useTSSelect: TSSelect = <T extends Element = HTMLElement>(\r\n selector: string,\r\n scope?: HTMLElement\r\n): T | null => {\r\n const root = scope ?? document;\r\n const elements = root.querySelectorAll<T>(selector);\r\n\r\n if (elements.length === 0) {\r\n if (process.env.NODE_ENV !== \"production\") {\r\n console.warn(`[useTSSelect] No element found for selector: '${selector}'`);\r\n }\r\n return null;\r\n }\r\n\r\n if (selector.startsWith(\"#\") && elements.length > 1) {\r\n if (process.env.NODE_ENV !== \"production\") {\r\n throw new Error(\r\n `[useTSSelect] Duplicate ID detected: '${selector}'. Found ${elements.length} elements with this ID.`\r\n );\r\n }\r\n return elements[0]; // fallback: just return first\r\n }\r\n\r\n if (elements.length > 1) {\r\n if (process.env.NODE_ENV !== \"production\") {\r\n console.warn(\r\n `[useTSSelect] Multiple elements found for selector: '${selector}'. Returning the first one.`\r\n );\r\n }\r\n }\r\n\r\n return elements[0];\r\n};\r\n\r\nexport { useTSSelect };\r\n","import { jwtDecode } from \"jwt-decode\";\r\n\r\nexport const useTSAuth = (_Component: HTMLElement | void, loginUrl: string) => {\r\n const token = localStorage.getItem(\"token\");\r\n\r\n if (!token) {\r\n // Redirect to login page if token is missing\r\n window.location.href = loginUrl;\r\n return null; // Return null when redirecting\r\n }\r\n\r\n try {\r\n const decodedToken: any = jwtDecode(token);\r\n\r\n // Example: Check if the token has expired\r\n const currentTime = Date.now() / 1000;\r\n if (decodedToken.exp && decodedToken.exp < currentTime) {\r\n console.error(\"Token has expired\");\r\n window.localStorage.removeItem(\"token\");\r\n window.location.href = loginUrl;\r\n return null; // Return null when redirecting\r\n }\r\n\r\n // If the user is authenticated, return the component\r\n return null;\r\n } catch (error) {\r\n console.error(\"Invalid token:\", error);\r\n // Redirect to login page if token decoding fails\r\n window.location.href = loginUrl;\r\n return null; // Return null when redirecting\r\n }\r\n};\r\n","\r\ntype TSElementEach = (\r\n elements: NodeListOf<HTMLElement> | HTMLElement[],\r\n events: (keyof HTMLElementEventMap)[],\r\n callback: (element: HTMLElement, event: Event) => void\r\n) => void;\r\n\r\nexport const useTSElementEach: TSElementEach = (\r\n elements,\r\n events,\r\n callback\r\n) => {\r\n elements.forEach(element => {\r\n events.forEach(eventType => {\r\n element.addEventListener(eventType, event => {\r\n callback(element, event);\r\n });\r\n });\r\n });\r\n};\r\n","export const useTSNavigate = () => {\r\n const back = () => window.history.back();\r\n const forward = () => window.history.forward();\r\n\r\n return {\r\n back,\r\n forward,\r\n };\r\n};\r\n","// types.ts\r\nexport type OutletComponent = (DOM: HTMLElement) => void;\r\n\r\nexport type ChildRoute = {\r\n path: string;\r\n outlet: string;\r\n element: OutletComponent;\r\n};\r\n\r\nexport type Route = {\r\n path: string;\r\n element: (DOM: HTMLElement) => void;\r\n children?: ChildRoute[];\r\n};\r\n\r\n// You don't actually need to import the class TSRouter type.\r\n// Instead, export a cleaner interface with routes.\r\nexport interface RouterInstance {\r\n routes: Route[];\r\n}\r\n\r\n\r\ntype OutletOptions = {\r\n path: string;\r\n component: OutletComponent;\r\n};\r\n\r\nexport const useTSOutlet = (\r\n selector: string,\r\n outlets: OutletOptions[]\r\n): void => {\r\n const outletDOM = document.querySelector<HTMLElement>(`#${selector}`)\r\n || document.querySelector<HTMLElement>(`.${selector}`);\r\n\r\n if (!outletDOM) return;\r\n\r\n const currentPath = window.location.pathname.replace(/\\/$/, \"\");\r\n\r\n for (const outlet of outlets) {\r\n const base = outlet.path.replace(/\\/$/, \"\");\r\n\r\n // Match exact or nested path (e.g., /openai/child/1)\r\n if (currentPath === base || currentPath.startsWith(`${base}/`)) {\r\n outlet.component(outletDOM);\r\n break;\r\n }\r\n }\r\n};\r\n\r\n\r\nexport function renderChildRoutes(DOM: HTMLElement, router: RouterInstance): void {\r\n const pathname = window.location.pathname.replace(/\\/$/, \"\");\r\n\r\n router.routes.forEach((route) => {\r\n if (!route.children?.length) return;\r\n\r\n route.children.forEach((child) => {\r\n const childPath = child.path.replace(/\\/$/, \"\");\r\n\r\n if (pathname === childPath || pathname.startsWith(`${childPath}/`)) {\r\n const outlet = DOM.querySelector(`#${child.outlet}`)\r\n || DOM.querySelector(`.${child.outlet}`);\r\n if (outlet instanceof HTMLElement && child.element) {\r\n child.element(outlet);\r\n }\r\n }\r\n });\r\n });\r\n}","// useTSReactivity.ts\r\nimport { createStore } from 'zustand/vanilla';\r\n\r\ntype Listener<T> = (value: T) => void;\r\n\r\ninterface Signal<T> {\r\n get: () => T;\r\n set: (newValue: T) => void;\r\n subscribe: (listener: Listener<T>) => () => void;\r\n}\r\n\r\nexport function createSignal<T>(initialValue: T): Signal<T> {\r\n const store = createStore<{ value: T }>(() => ({ value: initialValue }));\r\n const listeners = new Set<Listener<T>>();\r\n\r\n return {\r\n get: () => store.getState().value,\r\n set: (newValue: T) => {\r\n store.setState({ value: newValue });\r\n listeners.forEach((listener) => listener(newValue));\r\n },\r\n subscribe: (listener: Listener<T>) => {\r\n listeners.add(listener);\r\n listener(store.getState().value); // Trigger immediately\r\n return () => listeners.delete(listener);\r\n },\r\n };\r\n}\r\n\r\ntype CleanupFn = () => void;\r\n\r\nexport function createEffect(effectFn: () => void | CleanupFn): void {\r\n const cleanup = effectFn();\r\n\r\n // Optional: return a way to dispose the effect manually\r\n if (typeof cleanup === 'function') {\r\n // You may store this and call it later if needed\r\n cleanup();\r\n }\r\n}\r\n","import { useTSElementEach } from './useTSForEach';\r\n\r\n\r\nconst useTSHashAnchor = () => {\r\n const links = document.querySelectorAll<HTMLAnchorElement>('a[href^=\"#\"]');\r\n\r\n useTSElementEach(\r\n links,\r\n ['click'],\r\n (element, e) => {\r\n e.preventDefault();\r\n const targetId = element.getAttribute('href')?.substring(1);\r\n const targetElement = targetId ? document.getElementById(targetId) : null;\r\n\r\n if (targetElement) {\r\n targetElement.scrollIntoView({\r\n behavior: 'smooth',\r\n block: 'start'\r\n });\r\n }\r\n }\r\n );\r\n}\r\n\r\nexport { useTSHashAnchor }","import { debounce } from 'lodash-es';\r\n\r\nlet sanitizeInput = (input: string): string => input;\r\n\r\nif (typeof window !== 'undefined' && typeof document !== 'undefined') {\r\n sanitizeInput = (input: string): string => {\r\n const element = document.createElement(\"div\");\r\n element.innerText = input;\r\n return element.innerHTML;\r\n };\r\n}\r\n\r\ntype AnchorInput =\r\n | NodeListOf<HTMLAnchorElement>\r\n | HTMLAnchorElement[]\r\n | HTMLAnchorElement\r\n | null\r\n | undefined;\r\n\r\nconst _enhanceAnchors = debounce((anchors: AnchorInput) => {\r\n const resolvedAnchors: HTMLAnchorElement[] = (() => {\r\n if (!anchors) return Array.from(document.querySelectorAll(\"a\"));\r\n if (Array.isArray(anchors)) return anchors;\r\n if (anchors instanceof HTMLAnchorElement) return [anchors];\r\n return Array.from(anchors);\r\n })();\r\n\r\n resolvedAnchors.forEach(anchor => {\r\n if (!anchor || anchor.dataset.anchorEnhanced === 'true') return;\r\n anchor.dataset.anchorEnhanced = 'true';\r\n\r\n // Sanitize attributes\r\n const originalHref = anchor.getAttribute(\"href\") || \"#\";\r\n const sanitizedHref = sanitizeInput(originalHref);\r\n anchor.setAttribute(\"href\", sanitizedHref);\r\n\r\n const originalClassName = anchor.getAttribute(\"class\") || \"\";\r\n anchor.setAttribute(\"class\", sanitizeInput(originalClassName));\r\n\r\n const ariaLabel = anchor.getAttribute(\"aria-label\");\r\n if (ariaLabel) {\r\n anchor.setAttribute(\"aria-label\", sanitizeInput(ariaLabel));\r\n }\r\n\r\n // Keep child elements safe (optional — you can remove this block if not needed)\r\n const child = anchor.querySelector(\":scope > *\") as HTMLElement;\r\n if (child) {\r\n anchor.innerHTML = \"\";\r\n anchor.appendChild(child);\r\n }\r\n\r\n // Skip attaching click listener if:\r\n // - It's a hash link (in-page navigation)\r\n // - It's an external link\r\n const href = anchor.getAttribute(\"href\") || \"\";\r\n if (href.startsWith(\"#\")) return; // Let browser handle hash scrolling normally\r\n\r\n try {\r\n const url = new URL(href, window.location.href);\r\n if (url.origin !== window.location.origin) return; // external link\r\n } catch {\r\n return; // invalid URL — skip\r\n }\r\n\r\n // Intercept same-origin navigation for SPA\r\n anchor.addEventListener(\"click\", (e: MouseEvent) => {\r\n e.preventDefault();\r\n try {\r\n const url = new URL(href, window.location.href);\r\n window.history.pushState({}, \"\", url.pathname + url.search + url.hash);\r\n window.dispatchEvent(new PopStateEvent(\"popstate\"));\r\n } catch (err) {\r\n console.error(\"Invalid URL in anchor:\", href, err);\r\n }\r\n });\r\n });\r\n}, 50);\r\n\r\nexport const useAnchor = (anchors?: AnchorInput): void => {\r\n _enhanceAnchors(anchors);\r\n};\r\n","import { useAnchor } from './useTSAnchor';\r\n\r\nconst useTSNoReload = () => {\r\n const a = document.querySelectorAll(\"a\") as NodeListOf<HTMLAnchorElement>;\r\n return useAnchor(a);\r\n}\r\n\r\nexport { useTSNoReload };","import { useTSHashAnchor } from \"./useTSHashAnchor\";\r\nimport { useTSNoReload } from \"./useTSNoReload\";\r\n\r\nconst useTSAnchorMount = () => {\r\n useTSNoReload();\r\n useTSHashAnchor();\r\n};\r\n\r\nexport { useTSAnchorMount };","// src/loadBrython.ts\r\ntype LoadBrython = (src: string) => Promise<void>;\r\n\r\ndeclare global {\r\n interface Window {\r\n brython: Function;\r\n }\r\n}\r\n\r\nconst useTSloadBrython = async () => {\r\n const brythonJS = \"https://cdn.jsdelivr.net/npm/brython@3/brython.min.js\";\r\n const brythonStdlib = \"https://cdn.jsdelivr.net/npm/brython@3/brython_stdlib.js\";\r\n\r\n // Utility function to load a script\r\n const loadScript: LoadBrython = (src) => {\r\n return new Promise((resolve, reject) => {\r\n const script = document.createElement(\"script\");\r\n script.src = src;\r\n script.onload = () => resolve();\r\n script.onerror = () => reject(new Error(`Failed to load ${src}`));\r\n document.head.appendChild(script);\r\n });\r\n };\r\n\r\n // Load both scripts sequentially\r\n await loadScript(brythonJS);\r\n await loadScript(brythonStdlib);\r\n\r\n // Call brython() after scripts are loaded\r\n if (typeof window.brython === \"function\") {\r\n window.brython();\r\n } else {\r\n console.error(\"Brython did not load correctly.\");\r\n }\r\n};\r\n\r\ntype RequirePy = `${string}.py`;\r\n\r\ntype LoadPy = (src: RequirePy) => Promise<void>;\r\n\r\nconst loadPyFiles: LoadPy = (src) =>\r\n new Promise((resolve, reject) => {\r\n const script = document.createElement(\"script\");\r\n script.type = \"text/python\";\r\n script.src = `/src/python/${src}`;\r\n script.onload = () => resolve();\r\n script.onerror = () => reject(new Error(`Failed to load ${src}`));\r\n document.body.appendChild(script);\r\n });\r\n\r\nexport { useTSloadBrython, loadPyFiles };\r\n","export function useTSLazy(factory: () => Promise<any>) {\r\n let cached: any | null = null;\r\n\r\n return async (el?: HTMLElement, props?: any) => {\r\n try {\r\n if (!cached) {\r\n const mod = await factory();\r\n cached = mod.default || mod;\r\n }\r\n\r\n // If it's a component function (Vanilla TS style)\r\n if (typeof cached === \"function\") {\r\n return cached(el, props);\r\n }\r\n\r\n // If it's already an HTMLElement\r\n if (cached instanceof HTMLElement) {\r\n el?.appendChild(cached);\r\n return;\r\n }\r\n\r\n // If it's a plain object with render()\r\n if (cached && typeof cached.render === \"function\") {\r\n return cached.render(el, props);\r\n }\r\n\r\n console.warn(\"useTSLazy: Unsupported module type\", cached);\r\n } catch (err) {\r\n console.error(\"useTSLazy failed:\", err);\r\n }\r\n };\r\n}\r\n","import DOMPurify from \"dompurify\";\r\nimport { tsParamsStore } from \"../../store\";\r\n\r\ntype RouteCallback = (\r\n errorElement?: HTMLElement,\r\n params?: Record<string, string>,\r\n query?: Record<string, string>\r\n) => void;\r\n\r\ninterface RouteConfig {\r\n path: string;\r\n routeto?: string;\r\n element: RouteCallback;\r\n errorElement?: RouteCallback;\r\n children?: RouteConfig[];\r\n params?: Record<string, string>;\r\n}\r\n\r\nexport class TSRouter {\r\n private routes: RouteConfig[] = [];\r\n private expectedParams: Set<string>;\r\n\r\n constructor(routes: RouteConfig[], expectedParams: string[]) {\r\n this.routes = routes;\r\n this.expectedParams = new Set(expectedParams);\r\n window.addEventListener(\"popstate\", this.handlePopState.bind(this));\r\n this.handlePopState(); // Initial load\r\n }\r\n\r\n private handlePopState() {\r\n const currentPath = window.location.pathname;\r\n const currentSearch = window.location.search;\r\n const queryParams = this.parseQueryParams(currentSearch);\r\n\r\n const matchingRoute = this.findMatchingRoute(currentPath, this.routes);\r\n\r\n if (matchingRoute) {\r\n if (matchingRoute.routeto) {\r\n this.navigate(matchingRoute.routeto);\r\n return;\r\n }\r\n\r\n const sanitizedParams = this.filterAndSanitizeParams(matchingRoute.params);\r\n tsParamsStore.getState().setParams(sanitizedParams);\r\n tsParamsStore.getState().setQuery(queryParams);\r\n\r\n const errorElement = document.createElement(\"div\");\r\n\r\n matchingRoute.element?.(errorElement, sanitizedParams, queryParams);\r\n\r\n if (matchingRoute.children) {\r\n const nestedPath = currentPath.slice(matchingRoute.path.length);\r\n const childElement = errorElement.querySelector(\"#child\") as HTMLDivElement;\r\n if (childElement) {\r\n this.renderChildren(\r\n matchingRoute.children,\r\n nestedPath,\r\n childElement,\r\n sanitizedParams,\r\n queryParams\r\n );\r\n }\r\n }\r\n } else {\r\n const notFoundRoute = this.findMatchingRoute(\"*\", this.routes);\r\n if (notFoundRoute) {\r\n const fallbackParams = this.filterAndSanitizeParams(notFoundRoute.params);\r\n tsParamsStore.getState().setParams(fallbackParams);\r\n tsParamsStore.getState().setQuery(queryParams);\r\n\r\n const errorElement = document.createElement(\"div\");\r\n notFoundRoute.element?.(errorElement, fallbackParams, queryParams);\r\n }\r\n }\r\n }\r\n\r\n private renderChildren(\r\n children: RouteConfig[] | undefined,\r\n nestedPath: string,\r\n parentElement: HTMLElement,\r\n parentParams: Record<string, string>,\r\n queryParams: Record<string, string>\r\n ) {\r\n if (!children || children.length === 0) {\r\n const childElement = parentElement.querySelector(\"#child\") as HTMLDivElement;\r\n if (childElement) childElement.remove();\r\n return;\r\n }\r\n\r\n const matchingChild = this.findMatchingRoute(nestedPath, children);\r\n if (matchingChild) {\r\n const childElement = document.createElement(\"div\");\r\n childElement.id = \"child\";\r\n const mergedParams = { ...parentParams, ...matchingChild.params };\r\n const sanitizedParams = this.filterAndSanitizeParams(mergedParams);\r\n\r\n tsParamsStore.getState().setParams(sanitizedParams);\r\n tsParamsStore.getState().setQuery(queryParams);\r\n\r\n matchingChild.element?.(childElement, sanitizedParams, queryParams);\r\n parentElement.appendChild(childElement);\r\n\r\n if (matchingChild.children) {\r\n const nextNestedPath = nestedPath.slice(matchingChild.path.length);\r\n this.renderChildren(\r\n matchingChild.children,\r\n nextNestedPath,\r\n childElement,\r\n sanitizedParams,\r\n queryParams\r\n );\r\n }\r\n }\r\n }\r\n\r\n private parseQueryParams(search: string): Record<string, string> {\r\n const queryParams: Record<string, string> = {};\r\n const urlSearchParams = new URLSearchParams(search);\r\n\r\n for (const [key, value] of urlSearchParams.entries()) {\r\n if (this.expectedParams.has(key)) {\r\n queryParams[key] = DOMPurify.sanitize(value);\r\n }\r\n }\r\n\r\n return queryParams;\r\n }\r\n\r\n private findMatchingRoute(\r\n path: string,\r\n routes: RouteConfig[],\r\n inheritedParams: Record<string, string> = {}\r\n ): RouteConfig | undefined {\r\n for (const route of routes) {\r\n const routePath = route.path;\r\n const isDefaultRoute = routePath === \"*\";\r\n\r\n if (!isDefaultRoute) {\r\n const paramNames: string[] = [];\r\n const regexPattern = routePath.replace(/:[^\\s/]+/g, match => {\r\n paramNames.push(match.substring(1));\r\n return \"([^\\\\s/]+)\";\r\n });\r\n\r\n const regex = new RegExp(`^${regexPattern}(?:/|$)`);\r\n const match = path.match(regex);\r\n\r\n if (match) {\r\n const params: Record<string, string> = { ...inheritedParams };\r\n paramNames.forEach((name, index) => {\r\n params[name] = match[index + 1] ?? \"\";\r\n });\r\n\r\n if (route.children) {\r\n const nestedPath = path.slice(match[0].length);\r\n const matchingChild = this.findMatchingRoute(\r\n nestedPath,\r\n route.children,\r\n params\r\n );\r\n if (matchingChild) return matchingChild;\r\n }\r\n\r\n return { ...route, params };\r\n }\r\n } else {\r\n return route;\r\n }\r\n }\r\n\r\n return undefined;\r\n }\r\n\r\n private filterAndSanitizeParams(\r\n params?: Record<string, string>\r\n ): Record<string, string> {\r\n if (!params) return {};\r\n const sanitizedParams: Record<string, string> = {};\r\n for (const key in params) {\r\n if (this.expectedParams.has(key)) {\r\n sanitizedParams[key] = DOMPurify.sanitize(params[key] ?? \"\");\r\n }\r\n }\r\n return sanitizedParams;\r\n }\r\n\r\n navigate(path: string) {\r\n history.pushState(null, \"\", path);\r\n this.handlePopState();\r\n }\r\n\r\n addRoute(route: RouteConfig) {\r\n this.routes.push(route);\r\n }\r\n}\r\n","import { createStore } from \"zustand/vanilla\";\r\nimport DOMPurify from \"dompurify\";\r\n\r\ninterface TSParamsState {\r\n params: Record<string, string>;\r\n query: Record<string, string>;\r\n setParams: (params: Record<string, string>) => void;\r\n setQuery: (query: Record<string, string>) => void;\r\n}\r\n\r\nexport const tsParamsStore = createStore<TSParamsState>((set) => ({\r\n params: {},\r\n query: {},\r\n setParams: (params) =>\r\n set(() => ({\r\n params: sanitize(params),\r\n })),\r\n setQuery: (query) =>\r\n set(() => ({\r\n query: sanitize(query),\r\n })),\r\n}));\r\n\r\nfunction sanitize(obj: Record<string, string>): Record<string, string> {\r\n const output: Record<string, string> = {};\r\n for (const key in obj) {\r\n output[key] = DOMPurify.sanitize(obj[key]);\r\n }\r\n return output;\r\n}\r\n","import { autoRegister } from './src/define';\r\n\r\nexport { html } from './src/define';\r\nexport { mapper } from './src/func'\r\nexport { createEffect, createSignal, renderChildRoutes, useTSLazy, useTSOutlet, useTSloadBrython, loadPyFiles, useTSNavigate, useTSMetaData, useTSSelect, useTSCollection, useTSComponent, useTSAuth, useTSElementEach, useInitialDOM, useAnchorSingle, useTSPurifier, useTSEvent, useTSExtractParams, useTSParams, useTSEventAll, useTSElements, useTSAnchorMount } from \"./src/hooks\"\r\nexport { TSRouter } from \"./src/routes/class/Router.class\";\r\n\r\nif (typeof window !== 'undefined') {\r\n window.addEventListener('popstate', () => {\r\n autoRegister();\r\n });\r\n document.addEventListener('DOMContentLoaded', autoRegister);\r\n}\r\n\r\n"],"mappings":"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","names":["sanitize","input","html","strings","values","result","str","i","safeValue","autoRegister","allTags","el","tagName","tag","sanitizeHtml","str","mapper","arr","item","DOMPurify","useTSPurifier","input","config","mergedConfig","useTSEvent","id","eventType","handler","element","createStore","DOMPurify","extractPatternParams","pattern","path","paramNames","regexPattern","match","regex","result","name","i","extractQueryParams","search","urlSearchParams","key","value","useTSParams","set","get","params","query","useTSExtractParams","pattern","store","useTSParams","params","query","useTSEventAll","selector","eventType","handler","elements","element","DOMPurify","useTSElements","htmlElement","element","config","handlers","defaultConfig","node","data","tagName","sanitizedContent","el","key","DOMPurify","previousHTML","useInitialDOM","id","mount","targetElement","currentHTML","sanitizedHTML","fallbackEl","DOMPurify","e","state","useAnchorSingle","element","href","ariaLabel","className","childElement","sanitizedHref","sanitizedAriaLabel","hrefAttr","scrollPosition","DOMPurify","useTSCSP","scriptSrc","styleSrc","objectSrc","fontSrc","imgSrc","connectSrc","frameSrc","baseUri","reportUri","reportOnly","addOrUpdateCSPMeta","metaElement","reportUriDirective","error","useTSMetaData","config","cspConfig","metaData","DOMPurify","setName","name","updateMetaTag","setDescription","description","setAuthor","author","getName","getDescription","getAuthor","getAllMetaData","createMetaTag","content","metaTag","appendMetaTagsToHead","useTSCSP","DOMPurify","useTSComponent","id","parent","element","params","params2","selector","matches","target","useTSCollection","collections","DOM","elements","params","seenIds","id","index","matches","elementFn","param","useTSComponent","useTSSelect","selector","scope","elements","jwtDecode","useTSAuth","_Component","loginUrl","token","decodedToken","currentTime","error","useTSElementEach","elements","events","callback","element","eventType","event","useTSNavigate","useTSOutlet","selector","outlets","outletDOM","currentPath","outlet","base","renderChildRoutes","DOM","router","pathname","route","child","childPath","createStore","createSignal","initialValue","store","listeners","newValue","listener","createEffect","effectFn","cleanup","useTSHashAnchor","links","useTSElementEach","element","e","targetId","targetElement","debounce","sanitizeInput","input","element","_enhanceAnchors","anchors","anchor","originalHref","sanitizedHref","originalClassName","ariaLabel","child","href","e","url","err","useAnchor","useTSNoReload","a","useAnchor","useTSAnchorMount","useTSNoReload","useTSHashAnchor","useTSloadBrython","brythonJS","brythonStdlib","loadScript","src","resolve","reject","script","loadPyFiles","useTSLazy","factory","cached","el","props","mod","err","DOMPurify","createStore","DOMPurify","tsParamsStore","set","params","sanitize","query","obj","output","key","TSRouter","routes","expectedParams","currentPath","currentSearch","queryParams","matchingRoute","sanitizedParams","tsParamsStore","errorElement","nestedPath","childElement","notFoundRoute","fallbackParams","children","parentElement","parentParams","matchingChild","mergedParams","nextNestedPath","search","urlSearchParams","key","value","DOMPurify","path","inheritedParams","route","routePath","paramNames","regexPattern","match","regex","params","name","index","autoRegister"]}
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "@devwareng/vanilla-ts",
3
- "version": "1.2.125",
3
+ "version": "1.2.126",
4
4
  "description": "Framework-less TypeScript hooks for SPA development.",
5
5
  "author": "Waren Arapoc Gador",
6
6
  "license": "MIT",