@devwareng/vanilla-ts 1.4.49 → 1.4.50

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,4 +1,21 @@
1
- "use strict";var Le=Object.create;var O=Object.defineProperty;var we=Object.getOwnPropertyDescriptor;var Me=Object.getOwnPropertyNames;var Re=Object.getPrototypeOf,Ae=Object.prototype.hasOwnProperty;var Pe=(t,e)=>{for(var n in e)O(t,n,{get:e[n],enumerable:!0})},ce=(t,e,n,r)=>{if(e&&typeof e=="object"||typeof e=="function")for(let o of Me(e))!Ae.call(t,o)&&o!==n&&O(t,o,{get:()=>e[o],enumerable:!(r=we(e,o))||r.enumerable});return t};var E=(t,e,n)=>(n=t!=null?Le(Re(t)):{},ce(e||!t||!t.__esModule?O(n,"default",{value:t,enumerable:!0}):n,t)),xe=t=>ce(O({},"__esModule",{value:!0}),t);var Ne={};Pe(Ne,{TSFilebasedRouter:()=>ye,TSRouter:()=>k,createEffect:()=>ee,createSignal:()=>Z,html:()=>N,loadPyFiles:()=>oe,mapper:()=>le,renderChildRoutes:()=>K,useAnchor:()=>H,useAnchorSingle:()=>B,useInitialDOM:()=>j,useTSAnchorMount:()=>ne,useTSAuth:()=>X,useTSCollection:()=>Q,useTSComponent:()=>A,useTSElementEach:()=>P,useTSElements:()=>U,useTSEvent:()=>z,useTSEventAll:()=>q,useTSExtractParams:()=>_,useTSHashAnchor:()=>x,useTSLazy:()=>se,useTSMetaData:()=>G,useTSNavigate:()=>Y,useTSNoReload:()=>D,useTSOutlet:()=>J,useTSParams:()=>R,useTSPurifier:()=>F,useTSSSRHydration:()=>ie,useTSSelect:()=>V,useTSloadBrython:()=>re});module.exports=xe(Ne);function He(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 N(t,...e){return t.reduce((n,r,o)=>{let s=o<e.length?He(e[o]):"";return n+r+s},"")}var De=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,""),le=t=>t?.map(e=>De(e)).join("")??"";var $=E(require("dompurify"),1),F=(t,e)=>{let r={...{ADD_TAGS:["my-custom-tag"]},...e};return typeof t=="string"?$.default.sanitize(t,r):$.default.sanitize(t.innerHTML,r)};var z=(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 ue=require("zustand/vanilla"),I=E(require("dompurify"),1);function Oe(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]=I.default.sanitize(s[c+1]??"")}),i}function be(t){let e={},n=new URLSearchParams(t);for(let[r,o]of n.entries())e[r]=I.default.sanitize(o);return e}var R=(0,ue.createStore)((t,e)=>({params:{},query:{},setFromPattern:n=>{let r=window.location.pathname,o=Oe(n,r),s=be(window.location.search);t({params:o,query:s})},getParam:n=>e().params[n],getQuery:n=>e().query[n]}));function _(t){let e=R.getState();e.setFromPattern(t);let n=e.params,r=e.query;return{...n,...r}}var q=(t,e,n)=>{let r=document.querySelectorAll(t);return r.forEach(o=>{o.addEventListener(e,n)}),()=>{r.forEach(o=>{o.removeEventListener(e,n)})}};var b=E(require("dompurify"),1),U=(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","data-onselect"],FORBID_TAGS:["script","iframe"],ALLOWED_URI_REGEXP:/^(?:(?:https?|mailto|tel|ftp):|[^a-z]|[a-z+.\-]+(?:[^a-z+.\-:]|$))/i,...n};b.default.addHook("uponSanitizeElement",(i,a)=>{let c=a.tagName.toLowerCase();c.includes("-")&&(a.allowedTags[c]=!0)}),b.default.addHook("uponSanitizeAttribute",(i,a)=>{a.attrName&&a.attrName.toLowerCase().startsWith("on")&&(a.keepAttr=!1)});let s=b.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])}),t.querySelectorAll("[data-onselect]").forEach(i=>{let a=i.dataset.onselect;r[a]&&i.addEventListener("select",r[a])})};var me=E(require("dompurify"),1),C=null,j=(t,e)=>{if(typeof document>"u")return;let n=document.getElementById(t);if(!n)return;let r=n.innerHTML,s=me.default.sanitize(r,{ALLOWED_TAGS:["div","span","p","h1","h2","h3","h4","h5","h6","ul","ol","li","strong","em","a","img","br"],ALLOWED_ATTR:["href","src","alt","title","class","id","data-onclick","data-onchange"],ALLOW_DATA_ATTR:!1,KEEP_CONTENT:!1}).replace(/\b(href|src)=["']?(?!https?:|mailto:|\/|#)/gi,'$1="#"');if(C!==null&&s!==C){let i=document.createElement("div");e(i),n.innerHTML=C}else C=s,n.innerHTML=s,e(n)};var W=E(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 B=(t,e,n,r="",o=null)=>{if(!t)return;let s=W.default.sanitize(e,{ALLOWED_URI_REGEXP:/^(https?:|\/)/}),i=W.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 u=a.currentTarget.getAttribute("href");if(u){let f=window.scrollY;window.scrollTo(0,0),window.history.pushState({scrollPosition:f},"",u),dispatchEvent(new PopStateEvent("popstate"))}})};var w=E(require("dompurify"),1);var de=(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",u=!1)=>{let f=()=>{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 y=u?`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}; ${y}`)}catch(l){console.error("Error adding CSP meta element:",l)}};document.readyState==="loading"?document.addEventListener("DOMContentLoaded",f):f()};var G=(t,e)=>{let n={name:w.default.sanitize(t.name||""),description:w.default.sanitize(t.description||"Default description"),author:w.default.sanitize(t.author||"")},r=p=>{n.name=w.default.sanitize(p),l("name",n.name)},o=p=>{n.description=w.default.sanitize(p),l("description",n.description)},s=p=>{n.author=w.default.sanitize(p),l("author",n.author)},i=()=>n.name,a=()=>n.description,c=()=>n.author,u=()=>n,f=(p,m)=>{let d=document.createElement("meta");d.setAttribute("name",p),d.setAttribute("content",m),document.head.appendChild(d)},l=(p,m)=>{let d=document.querySelector(`meta[name="${p}"]`);d?d.setAttribute("content",m):f(p,m)},y=()=>{l("name",n.name),l("description",n.description),l("author",n.author)};return e&&de(e.scriptSrc,e.styleSrc,e.objectSrc,Array.isArray(e.connectSrc)?e.connectSrc.join(" "):e.connectSrc,e.reportOnly!==void 0?String(e.reportOnly):void 0),y(),{setName:r,setDescription:o,setAuthor:s,getName:i,getDescription:a,getAuthor:c,getAllMetaData:u,appendMetaTagsToHead:y}};var pe=E(require("dompurify"),1),A=(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=pe.default.sanitize(a.innerHTML,{USE_PROFILES:{html:!0}}),n(a,r,o)};var Q=(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],u=Array.isArray(r)?r[i]:void 0;typeof c=="function"?A(s,e,c,u):console.warn(`[useTSCollection] No valid component function found for ID: "${s}"`)})};var V=(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 fe=require("jwt-decode"),X=(t,e)=>{let n=localStorage.getItem("token");if(!n)return window.location.href=e,null;try{let r=(0,fe.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 P=(t,e,n)=>{t.forEach(r=>{e.forEach(o=>{r.addEventListener(o,s=>{n(r,s)})})})};var Y=()=>({back:()=>window.history.back(),forward:()=>window.history.forward()});var J=(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 K(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 he=require("zustand/vanilla");function Z(t){let e=(0,he.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 ee(t){let e=t();typeof e=="function"&&e()}var x=()=>{let t=document.querySelectorAll('a[href^="#"]');P(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 ge=require("lodash-es"),te=t=>t;typeof window<"u"&&typeof document<"u"&&(te=t=>{let e=document.createElement("div");return e.innerText=t,e.innerHTML});var Ce=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("class")||"";n.setAttribute("class",te(r));let o=n.getAttribute("aria-label");o&&n.setAttribute("aria-label",te(o));let s=n.querySelector(":scope > *");s&&(n.innerHTML="",n.appendChild(s));let i=n.getAttribute("href")||"";if(!i.startsWith("#")){try{if(new URL(i,window.location.href).origin!==window.location.origin)return}catch{return}n.addEventListener("click",a=>{a.preventDefault();let c=n.getAttribute("href")||"";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)}})}})},ke=(0,ge.debounce)(Ce,50),H=t=>{ke(t)};var D=t=>{let e=t.querySelectorAll("a");H(e)};var ne=t=>{x(),D(t)};var re=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.")},oe=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 se(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 ie=t=>typeof window>"u"?{isDOM:null}:{isDOM:t||document.body};var ae=E(require("dompurify"),1);var Se=require("zustand/vanilla"),Ee=E(require("dompurify"),1),v=(0,Se.createStore)(t=>({params:{},query:{},setParams:e=>t(()=>({params:Te(e)})),setQuery:e=>t(()=>({query:Te(e)}))}));function Te(t){let e={};for(let n in t)e[n]=Ee.default.sanitize(t[n]);return e}var k=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);v.getState().setParams(s),v.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);v.getState().setParams(i),v.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},u=this.filterAndSanitizeParams(c);if(v.getState().setParams(u),v.getState().setQuery(s),i.element?.(a,u,s),r.appendChild(a),i.children){let f=n.slice(i.path.length);this.renderChildren(i.children,f,a,u,s)}}}parseQueryParams(e){let n={},r=new URLSearchParams(e);for(let[o,s]of r.entries())this.expectedParams.has(o)&&(n[o]=ae.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/]+)")),u=new RegExp(`^${c}(?:/|$)`),f=e.match(u);if(f){let l={...r};if(a.forEach((y,p)=>{l[y]=f[p+1]??""}),o.children){let y=e.slice(f[0].length),p=this.findMatchingRoute(y,o.children,l);if(p)return p}return{...o,params:l}}}}}filterAndSanitizeParams(e){if(!e)return{};let n={};for(let r in e)this.expectedParams.has(r)&&(n[r]=ae.default.sanitize(e[r]??""));return n}navigate(e){history.pushState(null,"",e),this.handlePopState()}addRoute(e){this.routes.push(e)}};var ye=()=>({name:"ts-filebased-router",async buildStart(){if(typeof process>"u"||!process.versions?.node)return;let t=await import("fs/promises"),e=await import("path"),n=e.resolve("src/pages"),r=e.resolve("src/gen"),o=e.resolve("src/routes"),s=e.join(r,"tsrouter.gen.ts"),i=e.join(o,"__root.ts");async function a(m){try{await t.mkdir(m,{recursive:!0})}catch{}}function c(m,d){let S="/"+e.relative(d,m).replace(/\\/g,"/");return S=S.replace(/\.ts$/,"").replace(/\/index$/,"")||"/",S.replace(/\[(.+?)\]/g,":$1")}function u(m){return m.replace(/^\//,"").split("/").map(d=>d.startsWith(":")?d.slice(1):d).filter(Boolean).join("-")||"index"}function f(m,d){let h=e.relative(d,m).replace(/\\/g,"/").split("/").filter(Boolean),g=h[h.length-1].replace(".ts",""),L=h.length>1?h[h.length-2]:"";if(g.startsWith("[")&&g.endsWith("]")){let M=g.slice(1,-1);return L.charAt(0).toUpperCase()+L.slice(1)+M.charAt(0).toUpperCase()+M.slice(1)+"Param"}else return g.charAt(0).toUpperCase()+g.slice(1)}async function l(m){let d=await t.readdir(m,{withFileTypes:!0}),S=[];for(let h of d){let g=e.join(m,h.name);if(h.isDirectory())S=S.concat(await l(g));else if(h.isFile()&&h.name.endsWith(".ts")){let L=c(g,n),M=u(L),T=f(g,n);S.push({file:g,route:L,routeName:M,importName:T})}}return S}function y(){return`import { createRouter } from "@/gen/tsrouter.gen";
1
+ "use strict";var Me=Object.create;var C=Object.defineProperty;var Re=Object.getOwnPropertyDescriptor;var Ae=Object.getOwnPropertyNames;var Pe=Object.getPrototypeOf,xe=Object.prototype.hasOwnProperty;var De=(t,e)=>{for(var n in e)C(t,n,{get:e[n],enumerable:!0})},me=(t,e,n,r)=>{if(e&&typeof e=="object"||typeof e=="function")for(let o of Ae(e))!xe.call(t,o)&&o!==n&&C(t,o,{get:()=>e[o],enumerable:!(r=Re(e,o))||r.enumerable});return t};var E=(t,e,n)=>(n=t!=null?Me(Pe(t)):{},me(e||!t||!t.__esModule?C(n,"default",{value:t,enumerable:!0}):n,t)),He=t=>me(C({},"__esModule",{value:!0}),t);var Fe={};De(Fe,{TSFilebasedRouter:()=>Le,TSRouter:()=>k,createEffect:()=>ne,createSignal:()=>te,html:()=>F,loadPyFiles:()=>ie,mapper:()=>de,renderChildRoutes:()=>ee,useAnchor:()=>O,useAnchorSingle:()=>Q,useInitialDOM:()=>B,useTSAnchorMount:()=>oe,useTSAuth:()=>Y,useTSCollection:()=>J,useTSComponent:()=>x,useTSElementEach:()=>D,useTSElements:()=>W,useTSEvent:()=>_,useTSEventAll:()=>j,useTSExtractParams:()=>U,useTSHashAnchor:()=>H,useTSLazy:()=>ae,useTSMetaData:()=>V,useTSNavigate:()=>K,useTSNoReload:()=>b,useTSOutlet:()=>Z,useTSParams:()=>P,useTSPurifier:()=>I,useTSSSRHydration:()=>ce,useTSSelect:()=>X,useTSloadBrython:()=>se});module.exports=He(Fe);function Oe(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 F(t,...e){return t.reduce((n,r,o)=>{let s=o<e.length?Oe(e[o]):"";return n+r+s},"")}var be=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,""),de=t=>t?.map(e=>be(e)).join("")??"";var z=E(require("dompurify"),1),I=(t,e)=>{let r={...{ADD_TAGS:["my-custom-tag"]},...e};return typeof t=="string"?z.default.sanitize(t,r):z.default.sanitize(t.innerHTML,r)};var _=(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 pe=require("zustand/vanilla"),q=E(require("dompurify"),1);function Ce(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]=q.default.sanitize(s[c+1]??"")}),i}function $e(t){let e={},n=new URLSearchParams(t);for(let[r,o]of n.entries())e[r]=q.default.sanitize(o);return e}var P=(0,pe.createStore)((t,e)=>({params:{},query:{},setFromPattern:n=>{let r=window.location.pathname,o=Ce(n,r),s=$e(window.location.search);t({params:o,query:s})},getParam:n=>e().params[n],getQuery:n=>e().query[n]}));function U(t){let e=P.getState();e.setFromPattern(t);let n=e.params,r=e.query;return{...n,...r}}var j=(t,e,n)=>{let r=document.querySelectorAll(t);return r.forEach(o=>{o.addEventListener(e,n)}),()=>{r.forEach(o=>{o.removeEventListener(e,n)})}};var $=E(require("dompurify"),1),W=(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","data-onselect"],FORBID_TAGS:["script","iframe"],ALLOWED_URI_REGEXP:/^(?:(?:https?|mailto|tel|ftp):|[^a-z]|[a-z+.\-]+(?:[^a-z+.\-:]|$))/i,...n};$.default.addHook("uponSanitizeElement",(i,a)=>{let c=a.tagName.toLowerCase();c.includes("-")&&(a.allowedTags[c]=!0)}),$.default.addHook("uponSanitizeAttribute",(i,a)=>{a.attrName&&a.attrName.toLowerCase().startsWith("on")&&(a.keepAttr=!1)});let s=$.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])}),t.querySelectorAll("[data-onselect]").forEach(i=>{let a=i.dataset.onselect;r[a]&&i.addEventListener("select",r[a])})};var fe=E(require("dompurify"),1),N=null,B=(t,e)=>{if(typeof document>"u")return;let n=document.getElementById(t);if(!n)return;let r=n.innerHTML,s=fe.default.sanitize(r,{ALLOWED_TAGS:["div","span","p","h1","h2","h3","h4","h5","h6","ul","ol","li","strong","em","a","img","br"],ALLOWED_ATTR:["href","src","alt","title","class","id","data-onclick","data-onchange"],ALLOW_DATA_ATTR:!1,KEEP_CONTENT:!1}).replace(/\b(href|src)=["']?(?!https?:|mailto:|\/|#)/gi,'$1="#"');if(N!==null&&s!==N){let i=document.createElement("div");e(i),n.innerHTML=N}else N=s,n.innerHTML=s,e(n)};var G=E(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 Q=(t,e,n,r="",o=null)=>{if(!t)return;let s=G.default.sanitize(e,{ALLOWED_URI_REGEXP:/^(https?:|\/)/}),i=G.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 l=a.currentTarget.getAttribute("href");if(l){let T=window.scrollY;window.scrollTo(0,0),window.history.pushState({scrollPosition:T},"",l),dispatchEvent(new PopStateEvent("popstate"))}})};var A=E(require("dompurify"),1);var he=(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",l=!1)=>{let T=()=>{try{let u=document.querySelector('meta[http-equiv="Content-Security-Policy"]');u||(u=document.createElement("meta"),u.setAttribute("http-equiv","Content-Security-Policy"),document.head.appendChild(u));let y=l?`report-uri ${c};`:"";u.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}; ${y}`)}catch(u){console.error("Error adding CSP meta element:",u)}};document.readyState==="loading"?document.addEventListener("DOMContentLoaded",T):T()};var V=(t,e)=>{let n={name:A.default.sanitize(t.name||""),description:A.default.sanitize(t.description||"Default description"),author:A.default.sanitize(t.author||"")},r=p=>{n.name=A.default.sanitize(p),u("name",n.name)},o=p=>{n.description=A.default.sanitize(p),u("description",n.description)},s=p=>{n.author=A.default.sanitize(p),u("author",n.author)},i=()=>n.name,a=()=>n.description,c=()=>n.author,l=()=>n,T=(p,R)=>{let v=document.createElement("meta");v.setAttribute("name",p),v.setAttribute("content",R),document.head.appendChild(v)},u=(p,R)=>{let v=document.querySelector(`meta[name="${p}"]`);v?v.setAttribute("content",R):T(p,R)},y=()=>{u("name",n.name),u("description",n.description),u("author",n.author)};return e&&he(e.scriptSrc,e.styleSrc,e.objectSrc,Array.isArray(e.connectSrc)?e.connectSrc.join(" "):e.connectSrc,e.reportOnly!==void 0?String(e.reportOnly):void 0),y(),{setName:r,setDescription:o,setAuthor:s,getName:i,getDescription:a,getAuthor:c,getAllMetaData:l,appendMetaTagsToHead:y}};var ge=E(require("dompurify"),1),x=(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=ge.default.sanitize(a.innerHTML,{USE_PROFILES:{html:!0}}),n(a,r,o)};var J=(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],l=Array.isArray(r)?r[i]:void 0;typeof c=="function"?x(s,e,c,l):console.warn(`[useTSCollection] No valid component function found for ID: "${s}"`)})};var X=(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 Te=require("jwt-decode"),Y=(t,e)=>{let n=localStorage.getItem("token");if(!n)return window.location.href=e,null;try{let r=(0,Te.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 D=(t,e,n)=>{t.forEach(r=>{e.forEach(o=>{r.addEventListener(o,s=>{n(r,s)})})})};var K=()=>({back:()=>window.history.back(),forward:()=>window.history.forward()});var Z=(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 ee(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 Se=require("zustand/vanilla");function te(t){let e=(0,Se.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 ne(t){let e=t();typeof e=="function"&&e()}var H=()=>{let t=document.querySelectorAll('a[href^="#"]');D(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 Ee=require("lodash-es"),re=t=>t;typeof window<"u"&&typeof document<"u"&&(re=t=>{let e=document.createElement("div");return e.innerText=t,e.innerHTML});var Ne=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("class")||"";n.setAttribute("class",re(r));let o=n.getAttribute("aria-label");o&&n.setAttribute("aria-label",re(o));let s=n.querySelector(":scope > *");s&&(n.innerHTML="",n.appendChild(s));let i=n.getAttribute("href")||"";if(!i.startsWith("#")){try{if(new URL(i,window.location.href).origin!==window.location.origin)return}catch{return}n.addEventListener("click",a=>{a.preventDefault();let c=n.getAttribute("href")||"";try{let l=new URL(c,window.location.href);window.history.pushState({},"",l.pathname+l.search+l.hash),window.dispatchEvent(new PopStateEvent("popstate"))}catch(l){console.error("Invalid URL in anchor:",c,l)}})}})},ke=(0,Ee.debounce)(Ne,50),O=t=>{ke(t)};var b=t=>{let e=t.querySelectorAll("a");O(e)};var oe=t=>{H(),b(t)};var se=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.")},ie=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 ae(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 ce=t=>typeof window>"u"?{isDOM:null}:{isDOM:t||document.body};var le=E(require("dompurify"),1);var ve=require("zustand/vanilla"),we=E(require("dompurify"),1),M=(0,ve.createStore)(t=>({params:{},query:{},setParams:e=>t(()=>({params:ye(e)})),setQuery:e=>t(()=>({query:ye(e)}))}));function ye(t){let e={};for(let n in t)e[n]=we.default.sanitize(t[n]);return e}var k=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);M.getState().setParams(s),M.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);M.getState().setParams(i),M.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},l=this.filterAndSanitizeParams(c);if(M.getState().setParams(l),M.getState().setQuery(s),i.element?.(a,l,s),r.appendChild(a),i.children){let T=n.slice(i.path.length);this.renderChildren(i.children,T,a,l,s)}}}parseQueryParams(e){let n={},r=new URLSearchParams(e);for(let[o,s]of r.entries())this.expectedParams.has(o)&&(n[o]=le.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,u=>(a.push(u.substring(1)),"([^\\s/]+)")),l=new RegExp(`^${c}(?:/|$)`),T=e.match(l);if(T){let u={...r};if(a.forEach((y,p)=>{u[y]=T[p+1]??""}),o.children){let y=e.slice(T[0].length),p=this.findMatchingRoute(y,o.children,u);if(p)return p}return{...o,params:u}}}}}filterAndSanitizeParams(e){if(!e)return{};let n={};for(let r in e)this.expectedParams.has(r)&&(n[r]=le.default.sanitize(e[r]??""));return n}navigate(e){history.pushState(null,"",e),this.handlePopState()}addRoute(e){this.routes.push(e)}};var Le=()=>({name:"ts-filebased-router",async buildStart(){if(typeof process>"u"||!process.versions?.node)return;let t=await import("fs/promises"),e=await import("path"),n=await import("chokidar"),r=e.resolve("src/pages"),o=e.resolve("src/gen"),s=e.resolve("src/routes"),i=e.join(o,"tsrouter.gen.ts"),a=e.join(s,"__root.ts");async function c(d){try{await t.mkdir(d,{recursive:!0})}catch{}}function l(d,m){let f="/"+e.relative(m,d).replace(/\\/g,"/");return f=f.replace(/\.ts$/,"").replace(/\/index$/,"")||"/",f.replace(/\[(.+?)\]/g,":$1")}function T(d){return d.replace(/^\//,"").split("/").map(m=>m.startsWith(":")?m.slice(1):m).filter(Boolean).join("-")||"index"}function u(d,m){let g=e.relative(m,d).replace(/\\/g,"/").split("/").filter(Boolean),S=g[g.length-1].replace(".ts",""),w=g.length>1?g[g.length-2]:"";if(S.startsWith("[")&&S.endsWith("]")){let L=S.slice(1,-1);return w.charAt(0).toUpperCase()+w.slice(1)+L.charAt(0).toUpperCase()+L.slice(1)+"Param"}else return S.charAt(0).toUpperCase()+S.slice(1)}async function y(d){let m=await t.readdir(d,{withFileTypes:!0}),f=[];for(let g of m){let S=e.join(d,g.name);if(g.isDirectory())f=f.concat(await y(S));else if(g.isFile()&&g.name.endsWith(".ts")){let w=l(S,r),L=T(w),h=u(S,r);f.push({file:S,route:w,routeName:L,importName:h})}}return f}function p(d,m){let f=m.includes(":"),g=f?m.match(/:([^/]+)/)?.[1]:null;return`import { html, useTSElements, useTSMetaData${f?", useTSExtractParams":""} } from '@devwareng/vanilla-ts';
2
+
3
+ export default function ${d}(DOM: HTMLElement) {
4
+ useTSMetaData({ name: '${d.toLowerCase()}', description: '', author: '' });
5
+
6
+ ${f?`const params = useTSExtractParams("${m}");
7
+ if (!params.${g}) return;`:""}
8
+
9
+ return useTSElements(
10
+ DOM,
11
+ html\`
12
+ <div class="p-4">
13
+ <h1>${d}</h1>
14
+ ${f?"<pre>${JSON.stringify(params, null, 2)}</pre>":""}
15
+ </div>
16
+ \`
17
+ );
18
+ }`}function R(){return`import { createRouter } from "@/gen/tsrouter.gen";
2
19
  import { useTSParams } from "@devwareng/vanilla-ts";
3
20
 
4
21
  export const Router = (DOM: HTMLElement) => {
@@ -9,21 +26,21 @@ export const Router = (DOM: HTMLElement) => {
9
26
  window.addEventListener("popstate", () => {
10
27
  router.navigate(window.location.pathname);
11
28
  });
12
- };`}async function p(){let m=await l(n),d=m.find(T=>T.route==="/notfound"),S=m.filter(T=>T.route!=="/notfound"),h=m.map(T=>{let ve="../pages/"+e.relative(n,T.file).replace(/\\/g,"/").replace(/\.ts$/,"");return`import ${T.importName} from "${ve}";`}).join(`
13
- `),g=S.map(T=>`{ path: "${T.route}", name: "${T.routeName}", component: (DOM: HTMLElement) => ${T.importName}(DOM) }`).join(`,
14
- `),L=d?`export const NotFound = ${d.importName}`:"export function NotFound(DOM: HTMLElement) {\n return useTSElements(DOM, html`<div><h1>404 - Page Not Found</h1></div>`)\n}",M=`// AUTO-GENERATED FILE. DO NOT EDIT MANUALLY.
29
+ };`}async function v(){let d=await y(r),m=d.find(h=>h.route==="/notfound"),f=d.filter(h=>h.route!=="/notfound");for(let h of d)(await t.readFile(h.file,"utf-8")).trim()||await t.writeFile(h.file,p(h.importName,h.route),"utf-8");let g=d.map(h=>{let ue="../pages/"+e.relative(r,h.file).replace(/\\/g,"/").replace(/\.ts$/,"");return`import ${h.importName} from "${ue}";`}).join(`
30
+ `),S=f.map(h=>`{ path: "${h.route}", name: "${h.routeName}", component: (DOM: HTMLElement) => ${h.importName}(DOM) }`).join(`,
31
+ `),w=m?`export const NotFound = ${m.importName}`:"export function NotFound(DOM: HTMLElement) {\n return useTSElements(DOM, html`<div><h1>404 - Page Not Found</h1></div>`)\n}",L=`// AUTO-GENERATED FILE. DO NOT EDIT MANUALLY.
15
32
  import { html, useTSElements } from "@devwareng/vanilla-ts"
16
33
 
17
- ${h}
34
+ ${g}
18
35
 
19
- ${L}
36
+ ${w}
20
37
 
21
38
  export function RootDocument(DOM: HTMLElement) {
22
39
  return useTSElements(DOM, html\`<div><h1>Root</h1></div>\`)
23
40
  }
24
41
 
25
42
  export const routeTree = [
26
- ${g}
43
+ ${S}
27
44
  ]
28
45
 
29
46
  export function createRouter(DOM: HTMLElement) {
@@ -61,4 +78,4 @@ export function createRouter(DOM: HTMLElement) {
61
78
  navigate(window.location.pathname + window.location.search)
62
79
  return { navigate, routes: routeTree }
63
80
  }
64
- `;await a(r),await t.writeFile(s,M,"utf-8"),await t.writeFile(i,y(),"utf-8")}await a(r),await a(o),await p(),console.log("\u{1F7E2} TS Filebased Router Generated Successfully...")}});0&&(module.exports={TSFilebasedRouter,TSRouter,createEffect,createSignal,html,loadPyFiles,mapper,renderChildRoutes,useAnchor,useAnchorSingle,useInitialDOM,useTSAnchorMount,useTSAuth,useTSCollection,useTSComponent,useTSElementEach,useTSElements,useTSEvent,useTSEventAll,useTSExtractParams,useTSHashAnchor,useTSLazy,useTSMetaData,useTSNavigate,useTSNoReload,useTSOutlet,useTSParams,useTSPurifier,useTSSSRHydration,useTSSelect,useTSloadBrython});
81
+ `;await c(o),await t.writeFile(i,L,"utf-8"),await t.writeFile(a,R(),"utf-8")}await c(o),await c(s),await v(),n.watch(r).on("all",async(d,m)=>{if(d==="add"&&m.endsWith(".ts")){let g=e.basename(m,".ts").replace(/\[|\]/g,"Param").replace(/(^\w|-\w)/g,L=>L.replace("-","").toUpperCase()),S=l(m,r);(await t.readFile(m,"utf-8")).trim()||await t.writeFile(m,p(g,S),"utf-8"),await v()}}),n.watch(a).on("unlink",async()=>{await t.writeFile(a,R(),"utf-8")}),console.log("\u{1F7E2} TS Filebased Router Generated Successfully...")}});0&&(module.exports={TSFilebasedRouter,TSRouter,createEffect,createSignal,html,loadPyFiles,mapper,renderChildRoutes,useAnchor,useAnchorSingle,useInitialDOM,useTSAnchorMount,useTSAuth,useTSCollection,useTSComponent,useTSElementEach,useTSElements,useTSEvent,useTSEventAll,useTSExtractParams,useTSHashAnchor,useTSLazy,useTSMetaData,useTSNavigate,useTSNoReload,useTSOutlet,useTSParams,useTSPurifier,useTSSSRHydration,useTSSelect,useTSloadBrython});
package/dist/index.js CHANGED
@@ -1,4 +1,21 @@
1
- function le(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 k(t,...e){return t.reduce((n,r,o)=>{let s=o<e.length?le(e[o]):"";return n+r+s},"")}var ue=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,""),me=t=>t?.map(e=>ue(e)).join("")??"";import N from"dompurify";var $=(t,e)=>{let r={...{ADD_TAGS:["my-custom-tag"]},...e};return typeof t=="string"?N.sanitize(t,r):N.sanitize(t.innerHTML,r)};var F=(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.")};import{createStore as de}from"zustand/vanilla";import z from"dompurify";function pe(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]=z.sanitize(s[c+1]??"")}),i}function fe(t){let e={},n=new URLSearchParams(t);for(let[r,o]of n.entries())e[r]=z.sanitize(o);return e}var M=de((t,e)=>({params:{},query:{},setFromPattern:n=>{let r=window.location.pathname,o=pe(n,r),s=fe(window.location.search);t({params:o,query:s})},getParam:n=>e().params[n],getQuery:n=>e().query[n]}));function I(t){let e=M.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)})}};import O from"dompurify";var q=(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","data-onselect"],FORBID_TAGS:["script","iframe"],ALLOWED_URI_REGEXP:/^(?:(?:https?|mailto|tel|ftp):|[^a-z]|[a-z+.\-]+(?:[^a-z+.\-:]|$))/i,...n};O.addHook("uponSanitizeElement",(i,a)=>{let c=a.tagName.toLowerCase();c.includes("-")&&(a.allowedTags[c]=!0)}),O.addHook("uponSanitizeAttribute",(i,a)=>{a.attrName&&a.attrName.toLowerCase().startsWith("on")&&(a.keepAttr=!1)});let s=O.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])}),t.querySelectorAll("[data-onselect]").forEach(i=>{let a=i.dataset.onselect;r[a]&&i.addEventListener("select",r[a])})};import he from"dompurify";var R=null,U=(t,e)=>{if(typeof document>"u")return;let n=document.getElementById(t);if(!n)return;let r=n.innerHTML,s=he.sanitize(r,{ALLOWED_TAGS:["div","span","p","h1","h2","h3","h4","h5","h6","ul","ol","li","strong","em","a","img","br"],ALLOWED_ATTR:["href","src","alt","title","class","id","data-onclick","data-onchange"],ALLOW_DATA_ATTR:!1,KEEP_CONTENT:!1}).replace(/\b(href|src)=["']?(?!https?:|mailto:|\/|#)/gi,'$1="#"');if(R!==null&&s!==R){let i=document.createElement("div");e(i),n.innerHTML=R}else R=s,n.innerHTML=s,e(n)};import j from"dompurify";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 W=(t,e,n,r="",o=null)=>{if(!t)return;let s=j.sanitize(e,{ALLOWED_URI_REGEXP:/^(https?:|\/)/}),i=j.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 u=a.currentTarget.getAttribute("href");if(u){let f=window.scrollY;window.scrollTo(0,0),window.history.pushState({scrollPosition:f},"",u),dispatchEvent(new PopStateEvent("popstate"))}})};import w from"dompurify";var B=(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",u=!1)=>{let f=()=>{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 E=u?`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}; ${E}`)}catch(l){console.error("Error adding CSP meta element:",l)}};document.readyState==="loading"?document.addEventListener("DOMContentLoaded",f):f()};var G=(t,e)=>{let n={name:w.sanitize(t.name||""),description:w.sanitize(t.description||"Default description"),author:w.sanitize(t.author||"")},r=p=>{n.name=w.sanitize(p),l("name",n.name)},o=p=>{n.description=w.sanitize(p),l("description",n.description)},s=p=>{n.author=w.sanitize(p),l("author",n.author)},i=()=>n.name,a=()=>n.description,c=()=>n.author,u=()=>n,f=(p,m)=>{let d=document.createElement("meta");d.setAttribute("name",p),d.setAttribute("content",m),document.head.appendChild(d)},l=(p,m)=>{let d=document.querySelector(`meta[name="${p}"]`);d?d.setAttribute("content",m):f(p,m)},E=()=>{l("name",n.name),l("description",n.description),l("author",n.author)};return e&&B(e.scriptSrc,e.styleSrc,e.objectSrc,Array.isArray(e.connectSrc)?e.connectSrc.join(" "):e.connectSrc,e.reportOnly!==void 0?String(e.reportOnly):void 0),E(),{setName:r,setDescription:o,setAuthor:s,getName:i,getDescription:a,getAuthor:c,getAllMetaData:u,appendMetaTagsToHead:E}};import ge from"dompurify";var A=(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=ge.sanitize(a.innerHTML,{USE_PROFILES:{html:!0}}),n(a,r,o)};var Q=(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],u=Array.isArray(r)?r[i]:void 0;typeof c=="function"?A(s,e,c,u):console.warn(`[useTSCollection] No valid component function found for ID: "${s}"`)})};var V=(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]};import{jwtDecode as Te}from"jwt-decode";var X=(t,e)=>{let n=localStorage.getItem("token");if(!n)return window.location.href=e,null;try{let r=Te(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 P=(t,e,n)=>{t.forEach(r=>{e.forEach(o=>{r.addEventListener(o,s=>{n(r,s)})})})};var Y=()=>({back:()=>window.history.back(),forward:()=>window.history.forward()});var J=(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 K(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)}})})}import{createStore as Se}from"zustand/vanilla";function Z(t){let e=Se(()=>({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 ee(t){let e=t();typeof e=="function"&&e()}var x=()=>{let t=document.querySelectorAll('a[href^="#"]');P(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"})})};import{debounce as Ee}from"lodash-es";var b=t=>t;typeof window<"u"&&typeof document<"u"&&(b=t=>{let e=document.createElement("div");return e.innerText=t,e.innerHTML});var ye=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("class")||"";n.setAttribute("class",b(r));let o=n.getAttribute("aria-label");o&&n.setAttribute("aria-label",b(o));let s=n.querySelector(":scope > *");s&&(n.innerHTML="",n.appendChild(s));let i=n.getAttribute("href")||"";if(!i.startsWith("#")){try{if(new URL(i,window.location.href).origin!==window.location.origin)return}catch{return}n.addEventListener("click",a=>{a.preventDefault();let c=n.getAttribute("href")||"";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)}})}})},ve=Ee(ye,50),H=t=>{ve(t)};var D=t=>{let e=t.querySelectorAll("a");H(e)};var te=t=>{x(),D(t)};var ne=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.")},re=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 oe(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 se=t=>typeof window>"u"?{isDOM:null}:{isDOM:t||document.body};import ae from"dompurify";import{createStore as Le}from"zustand/vanilla";import we from"dompurify";var y=Le(t=>({params:{},query:{},setParams:e=>t(()=>({params:ie(e)})),setQuery:e=>t(()=>({query:ie(e)}))}));function ie(t){let e={};for(let n in t)e[n]=we.sanitize(t[n]);return e}var C=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);y.getState().setParams(s),y.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);y.getState().setParams(i),y.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},u=this.filterAndSanitizeParams(c);if(y.getState().setParams(u),y.getState().setQuery(s),i.element?.(a,u,s),r.appendChild(a),i.children){let f=n.slice(i.path.length);this.renderChildren(i.children,f,a,u,s)}}}parseQueryParams(e){let n={},r=new URLSearchParams(e);for(let[o,s]of r.entries())this.expectedParams.has(o)&&(n[o]=ae.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/]+)")),u=new RegExp(`^${c}(?:/|$)`),f=e.match(u);if(f){let l={...r};if(a.forEach((E,p)=>{l[E]=f[p+1]??""}),o.children){let E=e.slice(f[0].length),p=this.findMatchingRoute(E,o.children,l);if(p)return p}return{...o,params:l}}}}}filterAndSanitizeParams(e){if(!e)return{};let n={};for(let r in e)this.expectedParams.has(r)&&(n[r]=ae.sanitize(e[r]??""));return n}navigate(e){history.pushState(null,"",e),this.handlePopState()}addRoute(e){this.routes.push(e)}};var Me=()=>({name:"ts-filebased-router",async buildStart(){if(typeof process>"u"||!process.versions?.node)return;let t=await import("fs/promises"),e=await import("path"),n=e.resolve("src/pages"),r=e.resolve("src/gen"),o=e.resolve("src/routes"),s=e.join(r,"tsrouter.gen.ts"),i=e.join(o,"__root.ts");async function a(m){try{await t.mkdir(m,{recursive:!0})}catch{}}function c(m,d){let S="/"+e.relative(d,m).replace(/\\/g,"/");return S=S.replace(/\.ts$/,"").replace(/\/index$/,"")||"/",S.replace(/\[(.+?)\]/g,":$1")}function u(m){return m.replace(/^\//,"").split("/").map(d=>d.startsWith(":")?d.slice(1):d).filter(Boolean).join("-")||"index"}function f(m,d){let h=e.relative(d,m).replace(/\\/g,"/").split("/").filter(Boolean),g=h[h.length-1].replace(".ts",""),v=h.length>1?h[h.length-2]:"";if(g.startsWith("[")&&g.endsWith("]")){let L=g.slice(1,-1);return v.charAt(0).toUpperCase()+v.slice(1)+L.charAt(0).toUpperCase()+L.slice(1)+"Param"}else return g.charAt(0).toUpperCase()+g.slice(1)}async function l(m){let d=await t.readdir(m,{withFileTypes:!0}),S=[];for(let h of d){let g=e.join(m,h.name);if(h.isDirectory())S=S.concat(await l(g));else if(h.isFile()&&h.name.endsWith(".ts")){let v=c(g,n),L=u(v),T=f(g,n);S.push({file:g,route:v,routeName:L,importName:T})}}return S}function E(){return`import { createRouter } from "@/gen/tsrouter.gen";
1
+ function me(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 F(t,...e){return t.reduce((n,r,o)=>{let s=o<e.length?me(e[o]):"";return n+r+s},"")}var de=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,""),pe=t=>t?.map(e=>de(e)).join("")??"";import z from"dompurify";var I=(t,e)=>{let r={...{ADD_TAGS:["my-custom-tag"]},...e};return typeof t=="string"?z.sanitize(t,r):z.sanitize(t.innerHTML,r)};var _=(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.")};import{createStore as fe}from"zustand/vanilla";import q from"dompurify";function he(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]=q.sanitize(s[c+1]??"")}),i}function ge(t){let e={},n=new URLSearchParams(t);for(let[r,o]of n.entries())e[r]=q.sanitize(o);return e}var A=fe((t,e)=>({params:{},query:{},setFromPattern:n=>{let r=window.location.pathname,o=he(n,r),s=ge(window.location.search);t({params:o,query:s})},getParam:n=>e().params[n],getQuery:n=>e().query[n]}));function U(t){let e=A.getState();e.setFromPattern(t);let n=e.params,r=e.query;return{...n,...r}}var j=(t,e,n)=>{let r=document.querySelectorAll(t);return r.forEach(o=>{o.addEventListener(e,n)}),()=>{r.forEach(o=>{o.removeEventListener(e,n)})}};import C from"dompurify";var W=(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","data-onselect"],FORBID_TAGS:["script","iframe"],ALLOWED_URI_REGEXP:/^(?:(?:https?|mailto|tel|ftp):|[^a-z]|[a-z+.\-]+(?:[^a-z+.\-:]|$))/i,...n};C.addHook("uponSanitizeElement",(i,a)=>{let c=a.tagName.toLowerCase();c.includes("-")&&(a.allowedTags[c]=!0)}),C.addHook("uponSanitizeAttribute",(i,a)=>{a.attrName&&a.attrName.toLowerCase().startsWith("on")&&(a.keepAttr=!1)});let s=C.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])}),t.querySelectorAll("[data-onselect]").forEach(i=>{let a=i.dataset.onselect;r[a]&&i.addEventListener("select",r[a])})};import Te from"dompurify";var P=null,B=(t,e)=>{if(typeof document>"u")return;let n=document.getElementById(t);if(!n)return;let r=n.innerHTML,s=Te.sanitize(r,{ALLOWED_TAGS:["div","span","p","h1","h2","h3","h4","h5","h6","ul","ol","li","strong","em","a","img","br"],ALLOWED_ATTR:["href","src","alt","title","class","id","data-onclick","data-onchange"],ALLOW_DATA_ATTR:!1,KEEP_CONTENT:!1}).replace(/\b(href|src)=["']?(?!https?:|mailto:|\/|#)/gi,'$1="#"');if(P!==null&&s!==P){let i=document.createElement("div");e(i),n.innerHTML=P}else P=s,n.innerHTML=s,e(n)};import G from"dompurify";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 Q=(t,e,n,r="",o=null)=>{if(!t)return;let s=G.sanitize(e,{ALLOWED_URI_REGEXP:/^(https?:|\/)/}),i=G.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 l=a.currentTarget.getAttribute("href");if(l){let T=window.scrollY;window.scrollTo(0,0),window.history.pushState({scrollPosition:T},"",l),dispatchEvent(new PopStateEvent("popstate"))}})};import R from"dompurify";var V=(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",l=!1)=>{let T=()=>{try{let u=document.querySelector('meta[http-equiv="Content-Security-Policy"]');u||(u=document.createElement("meta"),u.setAttribute("http-equiv","Content-Security-Policy"),document.head.appendChild(u));let E=l?`report-uri ${c};`:"";u.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}; ${E}`)}catch(u){console.error("Error adding CSP meta element:",u)}};document.readyState==="loading"?document.addEventListener("DOMContentLoaded",T):T()};var J=(t,e)=>{let n={name:R.sanitize(t.name||""),description:R.sanitize(t.description||"Default description"),author:R.sanitize(t.author||"")},r=p=>{n.name=R.sanitize(p),u("name",n.name)},o=p=>{n.description=R.sanitize(p),u("description",n.description)},s=p=>{n.author=R.sanitize(p),u("author",n.author)},i=()=>n.name,a=()=>n.description,c=()=>n.author,l=()=>n,T=(p,M)=>{let y=document.createElement("meta");y.setAttribute("name",p),y.setAttribute("content",M),document.head.appendChild(y)},u=(p,M)=>{let y=document.querySelector(`meta[name="${p}"]`);y?y.setAttribute("content",M):T(p,M)},E=()=>{u("name",n.name),u("description",n.description),u("author",n.author)};return e&&V(e.scriptSrc,e.styleSrc,e.objectSrc,Array.isArray(e.connectSrc)?e.connectSrc.join(" "):e.connectSrc,e.reportOnly!==void 0?String(e.reportOnly):void 0),E(),{setName:r,setDescription:o,setAuthor:s,getName:i,getDescription:a,getAuthor:c,getAllMetaData:l,appendMetaTagsToHead:E}};import Se from"dompurify";var x=(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=Se.sanitize(a.innerHTML,{USE_PROFILES:{html:!0}}),n(a,r,o)};var X=(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],l=Array.isArray(r)?r[i]:void 0;typeof c=="function"?x(s,e,c,l):console.warn(`[useTSCollection] No valid component function found for ID: "${s}"`)})};var Y=(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]};import{jwtDecode as Ee}from"jwt-decode";var K=(t,e)=>{let n=localStorage.getItem("token");if(!n)return window.location.href=e,null;try{let r=Ee(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 D=(t,e,n)=>{t.forEach(r=>{e.forEach(o=>{r.addEventListener(o,s=>{n(r,s)})})})};var Z=()=>({back:()=>window.history.back(),forward:()=>window.history.forward()});var ee=(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 te(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)}})})}import{createStore as ye}from"zustand/vanilla";function ne(t){let e=ye(()=>({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 re(t){let e=t();typeof e=="function"&&e()}var H=()=>{let t=document.querySelectorAll('a[href^="#"]');D(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"})})};import{debounce as ve}from"lodash-es";var $=t=>t;typeof window<"u"&&typeof document<"u"&&($=t=>{let e=document.createElement("div");return e.innerText=t,e.innerHTML});var we=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("class")||"";n.setAttribute("class",$(r));let o=n.getAttribute("aria-label");o&&n.setAttribute("aria-label",$(o));let s=n.querySelector(":scope > *");s&&(n.innerHTML="",n.appendChild(s));let i=n.getAttribute("href")||"";if(!i.startsWith("#")){try{if(new URL(i,window.location.href).origin!==window.location.origin)return}catch{return}n.addEventListener("click",a=>{a.preventDefault();let c=n.getAttribute("href")||"";try{let l=new URL(c,window.location.href);window.history.pushState({},"",l.pathname+l.search+l.hash),window.dispatchEvent(new PopStateEvent("popstate"))}catch(l){console.error("Invalid URL in anchor:",c,l)}})}})},Le=ve(we,50),O=t=>{Le(t)};var b=t=>{let e=t.querySelectorAll("a");O(e)};var oe=t=>{H(),b(t)};var se=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.")},ie=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 ae(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 ce=t=>typeof window>"u"?{isDOM:null}:{isDOM:t||document.body};import ue from"dompurify";import{createStore as Me}from"zustand/vanilla";import Re from"dompurify";var L=Me(t=>({params:{},query:{},setParams:e=>t(()=>({params:le(e)})),setQuery:e=>t(()=>({query:le(e)}))}));function le(t){let e={};for(let n in t)e[n]=Re.sanitize(t[n]);return e}var N=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);L.getState().setParams(s),L.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);L.getState().setParams(i),L.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},l=this.filterAndSanitizeParams(c);if(L.getState().setParams(l),L.getState().setQuery(s),i.element?.(a,l,s),r.appendChild(a),i.children){let T=n.slice(i.path.length);this.renderChildren(i.children,T,a,l,s)}}}parseQueryParams(e){let n={},r=new URLSearchParams(e);for(let[o,s]of r.entries())this.expectedParams.has(o)&&(n[o]=ue.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,u=>(a.push(u.substring(1)),"([^\\s/]+)")),l=new RegExp(`^${c}(?:/|$)`),T=e.match(l);if(T){let u={...r};if(a.forEach((E,p)=>{u[E]=T[p+1]??""}),o.children){let E=e.slice(T[0].length),p=this.findMatchingRoute(E,o.children,u);if(p)return p}return{...o,params:u}}}}}filterAndSanitizeParams(e){if(!e)return{};let n={};for(let r in e)this.expectedParams.has(r)&&(n[r]=ue.sanitize(e[r]??""));return n}navigate(e){history.pushState(null,"",e),this.handlePopState()}addRoute(e){this.routes.push(e)}};var Ae=()=>({name:"ts-filebased-router",async buildStart(){if(typeof process>"u"||!process.versions?.node)return;let t=await import("fs/promises"),e=await import("path"),n=await import("chokidar"),r=e.resolve("src/pages"),o=e.resolve("src/gen"),s=e.resolve("src/routes"),i=e.join(o,"tsrouter.gen.ts"),a=e.join(s,"__root.ts");async function c(d){try{await t.mkdir(d,{recursive:!0})}catch{}}function l(d,m){let f="/"+e.relative(m,d).replace(/\\/g,"/");return f=f.replace(/\.ts$/,"").replace(/\/index$/,"")||"/",f.replace(/\[(.+?)\]/g,":$1")}function T(d){return d.replace(/^\//,"").split("/").map(m=>m.startsWith(":")?m.slice(1):m).filter(Boolean).join("-")||"index"}function u(d,m){let g=e.relative(m,d).replace(/\\/g,"/").split("/").filter(Boolean),S=g[g.length-1].replace(".ts",""),v=g.length>1?g[g.length-2]:"";if(S.startsWith("[")&&S.endsWith("]")){let w=S.slice(1,-1);return v.charAt(0).toUpperCase()+v.slice(1)+w.charAt(0).toUpperCase()+w.slice(1)+"Param"}else return S.charAt(0).toUpperCase()+S.slice(1)}async function E(d){let m=await t.readdir(d,{withFileTypes:!0}),f=[];for(let g of m){let S=e.join(d,g.name);if(g.isDirectory())f=f.concat(await E(S));else if(g.isFile()&&g.name.endsWith(".ts")){let v=l(S,r),w=T(v),h=u(S,r);f.push({file:S,route:v,routeName:w,importName:h})}}return f}function p(d,m){let f=m.includes(":"),g=f?m.match(/:([^/]+)/)?.[1]:null;return`import { html, useTSElements, useTSMetaData${f?", useTSExtractParams":""} } from '@devwareng/vanilla-ts';
2
+
3
+ export default function ${d}(DOM: HTMLElement) {
4
+ useTSMetaData({ name: '${d.toLowerCase()}', description: '', author: '' });
5
+
6
+ ${f?`const params = useTSExtractParams("${m}");
7
+ if (!params.${g}) return;`:""}
8
+
9
+ return useTSElements(
10
+ DOM,
11
+ html\`
12
+ <div class="p-4">
13
+ <h1>${d}</h1>
14
+ ${f?"<pre>${JSON.stringify(params, null, 2)}</pre>":""}
15
+ </div>
16
+ \`
17
+ );
18
+ }`}function M(){return`import { createRouter } from "@/gen/tsrouter.gen";
2
19
  import { useTSParams } from "@devwareng/vanilla-ts";
3
20
 
4
21
  export const Router = (DOM: HTMLElement) => {
@@ -9,12 +26,12 @@ export const Router = (DOM: HTMLElement) => {
9
26
  window.addEventListener("popstate", () => {
10
27
  router.navigate(window.location.pathname);
11
28
  });
12
- };`}async function p(){let m=await l(n),d=m.find(T=>T.route==="/notfound"),S=m.filter(T=>T.route!=="/notfound"),h=m.map(T=>{let ce="../pages/"+e.relative(n,T.file).replace(/\\/g,"/").replace(/\.ts$/,"");return`import ${T.importName} from "${ce}";`}).join(`
13
- `),g=S.map(T=>`{ path: "${T.route}", name: "${T.routeName}", component: (DOM: HTMLElement) => ${T.importName}(DOM) }`).join(`,
14
- `),v=d?`export const NotFound = ${d.importName}`:"export function NotFound(DOM: HTMLElement) {\n return useTSElements(DOM, html`<div><h1>404 - Page Not Found</h1></div>`)\n}",L=`// AUTO-GENERATED FILE. DO NOT EDIT MANUALLY.
29
+ };`}async function y(){let d=await E(r),m=d.find(h=>h.route==="/notfound"),f=d.filter(h=>h.route!=="/notfound");for(let h of d)(await t.readFile(h.file,"utf-8")).trim()||await t.writeFile(h.file,p(h.importName,h.route),"utf-8");let g=d.map(h=>{let k="../pages/"+e.relative(r,h.file).replace(/\\/g,"/").replace(/\.ts$/,"");return`import ${h.importName} from "${k}";`}).join(`
30
+ `),S=f.map(h=>`{ path: "${h.route}", name: "${h.routeName}", component: (DOM: HTMLElement) => ${h.importName}(DOM) }`).join(`,
31
+ `),v=m?`export const NotFound = ${m.importName}`:"export function NotFound(DOM: HTMLElement) {\n return useTSElements(DOM, html`<div><h1>404 - Page Not Found</h1></div>`)\n}",w=`// AUTO-GENERATED FILE. DO NOT EDIT MANUALLY.
15
32
  import { html, useTSElements } from "@devwareng/vanilla-ts"
16
33
 
17
- ${h}
34
+ ${g}
18
35
 
19
36
  ${v}
20
37
 
@@ -23,7 +40,7 @@ export function RootDocument(DOM: HTMLElement) {
23
40
  }
24
41
 
25
42
  export const routeTree = [
26
- ${g}
43
+ ${S}
27
44
  ]
28
45
 
29
46
  export function createRouter(DOM: HTMLElement) {
@@ -61,4 +78,4 @@ export function createRouter(DOM: HTMLElement) {
61
78
  navigate(window.location.pathname + window.location.search)
62
79
  return { navigate, routes: routeTree }
63
80
  }
64
- `;await a(r),await t.writeFile(s,L,"utf-8"),await t.writeFile(i,E(),"utf-8")}await a(r),await a(o),await p(),console.log("\u{1F7E2} TS Filebased Router Generated Successfully...")}});export{Me as TSFilebasedRouter,C as TSRouter,ee as createEffect,Z as createSignal,k as html,re as loadPyFiles,me as mapper,K as renderChildRoutes,H as useAnchor,W as useAnchorSingle,U as useInitialDOM,te as useTSAnchorMount,X as useTSAuth,Q as useTSCollection,A as useTSComponent,P as useTSElementEach,q as useTSElements,F as useTSEvent,_ as useTSEventAll,I as useTSExtractParams,x as useTSHashAnchor,oe as useTSLazy,G as useTSMetaData,Y as useTSNavigate,D as useTSNoReload,J as useTSOutlet,M as useTSParams,$ as useTSPurifier,se as useTSSSRHydration,V as useTSSelect,ne as useTSloadBrython};
81
+ `;await c(o),await t.writeFile(i,w,"utf-8"),await t.writeFile(a,M(),"utf-8")}await c(o),await c(s),await y(),n.watch(r).on("all",async(d,m)=>{if(d==="add"&&m.endsWith(".ts")){let g=e.basename(m,".ts").replace(/\[|\]/g,"Param").replace(/(^\w|-\w)/g,w=>w.replace("-","").toUpperCase()),S=l(m,r);(await t.readFile(m,"utf-8")).trim()||await t.writeFile(m,p(g,S),"utf-8"),await y()}}),n.watch(a).on("unlink",async()=>{await t.writeFile(a,M(),"utf-8")}),console.log("\u{1F7E2} TS Filebased Router Generated Successfully...")}});export{Ae as TSFilebasedRouter,N as TSRouter,re as createEffect,ne as createSignal,F as html,ie as loadPyFiles,pe as mapper,te as renderChildRoutes,O as useAnchor,Q as useAnchorSingle,B as useInitialDOM,oe as useTSAnchorMount,K as useTSAuth,X as useTSCollection,x as useTSComponent,D as useTSElementEach,W as useTSElements,_ as useTSEvent,j as useTSEventAll,U as useTSExtractParams,H as useTSHashAnchor,ae as useTSLazy,J as useTSMetaData,Z as useTSNavigate,b as useTSNoReload,ee as useTSOutlet,A as useTSParams,I as useTSPurifier,ce as useTSSSRHydration,Y as useTSSelect,se as useTSloadBrython};
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "@devwareng/vanilla-ts",
3
- "version": "1.4.49",
3
+ "version": "1.4.50",
4
4
  "description": "Framework-less TypeScript hooks for SPA development.",
5
5
  "author": "Waren Arapoc Gador",
6
6
  "license": "MIT",