llmd 0.1.0 → 0.1.1

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
package/README.md CHANGED
@@ -4,15 +4,6 @@
4
4
 
5
5
  A zero-config CLI tool for viewing Markdown files in your browser with syntax highlighting, live reload, and a clean interface. Built for developers reviewing LLM-generated documentation.
6
6
 
7
- ```
8
- ██╗ ██╗ ███╗ ███╗██████╗
9
- ██║ ██║ ████╗ ████║██╔══██╗
10
- ██║ ██║ ██╔████╔██║██║ ██║
11
- ██║ ██║ ██║╚██╔╝██║██║ ██║
12
- ███████╗███████╗██║ ╚═╝ ██║██████╔╝
13
- ╚══════╝╚══════╝╚═╝ ╚═╝╚═════╝
14
- ```
15
-
16
7
  ## Features
17
8
 
18
9
  - **Zero config** - Point at a directory and go
@@ -33,6 +24,7 @@ npm install -g llmd
33
24
  ```
34
25
 
35
26
  Or run directly without installing:
27
+
36
28
  ```bash
37
29
  npx llmd
38
30
  ```
@@ -88,6 +80,7 @@ Create custom font combinations in your `themes.json` config file.
88
80
  **Location:** `~/.config/llmd/themes.json` (or `$XDG_CONFIG_HOME/llmd/themes.json`)
89
81
 
90
82
  **Simple Example (Auto-loaded from Google Fonts):**
83
+
91
84
  ```json
