/**
* Minimal, runtime-agnostic HTML parser for the SSR renderer.
*
* This is intentionally a small, linear scanner rather than a full HTML5
* tokenizer. It is sufficient for templates authored against the `bQuery`
* directive vocabulary (HTML fragments, common void/raw elements, attributes)
* and lets the SSR pipeline run on Bun, Deno and Node without depending on a
* `DOMParser` polyfill.
*
* Output: a tiny virtual node tree (`SSRNode`) compatible with the pluggable
* DOM adapter API used by `renderer.ts`.
*
* @module bquery/ssr
* @internal
*/
const VOID_ELEMENTS = new Set([
'area',
'base',
'br',
'col',
'embed',
'hr',
'img',
'input',
'link',
'meta',
'param',
'source',
'track',
'wbr',
]);
const RAW_TEXT_ELEMENTS = new Set(['script', 'style', 'textarea', 'title']);
/** A DOM-free node structure produced by `parseTemplate()`. */
export type SSRNode = SSRElement | SSRText | SSRComment | SSRDocumentFragment;
export interface SSRElement {
type: 'element';
tag: string;
attributes: Record;
/** Order-preserving attribute list (so output is deterministic). */
attributeOrder: string[];
children: SSRNode[];
/** Whether this element should be serialised as a void element. */
void: boolean;
/** Whether the children are raw (e.g. `