92
85
  {
93
86
  "fontThemes": {
@@ -103,12 +96,13 @@ Create custom font combinations in your `themes.json` config file.
103
96
  Google Fonts are **loaded automatically** with weights 400 and 700. Just specify the font family names - no need to construct Google Fonts URLs manually!
104
97
 
105
98
  **Advanced Example (Custom Weights/Styles):**
99
+
106
100
  ```json
107
101
  {
108
102
  "fontThemes": {
109
103
  "custom": {
110
104
  "heading": "Poppins, sans-serif",
111
- "body": "Inter, sans-serif",
105
+ "body": "Inter, sans-serif",
112
106
  "code": "Fira Code, monospace",
113
107
  "googleFontsUrl": "https://fonts.googleapis.com/css2?family=Poppins:wght@400;600;700&family=Inter:wght@300;400;500&family=Fira+Code:wght@400;500&display=swap"
114
108
  }
@@ -119,11 +113,13 @@ Google Fonts are **loaded automatically** with weights 400 and 700. Just specify
119
113
  Use `googleFontsUrl` only if you need specific weights (like 300, 500, 600) or styles (italic, etc.). Get custom URLs from [Google Fonts](https://fonts.google.com).
120
114
 
121
115
  **Usage:**
116
+
122
117
  ```bash
123
118
  llmd --fonts myfont
124
119
  ```
125
120
 
126
121
  **Requirements:**
122
+
127
123
  - `heading`, `body`, and `code` properties are required
128
124
  - Font names should include CSS fallbacks (e.g., `"Roboto, sans-serif"`)
129
125
  - System fonts (Arial, Georgia, etc.) don't load from Google Fonts
@@ -147,6 +143,7 @@ Create custom color themes in your `themes.json` config file.
147
143
  **Location:** `~/.config/llmd/themes.json` (or `$XDG_CONFIG_HOME/llmd/themes.json`)
148
144
 
149
145
  **Format:**
146
+
150
147
  ```json
151
148
  {
152
149
  "colorThemes": {
@@ -167,6 +164,7 @@ Create custom color themes in your `themes.json` config file.
167
164
 
168
165
  **Unified Config:**
169
166
  You can combine both color themes and font themes in a single file:
167
+
170
168
  ```json
171
169
  {
172
170
  "colorThemes": {
@@ -179,6 +177,7 @@ You can combine both color themes and font themes in a single file:
179
177
  ```
180
178
 
181
179
  **Usage:**
180
+
182
181
  ```bash
183
182
  llmd --theme mytheme --fonts myfont
184
183
  ```
@@ -189,16 +188,16 @@ If a theme or font is not found, llmd will list all available options.
189
188
 
190
189
  ## Options
191
190
 
192
- | Flag | Description | Default |
193
- |------|-------------|---------|
194
- | `--port <number>` | Port (0 = random) | `0` (random) |
195
- | `--host <string>` | Host interface | `localhost` |
196
- | `--theme <name>` | Color theme: `dark`, `light`, `nord`, `dracula`, `solarized`, `monokai`, or custom | `dark` |
197
- | `--fonts <name>` | Font combination: `serif`, `sans`, `mono`, `classic`, `future`, `modern`, `artsy`, `literary`, `editorial` | `sans` |
198
- | `--open / --no-open` | Auto-open browser | `--open` |
199
- | `--watch / --no-watch` | Live reload on changes | `--no-watch` |
200
- | `-h, --help` | Show help | |
201
- | `--version` | Show version | |
191
+ | Flag | Description | Default |
192
+ | ---------------------- | ---------------------------------------------------------------------------------------------------------- | ------------ |
193
+ | `--port <number>` | Port (0 = random) | `0` (random) |
194
+ | `--host <string>` | Host interface | `localhost` |
195
+ | `--theme <name>` | Color theme: `dark`, `light`, `nord`, `dracula`, `solarized`, `monokai`, or custom | `dark` |
196
+ | `--fonts <name>` | Font combination: `serif`, `sans`, `mono`, `classic`, `future`, `modern`, `artsy`, `literary`, `editorial` | `sans` |
197
+ | `--open / --no-open` | Auto-open browser | `--open` |
198
+ | `--watch / --no-watch` | Live reload on changes | `--no-watch` |
199
+ | `-h, --help` | Show help | |
200
+ | `--version` | Show version | |
202
201
 
203
202
  ## Development
204
203
 
package/dist/client.js CHANGED
@@ -1 +1 @@
1
- var s=()=>{document.querySelectorAll("pre code").forEach((o)=>{let d=o.parentElement;if(!d)return;if(d.querySelector(".copy-button"))return;let t=document.createElement("button");t.className="copy-button",t.textContent="Copy",t.setAttribute("aria-label","Copy code to clipboard"),t.addEventListener("click",async()=>{try{await navigator.clipboard.writeText(o.textContent||""),t.textContent="Copied!",t.classList.add("copied"),setTimeout(()=>{t.textContent="Copy",t.classList.remove("copied")},2000)}catch(e){console.error("Failed to copy:",e),t.textContent="Failed",setTimeout(()=>{t.textContent="Copy"},2000)}}),d.appendChild(t)})};if(document.readyState==="loading")document.addEventListener("DOMContentLoaded",s);else s();var p=(o)=>{let t=`${window.location.protocol==="https:"?"wss:":"ws:"}//${window.location.host}/_ws`,e=null,n=null,l=()=>{e=new WebSocket(t),e.addEventListener("open",()=>{console.log("[llmd] Connected to file watcher"),e?.send(JSON.stringify({type:"watch",file:o}))}),e.addEventListener("message",(i)=>{try{let a=JSON.parse(i.data);if(a.type==="reload"&&a.file===o)console.log(`[llmd] File changed: ${o}, reloading...`),window.location.reload()}catch(a){console.error("[llmd] Failed to parse message:",a)}}),e.addEventListener("close",()=>{console.log("[llmd] Disconnected from file watcher"),n=window.setTimeout(()=>{console.log("[llmd] Reconnecting..."),l()},2000)}),e.addEventListener("error",(i)=>{console.error("[llmd] WebSocket error:",i),e?.close()})};l(),window.addEventListener("beforeunload",()=>{if(n)clearTimeout(n);e?.close()})};window.connectFileWatcher=p;console.log("[llmd] Client initialized");
1
+ var B=()=>{let t=document.querySelectorAll(".dir-label");for(let C of Array.from(t)){let p=C,y=document.createElement("span");y.className="dir-chevron",y.innerHTML='<svg xmlns="http://www.w3.org/2000/svg" width="16" height="16" viewBox="0 0 24 24" fill="none" stroke="currentColor" stroke-width="2" stroke-linecap="round" stroke-linejoin="round"><polyline points="6 9 12 15 18 9"></polyline></svg>',p.insertBefore(y,p.firstChild),p.style.cursor="pointer",p.addEventListener("click",(m)=>{m.preventDefault();let o=p.closest(".dir-item");if(o)o.classList.toggle("collapsed")})}},M=()=>{let t=document.querySelector(".toc");if(!t)return;let C=t.querySelector("h3");if(!C)return;let p=document.createElement("span");p.className="toc-chevron",p.innerHTML='<svg xmlns="http://www.w3.org/2000/svg" width="16" height="16" viewBox="0 0 24 24" fill="none" stroke="currentColor" stroke-width="2" stroke-linecap="round" stroke-linejoin="round"><polyline points="6 9 12 15 18 9"></polyline></svg>',C.style.cursor="pointer",C.insertBefore(p,C.firstChild),t.classList.add("collapsed"),C.addEventListener("click",()=>{t.classList.toggle("collapsed")})};if(typeof window<"u")window.addEventListener("DOMContentLoaded",()=>{B(),M()});var q=()=>{document.querySelectorAll("pre code").forEach((t)=>{let C=t.parentElement;if(!C)return;if(C.querySelector(".copy-button"))return;let p=document.createElement("button");p.className="copy-button",p.textContent="Copy",p.setAttribute("aria-label","Copy code to clipboard"),p.addEventListener("click",async()=>{try{await navigator.clipboard.writeText(t.textContent||""),p.textContent="Copied!",p.classList.add("copied"),setTimeout(()=>{p.textContent="Copy",p.classList.remove("copied")},2000)}catch(y){console.error("Failed to copy:",y),p.textContent="Failed",setTimeout(()=>{p.textContent="Copy"},2000)}}),C.appendChild(p)})};if(document.readyState==="loading")document.addEventListener("DOMContentLoaded",q);else q();var O=(t)=>{let p=`${window.location.protocol==="https:"?"wss:":"ws:"}//${window.location.host}/_ws`,y=null,m=null,o=()=>{y=new WebSocket(p),y.addEventListener("open",()=>{console.log("[llmd] Connected to file watcher"),y?.send(JSON.stringify({type:"watch",file:t}))}),y.addEventListener("message",(E)=>{try{let f=JSON.parse(E.data);if(f.type==="reload"&&f.file===t)console.log(`[llmd] File changed: ${t}, reloading...`),window.location.reload()}catch(f){console.error("[llmd] Failed to parse message:",f)}}),y.addEventListener("close",()=>{console.log("[llmd] Disconnected from file watcher"),m=window.setTimeout(()=>{console.log("[llmd] Reconnecting..."),o()},2000)}),y.addEventListener("error",(E)=>{console.error("[llmd] WebSocket error:",E),y?.close()})};o(),window.addEventListener("beforeunload",()=>{if(m)clearTimeout(m);y?.close()})};window.connectFileWatcher=O;var k=()=>{let t=document.querySelector(".sidebar");if(!t)return;let C=document.createElement("div");C.className="sidebar-resize-handle",t.appendChild(C);let p=!1,y=0,m=0,o=(u)=>{p=!0,y=u.clientX,m=t.offsetWidth,document.body.style.cursor="ew-resize",document.body.style.userSelect="none",u.preventDefault()},E=(u)=>{if(!p)return;let A=u.clientX-y,j=m+A,x=Math.max(200,Math.min(600,j));t.style.width=`${x}px`,localStorage.setItem("llmd-sidebar-width",x.toString())},f=()=>{if(!p)return;p=!1,document.body.style.cursor="",document.body.style.userSelect=""};C.addEventListener("mousedown",o),document.addEventListener("mousemove",E),document.addEventListener("mouseup",f);let L=localStorage.getItem("llmd-sidebar-width");if(L){let u=Number.parseInt(L,10);if(u>=200&&u<=600)t.style.width=`${u}px`}};if(typeof window<"u")window.addEventListener("DOMContentLoaded",()=>{k()});console.log("[llmd] Client initialized");
package/dist/llmd CHANGED
@@ -19,7 +19,6 @@ Arguments:
19
19
 
20
20
  Options:
21
21
  --port <number> Port to bind to (default: random)
22
- --host <string> Host interface (default: localhost)
23
22
  --theme <name> Color theme (default: dark)
24
23
  Built-in: dark, light, nord, dracula, solarized, monokai
25
24
  Custom themes: ~/.config/llmd/themes.json
@@ -39,7 +38,7 @@ Examples:
39
38
  llmd --fonts modern # Use modern font combo (Tajawal + Fira Code)
40
39
  llmd --theme nord # Use Nord color theme
41
40
  llmd --theme dracula --watch # Dracula theme with live reload
42
- `,Ap=(e)=>{let n={},t;for(let a=0;a<e.length;a++){let i=e[a];if(!i)continue;if(i==="--help"||i==="-h")n.help=!0;else if(i==="--version")n.version=!0;else if(i==="--port")n.port=Number.parseInt(e[++a]??"0",10);else if(i==="--host")n.host=e[++a];else if(i==="--theme")n.theme=e[++a];else if(i==="--fonts")n.fontTheme=e[++a];else if(i==="--open")n.open=!0;else if(i==="--no-open")n.open=!1;else if(i==="--watch")n.watch=!0;else if(i==="--no-watch")n.watch=!1;else if(!i.startsWith("-"))t=i}return{path:t,flags:n}},qp=(e)=>{let n=$p(e)?e:vp(process.cwd(),e);if(n.endsWith(".md"))return{directory:kp(n),initialFile:n};return{directory:n}},zp=(e)=>{let{path:n=".",flags:t}=e,{directory:a,initialFile:i}=qp(n);return{directory:a,initialFile:i,port:t.port??0,host:t.host??"localhost",theme:t.theme??"dark",fontTheme:t.fontTheme??"sans",open:t.open??!0,watch:t.watch??!1}},Zp=(e)=>{if(!xp(e.directory))throw Error(`Directory not found: ${e.directory}`);if(!nc(e.theme)){let n=ec();throw Error(`Theme "${e.theme}" not found. Available themes: ${n.join(", ")}`)}if(!Qi(e.fontTheme)){let n=Ji();throw Error(`Font "${e.fontTheme}" not found. Available fonts: ${n.join(", ")}`)}if(e.port<0||e.port>65535)throw Error(`Invalid port: ${e.port}. Must be 0-65535`)},Fp=()=>{console.log(jp)},Ep=()=>{console.log(`llmd v${Cp}`)},tc=(e)=>{let n=Ap(e);if(n.flags.help)return Fp(),null;if(n.flags.version)return Ep(),null;let t=zp(n);return Zp(t),t};import{readdirSync as Up,statSync as Wp}from"node:fs";import{join as Np,relative as ac,sep as Tp}from"node:path";var Ip=["node_modules",".git",".next",".svelte-kit","dist","build",".cache",".turbo",".vercel"],Op=(e,n)=>n.includes(e)||e.startsWith("."),Rp=(e)=>{if(e==="")return 0;let n=e.split(Tp);return Math.max(0,n.length-1)},ic=async(e,n,t,a)=>{if(t>=a.maxDepth)return[];let i=Up(e),c=[];for(let s of i){let o=Np(e,s),r=ac(n,o);if(Op(s,a.ignore))continue;let p;try{p=Wp(o)}catch{continue}if(p.isFile()&&s.endsWith(".md")){c.push({path:r,name:s,depth:Rp(r)});continue}if(p.isDirectory()){let m=await ic(o,n,t+1,a);c.push(...m)}}return c},Lp=(e)=>[...e].sort((n,t)=>n.path.localeCompare(t.path)),cc=async(e,n=5)=>{let a=await ic(e,e,0,{root:e,maxDepth:n,ignore:Ip});return Lp(a)},ma=(e,n)=>ac(n,e);import{readFile as Pi}from"node:fs/promises";import{createServer as Ig}from"node:http";import{join as Og}from"node:path";var iu=dn(es(),1),cu=dn(ga(),1),su=dn(fa(),1),ru=dn(lt(),1),Ca=dn(rs(),1);import{readFile as ou}from"node:fs/promises";import{dirname as pu,join as mu}from"node:path";import{fileURLToPath as uu}from"node:url";var bt=null,lu=async()=>{if(bt)return bt;try{let e=pu(uu(import.meta.url)),n=mu(e,"../dist/client.js");return bt=await ou(n,"utf-8"),bt}catch(e){return console.error("Failed to load client bundle:",e),""}},os=async()=>{return`<script>${await lu()}</script>`};function Aa(){return{async:!1,breaks:!1,extensions:null,gfm:!0,hooks:null,pedantic:!1,renderer:null,silent:!1,tokenizer:null,walkTokens:null}}var Te=Aa();function _s(e){Te=e}var Cn={exec:()=>null};function j(e,n=""){let t=typeof e=="string"?e:e.source,a={replace:(i,c)=>{let s=typeof c=="string"?c:c.source;return s=s.replace(G.caret,"$1"),t=t.replace(i,s),a},getRegex:()=>new RegExp(t,n)};return a}var du=(()=>{try{return!!new RegExp("(?<=1)(?<!1)")}catch{return!1}})(),G={codeRemoveIndent:/^(?: {1,4}| {0,3}\t)/gm,outputLinkReplace:/\\([\[\]])/g,indentCodeCompensation:/^(\s+)(?:```)/,beginningSpace:/^\s+/,endingHash:/#$/,startingSpaceChar:/^ /,endingSpaceChar:/ $/,nonSpaceChar:/[^ ]/,newLineCharGlobal:/\n/g,tabCharGlobal:/\t/g,multipleSpaceGlobal:/\s+/g,blankLine:/^[ \t]*$/,doubleBlankLine:/\n[ \t]*\n[ \t]*$/,blockquoteStart:/^ {0,3}>/,blockquoteSetextReplace:/\n {0,3}((?:=+|-+) *)(?=\n|$)/g,blockquoteSetextReplace2:/^ {0,3}>[ \t]?/gm,listReplaceTabs:/^\t+/,listReplaceNesting:/^ {1,4}(?=( {4})*[^ ])/g,listIsTask:/^\[[ xX]\] +\S/,listReplaceTask:/^\[[ xX]\] +/,listTaskCheckbox:/\[[ xX]\]/,anyLine:/\n.*\n/,hrefBrackets:/^<(.*)>$/,tableDelimiter:/[:|]/,tableAlignChars:/^\||\| *$/g,tableRowBlankLine:/\n[ \t]*$/,tableAlignRight:/^ *-+: *$/,tableAlignCenter:/^ *:-+: *$/,tableAlignLeft:/^ *:-+ *$/,startATag:/^<a /i,endATag:/^<\/a>/i,startPreScriptTag:/^<(pre|code|kbd|script)(\s|>)/i,endPreScriptTag:/^<\/(pre|code|kbd|script)(\s|>)/i,startAngleBracket:/^</,endAngleBracket:/>$/,pedanticHrefTitle:/^([^'"]*[^\s])\s+(['"])(.*)\2/,unicodeAlphaNumeric:/[\p{L}\p{N}]/u,escapeTest:/[&<>"']/,escapeReplace:/[&<>"']/g,escapeTestNoEncode:/[<>"']|&(?!(#\d{1,7}|#[Xx][a-fA-F0-9]{1,6}|\w+);)/,escapeReplaceNoEncode:/[<>"']|&(?!(#\d{1,7}|#[Xx][a-fA-F0-9]{1,6}|\w+);)/g,unescapeTest:/&(#(?:\d+)|(?:#x[0-9A-Fa-f]+)|(?:\w+));?/ig,caret:/(^|[^\[])\^/g,percentDecode:/%25/g,findPipe:/\|/g,splitPipe:/ \|/,slashPipe:/\\\|/g,carriageReturn:/\r\n|\r/g,spaceLine:/^ +$/gm,notSpaceStart:/^\S*/,endingNewline:/\n$/,listItemRegex:(e)=>new RegExp(`^( {0,3}${e})((?:[ ][^\\n]*)?(?:\\n|$))`),nextBulletRegex:(e)=>new RegExp(`^ {0,${Math.min(3,e-1)}}(?:[*+-]|\\d{1,9}[.)])((?:[ ][^\\n]*)?(?:\\n|$))`),hrRegex:(e)=>new RegExp(`^ {0,${Math.min(3,e-1)}}((?:- *){3,}|(?:_ *){3,}|(?:\\* *){3,})(?:\\n+|$)`),fencesBeginRegex:(e)=>new RegExp(`^ {0,${Math.min(3,e-1)}}(?:\`\`\`|~~~)`),headingBeginRegex:(e)=>new RegExp(`^ {0,${Math.min(3,e-1)}}#`),htmlBeginRegex:(e)=>new RegExp(`^ {0,${Math.min(3,e-1)}}<(?:[a-z].*>|!--)`,"i")},bu=/^(?:[ \t]*(?:\n|$))+/,_u=/^((?: {4}| {0,3}\t)[^\n]+(?:\n(?:[ \t]*(?:\n|$))*)?)+/,gu=/^ {0,3}(`{3,}(?=[^`\n]*(?:\n|$))|~{3,})([^\n]*)(?:\n|$)(?:|([\s\S]*?)(?:\n|$))(?: {0,3}\1[~`]* *(?=\n|$)|$)/,jn=/^ {0,3}((?:-[\t ]*){3,}|(?:_[ \t]*){3,}|(?:\*[ \t]*){3,})(?:\n+|$)/,hu=/^ {0,3}(#{1,6})(?=\s|$)(.*)(?:\n+|$)/,qa=/(?:[*+-]|\d{1,9}[.)])/,gs=/^(?!bull |blockCode|fences|blockquote|heading|html|table)((?:.|\n(?!\s*?\n|bull |blockCode|fences|blockquote|heading|html|table))+?)\n {0,3}(=+|-+) *(?:\n+|$)/,hs=j(gs).replace(/bull/g,qa).replace(/blockCode/g,/(?: {4}| {0,3}\t)/).replace(/fences/g,/ {0,3}(?:`{3,}|~{3,})/).replace(/blockquote/g,/ {0,3}>/).replace(/heading/g,/ {0,3}#{1,6}/).replace(/html/g,/ {0,3}<[^\n>]+>\n/).replace(/\|table/g,"").getRegex(),fu=j(gs).replace(/bull/g,qa).replace(/blockCode/g,/(?: {4}| {0,3}\t)/).replace(/fences/g,/ {0,3}(?:`{3,}|~{3,})/).replace(/blockquote/g,/ {0,3}>/).replace(/heading/g,/ {0,3}#{1,6}/).replace(/html/g,/ {0,3}<[^\n>]+>\n/).replace(/table/g,/ {0,3}\|?(?:[:\- ]*\|)+[\:\- ]*\n/).getRegex(),za=/^([^\n]+(?:\n(?!hr|heading|lheading|blockquote|fences|list|html|table| +\n)[^\n]+)*)/,yu=/^[^\n]+/,Za=/(?!\s*\])(?:\\[\s\S]|[^\[\]\\])+/,wu=j(/^ {0,3}\[(label)\]: *(?:\n[ \t]*)?([^<\s][^\s]*|<.*?>)(?:(?: +(?:\n[ \t]*)?| *\n[ \t]*)(title))? *(?:\n+|$)/).replace("label",Za).replace("title",/(?:"(?:\\"?|[^"\\])*"|'[^'\n]*(?:\n[^'\n]+)*\n?'|\([^()]*\))/).getRegex(),xu=j(/^( {0,3}bull)([ \t][^\n]+?)?(?:\n|$)/).replace(/bull/g,qa).getRegex(),yt="address|article|aside|base|basefont|blockquote|body|caption|center|col|colgroup|dd|details|dialog|dir|div|dl|dt|fieldset|figcaption|figure|footer|form|frame|frameset|h[1-6]|head|header|hr|html|iframe|legend|li|link|main|menu|menuitem|meta|nav|noframes|ol|optgroup|option|p|param|search|section|summary|table|tbody|td|tfoot|th|thead|title|tr|track|ul",Fa=/<!--(?:-?>|[\s\S]*?(?:-->|$))/,ku=j("^ {0,3}(?:<(script|pre|style|textarea)[\\s>][\\s\\S]*?(?:</\\1>[^\\n]*\\n+|$)|comment[^\\n]*(\\n+|$)|<\\?[\\s\\S]*?(?:\\?>\\n*|$)|<![A-Z][\\s\\S]*?(?:>\\n*|$)|<!\\[CDATA\\[[\\s\\S]*?(?:\\]\\]>\\n*|$)|</?(tag)(?: +|\\n|/?>)[\\s\\S]*?(?:(?:\\n[ \t]*)+\\n|$)|<(?!script|pre|style|textarea)([a-z][\\w-]*)(?:attribute)*? */?>(?=[ \\t]*(?:\\n|$))[\\s\\S]*?(?:(?:\\n[ \t]*)+\\n|$)|</(?!script|pre|style|textarea)[a-z][\\w-]*\\s*>(?=[ \\t]*(?:\\n|$))[\\s\\S]*?(?:(?:\\n[ ]*)+\\n|$))","i").replace("comment",Fa).replace("tag",yt).replace("attribute",/ +[a-zA-Z:_][\w.:-]*(?: *= *"[^"\n]*"| *= *'[^'\n]*'| *= *[^\s"'=<>`]+)?/).getRegex(),fs=j(za).replace("hr",jn).replace("heading"," {0,3}#{1,6}(?:\\s|$)").replace("|lheading","").replace("|table","").replace("blockquote"," {0,3}>").replace("fences"," {0,3}(?:`{3,}(?=[^`\\n]*\\n)|~{3,})[^\\n]*\\n").replace("list"," {0,3}(?:[*+-]|1[.)]) ").replace("html","</?(?:tag)(?: +|\\n|/?>)|<(?:script|pre|style|textarea|!--)").replace("tag",yt).getRegex(),$u=j(/^( {0,3}> ?(paragraph|[^\n]*)(?:\n|$))+/).replace("paragraph",fs).getRegex(),Ea={blockquote:$u,code:_u,def:wu,fences:gu,heading:hu,hr:jn,html:ku,lheading:hs,list:xu,newline:bu,paragraph:fs,table:Cn,text:yu},ps=j("^ *([^\\n ].*)\\n {0,3}((?:\\| *)?:?-+:? *(?:\\| *:?-+:? *)*(?:\\| *)?)(?:\\n((?:(?! *\\n|hr|heading|blockquote|code|fences|list|html).*(?:\\n|$))*)\\n*|$)").replace("hr",jn).replace("heading"," {0,3}#{1,6}(?:\\s|$)").replace("blockquote"," {0,3}>").replace("code","(?: {4}| {0,3}\t)[^\\n]").replace("fences"," {0,3}(?:`{3,}(?=[^`\\n]*\\n)|~{3,})[^\\n]*\\n").replace("list"," {0,3}(?:[*+-]|1[.)]) ").replace("html","</?(?:tag)(?: +|\\n|/?>)|<(?:script|pre|style|textarea|!--)").replace("tag",yt).getRegex(),vu={...Ea,lheading:fu,table:ps,paragraph:j(za).replace("hr",jn).replace("heading"," {0,3}#{1,6}(?:\\s|$)").replace("|lheading","").replace("table",ps).replace("blockquote"," {0,3}>").replace("fences"," {0,3}(?:`{3,}(?=[^`\\n]*\\n)|~{3,})[^\\n]*\\n").replace("list"," {0,3}(?:[*+-]|1[.)]) ").replace("html","</?(?:tag)(?: +|\\n|/?>)|<(?:script|pre|style|textarea|!--)").replace("tag",yt).getRegex()},Cu={...Ea,html:j(`^ *(?:comment *(?:\\n|\\s*$)|<(tag)[\\s\\S]+?</\\1> *(?:\\n{2,}|\\s*$)|<tag(?:"[^"]*"|'[^']*'|\\s[^'"/>\\s]*)*?/?> *(?:\\n{2,}|\\s*$))`).replace("comment",Fa).replace(/tag/g,"(?!(?:a|em|strong|small|s|cite|q|dfn|abbr|data|time|code|var|samp|kbd|sub|sup|i|b|u|mark|ruby|rt|rp|bdi|bdo|span|br|wbr|ins|del|img)\\b)\\w+(?!:|[^\\w\\s@]*@)\\b").getRegex(),def:/^ *\[([^\]]+)\]: *<?([^\s>]+)>?(?: +(["(][^\n]+[")]))? *(?:\n+|$)/,heading:/^(#{1,6})(.*)(?:\n+|$)/,fences:Cn,lheading:/^(.+?)\n {0,3}(=+|-+) *(?:\n+|$)/,paragraph:j(za).replace("hr",jn).replace("heading",` *#{1,6} *[^
41
+ `,Ap=(e)=>{let n={},t;for(let a=0;a<e.length;a++){let i=e[a];if(!i)continue;if(i==="--help"||i==="-h")n.help=!0;else if(i==="--version")n.version=!0;else if(i==="--port")n.port=Number.parseInt(e[++a]??"0",10);else if(i==="--theme")n.theme=e[++a];else if(i==="--fonts")n.fontTheme=e[++a];else if(i==="--open")n.open=!0;else if(i==="--no-open")n.open=!1;else if(i==="--watch")n.watch=!0;else if(i==="--no-watch")n.watch=!1;else if(!i.startsWith("-"))t=i}return{path:t,flags:n}},qp=(e)=>{let n=$p(e)?e:vp(process.cwd(),e);if(n.endsWith(".md"))return{directory:kp(n),initialFile:n};return{directory:n}},zp=(e)=>{let{path:n=".",flags:t}=e,{directory:a,initialFile:i}=qp(n);return{directory:a,initialFile:i,port:t.port??0,host:"localhost",theme:t.theme??"dark",fontTheme:t.fontTheme??"sans",open:t.open??!0,watch:t.watch??!1}},Zp=(e)=>{if(!xp(e.directory))throw Error(`Directory not found: ${e.directory}`);if(!nc(e.theme)){let n=ec();throw Error(`Theme "${e.theme}" not found. Available themes: ${n.join(", ")}`)}if(!Qi(e.fontTheme)){let n=Ji();throw Error(`Font "${e.fontTheme}" not found. Available fonts: ${n.join(", ")}`)}if(e.port<0||e.port>65535)throw Error(`Invalid port: ${e.port}. Must be 0-65535`)},Fp=()=>{console.log(jp)},Ep=()=>{console.log(`llmd v${Cp}`)},tc=(e)=>{let n=Ap(e);if(n.flags.help)return Fp(),null;if(n.flags.version)return Ep(),null;let t=zp(n);return Zp(t),t};import{readdirSync as Up,statSync as Wp}from"node:fs";import{join as Np,relative as ac,sep as Tp}from"node:path";var Ip=["node_modules",".git",".next",".svelte-kit","dist","build",".cache",".turbo",".vercel"],Op=(e,n)=>n.includes(e)||e.startsWith("."),Rp=(e)=>{if(e==="")return 0;let n=e.split(Tp);return Math.max(0,n.length-1)},ic=async(e,n,t,a)=>{if(t>=a.maxDepth)return[];let i=Up(e),c=[];for(let s of i){let o=Np(e,s),r=ac(n,o);if(Op(s,a.ignore))continue;let p;try{p=Wp(o)}catch{continue}if(p.isFile()&&s.endsWith(".md")){c.push({path:r,name:s,depth:Rp(r)});continue}if(p.isDirectory()){let m=await ic(o,n,t+1,a);c.push(...m)}}return c},Lp=(e)=>[...e].sort((n,t)=>n.path.localeCompare(t.path)),cc=async(e,n=5)=>{let a=await ic(e,e,0,{root:e,maxDepth:n,ignore:Ip});return Lp(a)},ma=(e,n)=>ac(n,e);import{readFile as Pi}from"node:fs/promises";import{createServer as Ig}from"node:http";import{join as Og}from"node:path";var iu=dn(es(),1),cu=dn(ga(),1),su=dn(fa(),1),ru=dn(lt(),1),Ca=dn(rs(),1);import{readFile as ou}from"node:fs/promises";import{dirname as pu,join as mu}from"node:path";import{fileURLToPath as uu}from"node:url";var bt=null,lu=async()=>{if(bt)return bt;try{let e=pu(uu(import.meta.url)),n=mu(e,"../dist/client.js");return bt=await ou(n,"utf-8"),bt}catch(e){return console.error("Failed to load client bundle:",e),""}},os=async()=>{return`<script>${await lu()}</script>`};function Aa(){return{async:!1,breaks:!1,extensions:null,gfm:!0,hooks:null,pedantic:!1,renderer:null,silent:!1,tokenizer:null,walkTokens:null}}var Te=Aa();function _s(e){Te=e}var Cn={exec:()=>null};function j(e,n=""){let t=typeof e=="string"?e:e.source,a={replace:(i,c)=>{let s=typeof c=="string"?c:c.source;return s=s.replace(G.caret,"$1"),t=t.replace(i,s),a},getRegex:()=>new RegExp(t,n)};return a}var du=(()=>{try{return!!new RegExp("(?<=1)(?<!1)")}catch{return!1}})(),G={codeRemoveIndent:/^(?: {1,4}| {0,3}\t)/gm,outputLinkReplace:/\\([\[\]])/g,indentCodeCompensation:/^(\s+)(?:```)/,beginningSpace:/^\s+/,endingHash:/#$/,startingSpaceChar:/^ /,endingSpaceChar:/ $/,nonSpaceChar:/[^ ]/,newLineCharGlobal:/\n/g,tabCharGlobal:/\t/g,multipleSpaceGlobal:/\s+/g,blankLine:/^[ \t]*$/,doubleBlankLine:/\n[ \t]*\n[ \t]*$/,blockquoteStart:/^ {0,3}>/,blockquoteSetextReplace:/\n {0,3}((?:=+|-+) *)(?=\n|$)/g,blockquoteSetextReplace2:/^ {0,3}>[ \t]?/gm,listReplaceTabs:/^\t+/,listReplaceNesting:/^ {1,4}(?=( {4})*[^ ])/g,listIsTask:/^\[[ xX]\] +\S/,listReplaceTask:/^\[[ xX]\] +/,listTaskCheckbox:/\[[ xX]\]/,anyLine:/\n.*\n/,hrefBrackets:/^<(.*)>$/,tableDelimiter:/[:|]/,tableAlignChars:/^\||\| *$/g,tableRowBlankLine:/\n[ \t]*$/,tableAlignRight:/^ *-+: *$/,tableAlignCenter:/^ *:-+: *$/,tableAlignLeft:/^ *:-+ *$/,startATag:/^<a /i,endATag:/^<\/a>/i,startPreScriptTag:/^<(pre|code|kbd|script)(\s|>)/i,endPreScriptTag:/^<\/(pre|code|kbd|script)(\s|>)/i,startAngleBracket:/^</,endAngleBracket:/>$/,pedanticHrefTitle:/^([^'"]*[^\s])\s+(['"])(.*)\2/,unicodeAlphaNumeric:/[\p{L}\p{N}]/u,escapeTest:/[&<>"']/,escapeReplace:/[&<>"']/g,escapeTestNoEncode:/[<>"']|&(?!(#\d{1,7}|#[Xx][a-fA-F0-9]{1,6}|\w+);)/,escapeReplaceNoEncode:/[<>"']|&(?!(#\d{1,7}|#[Xx][a-fA-F0-9]{1,6}|\w+);)/g,unescapeTest:/&(#(?:\d+)|(?:#x[0-9A-Fa-f]+)|(?:\w+));?/ig,caret:/(^|[^\[])\^/g,percentDecode:/%25/g,findPipe:/\|/g,splitPipe:/ \|/,slashPipe:/\\\|/g,carriageReturn:/\r\n|\r/g,spaceLine:/^ +$/gm,notSpaceStart:/^\S*/,endingNewline:/\n$/,listItemRegex:(e)=>new RegExp(`^( {0,3}${e})((?:[ ][^\\n]*)?(?:\\n|$))`),nextBulletRegex:(e)=>new RegExp(`^ {0,${Math.min(3,e-1)}}(?:[*+-]|\\d{1,9}[.)])((?:[ ][^\\n]*)?(?:\\n|$))`),hrRegex:(e)=>new RegExp(`^ {0,${Math.min(3,e-1)}}((?:- *){3,}|(?:_ *){3,}|(?:\\* *){3,})(?:\\n+|$)`),fencesBeginRegex:(e)=>new RegExp(`^ {0,${Math.min(3,e-1)}}(?:\`\`\`|~~~)`),headingBeginRegex:(e)=>new RegExp(`^ {0,${Math.min(3,e-1)}}#`),htmlBeginRegex:(e)=>new RegExp(`^ {0,${Math.min(3,e-1)}}<(?:[a-z].*>|!--)`,"i")},bu=/^(?:[ \t]*(?:\n|$))+/,_u=/^((?: {4}| {0,3}\t)[^\n]+(?:\n(?:[ \t]*(?:\n|$))*)?)+/,gu=/^ {0,3}(`{3,}(?=[^`\n]*(?:\n|$))|~{3,})([^\n]*)(?:\n|$)(?:|([\s\S]*?)(?:\n|$))(?: {0,3}\1[~`]* *(?=\n|$)|$)/,jn=/^ {0,3}((?:-[\t ]*){3,}|(?:_[ \t]*){3,}|(?:\*[ \t]*){3,})(?:\n+|$)/,hu=/^ {0,3}(#{1,6})(?=\s|$)(.*)(?:\n+|$)/,qa=/(?:[*+-]|\d{1,9}[.)])/,gs=/^(?!bull |blockCode|fences|blockquote|heading|html|table)((?:.|\n(?!\s*?\n|bull |blockCode|fences|blockquote|heading|html|table))+?)\n {0,3}(=+|-+) *(?:\n+|$)/,hs=j(gs).replace(/bull/g,qa).replace(/blockCode/g,/(?: {4}| {0,3}\t)/).replace(/fences/g,/ {0,3}(?:`{3,}|~{3,})/).replace(/blockquote/g,/ {0,3}>/).replace(/heading/g,/ {0,3}#{1,6}/).replace(/html/g,/ {0,3}<[^\n>]+>\n/).replace(/\|table/g,"").getRegex(),fu=j(gs).replace(/bull/g,qa).replace(/blockCode/g,/(?: {4}| {0,3}\t)/).replace(/fences/g,/ {0,3}(?:`{3,}|~{3,})/).replace(/blockquote/g,/ {0,3}>/).replace(/heading/g,/ {0,3}#{1,6}/).replace(/html/g,/ {0,3}<[^\n>]+>\n/).replace(/table/g,/ {0,3}\|?(?:[:\- ]*\|)+[\:\- ]*\n/).getRegex(),za=/^([^\n]+(?:\n(?!hr|heading|lheading|blockquote|fences|list|html|table| +\n)[^\n]+)*)/,yu=/^[^\n]+/,Za=/(?!\s*\])(?:\\[\s\S]|[^\[\]\\])+/,wu=j(/^ {0,3}\[(label)\]: *(?:\n[ \t]*)?([^<\s][^\s]*|<.*?>)(?:(?: +(?:\n[ \t]*)?| *\n[ \t]*)(title))? *(?:\n+|$)/).replace("label",Za).replace("title",/(?:"(?:\\"?|[^"\\])*"|'[^'\n]*(?:\n[^'\n]+)*\n?'|\([^()]*\))/).getRegex(),xu=j(/^( {0,3}bull)([ \t][^\n]+?)?(?:\n|$)/).replace(/bull/g,qa).getRegex(),yt="address|article|aside|base|basefont|blockquote|body|caption|center|col|colgroup|dd|details|dialog|dir|div|dl|dt|fieldset|figcaption|figure|footer|form|frame|frameset|h[1-6]|head|header|hr|html|iframe|legend|li|link|main|menu|menuitem|meta|nav|noframes|ol|optgroup|option|p|param|search|section|summary|table|tbody|td|tfoot|th|thead|title|tr|track|ul",Fa=/<!--(?:-?>|[\s\S]*?(?:-->|$))/,ku=j("^ {0,3}(?:<(script|pre|style|textarea)[\\s>][\\s\\S]*?(?:</\\1>[^\\n]*\\n+|$)|comment[^\\n]*(\\n+|$)|<\\?[\\s\\S]*?(?:\\?>\\n*|$)|<![A-Z][\\s\\S]*?(?:>\\n*|$)|<!\\[CDATA\\[[\\s\\S]*?(?:\\]\\]>\\n*|$)|</?(tag)(?: +|\\n|/?>)[\\s\\S]*?(?:(?:\\n[ \t]*)+\\n|$)|<(?!script|pre|style|textarea)([a-z][\\w-]*)(?:attribute)*? */?>(?=[ \\t]*(?:\\n|$))[\\s\\S]*?(?:(?:\\n[ \t]*)+\\n|$)|</(?!script|pre|style|textarea)[a-z][\\w-]*\\s*>(?=[ \\t]*(?:\\n|$))[\\s\\S]*?(?:(?:\\n[ \t]*)+\\n|$))","i").replace("comment",Fa).replace("tag",yt).replace("attribute",/ +[a-zA-Z:_][\w.:-]*(?: *= *"[^"\n]*"| *= *'[^'\n]*'| *= *[^\s"'=<>`]+)?/).getRegex(),fs=j(za).replace("hr",jn).replace("heading"," {0,3}#{1,6}(?:\\s|$)").replace("|lheading","").replace("|table","").replace("blockquote"," {0,3}>").replace("fences"," {0,3}(?:`{3,}(?=[^`\\n]*\\n)|~{3,})[^\\n]*\\n").replace("list"," {0,3}(?:[*+-]|1[.)]) ").replace("html","</?(?:tag)(?: +|\\n|/?>)|<(?:script|pre|style|textarea|!--)").replace("tag",yt).getRegex(),$u=j(/^( {0,3}> ?(paragraph|[^\n]*)(?:\n|$))+/).replace("paragraph",fs).getRegex(),Ea={blockquote:$u,code:_u,def:wu,fences:gu,heading:hu,hr:jn,html:ku,lheading:hs,list:xu,newline:bu,paragraph:fs,table:Cn,text:yu},ps=j("^ *([^\\n ].*)\\n {0,3}((?:\\| *)?:?-+:? *(?:\\| *:?-+:? *)*(?:\\| *)?)(?:\\n((?:(?! *\\n|hr|heading|blockquote|code|fences|list|html).*(?:\\n|$))*)\\n*|$)").replace("hr",jn).replace("heading"," {0,3}#{1,6}(?:\\s|$)").replace("blockquote"," {0,3}>").replace("code","(?: {4}| {0,3}\t)[^\\n]").replace("fences"," {0,3}(?:`{3,}(?=[^`\\n]*\\n)|~{3,})[^\\n]*\\n").replace("list"," {0,3}(?:[*+-]|1[.)]) ").replace("html","</?(?:tag)(?: +|\\n|/?>)|<(?:script|pre|style|textarea|!--)").replace("tag",yt).getRegex(),vu={...Ea,lheading:fu,table:ps,paragraph:j(za).replace("hr",jn).replace("heading"," {0,3}#{1,6}(?:\\s|$)").replace("|lheading","").replace("table",ps).replace("blockquote"," {0,3}>").replace("fences"," {0,3}(?:`{3,}(?=[^`\\n]*\\n)|~{3,})[^\\n]*\\n").replace("list"," {0,3}(?:[*+-]|1[.)]) ").replace("html","</?(?:tag)(?: +|\\n|/?>)|<(?:script|pre|style|textarea|!--)").replace("tag",yt).getRegex()},Cu={...Ea,html:j(`^ *(?:comment *(?:\\n|\\s*$)|<(tag)[\\s\\S]+?</\\1> *(?:\\n{2,}|\\s*$)|<tag(?:"[^"]*"|'[^']*'|\\s[^'"/>\\s]*)*?/?> *(?:\\n{2,}|\\s*$))`).replace("comment",Fa).replace(/tag/g,"(?!(?:a|em|strong|small|s|cite|q|dfn|abbr|data|time|code|var|samp|kbd|sub|sup|i|b|u|mark|ruby|rt|rp|bdi|bdo|span|br|wbr|ins|del|img)\\b)\\w+(?!:|[^\\w\\s@]*@)\\b").getRegex(),def:/^ *\[([^\]]+)\]: *<?([^\s>]+)>?(?: +(["(][^\n]+[")]))? *(?:\n+|$)/,heading:/^(#{1,6})(.*)(?:\n+|$)/,fences:Cn,lheading:/^(.+?)\n {0,3}(=+|-+) *(?:\n+|$)/,paragraph:j(za).replace("hr",jn).replace("heading",` *#{1,6} *[^
43
42
  ]`).replace("lheading",hs).replace("|table","").replace("blockquote"," {0,3}>").replace("|fences","").replace("|list","").replace("|html","").replace("|tag","").getRegex()},ju=/^\\([!"#$%&'()*+,\-./:;<=>?@\[\]\\^_`{|}~])/,Au=/^(`+)([^`]|[^`][\s\S]*?[^`])\1(?!`)/,ys=/^( {2,}|\\)\n(?!\s*$)/,qu=/^(`+|[^`])(?:(?= {2,}\n)|[\s\S]*?(?:(?=[\\<!\[`*_]|\b_|$)|[^ ](?= {2,}\n)))/,wt=/[\p{P}\p{S}]/u,Ua=/[\s\p{P}\p{S}]/u,ws=/[^\s\p{P}\p{S}]/u,zu=j(/^((?![*_])punctSpace)/,"u").replace(/punctSpace/g,Ua).getRegex(),xs=/(?!~)[\p{P}\p{S}]/u,Zu=/(?!~)[\s\p{P}\p{S}]/u,Fu=/(?:[^\s\p{P}\p{S}]|~)/u,Eu=j(/link|precode-code|html/,"g").replace("link",/\[(?:[^\[\]`]|(?<a>`+)[^`]+\k<a>(?!`))*?\]\((?:\\[\s\S]|[^\\\(\)]|\((?:\\[\s\S]|[^\\\(\)])*\))*\)/).replace("precode-",du?"(?<!`)()":"(^^|[^`])").replace("code",/(?<b>`+)[^`]+\k<b>(?!`)/).replace("html",/<(?! )[^<>]*?>/).getRegex(),ks=/^(?:\*+(?:((?!\*)punct)|[^\s*]))|^_+(?:((?!_)punct)|([^\s_]))/,Uu=j(ks,"u").replace(/punct/g,wt).getRegex(),Wu=j(ks,"u").replace(/punct/g,xs).getRegex(),$s="^[^_*]*?__[^_*]*?\\*[^_*]*?(?=__)|[^*]+(?=[^*])|(?!\\*)punct(\\*+)(?=[\\s]|$)|notPunctSpace(\\*+)(?!\\*)(?=punctSpace|$)|(?!\\*)punctSpace(\\*+)(?=notPunctSpace)|[\\s](\\*+)(?!\\*)(?=punct)|(?!\\*)punct(\\*+)(?!\\*)(?=punct)|notPunctSpace(\\*+)(?=notPunctSpace)",Nu=j($s,"gu").replace(/notPunctSpace/g,ws).replace(/punctSpace/g,Ua).replace(/punct/g,wt).getRegex(),Tu=j($s,"gu").replace(/notPunctSpace/g,Fu).replace(/punctSpace/g,Zu).replace(/punct/g,xs).getRegex(),Iu=j("^[^_*]*?\\*\\*[^_*]*?_[^_*]*?(?=\\*\\*)|[^_]+(?=[^_])|(?!_)punct(_+)(?=[\\s]|$)|notPunctSpace(_+)(?!_)(?=punctSpace|$)|(?!_)punctSpace(_+)(?=notPunctSpace)|[\\s](_+)(?!_)(?=punct)|(?!_)punct(_+)(?!_)(?=punct)","gu").replace(/notPunctSpace/g,ws).replace(/punctSpace/g,Ua).replace(/punct/g,wt).getRegex(),Ou=j(/\\(punct)/,"gu").replace(/punct/g,wt).getRegex(),Ru=j(/^<(scheme:[^\s\x00-\x1f<>]*|email)>/).replace("scheme",/[a-zA-Z][a-zA-Z0-9+.-]{1,31}/).replace("email",/[a-zA-Z0-9.!#$%&'*+/=?^_`{|}~-]+(@)[a-zA-Z0-9](?:[a-zA-Z0-9-]{0,61}[a-zA-Z0-9])?(?:\.[a-zA-Z0-9](?:[a-zA-Z0-9-]{0,61}[a-zA-Z0-9])?)+(?![-_])/).getRegex(),Lu=j(Fa).replace("(?:-->|$)","-->").getRegex(),Gu=j("^comment|^</[a-zA-Z][\\w:-]*\\s*>|^<[a-zA-Z][\\w-]*(?:attribute)*?\\s*/?>|^<\\?[\\s\\S]*?\\?>|^<![a-zA-Z]+\\s[\\s\\S]*?>|^<!\\[CDATA\\[[\\s\\S]*?\\]\\]>").replace("comment",Lu).replace("attribute",/\s+[a-zA-Z:_][\w.:-]*(?:\s*=\s*"[^"]*"|\s*=\s*'[^']*'|\s*=\s*[^\s"'=<>`]+)?/).getRegex(),gt=/(?:\[(?:\\[\s\S]|[^\[\]\\])*\]|\\[\s\S]|`+[^`]*?`+(?!`)|[^\[\]\\`])*?/,Du=j(/^!?\[(label)\]\(\s*(href)(?:(?:[ \t]*(?:\n[ \t]*)?)(title))?\s*\)/).replace("label",gt).replace("href",/<(?:\\.|[^\n<>\\])+>|[^ \t\n\x00-\x1f]*/).replace("title",/"(?:\\"?|[^"\\])*"|'(?:\\'?|[^'\\])*'|\((?:\\\)?|[^)\\])*\)/).getRegex(),vs=j(/^!?\[(label)\]\[(ref)\]/).replace("label",gt).replace("ref",Za).getRegex(),Cs=j(/^!?\[(ref)\](?:\[\])?/).replace("ref",Za).getRegex(),Bu=j("reflink|nolink(?!\\()","g").replace("reflink",vs).replace("nolink",Cs).getRegex(),ms=/[hH][tT][tT][pP][sS]?|[fF][tT][pP]/,Wa={_backpedal:Cn,anyPunctuation:Ou,autolink:Ru,blockSkip:Eu,br:ys,code:Au,del:Cn,emStrongLDelim:Uu,emStrongRDelimAst:Nu,emStrongRDelimUnd:Iu,escape:ju,link:Du,nolink:Cs,punctuation:zu,reflink:vs,reflinkSearch:Bu,tag:Gu,text:qu,url:Cn},Su={...Wa,link:j(/^!?\[(label)\]\((.*?)\)/).replace("label",gt).getRegex(),reflink:j(/^!?\[(label)\]\s*\[([^\]]*)\]/).replace("label",gt).getRegex()},ja={...Wa,emStrongRDelimAst:Tu,emStrongLDelim:Wu,url:j(/^((?:protocol):\/\/|www\.)(?:[a-zA-Z0-9\-]+\.?)+[^\s<]*|^email/).replace("protocol",ms).replace("email",/[A-Za-z0-9._+-]+(@)[a-zA-Z0-9-_]+(?:\.[a-zA-Z0-9-_]*[a-zA-Z0-9])+(?![-_])/).getRegex(),_backpedal:/(?:[^?!.,:;*_'"~()&]+|\([^)]*\)|&(?![a-zA-Z0-9]+;$)|[?!.,:;*_'"~)]+(?!$))+/,del:/^(~~?)(?=[^\s~])((?:\\[\s\S]|[^\\])*?(?:\\[\s\S]|[^\s~\\]))\1(?=[^~]|$)/,text:j(/^([`~]+|[^`~])(?:(?= {2,}\n)|(?=[a-zA-Z0-9.!#$%&'*+\/=?_`{\|}~-]+@)|[\s\S]*?(?:(?=[\\<!\[`*~_]|\b_|protocol:\/\/|www\.|$)|[^ ](?= {2,}\n)|[^a-zA-Z0-9.!#$%&'*+\/=?_`{\|}~-](?=[a-zA-Z0-9.!#$%&'*+\/=?_`{\|}~-]+@)))/).replace("protocol",ms).getRegex()},Mu={...ja,br:j(ys).replace("{2,}","*").getRegex(),text:j(ja.text).replace("\\b_","\\b_| {2,}\\n").replace(/\{2,\}/g,"*").getRegex()},_t={normal:Ea,gfm:vu,pedantic:Cu},kn={normal:Wa,gfm:ja,breaks:Mu,pedantic:Su},Pu={"&":"&amp;","<":"&lt;",">":"&gt;",'"':"&quot;","'":"&#39;"},us=(e)=>Pu[e];function oe(e,n){if(n){if(G.escapeTest.test(e))return e.replace(G.escapeReplace,us)}else if(G.escapeTestNoEncode.test(e))return e.replace(G.escapeReplaceNoEncode,us);return e}function ls(e){try{e=encodeURI(e).replace(G.percentDecode,"%")}catch{return null}return e}function ds(e,n){let t=e.replace(G.findPipe,(c,s,o)=>{let r=!1,p=s;for(;--p>=0&&o[p]==="\\";)r=!r;return r?"|":" |"}),a=t.split(G.splitPipe),i=0;if(a[0].trim()||a.shift(),a.length>0&&!a.at(-1)?.trim()&&a.pop(),n)if(a.length>n)a.splice(n);else for(;a.length<n;)a.push("");for(;i<a.length;i++)a[i]=a[i].trim().replace(G.slashPipe,"|");return a}function $n(e,n,t){let a=e.length;if(a===0)return"";let i=0;for(;i<a;){let c=e.charAt(a-i-1);if(c===n&&!t)i++;else if(c!==n&&t)i++;else break}return e.slice(0,a-i)}function Xu(e,n){if(e.indexOf(n[1])===-1)return-1;let t=0;for(let a=0;a<e.length;a++)if(e[a]==="\\")a++;else if(e[a]===n[0])t++;else if(e[a]===n[1]&&(t--,t<0))return a;return t>0?-2:-1}function bs(e,n,t,a,i){let c=n.href,s=n.title||null,o=e[1].replace(i.other.outputLinkReplace,"$1");a.state.inLink=!0;let r={type:e[0].charAt(0)==="!"?"image":"link",raw:t,href:c,title:s,text:o,tokens:a.inlineTokens(o)};return a.state.inLink=!1,r}function Hu(e,n,t){let a=e.match(t.other.indentCodeCompensation);if(a===null)return n;let i=a[1];return n.split(`
44
43
  `).map((c)=>{let s=c.match(t.other.beginningSpace);if(s===null)return c;let[o]=s;return o.length>=i.length?c.slice(i.length):c}).join(`
45
44
  `)}var ht=class{options;rules;lexer;constructor(e){this.options=e||Te}space(e){let n=this.rules.block.newline.exec(e);if(n&&n[0].length>0)return{type:"space",raw:n[0]}}code(e){let n=this.rules.block.code.exec(e);if(n){let t=n[0].replace(this.rules.other.codeRemoveIndent,"");return{type:"code",raw:n[0],codeBlockStyle:"indented",text:this.options.pedantic?t:$n(t,`
@@ -155,7 +154,7 @@ Please report this to https://github.com/markedjs/marked.`,e){let a="<p>An error
155
154
  ))?
156
155
  | (?<qBase>${_o})(?<qMod>[?+]?)(?<invalidQ>[?*+\{]?)
157
156
  | \\?.
158
- `.replace(/\s+/g,""),"gsu");function yi(e){if(!new RegExp(`${_o}\\+`).test(e))return{pattern:e};let n=[],t=null,a=null,i="",c=0,s;hi.lastIndex=0;while(s=hi.exec(e)){let{0:o,index:r,groups:{qBase:p,qMod:m,invalidQ:u}}=s;if(o==="["){if(!c)a=r;c++}else if(o==="]")if(c)c--;else a=null;else if(!c){if(m==="+"&&i&&!i.startsWith("(")){if(u)throw Error(`Invalid quantifier "${o}"`);let l=-1;if(/^\{\d+\}$/.test(p))e=uo(e,r+p.length,m,"");else{if(i===")"||i==="]"){let b=i===")"?t:a;if(b===null)throw Error(`Invalid unmatched "${i}"`);e=`${e.slice(0,b)}(?>${e.slice(b,r)}${p})${e.slice(r+o.length)}`}else e=`${e.slice(0,r-i.length)}(?>${i}${p})${e.slice(r+o.length)}`;l+=4}hi.lastIndex+=l}else if(o[0]==="(")n.push(r);else if(o===")")t=n.length?n.pop():null}i=o}return{pattern:e}}var Q=String.raw,a_=Q`\\g<(?<gRNameOrNum>[^>&]+)&R=(?<gRDepth>[^>]+)>`,xi=Q`\(\?R=(?<rDepth>[^\)]+)\)|${a_}`,Jt=Q`\(\?<(?![=!])(?<captureName>[^>]+)>`,wo=Q`${Jt}|(?<unnamed>\()(?!\?)`,Me=new RegExp(Q`${Jt}|${xi}|\(\?|\\?.`,"gsu"),wi="Cannot use multiple overlapping recursions";function xo(e,n){let{hiddenCaptures:t,mode:a}={hiddenCaptures:[],mode:"plugin",...n},i=n?.captureTransfers??new Map;if(!new RegExp(xi,"su").test(e))return{pattern:e,captureTransfers:i,hiddenCaptures:t};if(a==="plugin"&&Bn(e,Q`\(\?\(DEFINE\)`,B.DEFAULT))throw Error("DEFINE groups cannot be used with recursion");let c=[],s=Bn(e,Q`\\[1-9]`,B.DEFAULT),o=new Map,r=[],p=!1,m=0,u=0,l;Me.lastIndex=0;while(l=Me.exec(e)){let{0:b,groups:{captureName:d,rDepth:_,gRNameOrNum:f,gRDepth:g}}=l;if(b==="[")m++;else if(!m){if(_){if(go(_),p)throw Error(wi);if(s)throw Error(`${a==="external"?"Backrefs":"Numbered backrefs"} cannot be used with global recursion`);let w=e.slice(0,l.index),y=e.slice(Me.lastIndex);if(Bn(y,xi,B.DEFAULT))throw Error(wi);let x=+_-1;e=ho(w,y,x,!1,t,c,u),i=yo(i,w,x,c.length,0,u);break}else if(f){go(g);let w=!1;for(let ye of r)if(ye.name===f||ye.num===+f){if(w=!0,ye.hasRecursedWithin)throw Error(wi);break}if(!w)throw Error(Q`Recursive \g cannot be used outside the referenced group "${a==="external"?f:Q`\g<${f}&R=${g}>`}"`);let y=o.get(f),x=lo(e,y);if(s&&Bn(x,Q`${Jt}|\((?!\?)`,B.DEFAULT))throw Error(`${a==="external"?"Backrefs":"Numbered backrefs"} cannot be used with recursion of capturing groups`);let k=e.slice(y,l.index),I=x.slice(k.length+b.length),O=c.length,Y=+g-1,fe=ho(k,I,Y,!0,t,c,u);i=yo(i,k,Y,c.length-O,O,u);let un=e.slice(0,y),ln=e.slice(y+x.length);e=`${un}${fe}${ln}`,Me.lastIndex+=fe.length-b.length-k.length-I.length,r.forEach((ye)=>ye.hasRecursedWithin=!0),p=!0}else if(d)u++,o.set(String(u),Me.lastIndex),o.set(d,Me.lastIndex),r.push({num:u,name:d});else if(b[0]==="("){let w=b==="(";if(w)u++,o.set(String(u),Me.lastIndex);r.push(w?{num:u}:{})}else if(b===")")r.pop()}else if(b==="]")m--}return t.push(...c),{pattern:e,captureTransfers:i,hiddenCaptures:t}}function go(e){let n=`Max depth must be integer between 2 and 100; used ${e}`;if(!/^[1-9]\d*$/.test(e))throw Error(n);if(e=+e,e<2||e>100)throw Error(n)}function ho(e,n,t,a,i,c,s){let o=new Set;if(a)gi(e+n,Jt,({groups:{captureName:p}})=>{o.add(p)},B.DEFAULT);let r=[t,a?o:null,i,c,s];return`${e}${fo(`(?:${e}`,"forward",...r)}(?:)${fo(`${n})`,"backward",...r)}${n}`}function fo(e,n,t,a,i,c,s){let r=(m)=>n==="forward"?m+2:t-m+2-1,p="";for(let m=0;m<t;m++){let u=r(m);p+=Dn(e,Q`${wo}|\\k<(?<backref>[^>]+)>`,({0:l,groups:{captureName:b,unnamed:d,backref:_}})=>{if(_&&a&&!a.has(_))return l;let f=`_$${u}`;if(d||b){let g=s+c.length+1;return c.push(g),i_(i,g),d?l:`(?<${b}${f}>`}return Q`\k<${_}${f}>`},B.DEFAULT)}return p}function i_(e,n){for(let t=0;t<e.length;t++)if(e[t]>=n)e[t]++}function yo(e,n,t,a,i,c){if(e.size&&a){let s=0;gi(n,wo,()=>s++,B.DEFAULT);let o=c-s+i,r=new Map;return e.forEach((p,m)=>{let u=(a-s*t)/t,l=s*t,b=m>o+s?m+a:m,d=[];for(let _ of p)if(_<=o)d.push(_);else if(_>o+s+u)d.push(_+a);else if(_<=o+s)for(let f=0;f<=t;f++)d.push(_+s*f);else for(let f=0;f<=t;f++)d.push(_+l+u*f);r.set(b,d)}),r}return e}var{fromCodePoint:T,raw:C}=String,_e={flagGroups:(()=>{try{new RegExp("(?i:)")}catch{return!1}return!0})(),unicodeSets:(()=>{try{new RegExp("[[]]","v")}catch{return!1}return!0})()};_e.bugFlagVLiteralHyphenIsRange=_e.unicodeSets?(()=>{try{new RegExp(C`[\d\-a]`,"v")}catch{return!0}return!1})():!1;_e.bugNestedClassIgnoresNegation=_e.unicodeSets&&new RegExp("[[^a]]","v").test("a");function Qt(e,{enable:n,disable:t}){return{dotAll:!t?.dotAll&&!!(n?.dotAll||e.dotAll),ignoreCase:!t?.ignoreCase&&!!(n?.ignoreCase||e.ignoreCase)}}function Sn(e,n,t){if(!e.has(n))e.set(n,t);return e.get(n)}function ji(e,n){return ko[e]>=ko[n]}function c_(e,n){if(e==null)throw Error(n??"Value expected");return e}var ko={ES2025:2025,ES2024:2024,ES2018:2018},s_={auto:"auto",ES2025:"ES2025",ES2024:"ES2024",ES2018:"ES2018"};function Ao(e={}){if({}.toString.call(e)!=="[object Object]")throw Error("Unexpected options");if(e.target!==void 0&&!s_[e.target])throw Error(`Unexpected target "${e.target}"`);let n={accuracy:"default",avoidSubclass:!1,flags:"",global:!1,hasIndices:!1,lazyCompileLength:1/0,target:"auto",verbose:!1,...e,rules:{allowOrphanBackrefs:!1,asciiWordBoundaries:!1,captureGroup:!1,recursionLimit:20,singleline:!1,...e.rules}};if(n.target==="auto")n.target=_e.flagGroups?"ES2025":_e.unicodeSets?"ES2024":"ES2018";return n}var r_="[ -\r ]",o_=new Set([T(304),T(305)]),de=C`[\p{L}\p{M}\p{N}\p{Pc}]`;function qo(e){if(o_.has(e))return[e];let n=new Set,t=e.toLowerCase(),a=t.toUpperCase(),i=u_.get(t),c=p_.get(t),s=m_.get(t);if([...a].length===1)n.add(a);return s&&n.add(s),i&&n.add(i),n.add(t),c&&n.add(c),[...n]}var Ai=new Map(`C Other
157
+ `.replace(/\s+/g,""),"gsu");function yi(e){if(!new RegExp(`${_o}\\+`).test(e))return{pattern:e};let n=[],t=null,a=null,i="",c=0,s;hi.lastIndex=0;while(s=hi.exec(e)){let{0:o,index:r,groups:{qBase:p,qMod:m,invalidQ:u}}=s;if(o==="["){if(!c)a=r;c++}else if(o==="]")if(c)c--;else a=null;else if(!c){if(m==="+"&&i&&!i.startsWith("(")){if(u)throw Error(`Invalid quantifier "${o}"`);let l=-1;if(/^\{\d+\}$/.test(p))e=uo(e,r+p.length,m,"");else{if(i===")"||i==="]"){let b=i===")"?t:a;if(b===null)throw Error(`Invalid unmatched "${i}"`);e=`${e.slice(0,b)}(?>${e.slice(b,r)}${p})${e.slice(r+o.length)}`}else e=`${e.slice(0,r-i.length)}(?>${i}${p})${e.slice(r+o.length)}`;l+=4}hi.lastIndex+=l}else if(o[0]==="(")n.push(r);else if(o===")")t=n.length?n.pop():null}i=o}return{pattern:e}}var Q=String.raw,a_=Q`\\g<(?<gRNameOrNum>[^>&]+)&R=(?<gRDepth>[^>]+)>`,xi=Q`\(\?R=(?<rDepth>[^\)]+)\)|${a_}`,Jt=Q`\(\?<(?![=!])(?<captureName>[^>]+)>`,wo=Q`${Jt}|(?<unnamed>\()(?!\?)`,Me=new RegExp(Q`${Jt}|${xi}|\(\?|\\?.`,"gsu"),wi="Cannot use multiple overlapping recursions";function xo(e,n){let{hiddenCaptures:t,mode:a}={hiddenCaptures:[],mode:"plugin",...n},i=n?.captureTransfers??new Map;if(!new RegExp(xi,"su").test(e))return{pattern:e,captureTransfers:i,hiddenCaptures:t};if(a==="plugin"&&Bn(e,Q`\(\?\(DEFINE\)`,B.DEFAULT))throw Error("DEFINE groups cannot be used with recursion");let c=[],s=Bn(e,Q`\\[1-9]`,B.DEFAULT),o=new Map,r=[],p=!1,m=0,u=0,l;Me.lastIndex=0;while(l=Me.exec(e)){let{0:b,groups:{captureName:d,rDepth:_,gRNameOrNum:f,gRDepth:g}}=l;if(b==="[")m++;else if(!m){if(_){if(go(_),p)throw Error(wi);if(s)throw Error(`${a==="external"?"Backrefs":"Numbered backrefs"} cannot be used with global recursion`);let w=e.slice(0,l.index),y=e.slice(Me.lastIndex);if(Bn(y,xi,B.DEFAULT))throw Error(wi);let x=+_-1;e=ho(w,y,x,!1,t,c,u),i=yo(i,w,x,c.length,0,u);break}else if(f){go(g);let w=!1;for(let ye of r)if(ye.name===f||ye.num===+f){if(w=!0,ye.hasRecursedWithin)throw Error(wi);break}if(!w)throw Error(Q`Recursive \g cannot be used outside the referenced group "${a==="external"?f:Q`\g<${f}&R=${g}>`}"`);let y=o.get(f),x=lo(e,y);if(s&&Bn(x,Q`${Jt}|\((?!\?)`,B.DEFAULT))throw Error(`${a==="external"?"Backrefs":"Numbered backrefs"} cannot be used with recursion of capturing groups`);let k=e.slice(y,l.index),I=x.slice(k.length+b.length),O=c.length,Y=+g-1,fe=ho(k,I,Y,!0,t,c,u);i=yo(i,k,Y,c.length-O,O,u);let un=e.slice(0,y),ln=e.slice(y+x.length);e=`${un}${fe}${ln}`,Me.lastIndex+=fe.length-b.length-k.length-I.length,r.forEach((ye)=>ye.hasRecursedWithin=!0),p=!0}else if(d)u++,o.set(String(u),Me.lastIndex),o.set(d,Me.lastIndex),r.push({num:u,name:d});else if(b[0]==="("){let w=b==="(";if(w)u++,o.set(String(u),Me.lastIndex);r.push(w?{num:u}:{})}else if(b===")")r.pop()}else if(b==="]")m--}return t.push(...c),{pattern:e,captureTransfers:i,hiddenCaptures:t}}function go(e){let n=`Max depth must be integer between 2 and 100; used ${e}`;if(!/^[1-9]\d*$/.test(e))throw Error(n);if(e=+e,e<2||e>100)throw Error(n)}function ho(e,n,t,a,i,c,s){let o=new Set;if(a)gi(e+n,Jt,({groups:{captureName:p}})=>{o.add(p)},B.DEFAULT);let r=[t,a?o:null,i,c,s];return`${e}${fo(`(?:${e}`,"forward",...r)}(?:)${fo(`${n})`,"backward",...r)}${n}`}function fo(e,n,t,a,i,c,s){let r=(m)=>n==="forward"?m+2:t-m+2-1,p="";for(let m=0;m<t;m++){let u=r(m);p+=Dn(e,Q`${wo}|\\k<(?<backref>[^>]+)>`,({0:l,groups:{captureName:b,unnamed:d,backref:_}})=>{if(_&&a&&!a.has(_))return l;let f=`_$${u}`;if(d||b){let g=s+c.length+1;return c.push(g),i_(i,g),d?l:`(?<${b}${f}>`}return Q`\k<${_}${f}>`},B.DEFAULT)}return p}function i_(e,n){for(let t=0;t<e.length;t++)if(e[t]>=n)e[t]++}function yo(e,n,t,a,i,c){if(e.size&&a){let s=0;gi(n,wo,()=>s++,B.DEFAULT);let o=c-s+i,r=new Map;return e.forEach((p,m)=>{let u=(a-s*t)/t,l=s*t,b=m>o+s?m+a:m,d=[];for(let _ of p)if(_<=o)d.push(_);else if(_>o+s+u)d.push(_+a);else if(_<=o+s)for(let f=0;f<=t;f++)d.push(_+s*f);else for(let f=0;f<=t;f++)d.push(_+l+u*f);r.set(b,d)}),r}return e}var{fromCodePoint:T,raw:C}=String,_e={flagGroups:(()=>{try{new RegExp("(?i:)")}catch{return!1}return!0})(),unicodeSets:(()=>{try{new RegExp("[[]]","v")}catch{return!1}return!0})()};_e.bugFlagVLiteralHyphenIsRange=_e.unicodeSets?(()=>{try{new RegExp(C`[\d\-a]`,"v")}catch{return!0}return!1})():!1;_e.bugNestedClassIgnoresNegation=_e.unicodeSets&&new RegExp("[[^a]]","v").test("a");function Qt(e,{enable:n,disable:t}){return{dotAll:!t?.dotAll&&!!(n?.dotAll||e.dotAll),ignoreCase:!t?.ignoreCase&&!!(n?.ignoreCase||e.ignoreCase)}}function Sn(e,n,t){if(!e.has(n))e.set(n,t);return e.get(n)}function ji(e,n){return ko[e]>=ko[n]}function c_(e,n){if(e==null)throw Error(n??"Value expected");return e}var ko={ES2025:2025,ES2024:2024,ES2018:2018},s_={auto:"auto",ES2025:"ES2025",ES2024:"ES2024",ES2018:"ES2018"};function Ao(e={}){if({}.toString.call(e)!=="[object Object]")throw Error("Unexpected options");if(e.target!==void 0&&!s_[e.target])throw Error(`Unexpected target "${e.target}"`);let n={accuracy:"default",avoidSubclass:!1,flags:"",global:!1,hasIndices:!1,lazyCompileLength:1/0,target:"auto",verbose:!1,...e,rules:{allowOrphanBackrefs:!1,asciiWordBoundaries:!1,captureGroup:!1,recursionLimit:20,singleline:!1,...e.rules}};if(n.target==="auto")n.target=_e.flagGroups?"ES2025":_e.unicodeSets?"ES2024":"ES2018";return n}var r_="[\t-\r ]",o_=new Set([T(304),T(305)]),de=C`[\p{L}\p{M}\p{N}\p{Pc}]`;function qo(e){if(o_.has(e))return[e];let n=new Set,t=e.toLowerCase(),a=t.toUpperCase(),i=u_.get(t),c=p_.get(t),s=m_.get(t);if([...a].length===1)n.add(a);return s&&n.add(s),i&&n.add(i),n.add(t),c&&n.add(c),[...n]}var Ai=new Map(`C Other
159
158
  Cc Control cntrl
160
159
  Cf Format
161
160
  Cn Unassigned
@@ -282,6 +281,44 @@ XID_Start XIDS`.split(/\s/).map((e)=>[on(e),e])),p_=new Map([["s",T(383)],[T(383
282
281
  border-right: 1px solid var(--border);
283
282
  overflow-y: auto;
284
283
  flex-shrink: 0;
284
+ position: relative;
285
+ }
286
+
287
+ .sidebar::-webkit-scrollbar {
288
+ width: 8px;
289
+ }
290
+
291
+ .sidebar::-webkit-scrollbar-track {
292
+ background: transparent;
293
+ }
294
+
295
+ .sidebar::-webkit-scrollbar-thumb {
296
+ background: ${i?"#333":"#ddd"};
297
+ border-radius: 4px;
298
+ }
299
+
300
+ .sidebar::-webkit-scrollbar-thumb:hover {
301
+ background: ${i?"#444":"#ccc"};
302
+ }
303
+
304
+ .sidebar {
305
+ scrollbar-width: thin;
306
+ scrollbar-color: ${i?"#333 transparent":"#ddd transparent"};
307
+ }
308
+
309
+ .sidebar-resize-handle {
310
+ position: absolute;
311
+ top: 0;
312
+ right: 0;
313
+ width: 4px;
314
+ height: 100%;
315
+ cursor: ew-resize;
316
+ background: transparent;
317
+ transition: background 0.2s;
318
+ }
319
+
320
+ .sidebar-resize-handle:hover {
321
+ background: var(--accent);
285
322
  }
286
323
 
287
324
  .sidebar-header {
@@ -321,6 +358,10 @@ XID_Start XIDS`.split(/\s/).map((e)=>[on(e),e])),p_=new Map([["s",T(383)],[T(383
321
358
  position: relative;
322
359
  }
323
360
 
361
+ .sidebar-nav .dir-item.collapsed > ul {
362
+ display: none;
363
+ }
364
+
324
365
  .sidebar-nav .dir-item > ul {
325
366
  margin-top: 2px;
326
367
  position: relative;
@@ -340,6 +381,35 @@ XID_Start XIDS`.split(/\s/).map((e)=>[on(e),e])),p_=new Map([["s",T(383)],[T(383
340
381
  align-items: center;
341
382
  gap: 8px;
342
383
  letter-spacing: 0.01em;
384
+ border-radius: 6px;
385
+ transition: background 0.15s;
386
+ }
387
+
388
+ .sidebar-nav .dir-label:hover {
389
+ background: var(--hover);
390
+ }
391
+
392
+ .dir-chevron {
393
+ display: inline-flex;
394
+ transition: transform 0.2s;
395
+ flex-shrink: 0;
396
+ opacity: 0.6;
397
+ }
398
+
399
+ .dir-item.collapsed .dir-chevron {
400
+ transform: rotate(-90deg);
401
+ }
402
+
403
+ .dir-chevron svg {
404
+ width: 16px;
405
+ height: 16px;
406
+ }
407
+
408
+ .sidebar-nav .dir-label span,
409
+ .sidebar-nav a span {
410
+ overflow: hidden;
411
+ text-overflow: ellipsis;
412
+ white-space: nowrap;
343
413
  }
344
414
 
345
415
  .sidebar-nav .dir-label svg {
@@ -573,17 +643,82 @@ XID_Start XIDS`.split(/\s/).map((e)=>[on(e),e])),p_=new Map([["s",T(383)],[T(383
573
643
  background: var(--sidebar-bg);
574
644
  border: 1px solid var(--border);
575
645
  border-radius: 8px;
576
- padding: 20px;
646
+ padding: 16px 20px;
577
647
  margin: 24px 0;
648
+ overflow: hidden;
649
+ }
650
+
651
+ .toc ul {
652
+ max-height: 400px;
653
+ overflow-y: auto;
654
+ opacity: 1;
655
+ transition: max-height 0.3s ease-out, opacity 0.2s ease-out, margin 0.2s;
656
+ margin: 0 -16px 0 0;
657
+ padding: 0 16px 0 0;
658
+ }
659
+
660
+ .toc ul::-webkit-scrollbar {
661
+ width: 6px;
662
+ }
663
+
664
+ .toc ul::-webkit-scrollbar-track {
665
+ background: transparent;
666
+ }
667
+
668
+ .toc ul::-webkit-scrollbar-thumb {
669
+ background: ${i?"#444":"#ccc"};
670
+ border-radius: 3px;
671
+ }
672
+
673
+ .toc ul::-webkit-scrollbar-thumb:hover {
674
+ background: ${i?"#555":"#bbb"};
675
+ }
676
+
677
+ .toc ul {
678
+ scrollbar-width: thin;
679
+ scrollbar-color: ${i?"#444 transparent":"#ccc transparent"};
680
+ }
681
+
682
+ .toc.collapsed ul {
683
+ max-height: 0;
684
+ opacity: 0;
685
+ overflow: hidden;
578
686
  }
579
687
 
580
688
  .toc h3 {
581
689
  font-size: 0.875rem;
582
- margin-bottom: 12px;
690
+ margin: 0 0 12px 0;
583
691
  text-transform: uppercase;
584
692
  letter-spacing: 0.08em;
585
693
  font-weight: 700;
586
694
  color: ${i?"#b3b3b3":"#666"};
695
+ display: flex;
696
+ align-items: center;
697
+ gap: 6px;
698
+ transition: margin 0.2s;
699
+ }
700
+
701
+ .toc.collapsed h3 {
702
+ margin-bottom: 0;
703
+ }
704
+
705
+ .toc-chevron {
706
+ display: inline-flex;
707
+ align-items: center;
708
+ justify-content: center;
709
+ transition: transform 0.2s;
710
+ opacity: 0.6;
711
+ transform-origin: center center;
712
+ }
713
+
714
+ .toc.collapsed .toc-chevron {
715
+ transform: rotate(-90deg);
716
+ }
717
+
718
+ .toc-chevron svg {
719
+ width: 16px;
720
+ height: 16px;
721
+ display: block;
587
722
  }
588
723
 
589
724
  .toc ul {
@@ -717,7 +852,7 @@ XID_Start XIDS`.split(/\s/).map((e)=>[on(e),e])),p_=new Map([["s",T(383)],[T(383
717
852
  </div>`;return Mi({content:r,title:a,theme:c.theme,fontTheme:c.fontTheme,files:i,currentPath:s,clientScript:o,watchEnabled:c.watch,watchFile:s})},ta=(e)=>{let{errorCode:n,message:t,files:a,config:i,clientScript:c}=e,s=`<div class="error">
718
853
  <h1>${n}</h1>
719
854
  <p>${t}</p>
720
- </div>`;return Mi({content:s,title:`Error ${n}`,theme:i.theme,fontTheme:i.fontTheme,files:a,clientScript:c})};import{watch as Ug}from"node:fs";import{join as Wg}from"node:path";var Qn=new Map,Kn=new Map,Ng=300,Tg=(e,n)=>{return()=>{let t=Kn.get(e);if(t)clearTimeout(t);let a=setTimeout(()=>{n(),Kn.delete(e)},Ng);Kn.set(e,a)}},Vo=(e,n,t)=>{let a=Wg(e,n),i=Qn.get(n);if(i){i.subscribers.add(t),console.log(`[watcher] Added subscriber to ${n} (${i.subscribers.size} total)`);return}console.log(`[watcher] Starting watch for ${n}`);let c=Ug(a,(s)=>{if(s==="change"){let o=Qn.get(n);if(!o)return;Tg(n,()=>{console.log(`[watcher] File changed: ${n}, notifying ${o.subscribers.size} subscriber(s)`),o.subscribers.forEach((p)=>{try{p.send(JSON.stringify({type:"reload",file:n}))}catch(m){console.error("[watcher] Failed to send reload message:",m)}})})()}});c.on("error",(s)=>{console.error(`[watcher] Error watching ${n}:`,s)}),Qn.set(n,{path:n,watcher:c,subscribers:new Set([t])})},Jo=(e,n)=>{let t=Qn.get(e);if(!t)return;if(t.subscribers.delete(n),console.log(`[watcher] Removed subscriber from ${e} (${t.subscribers.size} remaining)`),t.subscribers.size===0){console.log(`[watcher] Stopping watch for ${e}`),t.watcher.close(),Qn.delete(e);let a=Kn.get(e);if(a)clearTimeout(a),Kn.delete(e)}};var et=()=>({"Content-Type":"text/html","Cache-Control":"no-cache, no-store, must-revalidate",Pragma:"no-cache",Expires:"0"}),Rg=(e)=>{if(!e.startsWith("/view/"))return null;let n=e.slice(6);return n.endsWith(".md")?n:null},Lg=async(e,n)=>{try{let t=Og(e,n);return await Pi(t,"utf-8")}catch{return null}},He=(e,n,t,a)=>{e.writeHead(n,t),e.end(a)},Gg=/\.md$/,Dg=(e)=>{let t=e.replace(Gg,"").split("-");if(t.length===2){let[a,i]=t;return{theme:a,font:i}}return null},Bg=async(e,n,t,a,i)=>{let c=await Lg(n.directory,e);if(!c){let s=ta({errorCode:404,message:`File not found: ${e}`,files:t,config:n,clientScript:a});He(i,404,et(),s);return}try{let s=e.split("/").pop()??e,o=Dg(s),r=o?{...n,theme:o.theme??n.theme,fontTheme:o.font??n.fontTheme}:n,{html:p,toc:m}=await Mo(c,r.theme),u=Yo({html:p,toc:m,fileName:s,files:t,config:r,currentPath:e,clientScript:a});He(i,200,et(),u)}catch(s){let o=s instanceof Error?s.message:"Failed to render markdown",r=ta({errorCode:500,message:o,files:t,config:n,clientScript:a});He(i,500,et(),r)}},Sg=(e,n,t)=>{return async(a,i)=>{let s=new URL(a.url??"/",`http://${a.headers.host}`).pathname;if(s==="/"||s.startsWith("/view/")){let m=new Date().toISOString().split("T")[1]?.split(".")[0];console.log(`[${m}] ${a.method} ${s}`)}if(s==="/_favicon")try{let m=await Pi("./src/favicon.svg","utf-8");i.writeHead(200,{"Content-Type":"image/svg+xml","Cache-Control":"public, max-age=31536000, immutable"}),i.end(m);return}catch{He(i,404,{"Content-Type":"text/plain"},"Favicon not found");return}if(s.startsWith("/_fonts/")){let m=s.slice(8);try{let u=await Pi(`./src/fonts/${m}`);i.writeHead(200,{"Content-Type":"font/woff2","Cache-Control":"public, max-age=31536000, immutable"}),i.end(u);return}catch{He(i,404,{"Content-Type":"text/plain"},"Font not found");return}}if(s==="/"){let m=Ho(n,e,t);He(i,200,et(),m);return}let r=Rg(s);if(r){await Bg(r,e,n,t,i);return}let p=ta({errorCode:404,message:"Page not found",files:n,config:e,clientScript:t});He(i,404,et(),p)}},Mg=(e,n,t)=>{try{let a=JSON.parse(n.toString());if(a.type==="watch"&&a.file)e.file=a.file,Vo(t.directory,a.file,e)}catch(a){console.error("[ws] Failed to parse message:",a)}},Qo=async(e,n)=>{let t=await os(),a=Ig(Sg(e,n,t)),i;if(e.watch)i=new Ca.default({noServer:!0}),a.on("upgrade",(o,r,p)=>{if(new URL(o.url??"/",`http://${o.headers.host}`).pathname==="/_ws")i?.handleUpgrade(o,r,p,(u)=>{i?.emit("connection",u,o)});else r.destroy()}),i.on("connection",(o)=>{console.log("[ws] Client connected"),o.on("message",(r)=>{Mg(o,r,e)}),o.on("close",()=>{if(console.log("[ws] Client disconnected"),o.file)Jo(o.file,o)})});await new Promise((o)=>{a.listen(e.port,e.host,()=>{o()})});let c=a.address(),s=typeof c==="object"&&c!==null?c.port:e.port;return{hostname:e.host,port:s,stop:()=>{i?.close(),a.close()}}},Ko=(e)=>`http://${e.hostname}:${e.port}`;var Pg=["dP dP dP","88 88 88","88 88 88d8b.d8b. .d888b88","88 88 88'`88'`88 88' `88","88 88 88 88 88 88. .88","dP dP dP dP dP `88888P8"],Xg=["\x1B[96m","\x1B[96m","\x1B[36m","\x1B[36m","\x1B[34m","\x1B[94m"];var Hg=()=>{return`
855
+ </div>`;return Mi({content:s,title:`Error ${n}`,theme:i.theme,fontTheme:i.fontTheme,files:a,clientScript:c})};import{watch as Ug}from"node:fs";import{join as Wg}from"node:path";var Qn=new Map,Kn=new Map,Ng=300,Tg=(e,n)=>{return()=>{let t=Kn.get(e);if(t)clearTimeout(t);let a=setTimeout(()=>{n(),Kn.delete(e)},Ng);Kn.set(e,a)}},Vo=(e,n,t)=>{let a=Wg(e,n),i=Qn.get(n);if(i){i.subscribers.add(t),console.log(`[watcher] Added subscriber to ${n} (${i.subscribers.size} total)`);return}console.log(`[watcher] Starting watch for ${n}`);let c=Ug(a,(s)=>{if(s==="change"){let o=Qn.get(n);if(!o)return;Tg(n,()=>{console.log(`[watcher] File changed: ${n}, notifying ${o.subscribers.size} subscriber(s)`),o.subscribers.forEach((p)=>{try{p.send(JSON.stringify({type:"reload",file:n}))}catch(m){console.error("[watcher] Failed to send reload message:",m)}})})()}});c.on("error",(s)=>{console.error(`[watcher] Error watching ${n}:`,s)}),Qn.set(n,{path:n,watcher:c,subscribers:new Set([t])})},Jo=(e,n)=>{let t=Qn.get(e);if(!t)return;if(t.subscribers.delete(n),console.log(`[watcher] Removed subscriber from ${e} (${t.subscribers.size} remaining)`),t.subscribers.size===0){console.log(`[watcher] Stopping watch for ${e}`),t.watcher.close(),Qn.delete(e);let a=Kn.get(e);if(a)clearTimeout(a),Kn.delete(e)}};var et=()=>({"Content-Type":"text/html","Cache-Control":"no-cache, no-store, must-revalidate",Pragma:"no-cache",Expires:"0"}),Rg=(e)=>{if(!e.startsWith("/view/"))return null;let n=e.slice(6);return n.endsWith(".md")?n:null},Lg=async(e,n)=>{try{let t=Og(e,n);return await Pi(t,"utf-8")}catch{return null}},He=(e,n,t,a)=>{e.writeHead(n,t),e.end(a)},Gg=/\.md$/,Dg=(e)=>{let t=e.replace(Gg,"").split("-");if(t.length===2){let[a,i]=t;return{theme:a,font:i}}return null},Bg=async(e,n,t,a,i)=>{let c=await Lg(n.directory,e);if(!c){let s=ta({errorCode:404,message:`File not found: ${e}`,files:t,config:n,clientScript:a});He(i,404,et(),s);return}try{let s=e.split("/").pop()??e,o=Dg(s),r=o?{...n,theme:o.theme??n.theme,fontTheme:o.font??n.fontTheme}:n,{html:p,toc:m}=await Mo(c,r.theme),u=Yo({html:p,toc:m,fileName:s,files:t,config:r,currentPath:e,clientScript:a});He(i,200,et(),u)}catch(s){let o=s instanceof Error?s.message:"Failed to render markdown",r=ta({errorCode:500,message:o,files:t,config:n,clientScript:a});He(i,500,et(),r)}},Sg=(e,n,t)=>{return async(a,i)=>{let s=new URL(a.url??"/",`http://${a.headers.host}`).pathname;if(s==="/"||s.startsWith("/view/")){let m=new Date().toISOString().split("T")[1]?.split(".")[0];console.log(`[${m}] ${a.method} ${s}`)}if(s==="/_favicon")try{let m=await Pi("./src/favicon.svg","utf-8");i.writeHead(200,{"Content-Type":"image/svg+xml","Cache-Control":"public, max-age=31536000, immutable"}),i.end(m);return}catch{He(i,404,{"Content-Type":"text/plain"},"Favicon not found");return}if(s.startsWith("/_fonts/")){let m=s.slice(8);try{let u=await Pi(`./src/fonts/${m}`);i.writeHead(200,{"Content-Type":"font/woff2","Cache-Control":"public, max-age=31536000, immutable"}),i.end(u);return}catch{He(i,404,{"Content-Type":"text/plain"},"Font not found");return}}if(s==="/"){let m=Ho(n,e,t);He(i,200,et(),m);return}let r=Rg(s);if(r){await Bg(r,e,n,t,i);return}let p=ta({errorCode:404,message:"Page not found",files:n,config:e,clientScript:t});He(i,404,et(),p)}},Mg=(e,n,t)=>{try{let a=JSON.parse(n.toString());if(a.type==="watch"&&a.file)e.file=a.file,Vo(t.directory,a.file,e)}catch(a){console.error("[ws] Failed to parse message:",a)}},Qo=async(e,n)=>{let t=await os(),a=Ig(Sg(e,n,t)),i;if(e.watch)i=new Ca.default({noServer:!0}),a.on("upgrade",(o,r,p)=>{if(new URL(o.url??"/",`http://${o.headers.host}`).pathname==="/_ws")i?.handleUpgrade(o,r,p,(u)=>{i?.emit("connection",u,o)});else r.destroy()}),i.on("connection",(o)=>{console.log("[ws] Client connected"),o.on("message",(r)=>{Mg(o,r,e)}),o.on("close",()=>{if(console.log("[ws] Client disconnected"),o.file)Jo(o.file,o)})});await new Promise((o)=>{a.listen(e.port,"localhost",()=>{o()})});let c=a.address();return{hostname:"localhost",port:typeof c==="object"&&c!==null?c.port:e.port,stop:()=>{i?.close(),a.close()}}},Ko=(e)=>`http://${e.hostname}:${e.port}`;var Pg=["dP dP dP","88 88 88","88 88 88d8b.d8b. .d888b88","88 88 88'`88'`88 88' `88","88 88 88 88 88 88. .88","dP dP dP dP dP `88888P8"],Xg=["\x1B[96m","\x1B[96m","\x1B[36m","\x1B[36m","\x1B[34m","\x1B[94m"];var Hg=()=>{return`
721
856
  ${Pg.map((n,t)=>`${Xg[t]}${n}\x1B[0m`).join(`
722
857
  `)}
723
858
  `},ep=()=>{console.log(Hg())};var Yg=async()=>{try{ep(),console.log();let e=tc(process.argv.slice(2));if(!e)process.exit(0);console.log(`\u2192 Scanning ${e.directory}...`);let n=await cc(e.directory);console.log(`\u2713 Found ${n.length} markdown file${n.length===1?"":"s"}
@@ -731,5 +866,5 @@ ${Pg.map((n,t)=>`${Xg[t]}${n}\x1B[0m`).join(`
731
866
  \u2717 Unknown error occurred
732
867
  `);process.exit(1)}};Yg();
733
868
 
734
- //# debugId=5DCAF391AB09672D64756E2164756E21
869
+ //# debugId=E7591978BC2E275A64756E2164756E21
735
870
  //# sourceMappingURL=llmd.js.map
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "llmd",
3
- "version": "0.1.0",
3
+ "version": "0.1.1",
4
4
  "description": "Local markdown server for LLM-generated docs",
5
5
  "author": "Phil Zona <phil.b.zona@gmail.com>",
6
6
  "license": "MIT",
@@ -31,7 +31,7 @@
31
31
  "scripts": {
32
32
  "dev": "bun --hot index.ts",
33
33
  "test": "bun test",
34
- "build": "rm -f dist/llmd dist/llmd.js* llmd.js* dist/client.js && mkdir -p dist && bun build --target=browser --minify ./src/client-bundle.ts --outfile=dist/client.js && bun build --target=node --minify --sourcemap ./index.ts --outfile=llmd.js && mv llmd.js* dist/ && sed -i '' '1s|#!/usr/bin/env bun|#!/usr/bin/env node|' dist/llmd.js && mv dist/llmd.js dist/llmd && chmod +x dist/llmd",
34
+ "build": "rm -f dist/llmd dist/llmd.js* llmd.js* dist/client.js && mkdir -p dist && bun build --target=browser --minify ./src/client-bundle.ts --outfile=dist/client.js && bun build --target=node --minify --sourcemap ./index.ts --outfile=llmd.js && mv llmd.js* dist/ && sed -i.bak '1s|#!/usr/bin/env bun|#!/usr/bin/env node|' dist/llmd.js && rm -f dist/llmd.js.bak && mv dist/llmd.js dist/llmd && chmod +x dist/llmd",
35
35
  "prepublishOnly": "bun test && bun run build",
36
36
  "preview": "bun scripts/generate-preview.ts",
37
37
  "check-contrast": "bun scripts/check-contrast.ts",
@@ -51,6 +51,7 @@
51
51
  ],
52
52
  "dependencies": {
53
53
  "@types/ws": "^8.18.1",
54
+ "better-sqlite3": "^12.5.0",
54
55
  "fast-glob": "^3.3.3",
55
56
  "figlet": "^1.9.4",
56
57
  "marked": "^17.0.1",
@@ -59,6 +60,7 @@
59
60
  },
60
61
  "devDependencies": {
61
62
  "@biomejs/biome": "2.3.8",
63
+ "@types/better-sqlite3": "^7.6.13",
62
64
  "@types/bun": "latest",
63
65
  "@types/figlet": "^1.7.0",
64
66
  "husky": "^9.1.7",