@bettercms-ai/types 1.20.0 → 1.21.0

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.d.ts CHANGED
@@ -81,6 +81,8 @@ interface BlockStyle {
81
81
  shadow?: ShadowToken;
82
82
  borderTop?: boolean;
83
83
  borderBottom?: boolean;
84
+ /** All four sides, `1px solid currentColor` — an outline button's border follows its text colour. */
85
+ border?: boolean;
84
86
  /** 🔴 The one free-form string. MUST go through `safeCssUrl()` before reaching CSS. */
85
87
  bgImage?: string;
86
88
  }
package/dist/index.js CHANGED
@@ -124,6 +124,7 @@ function blockStyleToCss(style) {
124
124
  if (s.fontSize && FONT_SIZE_REM[s.fontSize]) css.fontSize = FONT_SIZE_REM[s.fontSize];
125
125
  if (s.weight && WEIGHT[s.weight] != null) css.fontWeight = WEIGHT[s.weight];
126
126
  if (s.radius && RADIUS_PX[s.radius] != null) css.borderRadius = RADIUS_PX[s.radius];
127
+ if (style.border === true) css.border = "1px solid currentColor";
127
128
  return Object.keys(css).length ? css : void 0;
128
129
  }
129
130
 
package/dist/index.js.map CHANGED
@@ -1 +1 @@
1
- {"version":3,"sources":["../src/block.ts","../src/block-bindings.ts","../src/blockStyle.ts","../src/component.ts","../src/layout-lucide-icons.ts","../src/layout.ts","../src/locator.ts"],"sourcesContent":["/**\n * ContentBlock — a discriminated union of all CMS block types.\n * Each block has a `type` discriminator and a `props` object\n * whose shape matches the block type.\n */\n\n// ── Block style (FLO-264) ──────────────────────────────────────────────────────\n// A uniform, BOUNDED set of design tokens any block may carry (sibling to `props`).\n// Tokens map to fixed CSS values in the renderer (`styleTokensToCss`) so styling\n// reaches the live site WITHOUT arbitrary CSS. Additive + fully optional.\n\nexport type SpaceToken = \"none\" | \"xs\" | \"sm\" | \"md\" | \"lg\" | \"xl\";\nexport type ColorToken = \"none\" | \"white\" | \"black\" | \"muted\" | \"mutedBg\" | \"primary\" | \"accent\";\nexport type AlignToken = \"left\" | \"center\" | \"right\";\nexport type FontSizeToken = \"sm\" | \"base\" | \"lg\" | \"xl\" | \"2xl\";\nexport type WeightToken = \"normal\" | \"medium\" | \"semibold\" | \"bold\";\nexport type RadiusToken = \"none\" | \"sm\" | \"md\" | \"lg\" | \"full\";\n\n// Section design (task 4) — the per-instance design a section carries on the page.\nexport type ThemeToken = \"inherit\" | \"light\" | \"dark\";\nexport type BgToken = \"none\" | \"surface\" | \"muted\" | \"accent\" | \"dark\" | \"custom\";\nexport type ContentWidthToken = \"narrow\" | \"default\" | \"wide\" | \"full\";\nexport type CornerToken = \"0\" | \"s\" | \"m\" | \"l\" | \"xl\" | \"2xl\";\nexport type ShadowToken = \"0\" | \"s\" | \"m\" | \"l\" | \"xl\";\n\nexport interface BlockStyle {\n // Legacy token set (FLO-264). Where these overlap the section fields below\n // (background, radius, padding), the section field WINS in the renderer.\n paddingY?: SpaceToken;\n paddingX?: SpaceToken;\n marginTop?: SpaceToken;\n marginBottom?: SpaceToken;\n background?: ColorToken;\n textColor?: ColorToken;\n align?: AlignToken;\n fontSize?: FontSizeToken;\n weight?: WeightToken;\n radius?: RadiusToken;\n\n // Section design (task 4).\n theme?: ThemeToken;\n bg?: BgToken;\n /** Only read when `bg === \"custom\"`. Hex only. */\n bgCustom?: string;\n /** Padding sliders, in px (0–240). */\n paddingTop?: number;\n paddingBottom?: number;\n paddingSides?: number;\n contentWidth?: ContentWidthToken;\n /**\n * Where the constrained content column sits, when `contentWidth` constrains it.\n *\n * Split out of `align`, which still means text alignment and is still the fallback when this\n * is unset — so everything written before the split renders byte-identically. The two were one\n * token until anything MEASURED a section's text alignment: copying a source site's\n * `text-align: left` would otherwise also shove its column to the page edge.\n */\n contentAlign?: AlignToken;\n fullHeight?: boolean;\n /** 0–100. */\n opacity?: number;\n corner?: CornerToken;\n shadow?: ShadowToken;\n borderTop?: boolean;\n borderBottom?: boolean;\n /** 🔴 The one free-form string. MUST go through `safeCssUrl()` before reaching CSS. */\n bgImage?: string;\n}\n\n// ── Heading ──────────────────────────────────────────────────────────────────\n\nexport interface HeadingProps {\n text: string;\n level?: 1 | 2 | 3;\n}\n\nexport interface HeadingBlock {\n type: \"heading\";\n id: string;\n style?: BlockStyle;\n /** Editor-facing display name for this block's dock card. Not rendered. */\n label?: string;\n props: HeadingProps;\n}\n\n// ── Text ─────────────────────────────────────────────────────────────────────\n\nexport interface TextProps {\n html: string;\n /** @see RichTextProps.level — the same payload takes the same level. */\n level?: 1 | 2 | 3 | 4 | 5 | 6;\n}\n\nexport interface TextBlock {\n type: \"text\";\n id: string;\n style?: BlockStyle;\n /** Editor-facing display name for this block's dock card. Not rendered. */\n label?: string;\n props: TextProps;\n}\n\n/**\n * A rich-text block: the same HTML payload as `text`, authored through a real editor.\n *\n * WHY A SEPARATE TYPE RATHER THAN CHANGING `text`. Every `text` block already on a live page\n * holds an HTML string that the delivery renderer injects as-is. Repurposing that type would\n * mean migrating published content, and getting it wrong renders visible markup to visitors.\n * A new type costs nothing at rest and leaves existing pages untouched.\n *\n * The payload is deliberately IDENTICAL to TextProps (an HTML string) so the two are\n * interchangeable at the renderer: delivery treats them the same, and the difference is\n * entirely in how an author edits them — `text` is a plain field, `richtext` gets the\n * formatting surface.\n */\n/**\n * A Portable Text node — the structured form of rich text.\n *\n * Kept alongside `html` rather than replacing it, so nothing already published moves. The\n * structure exists because an HTML string cannot carry INTENT: a colour is a hex with no\n * notion of which brand token produced it, an embedded component is a div with no reference\n * to resolve, and neither can be read back by tooling. Nodes can carry all of that.\n */\nexport interface PortableTextNode {\n _type: string;\n _key?: string;\n /** Block style — \"normal\", \"h2\", \"blockquote\". */\n style?: string;\n text?: string;\n children?: PortableTextNode[];\n /** Marks on a span: \"strong\", \"em\", or a token reference like \"color:brand-accent\". */\n marks?: string[];\n /** An embedded component or reference resolves through these. */\n schemaKey?: string;\n _ref?: string;\n fields?: Record<string, unknown>;\n}\n\nexport interface PortableTextDocument {\n version: 1;\n content: PortableTextNode[];\n}\n\nexport interface RichTextProps {\n /**\n * The RENDERED CACHE. Delivery reads this, so the fast path stays a string interpolation\n * and every page published before `content` existed keeps rendering byte-identically.\n */\n html: string;\n /**\n * The SOURCE OF TRUTH, when present — `content` always wins over `html`.\n *\n * Optional on purpose: this is the same envelope the field values already use\n * (`{ format, value, html }`), where `html` is likewise derived. Any writer that sets\n * `html` alone on a block that HAS `content` must delete `content` in the same write, or\n * the stale string silently shadows the newer structure.\n */\n content?: PortableTextDocument;\n /**\n * Render the rich copy AS `<h1>`–`<h6>` instead of a paragraph container, so a title keeps\n * its inline marks (a brand-coloured span) AND its heading semantics. Absent ⇒ ordinary rich\n * text, as before. Set ⇒ the value must be ONE line of inline copy; the write schema refuses\n * more. A component prop of type `number` or `select` can target `props.level`.\n */\n level?: 1 | 2 | 3 | 4 | 5 | 6;\n}\n\nexport interface RichTextBlock {\n type: \"richtext\";\n id: string;\n style?: BlockStyle;\n /** Editor-facing display name for this block's dock card. Not rendered. */\n label?: string;\n props: RichTextProps;\n}\n\n// ── Image ────────────────────────────────────────────────────────────────────\n\nexport interface ImageProps {\n src: string;\n alt: string;\n width?: number;\n height?: number;\n caption?: string;\n}\n\nexport interface ImageBlock {\n type: \"image\";\n id: string;\n style?: BlockStyle;\n /** Editor-facing display name for this block's dock card. Not rendered. */\n label?: string;\n props: ImageProps;\n}\n\n// ── Button ───────────────────────────────────────────────────────────────────\n\nexport interface ButtonProps {\n text: string;\n href: string;\n variant?: \"primary\" | \"secondary\";\n}\n\nexport interface ButtonBlock {\n type: \"button\";\n id: string;\n style?: BlockStyle;\n /** Editor-facing display name for this block's dock card. Not rendered. */\n label?: string;\n props: ButtonProps;\n}\n\n// ── Spacer ───────────────────────────────────────────────────────────────────\n\nexport interface SpacerProps {\n height: number; // in px\n}\n\nexport interface SpacerBlock {\n type: \"spacer\";\n id: string;\n style?: BlockStyle;\n /** Editor-facing display name for this block's dock card. Not rendered. */\n label?: string;\n props: SpacerProps;\n}\n\n// ── Columns ───────────────────────────────────────────────────────────────────\n\nexport interface ColumnsProps {\n columns: ContentBlock[][]; // array of column slots, each slot is an array of blocks\n gap?: number; // in px\n}\n\nexport interface ColumnsBlock {\n type: \"columns\";\n id: string;\n style?: BlockStyle;\n /** Editor-facing display name for this block's dock card. Not rendered. */\n label?: string;\n props: ColumnsProps;\n}\n\n// ── Video ────────────────────────────────────────────────────────────────────\n\nexport interface VideoProps {\n url: string;\n poster?: string;\n autoplay?: boolean;\n loop?: boolean;\n /**\n * What is said in the video (CPO-093). The block carries its own because its url may be a\n * pasted provider link with no library asset to hang one from. Rendered as <details> after\n * the player and published in the .md twin.\n */\n transcript?: string;\n}\n\nexport interface VideoBlock {\n type: \"video\";\n id: string;\n style?: BlockStyle;\n /** Editor-facing display name for this block's dock card. Not rendered. */\n label?: string;\n props: VideoProps;\n}\n\n// ── Form ─────────────────────────────────────────────────────────────────────\n\nexport interface FormProps {\n formId: string; // references forms.id (a nanoid). Resolved against delivered forms at render time.\n}\n\nexport interface FormBlock {\n type: \"form\";\n id: string;\n style?: BlockStyle;\n /** Editor-facing display name for this block's dock card. Not rendered. */\n label?: string;\n props: FormProps;\n}\n\n// ── Section (recursive container) ──────────────────────────────────────────────\n\nexport interface SectionProps {\n children: ContentBlock[];\n background?: string;\n paddingY?: number; // in px\n maxWidth?: number; // in px\n}\n\nexport interface SectionBlock {\n type: \"section\";\n id: string;\n style?: BlockStyle;\n /** Editor-facing display name for this block's dock card. Not rendered. */\n label?: string;\n props: SectionProps;\n}\n\n// ── Navbar ─────────────────────────────────────────────────────────────────────\n\nexport interface NavLink {\n label: string;\n href: string;\n}\n\nexport interface NavbarProps {\n logo?: { src: string; alt: string; href?: string };\n logoAlt?: string;\n links: NavLink[];\n mobileMenu?: boolean;\n cta?: { text: string; href: string };\n}\n\nexport interface NavbarBlock {\n type: \"navbar\";\n id: string;\n style?: BlockStyle;\n /** Editor-facing display name for this block's dock card. Not rendered. */\n label?: string;\n props: NavbarProps;\n}\n\n// ── Footer ─────────────────────────────────────────────────────────────────────\n\nexport interface FooterColumn {\n heading?: string;\n links: NavLink[];\n}\n\nexport interface FooterProps {\n columns: FooterColumn[];\n copyright?: string;\n}\n\nexport interface FooterBlock {\n type: \"footer\";\n id: string;\n style?: BlockStyle;\n /** Editor-facing display name for this block's dock card. Not rendered. */\n label?: string;\n props: FooterProps;\n}\n\n// ── Slider / Carousel (recursive container, client-hydrated) ────────────────────\n\nexport interface SlideItem {\n id: string;\n children: ContentBlock[];\n}\n\nexport interface SliderProps {\n slides: SlideItem[];\n autoplay?: boolean;\n interval?: number; // in ms\n loop?: boolean;\n}\n\nexport interface SliderBlock {\n type: \"slider\";\n id: string;\n style?: BlockStyle;\n /** Editor-facing display name for this block's dock card. Not rendered. */\n label?: string;\n props: SliderProps;\n}\n\n// ── Tabs (recursive container, client-hydrated) ─────────────────────────────────\n\nexport interface TabItem {\n id: string;\n label: string;\n children: ContentBlock[];\n}\n\nexport interface TabsProps {\n tabs: TabItem[];\n}\n\nexport interface TabsBlock {\n type: \"tabs\";\n id: string;\n style?: BlockStyle;\n /** Editor-facing display name for this block's dock card. Not rendered. */\n label?: string;\n props: TabsProps;\n}\n\n// ── Component instance (Webflow-style reusable symbol) ──────────────────────────\n// References a reusable component by id. `overrides` maps a component prop key\n// (declared in the component's `props[]` allowlist) to a value, applied to the\n// component's block tree at render time. Resolved against delivered components.\n\nexport interface ComponentProps {\n componentId: string;\n overrides?: Record<string, unknown>;\n /** Phase A: the page field group this placement renders (its copy + bindings live there). */\n bind?: string;\n /**\n * Phase B: where each override's copy CAME FROM — `{ <propKey>: \"<page field path>\" }`.\n *\n * Written when a placement takes ownership of its copy (`bind` is deleted at the same moment),\n * and it is not decoration:\n * - the COVERAGE METER counts a block-lane declaration\n * (`data-bcms-block=\"<id>\"` + `data-bcms-field=\"<id>__overrides.<propKey>\"`) as bound for\n * the page path named here, so a converted page does not read as a site that lost its\n * bindings;\n * - it is how the componentize lane still recognises WHICH GROUP an instance renders once\n * `bind` is gone — without it a second run would mint a second instance for the same band.\n * A `table` prop names its repeater's path (`faq.items`); every row path under it is that one\n * declaration's, because the prop holds every row.\n */\n source?: Record<string, string>;\n}\n\nexport interface ComponentBlock {\n type: \"component\";\n id: string;\n style?: BlockStyle;\n /** Editor-facing display name for this block's dock card. Not rendered. */\n label?: string;\n props: ComponentProps;\n}\n\n// ── Collection (the entries of the page this block sits on) ─────────────────────\n//\n// LANE-AWARE, and that is the whole idea. A dynamic page's `blockJson` is BOTH what\n// `/blog` renders and the template interpolated into every `/blog/<slug>`. One array\n// cannot be an index and a post layout — unless the one block that differs between them\n// knows which lane it is in. The route supplies that (see CollectionCtx in render-page.ts):\n//\n// /blog → this block renders a card per published entry\n// /blog/my-post → this block renders THAT entry's detail; every other block in the\n// array is interpolated with {{placeholders}} exactly as before\n//\n// So no second template column, no migration, and a page without a collection block\n// behaves byte-identically to before.\n//\n// Scope is IMPLIED, never configured: a collection lists the entries of the page it sits\n// on, which is precisely the set whose detail URLs are /<thisPage>/<slug>. There is no\n// model picker because there is no other correct answer.\n\nexport interface CollectionProps {\n /** Component rendered once per entry, interpolated with {{field}} and {{url}}. Omit for a built-in card. */\n cardComponentId?: string;\n /** Component rendered for the single entry on a detail URL. Omit to fall back to the generic field layout. */\n detailComponentId?: string;\n /** Built-in card only. Defaults to \"title\" / no excerpt. */\n titleField?: string;\n excerptField?: string;\n /** Max cards to render. Defaults to 20. */\n limit?: number;\n /** \"newest\" (default) reverses the reader's created_at ordering. */\n order?: \"newest\" | \"oldest\";\n emptyText?: string;\n}\n\nexport interface CollectionBlock {\n type: \"collection\";\n id: string;\n style?: BlockStyle;\n /** Editor-facing display name for this block's dock card. Not rendered. */\n label?: string;\n props: CollectionProps;\n}\n\n// ── Union ─────────────────────────────────────────────────────────────────────\n\nexport type ContentBlock =\n | CollectionBlock\n | HeadingBlock\n | TextBlock\n | RichTextBlock\n | ImageBlock\n | ButtonBlock\n | SpacerBlock\n | ColumnsBlock\n | VideoBlock\n | FormBlock\n | SectionBlock\n | NavbarBlock\n | FooterBlock\n | SliderBlock\n | TabsBlock\n | ComponentBlock;\n\n/** Literal union of all block type discriminators. */\nexport type BlockType = ContentBlock[\"type\"];\n\n/**\n * Type guard — narrows an unknown block to `ContentBlock`.\n *\n * @example\n * const block = maybeBlock as unknown;\n * if (isBlock(block)) {\n * // block is ContentBlock here\n * }\n */\nexport function isBlock(value: unknown): value is ContentBlock {\n return (\n typeof value === \"object\" &&\n value !== null &&\n \"type\" in value &&\n typeof (value as Record<string, unknown>)[\"type\"] === \"string\"\n );\n}\n\n/**\n * Extract the `type` discriminator from a block, or `null` if not a block.\n *\n * @example\n * const block = { type: \"heading\", id: \"1\", props: { text: \"Hi\" } };\n * getBlockType(block); // \"heading\"\n * getBlockType({ not: \"a block\" }); // null\n */\nexport function getBlockType(value: unknown): BlockType | null {\n if (isBlock(value)) return value.type;\n return null;\n}\n","/**\n * The ONE declaration of which block props the Visual Editor can address.\n *\n * Four renderers stamp `data-bcms-field` — the hosted renderer, the Next SDK, the Astro SDK\n * and (for minting keys rather than markup) the dashboard's `buildBlockPageDoc`. Until this\n * file existed each carried its own hand-written list, they disagreed by two props, and the\n * dashboard's copy said so in a comment while having nothing to enforce it. A block listed in\n * one and missing from another does not error: it simply never binds, or it binds to a node\n * that resolves to no field. Both failures are silent, which is why they survived.\n *\n * This file is the declaration. The renderers remain the implementation — only they know which\n * ELEMENT carries a value — and `block-binding-coverage.test.ts` asserts the two agree.\n *\n * ── Two kinds of address, because an element is not an attribute ────────────────────────────\n *\n * `data-bcms-field` addresses ONE element. That is enough for a heading's text or an image's\n * src, and not enough for an image's `alt`: the `<img>` already carries a binding, and an\n * element cannot hold two. Entries that name an `attr` are therefore emitted on a SECOND\n * attribute, `data-bcms-props`, whose grammar is:\n *\n * <address>|<kind>|<domAttribute>[;<address>|<kind>|<domAttribute>]*\n *\n * No JSON, because the values are already constrained: an address is grammar A\n * (`[A-Za-z0-9_$-]`, `.`, `[n]`), and kinds and attributes are plain identifiers. A split on\n * two characters parses it, in any language, with no escaping.\n *\n * ── Path templates ──────────────────────────────────────────────────────────────────────────\n *\n * `[]` marks an array the renderer walks. `expandBlockBindings` substitutes real indices from a\n * block's actual props, so `links[].label` on a three-link navbar yields three concrete\n * addresses and on an empty one yields none. `parseFieldPath`/`setFieldPath` in the dashboard\n * have handled N indices since FLO-949; the cap was in what the renderer offered, not in what\n * the writer could persist.\n */\nimport type { ContentBlock, BlockType } from \"./block.js\";\n\n/**\n * How the editor paints a value, and whether it may take a caret.\n *\n * `text`/`richtext` are inline-editable. `image` selects and swaps through the media picker.\n * `url` never takes a caret — a URL typed onto the page has nowhere to report a malformed\n * value — so it is edited in the element toolbar. `array` is a repeater slot: selectable and\n * locatable, edited in the dock.\n *\n * `document` is a whole Portable Text body: selectable as ONE container, repainted whole from the\n * form, and edited per keyed block inside it. It is not a longer `richtext` — a Body stamped\n * `richtext` goes into the rich-text lane, where an opt-out rewrites the value as an `{html}`\n * envelope and the document's own block structure is destroyed.\n */\nexport type BindingKind = \"text\" | \"richtext\" | \"image\" | \"document\" | \"url\" | \"number\" | \"array\";\n\nexport interface BlockBinding {\n /** Path template in grammar A, relative to the block's `props`. `[]` = an array to walk. */\n readonly path: string;\n readonly kind: BindingKind;\n /**\n * The DOM attribute this value lives in, when it is not the element's own text or `src`.\n * Present ⇒ the renderer emits it on `data-bcms-props`, never on `data-bcms-field`.\n */\n readonly attr?: string;\n}\n\n/**\n * Props deliberately absent, and still absent for the original reason:\n *\n * `spacer.height`, `columns.gap`, `section.background` and every `style` token — design, not\n * content. They are edited in the Design accordion, where a slider can express a bounded\n * range that free typing on the page cannot.\n *\n * `text.html` when Portable Text is present — `html` is a cache derived from `content`, so\n * advertising it would persist an ignored sibling and the next frame would read as a revert.\n * The renderer suppresses it; the expander cannot see `content`, so the branch stays there.\n *\n * `component.overrides.*` — instance-scoped, so it cannot be a static template. The renderer\n * derives those addresses per instance from the definition's declared props.\n */\nexport const BLOCK_BINDINGS: Partial<Record<BlockType, readonly BlockBinding[]>> = {\n heading: [{ path: \"text\", kind: \"text\" }],\n text: [{ path: \"html\", kind: \"richtext\" }],\n richtext: [{ path: \"html\", kind: \"richtext\" }],\n image: [\n { path: \"src\", kind: \"image\" },\n { path: \"caption\", kind: \"text\" },\n { path: \"alt\", kind: \"text\", attr: \"alt\" },\n ],\n button: [\n { path: \"text\", kind: \"text\" },\n { path: \"href\", kind: \"url\", attr: \"href\" },\n ],\n video: [\n { path: \"url\", kind: \"url\", attr: \"src\" },\n { path: \"poster\", kind: \"url\", attr: \"poster\" },\n ],\n navbar: [\n { path: \"logo.src\", kind: \"image\" },\n { path: \"logo.alt\", kind: \"text\", attr: \"alt\" },\n { path: \"links[].label\", kind: \"text\" },\n { path: \"links[].href\", kind: \"url\", attr: \"href\" },\n { path: \"cta.text\", kind: \"text\" },\n { path: \"cta.href\", kind: \"url\", attr: \"href\" },\n ],\n footer: [\n { path: \"copyright\", kind: \"text\" },\n { path: \"columns[].heading\", kind: \"text\" },\n { path: \"columns[].links[].label\", kind: \"text\" },\n { path: \"columns[].links[].href\", kind: \"url\", attr: \"href\" },\n ],\n tabs: [{ path: \"tabs[].label\", kind: \"text\" }],\n};\n\n/** One concrete, writable address on one block. */\nexport interface ExpandedBinding extends BlockBinding {\n /** The template with every `[]` replaced by a real index, e.g. `links[2].href`. */\n readonly path: string;\n}\n\nconst isRecord = (v: unknown): v is Record<string, unknown> =>\n typeof v === \"object\" && v !== null && !Array.isArray(v);\n\n/**\n * Read a grammar-A path — dotted object keys and zero or more `[n]` indices.\n *\n * Positional, exactly like the dashboard's `parseFieldPath`: a dotted segment is always an\n * object key and a bracketed one always an index, so `links.0` reads the string key \"0\" and\n * misses, rather than being quietly treated as `links[0]`. Any miss returns undefined; nothing\n * here throws, because a template that does not resolve must yield no address, not an error.\n *\n * EXPORTED because a second reader of this grammar now exists: `@bettercms-ai/convert` commits a\n * build-time helper into a customer's repository, and that helper must resolve a path exactly the\n * way the editor does or a converted template renders a fallback where a value exists. The helper\n * itself carries an inlined copy (it lands in a repo where our packages do not exist) and a parity\n * test pins the copy to this original.\n */\nexport function readPath(root: unknown, path: string): unknown {\n let cursor: unknown = root;\n for (const segment of path.split(\".\")) {\n if (!segment) return undefined;\n const key = segment.replace(/\\[\\d+\\]/g, \"\");\n if (key) {\n if (!isRecord(cursor)) return undefined;\n cursor = cursor[key];\n }\n for (const index of segment.matchAll(/\\[(\\d+)\\]/g)) {\n if (!Array.isArray(cursor)) return undefined;\n cursor = cursor[Number(index[1])];\n }\n }\n return cursor;\n}\n\n/** Substitute the FIRST `[]` with every real index, then recurse for any deeper array. */\nfunction expandTemplate(binding: BlockBinding, props: unknown, path: string): ExpandedBinding[] {\n const at = path.indexOf(\"[]\");\n if (at < 0) return [{ ...binding, path }];\n\n const head = path.slice(0, at);\n const tail = path.slice(at + 2);\n const array = readPath(props, head);\n if (!Array.isArray(array)) return [];\n\n return array.flatMap((_item, index) =>\n expandTemplate(binding, props, `${head}[${index}]${tail}`),\n );\n}\n\n/**\n * Every concrete address a block actually offers right now.\n *\n * Array templates expand against the array's real length, so an address is only ever minted\n * for an element that exists. That is the load-bearing property: `setFieldPath` refuses to\n * fabricate an array member, so an address for `links[3]` on a two-link navbar would be a\n * binding the writer rejects — the \"advertises an edit that silently fails\" failure this whole\n * grammar exists to avoid.\n *\n * A prop whose KEY is absent does NOT expand, and that is not a nicety. `setFieldPath` refuses\n * to create a final key unless `createMissingObjects` is set, which only component overrides\n * pass — so an address for a key the block does not carry is a write the editor would reject.\n * An empty string still expands: `\"\"` is a value, and clearing a heading must not make it\n * uneditable.\n */\nexport function expandBlockBindings(block: ContentBlock): ExpandedBinding[] {\n const declared = BLOCK_BINDINGS[block.type];\n if (!declared) return [];\n const props = (block as { props?: unknown }).props;\n if (!isRecord(props)) return [];\n return declared\n .flatMap((binding) => expandTemplate(binding, props, binding.path))\n .filter((binding) => readPath(props, binding.path) !== undefined);\n}\n\n/** The `data-bcms-props` value for a block's attribute bindings, or \"\" when it has none. */\nexport function formatPropsAttribute(\n entries: readonly { address: string; kind: BindingKind; attr: string }[],\n): string {\n return entries.map((e) => `${e.address}|${e.kind}|${e.attr}`).join(\";\");\n}\n\n/** Parse a `data-bcms-props` value. Malformed entries are dropped, never guessed at. */\nexport function parsePropsAttribute(\n value: string | null | undefined,\n): { address: string; kind: BindingKind; attr: string }[] {\n if (!value) return [];\n return value\n .split(\";\")\n .map((entry) => entry.split(\"|\"))\n .filter((parts): parts is [string, BindingKind, string] => parts.length === 3 && parts.every(Boolean))\n .map(([address, kind, attr]) => ({ address, kind, attr }));\n}\n\n/** The shape of a declared component prop this module needs: where it points, and its key. */\ninterface PropTarget {\n key?: string;\n target?: { blockId?: string; path?: string };\n}\n\n/**\n * `<defBlockId>__<prop>` → `<instanceBlockId>__overrides.<propKey>`, for one placed component.\n *\n * Shared by every renderer, because the mapping is a property of the DEFINITION and not of any\n * one output format. A component's block ids belong to the definition and are shared by every\n * instance of it, so `<defBlockId>__text` addresses no instance's value — which is why component\n * subtrees used to render unannotated, and why the SDKs (which never had that suppression)\n * stamped definition-scoped addresses that resolve to no field and, on a component placed twice,\n * collide into a duplicate that drops BOTH copies.\n *\n * The definition already states the mapping in `props[].target`. This only re-keys that\n * statement into the address the editor writes through. Nothing is inferred: a prop with no\n * target produces no entry, so it keeps its dock control and stays uneditable on the canvas,\n * which is the truthful outcome rather than a broken one.\n */\n/**\n * The definition-scoped key a declared prop POINTS AT — `<defBlockId>__<path>`, the same\n * grammar `expandBlockBindings` produces for a block's own bindings.\n *\n * Exported so the \"which leaves does no prop reach?\" check and the address minter below read\n * the key from ONE place. They ask opposite questions of the same mapping, and two spellings\n * of `.replace(/^props\\./, \"\")` is precisely how a leaf ends up counted as bound by one and\n * unbound by the other. Null when the prop declares no target — which is the honest answer:\n * such a prop reaches nothing.\n */\nexport function componentPropTargetKey(prop: PropTarget | undefined): string | null {\n if (!prop?.key || !prop.target?.blockId) return null;\n return `${prop.target.blockId}__${String(prop.target.path ?? \"\").replace(/^props\\./, \"\")}`;\n}\n\n/**\n * `owner` is the address of the rich-text field an instance is EMBEDDED in. Its `_key` is unique\n * only within that field, so the instance is named `<owner>#<_key>` — the same grammar a\n * rich-text node's own address uses — giving `<owner>#<_key>__overrides.<propKey>`.\n */\nexport function componentInstanceAddresses(\n instanceBlockId: string,\n props: readonly PropTarget[] | undefined,\n owner?: string,\n): Map<string, string> {\n const instance = owner ? `${owner}#${instanceBlockId}` : instanceBlockId;\n const out = new Map<string, string>();\n for (const prop of props ?? []) {\n if (!prop?.key || !prop.target?.blockId) continue;\n const from = componentPropTargetKey(prop)!;\n // Two props aimed at one target would make the address ambiguous; first declaration wins\n // and the duplicate is dropped rather than silently overwriting it.\n if (!out.has(from)) out.set(from, `${instance}__overrides.${prop.key}`);\n }\n return out;\n}\n","/**\n * FLO-264 — bounded block-style tokens → CSS. Framework-agnostic (returns a plain\n * declaration object, no React types) so every renderer shares ONE mapping: the\n * headless @bettercms-ai/next adapter, @bettercms-ai/ui, and (string form) the hosted\n * render-page.ts. Unknown tokens are dropped — closed set, no arbitrary CSS.\n */\nimport type { BlockStyle } from \"./block.js\";\n\nconst SPACE_PX: Record<string, string> = { none: \"0\", xs: \"4px\", sm: \"8px\", md: \"16px\", lg: \"32px\", xl: \"64px\" };\nconst FONT_SIZE_REM: Record<string, string> = { sm: \"0.875rem\", base: \"1rem\", lg: \"1.25rem\", xl: \"1.5rem\", \"2xl\": \"2rem\" };\nconst WEIGHT: Record<string, number> = { normal: 400, medium: 500, semibold: 600, bold: 700 };\nconst RADIUS_PX: Record<string, string> = { none: \"0\", sm: \"4px\", md: \"8px\", lg: \"16px\", full: \"9999px\" };\nconst COLOR_HEX: Record<string, string> = { white: \"#ffffff\", black: \"#111111\", muted: \"#6b7280\", mutedBg: \"#f3f4f6\", primary: \"#111111\", accent: \"#4f46e5\" };\n\n/** A CSS declaration object (key → value) usable as a React `style` prop, or undefined when empty. */\nexport function blockStyleToCss(style: BlockStyle | undefined): Record<string, string | number> | undefined {\n if (!style || typeof style !== \"object\") return undefined;\n const s = style as Record<string, string>;\n const css: Record<string, string | number> = {};\n if (s.paddingY && SPACE_PX[s.paddingY] != null) { css.paddingTop = SPACE_PX[s.paddingY]!; css.paddingBottom = SPACE_PX[s.paddingY]!; }\n if (s.paddingX && SPACE_PX[s.paddingX] != null) { css.paddingLeft = SPACE_PX[s.paddingX]!; css.paddingRight = SPACE_PX[s.paddingX]!; }\n if (s.marginTop && SPACE_PX[s.marginTop] != null) css.marginTop = SPACE_PX[s.marginTop]!;\n if (s.marginBottom && SPACE_PX[s.marginBottom] != null) css.marginBottom = SPACE_PX[s.marginBottom]!;\n if (s.background && COLOR_HEX[s.background]) css.background = COLOR_HEX[s.background]!;\n if (s.textColor && COLOR_HEX[s.textColor]) css.color = COLOR_HEX[s.textColor]!;\n if (s.align === \"left\" || s.align === \"center\" || s.align === \"right\") css.textAlign = s.align;\n if (s.fontSize && FONT_SIZE_REM[s.fontSize]) css.fontSize = FONT_SIZE_REM[s.fontSize]!;\n if (s.weight && WEIGHT[s.weight] != null) css.fontWeight = WEIGHT[s.weight]!;\n if (s.radius && RADIUS_PX[s.radius] != null) css.borderRadius = RADIUS_PX[s.radius]!;\n return Object.keys(css).length ? css : undefined;\n}\n","/**\n * Component — a reusable, Webflow-style block tree (a \"symbol\").\n *\n * A component is authored once and placed across pages via `component` blocks\n * (see `ComponentBlock` in `./block.ts`). Its definition lives in `blockJson`;\n * `props` declares a flat allowlist of values an instance may override.\n */\nimport type { ContentBlock } from \"./block.js\";\nimport type { ContentModelFieldUi } from \"./content-model.js\";\nimport type { VariantInputMapping } from \"./layout.js\";\n\n/**\n * The category a component belongs to (drives library grouping + icons). The first eight\n * are structural (what the component IS); the last four are the \"Add a section\" library\n * tabs (where it appears). One varchar column, not a PG enum — widening is code-only.\n */\n/**\n * 🔴 THE STRUCTURE DOCTRINE — one sentence, one home, spliced into every surface that builds a page.\n *\n * It lives HERE, beside the component contract it describes, because there are THREE places that teach\n * an agent how to build a page and they drifted apart:\n * • `packages/mcp/src/tools.ts` — the MCP tool descriptions (external agents)\n * • `src/lib/ai/agent.ts` — the in-product Studio Agent's system prompt\n * • `packages/mcp/src/prompts.ts` — the authoring playbook, which a tool call does not carry\n *\n * Only the playbook explained sections. `create_page` taught the SCHEMA axis in detail (\"each visual\n * section becomes a nested field\") and said nothing about STRUCTURE; the Studio Agent's prompt named\n * \"pages & reusable components (structure/layout)\" without ever mentioning `sectionType`.\n *\n * Measured consequence, production 2026-08-18: project `acme` has three components, ALL with\n * `section_type = (none)`, and its home page is 18 loose top-level blocks with ZERO sections. Every\n * generated page came out flat, so the visual editor's section lane — outline, name, move, duplicate,\n * delete, variant swap — had nothing to attach to. The editor was faithfully showing pages that were\n * never built out of sections.\n *\n * A constant rather than three paraphrases, because updating some of them is exactly how this happened.\n */\nexport const SECTION_DOCTRINE =\n \"STRUCTURE (separate from schema): a page is composed of SECTIONS. NEVER build a page out of loose top-level heading/text/image/button/spacer blocks — they cannot be moved, duplicated or swapped as a unit, the visual editor cannot outline or name them, and every one of them becomes its own section in the editor. A hero of a headline, a lede and two CTAs is ONE section, not four. TWO SHAPES, and the choice is about REUSE. (1) A band that appears on more than one page, or that needs layout variants, is a COMPONENT with a `sectionType` — see create_component. Components sharing a `sectionType` are that section's VARIANTS (one Hero: 'Centered' for the home page and 'Two-column' for about, same prop keys so a swap keeps the content). This is also the only shape the editor's 'Add a section' picker can insert, and the only one that gets a family name and a variant switcher. (2) A genuinely one-off band on a single page is a `section` BLOCK whose `props.children` hold its blocks. THE TRADEOFF, stated in the present tense because it is real today: inside a component, ONLY the leaves a declared prop TARGETS are click-to-edit on the canvas — each declared prop's `target` is re-keyed to that PLACEMENT's own override address, so editing it changes this page and not the shared definition. A prop with no `target` still SHOWS as a dock control, but its override reaches no rendered slot, so editing it changes nothing on the page. Copy that no prop points at is worse still: no binding and no control, unreachable from click-to-edit AND from the dock, changeable only by editing the component definition, which rewrites every page that places it. A `section` block's children stay click-to-edit unconditionally. So when you choose a component, DECLARE A PROP — WITH A `target` — for every string, link and image a marketer will ever touch; a component with un-propped editable copy is the defect, not the component. In the dock an unset prop shows EMPTY and inherits the definition's default, so set props explicitly when you want the current copy visible there. Do not hand-write a band's JSON: start from a built-in section blueprint (list_components returns locked `builtin:*` blueprints with no projectId — hero-centered, hero-split, feature-grid-three, cta-banner and nine more), each already rooted in a `section` block with its editable leaves declared as props. INLINE its blockJson as a `section` block for a one-off band; for a recurring band, materialize the blueprint with create_component so it becomes project-scoped before implementation validation, Output or publication. Direct `builtin:*` component references exist only for legacy delivery compatibility. Two consecutive call-to-action buttons are two sibling `button` blocks inside the same section — never a `columns` block, which is a `repeat(N,1fr)` grid and would stretch each CTA to half the container. Buttons are inline-level and flow side by side on their own.\";\n\nexport type ComponentCategory =\n | \"navbar\"\n | \"footer\"\n | \"button\"\n | \"section\"\n | \"slider\"\n | \"tabs\"\n | \"form\"\n | \"custom\"\n | \"hero\"\n | \"content\"\n | \"social-proof\"\n | \"conversion\";\n\n/**\n * A single overridable field on a component. `target` points at the block + JSON\n * path inside `blockJson` the override writes to (e.g. blockId \"cta\", path\n * \"props.text\"). Keeping overrides a declared allowlist (not arbitrary nested\n * rewrites) keeps instance data small and the contract explicit.\n */\n/**\n * THE prop vocabulary. One list, imported everywhere a prop type is enumerated.\n *\n * It exists as a value (not just a union) because four places used to spell it out by hand —\n * this file, the Drizzle schema, `COMPONENT_PROP_TYPES` in the backend's Zod schemas, and the\n * MCP tool shape — and the MCP copy is the dangerous one: `update_component` REPLACES the whole\n * `props` array, so a type its enum omits cannot be echoed back, and an agent that reads a\n * component and writes it straight back DESTROYS every prop of that type with a 200.\n *\n * Order is not semantic; append rather than re-sort, so a diff stays readable.\n */\nexport const COMPONENT_PROP_TYPES = [\n \"text\",\n \"richtext\",\n \"image\",\n \"url\",\n \"boolean\",\n \"number\",\n \"select\",\n \"group\",\n \"table\",\n \"slot\",\n \"form\",\n] as const;\n\nexport type ComponentPropType = (typeof COMPONENT_PROP_TYPES)[number];\n\n/**\n * The value a `form` prop STORES: just the id. The form itself is a Form document and stays the\n * single source of truth for its fields — a component references one, it never re-declares it.\n *\n * `.strict()` at the write boundary, so a client that POSTs a hydrated form object alongside the\n * id gets a 400 rather than a silent strip.\n *\n * There is deliberately NO resolved twin of this shape. Every renderer already receives forms the\n * same way — a catalogue beside the blocks (`BcmsBlocks({blocks, forms})`, the site renderer's\n * forms map) — and looks the id up in it. A hydrated `{formId, form}` prop value would be a shape\n * that exists nowhere in delivery.\n */\nexport interface ComponentFormPropRef {\n formId: string;\n}\n\nexport interface ComponentPropDef {\n key: string;\n label: string;\n target: { blockId: string; path: string };\n /**\n * `slot` holds ONE nested component instance — the component-level twin of the\n * content-model field type `component-ref` (see content-model.ts), named differently for\n * the same reason that one is: `component` already means a BLOCK type. Its value is\n * `{ componentId, overrides }` and its `target.path` is `props`, so filling a slot writes\n * that object over an empty `component` block's props.\n *\n * On a PAGE a slot fill is a LIVE reference; a published ENTRY freezes it (resolveDeep).\n */\n /**\n * The EDITOR contract, not a storage one: `applyOverrides` writes the value at\n * `target.path` whatever its shape, so `type` decides which control the inspector renders\n * and what shape that control produces (FLO-1020).\n *\n * number → a number (heading.level, columns.count)\n * select → one string from `config.options`\n * group → an object keyed by `config.fields`\n * table → an array of such objects (slider.slides)\n *\n * `reference` is absent on purpose: nothing resolves a content-entry id at component render\n * time, so such a prop would save cleanly and render as nothing.\n */\n type: ComponentPropType;\n defaultValue?: unknown;\n /**\n * EDITOR HINTS (playbook §12). Stored in the props JSON, so no migration.\n *\n * 🔴 `required` IS NOT ENFORCED AT WRITE TIME, deliberately. Nothing on the write path\n * refuses an override that omits a required prop — a placement saves either way — because\n * the alternative is a component definition that can retroactively make already-saved pages\n * unsaveable. It is a marker the dashboard renders and `get_site_composition` counts, which\n * is the honest shape: the receipt names what is missing instead of the write refusing it.\n */\n required?: boolean;\n /** Hint shown under the control, muted. */\n helpText?: string;\n /** Ghost text inside a text-ish control. */\n placeholder?: string;\n /** Per-type settings; the save schema enforces that each is present on the type needing it. */\n config?: {\n /** `slot` — a pick allowlist. */\n componentIds?: string[];\n /**\n * `select` — the choices. Required, and a default must be one of them. `{ label, value }`\n * when the stored value is not what an author should read (a component id, for instance).\n */\n options?: Array<string | { label: string; value: string }>;\n /** `group` / `table` — the sub-shape, nestable to 3 levels. */\n fields?: ComponentSubField[];\n /** `number` — bounds for the control. */\n min?: number;\n max?: number;\n step?: number;\n } & Record<string, unknown>;\n /**\n * AUTHORING CHROME — the same object a content-model FIELD carries ({@link ContentModelFieldUi}),\n * deliberately: an agent that has learned `ui` once has learned it on both lanes.\n *\n * A SIBLING of `config`, not a member of it. `config` is a loose bag, so a `config.ui` already\n * survived the write — and that is the problem this key fixes: surviving is not declared, and\n * an undeclared prop is a typo that saves cleanly and renders as nothing.\n *\n * WHERE EACH KEY IS LEGAL differs from the field lane, because the vocabulary does:\n * `preview`/`layout` on `group`, `table` and `slot`; `reorderable` on `table` ALONE, the only\n * prop type whose value is a list. The save schema refuses the rest with the valid set named.\n */\n ui?: ContentModelFieldUi;\n}\n\n/** One field inside a `group` prop or a `table` row. Recursive, capped at 3 levels deep. */\nexport interface ComponentSubField {\n key: string;\n label: string;\n /** No `slot`: a nested component instance belongs on the prop itself, not inside a row. */\n // `slot` and `form` are reference-shaped props: they belong ON a prop, never inside a row of\n // one. A form in a table row would mean N form documents per component with no way to author\n // them — the second field model this design exists to avoid.\n type: Exclude<ComponentPropDef[\"type\"], \"slot\" | \"form\">;\n defaultValue?: unknown;\n /** The same editor hints as the prop above, one level down. @see ComponentPropDef */\n required?: boolean;\n helpText?: string;\n placeholder?: string;\n options?: string[];\n /** CANONICAL. A nested `group`/`table`'s own sub-shape. */\n fields?: ComponentSubField[];\n /**\n * A READ-ONLY MIRROR of `options`/`fields`, in the shape `ComponentPropDef` puts them in.\n *\n * 🔴 WHY A SECOND COPY EXISTS AT ALL. A `group`/`table` PROP declares its sub-shape under\n * `config.fields`; a sub-field of one declares its own under a bare `fields`. So a consumer\n * walking a nested table has to switch shape after the first level, and the componentize lane's\n * repo half (`@bettercms-ai/convert --componentize`) walks exactly that — it reads one node\n * shape at every depth. Mirroring the sub-shape here lets it, without the CMS having to\n * describe a nested table differently from a top-level one.\n *\n * `fields` is the authority. The save schema REFUSES a node whose mirror disagrees with it\n * (`componentPropDefSchema`), because two copies that may drift are worse than one awkward\n * shape — an editor that rewrote `fields` alone would leave a stale row description behind.\n */\n config?: { fields?: ComponentSubField[]; options?: string[] } & Record<string, unknown>;\n}\n\n/** The value a `slot` prop holds — the draft half of a `component-ref`, deliberately. */\nexport interface SlotValue {\n componentId: string;\n overrides?: Record<string, unknown>;\n}\n\n/**\n * A component is a DRAFT until published; only the published copy reaches a visitor.\n * Mirrors pages and entries. See migration 0186_component_draft_live_split.sql.\n */\nexport type ComponentStatus = \"draft\" | \"published\";\n\n/**\n * Archive state (FLO-1012), deliberately SEPARATE from `ComponentStatus`.\n *\n * Archive takes a component out of the working set — hidden from the components list by\n * default, not offered in the visual editor's insert surfaces — while every existing usage\n * keeps serving. It is not unpublish (which pulls the live copy and re-bakes every page that\n * embeds it) and it is not delete.\n *\n * It is a timestamp rather than a third `status` value because a component can be published\n * AND archived; collapsing the two would lose the bit restore has to put back.\n */\n\nexport interface Component {\n id: string;\n workspaceId: string;\n projectId?: string | null;\n name: string;\n slug: string;\n category: ComponentCategory;\n /**\n * Section library: the family this component is a LAYOUT of, e.g. \"Hero\". `name` is the\n * layout label (\"Centered\"), so components sharing a sectionType are selectable variants\n * of one section. Null/absent = an ordinary component, not shown in the section library.\n */\n sectionType?: string | null;\n /** First-class variant family membership; exact workspace/project scope is enforced in DB. */\n variantGroupId?: string | null;\n variantInputMappings?: VariantInputMapping[];\n /** Placement governance: `*`, `slug:<page-slug>`, and/or `type:<page-type>`. */\n allowedOn: string[];\n description?: string | null;\n /** The DRAFT definition. Every builder/autosave/import write path targets these two. */\n blockJson: ContentBlock[];\n props: ComponentPropDef[];\n status: ComponentStatus;\n /** When it left the working set, or null/absent while active. @see ComponentStatus */\n archivedAt?: string | Date | null;\n /** Derived from `archivedAt`, so a client never has to know the column. */\n archived?: boolean;\n /**\n * The LIVE snapshot get_components_by_handle() serves. Null until the first publish.\n * Returned by GET-one (the Compare view needs it), omitted from list rows for payload.\n */\n publishedBlockJson?: ContentBlock[] | null;\n publishedProps?: ComponentPropDef[] | null;\n publishedAt?: string | null; // ISO 8601\n /**\n * Computed in SQL on list/get, never stored:\n * status='published' AND (blockJson or props has diverged from its published copy).\n * An exact jsonb compare, so it self-clears when an edit is reverted.\n */\n pendingChanges?: boolean;\n thumbnail?: string | null;\n createdAt: string; // ISO 8601\n updatedAt: string; // ISO 8601\n}\n\n/**\n * Public/delivery projection — the fields a renderer needs to resolve instances.\n *\n * DELIBERATELY UNCHANGED by the 0186 draft/live split: delivery aliases\n * publishedBlockJson -> blockJson, so every already-deployed site and every\n * bcms-content.json on disk keeps a byte-identical wire shape. Do not add `status` here —\n * delivery only ever returns published rows, so it would always be the same constant.\n */\nexport interface DeliveryComponent {\n id: string;\n name: string;\n slug: string;\n category: ComponentCategory;\n sectionType?: string | null;\n blockJson: ContentBlock[];\n props: ComponentPropDef[];\n}\n","/**\n * Generated from lucide-react@1.8.0 dynamic icon names.\n * Legacy CamelCase identifiers remain valid for existing Layout documents.\n */\nexport const LAYOUT_SECTION_ICONS: readonly string[] = Object.freeze([\n \"LayoutPanelTop\",\n \"PanelTop\",\n \"PanelBottom\",\n \"Menu\",\n \"Navigation\",\n \"Megaphone\",\n \"GalleryHorizontal\",\n \"Rows3\",\n \"Grid2X2\",\n \"FileText\",\n \"Link\",\n \"Contact\",\n \"BadgeInfo\",\n \"Sparkles\",\n \"a-arrow-down\",\n \"a-arrow-up\",\n \"a-large-small\",\n \"accessibility\",\n \"activity\",\n \"air-vent\",\n \"airplay\",\n \"alarm-clock-check\",\n \"alarm-check\",\n \"alarm-clock-minus\",\n \"alarm-minus\",\n \"alarm-clock-off\",\n \"alarm-clock-plus\",\n \"alarm-plus\",\n \"alarm-clock\",\n \"alarm-smoke\",\n \"album\",\n \"align-center-horizontal\",\n \"align-center-vertical\",\n \"align-end-horizontal\",\n \"align-end-vertical\",\n \"align-horizontal-distribute-center\",\n \"align-horizontal-distribute-end\",\n \"align-horizontal-distribute-start\",\n \"align-horizontal-justify-center\",\n \"align-horizontal-justify-end\",\n \"align-horizontal-justify-start\",\n \"align-horizontal-space-around\",\n \"align-horizontal-space-between\",\n \"align-start-horizontal\",\n \"align-start-vertical\",\n \"align-vertical-distribute-center\",\n \"align-vertical-distribute-end\",\n \"align-vertical-distribute-start\",\n \"align-vertical-justify-center\",\n \"align-vertical-justify-end\",\n \"align-vertical-justify-start\",\n \"align-vertical-space-around\",\n \"align-vertical-space-between\",\n \"ambulance\",\n \"ampersand\",\n \"ampersands\",\n \"amphora\",\n \"anchor\",\n \"angry\",\n \"annoyed\",\n \"antenna\",\n \"anvil\",\n \"aperture\",\n \"app-window-mac\",\n \"app-window\",\n \"apple\",\n \"archive-restore\",\n \"archive-x\",\n \"archive\",\n \"armchair\",\n \"arrow-big-down-dash\",\n \"arrow-big-down\",\n \"arrow-big-left-dash\",\n \"arrow-big-left\",\n \"arrow-big-right-dash\",\n \"arrow-big-right\",\n \"arrow-big-up-dash\",\n \"arrow-big-up\",\n \"arrow-down-0-1\",\n \"arrow-down-01\",\n \"arrow-down-1-0\",\n \"arrow-down-10\",\n \"arrow-down-a-z\",\n \"arrow-down-az\",\n \"arrow-down-from-line\",\n \"arrow-down-left\",\n \"arrow-down-narrow-wide\",\n \"arrow-down-right\",\n \"arrow-down-to-dot\",\n \"arrow-down-to-line\",\n \"arrow-down-up\",\n \"arrow-down-wide-narrow\",\n \"sort-desc\",\n \"arrow-down-z-a\",\n \"arrow-down-za\",\n \"arrow-down\",\n \"arrow-left-from-line\",\n \"arrow-left-right\",\n \"arrow-left-to-line\",\n \"arrow-left\",\n \"arrow-right-from-line\",\n \"arrow-right-left\",\n \"arrow-right-to-line\",\n \"arrow-right\",\n \"arrow-up-0-1\",\n \"arrow-up-01\",\n \"arrow-up-1-0\",\n \"arrow-up-10\",\n \"arrow-up-a-z\",\n \"arrow-up-az\",\n \"arrow-up-down\",\n \"arrow-up-from-dot\",\n \"arrow-up-from-line\",\n \"arrow-up-left\",\n \"arrow-up-narrow-wide\",\n \"sort-asc\",\n \"arrow-up-right\",\n \"arrow-up-to-line\",\n \"arrow-up-wide-narrow\",\n \"arrow-up-z-a\",\n \"arrow-up-za\",\n \"arrow-up\",\n \"arrows-up-from-line\",\n \"asterisk\",\n \"at-sign\",\n \"atom\",\n \"audio-lines\",\n \"audio-waveform\",\n \"award\",\n \"axe\",\n \"axis-3d\",\n \"axis-3-d\",\n \"baby\",\n \"backpack\",\n \"badge-alert\",\n \"badge-cent\",\n \"badge-check\",\n \"verified\",\n \"badge-dollar-sign\",\n \"badge-euro\",\n \"badge-indian-rupee\",\n \"badge-info\",\n \"badge-japanese-yen\",\n \"badge-minus\",\n \"badge-percent\",\n \"badge-plus\",\n \"badge-pound-sterling\",\n \"badge-question-mark\",\n \"badge-help\",\n \"badge-russian-ruble\",\n \"badge-swiss-franc\",\n \"badge-turkish-lira\",\n \"badge-x\",\n \"badge\",\n \"baggage-claim\",\n \"balloon\",\n \"ban\",\n \"banana\",\n \"bandage\",\n \"banknote-arrow-down\",\n \"banknote-arrow-up\",\n \"banknote-x\",\n \"banknote\",\n \"barcode\",\n \"barrel\",\n \"baseline\",\n \"bath\",\n \"battery-charging\",\n \"battery-full\",\n \"battery-low\",\n \"battery-medium\",\n \"battery-plus\",\n \"battery-warning\",\n \"battery\",\n \"beaker\",\n \"bean-off\",\n \"bean\",\n \"bed-double\",\n \"bed-single\",\n \"bed\",\n \"beef-off\",\n \"beef\",\n \"beer-off\",\n \"beer\",\n \"bell-dot\",\n \"bell-electric\",\n \"bell-minus\",\n \"bell-off\",\n \"bell-plus\",\n \"bell-ring\",\n \"bell\",\n \"between-horizontal-end\",\n \"between-horizonal-end\",\n \"between-horizontal-start\",\n \"between-horizonal-start\",\n \"between-vertical-end\",\n \"between-vertical-start\",\n \"biceps-flexed\",\n \"bike\",\n \"binary\",\n \"binoculars\",\n \"biohazard\",\n \"bird\",\n \"birdhouse\",\n \"bitcoin\",\n \"blend\",\n \"blinds\",\n \"blocks\",\n \"bluetooth-connected\",\n \"bluetooth-off\",\n \"bluetooth-searching\",\n \"bluetooth\",\n \"bold\",\n \"bolt\",\n \"bomb\",\n \"bone\",\n \"book-a\",\n \"book-alert\",\n \"book-audio\",\n \"book-check\",\n \"book-copy\",\n \"book-dashed\",\n \"book-template\",\n \"book-down\",\n \"book-headphones\",\n \"book-heart\",\n \"book-image\",\n \"book-key\",\n \"book-lock\",\n \"book-marked\",\n \"book-minus\",\n \"book-open-check\",\n \"book-open-text\",\n \"book-open\",\n \"book-plus\",\n \"book-search\",\n \"book-text\",\n \"book-type\",\n \"book-up-2\",\n \"book-up\",\n \"book-user\",\n \"book-x\",\n \"book\",\n \"bookmark-check\",\n \"bookmark-minus\",\n \"bookmark-off\",\n \"bookmark-plus\",\n \"bookmark-x\",\n \"bookmark\",\n \"boom-box\",\n \"bot-message-square\",\n \"bot-off\",\n \"bot\",\n \"bottle-wine\",\n \"bow-arrow\",\n \"box\",\n \"boxes\",\n \"braces\",\n \"curly-braces\",\n \"brackets\",\n \"brain-circuit\",\n \"brain-cog\",\n \"brain\",\n \"brick-wall-fire\",\n \"brick-wall-shield\",\n \"brick-wall\",\n \"briefcase-business\",\n \"briefcase-conveyor-belt\",\n \"briefcase-medical\",\n \"briefcase\",\n \"bring-to-front\",\n \"brush-cleaning\",\n \"brush\",\n \"bubbles\",\n \"bug-off\",\n \"bug-play\",\n \"bug\",\n \"building-2\",\n \"building\",\n \"bus-front\",\n \"bus\",\n \"cable-car\",\n \"cable\",\n \"cake-slice\",\n \"cake\",\n \"calculator\",\n \"calendar-1\",\n \"calendar-arrow-down\",\n \"calendar-arrow-up\",\n \"calendar-check-2\",\n \"calendar-check\",\n \"calendar-clock\",\n \"calendar-cog\",\n \"calendar-days\",\n \"calendar-fold\",\n \"calendar-heart\",\n \"calendar-minus-2\",\n \"calendar-minus\",\n \"calendar-off\",\n \"calendar-plus-2\",\n \"calendar-plus\",\n \"calendar-range\",\n \"calendar-search\",\n \"calendar-sync\",\n \"calendar-x-2\",\n \"calendar-x\",\n \"calendar\",\n \"calendars\",\n \"camera-off\",\n \"camera\",\n \"candy-cane\",\n \"candy-off\",\n \"candy\",\n \"cannabis-off\",\n \"cannabis\",\n \"captions-off\",\n \"captions\",\n \"subtitles\",\n \"car-front\",\n \"car-taxi-front\",\n \"car\",\n \"caravan\",\n \"card-sim\",\n \"carrot\",\n \"case-lower\",\n \"case-sensitive\",\n \"case-upper\",\n \"cassette-tape\",\n \"cast\",\n \"castle\",\n \"cat\",\n \"cctv-off\",\n \"cctv\",\n \"chart-area\",\n \"area-chart\",\n \"chart-bar-big\",\n \"bar-chart-horizontal-big\",\n \"chart-bar-decreasing\",\n \"chart-bar-increasing\",\n \"chart-bar-stacked\",\n \"chart-bar\",\n \"bar-chart-horizontal\",\n \"chart-candlestick\",\n \"candlestick-chart\",\n \"chart-column-big\",\n \"bar-chart-big\",\n \"chart-column-decreasing\",\n \"chart-column-increasing\",\n \"bar-chart-4\",\n \"chart-column-stacked\",\n \"chart-column\",\n \"bar-chart-3\",\n \"chart-gantt\",\n \"chart-line\",\n \"line-chart\",\n \"chart-network\",\n \"chart-no-axes-column-decreasing\",\n \"chart-no-axes-column-increasing\",\n \"bar-chart\",\n \"chart-no-axes-column\",\n \"bar-chart-2\",\n \"chart-no-axes-combined\",\n \"chart-no-axes-gantt\",\n \"gantt-chart\",\n \"chart-pie\",\n \"pie-chart\",\n \"chart-scatter\",\n \"scatter-chart\",\n \"chart-spline\",\n \"check-check\",\n \"check-line\",\n \"check\",\n \"chef-hat\",\n \"cherry\",\n \"chess-bishop\",\n \"chess-king\",\n \"chess-knight\",\n \"chess-pawn\",\n \"chess-queen\",\n \"chess-rook\",\n \"chevron-down\",\n \"chevron-first\",\n \"chevron-last\",\n \"chevron-left\",\n \"chevron-right\",\n \"chevron-up\",\n \"chevrons-down-up\",\n \"chevrons-down\",\n \"chevrons-left-right-ellipsis\",\n \"chevrons-left-right\",\n \"chevrons-left\",\n \"chevrons-right-left\",\n \"chevrons-right\",\n \"chevrons-up-down\",\n \"chevrons-up\",\n \"church\",\n \"cigarette-off\",\n \"cigarette\",\n \"circle-alert\",\n \"alert-circle\",\n \"circle-arrow-down\",\n \"arrow-down-circle\",\n \"circle-arrow-left\",\n \"arrow-left-circle\",\n \"circle-arrow-out-down-left\",\n \"arrow-down-left-from-circle\",\n \"circle-arrow-out-down-right\",\n \"arrow-down-right-from-circle\",\n \"circle-arrow-out-up-left\",\n \"arrow-up-left-from-circle\",\n \"circle-arrow-out-up-right\",\n \"arrow-up-right-from-circle\",\n \"circle-arrow-right\",\n \"arrow-right-circle\",\n \"circle-arrow-up\",\n \"arrow-up-circle\",\n \"circle-check-big\",\n \"check-circle\",\n \"circle-check\",\n \"check-circle-2\",\n \"circle-chevron-down\",\n \"chevron-down-circle\",\n \"circle-chevron-left\",\n \"chevron-left-circle\",\n \"circle-chevron-right\",\n \"chevron-right-circle\",\n \"circle-chevron-up\",\n \"chevron-up-circle\",\n \"circle-dashed\",\n \"circle-divide\",\n \"divide-circle\",\n \"circle-dollar-sign\",\n \"circle-dot-dashed\",\n \"circle-dot\",\n \"circle-ellipsis\",\n \"circle-equal\",\n \"circle-fading-arrow-up\",\n \"circle-fading-plus\",\n \"circle-gauge\",\n \"gauge-circle\",\n \"circle-minus\",\n \"minus-circle\",\n \"circle-off\",\n \"circle-parking-off\",\n \"parking-circle-off\",\n \"circle-parking\",\n \"parking-circle\",\n \"circle-pause\",\n \"pause-circle\",\n \"circle-percent\",\n \"percent-circle\",\n \"circle-pile\",\n \"circle-play\",\n \"play-circle\",\n \"circle-plus\",\n \"plus-circle\",\n \"circle-pound-sterling\",\n \"circle-power\",\n \"power-circle\",\n \"circle-question-mark\",\n \"help-circle\",\n \"circle-help\",\n \"circle-slash-2\",\n \"circle-slashed\",\n \"circle-slash\",\n \"circle-small\",\n \"circle-star\",\n \"circle-stop\",\n \"stop-circle\",\n \"circle-user-round\",\n \"user-circle-2\",\n \"circle-user\",\n \"user-circle\",\n \"circle-x\",\n \"x-circle\",\n \"circle\",\n \"circuit-board\",\n \"citrus\",\n \"clapperboard\",\n \"clipboard-check\",\n \"clipboard-clock\",\n \"clipboard-copy\",\n \"clipboard-list\",\n \"clipboard-minus\",\n \"clipboard-paste\",\n \"clipboard-pen-line\",\n \"clipboard-signature\",\n \"clipboard-pen\",\n \"clipboard-edit\",\n \"clipboard-plus\",\n \"clipboard-type\",\n \"clipboard-x\",\n \"clipboard\",\n \"clock-1\",\n \"clock-10\",\n \"clock-11\",\n \"clock-12\",\n \"clock-2\",\n \"clock-3\",\n \"clock-4\",\n \"clock-5\",\n \"clock-6\",\n \"clock-7\",\n \"clock-8\",\n \"clock-9\",\n \"clock-alert\",\n \"clock-arrow-down\",\n \"clock-arrow-up\",\n \"clock-check\",\n \"clock-fading\",\n \"clock-plus\",\n \"clock\",\n \"closed-caption\",\n \"cloud-alert\",\n \"cloud-backup\",\n \"cloud-check\",\n \"cloud-cog\",\n \"cloud-download\",\n \"download-cloud\",\n \"cloud-drizzle\",\n \"cloud-fog\",\n \"cloud-hail\",\n \"cloud-lightning\",\n \"cloud-moon-rain\",\n \"cloud-moon\",\n \"cloud-off\",\n \"cloud-rain-wind\",\n \"cloud-rain\",\n \"cloud-snow\",\n \"cloud-sun-rain\",\n \"cloud-sun\",\n \"cloud-sync\",\n \"cloud-upload\",\n \"upload-cloud\",\n \"cloud\",\n \"cloudy\",\n \"clover\",\n \"club\",\n \"code-xml\",\n \"code-2\",\n \"code\",\n \"coffee\",\n \"cog\",\n \"coins\",\n \"columns-2\",\n \"columns\",\n \"columns-3-cog\",\n \"columns-settings\",\n \"table-config\",\n \"columns-3\",\n \"panels-left-right\",\n \"columns-4\",\n \"combine\",\n \"command\",\n \"compass\",\n \"component\",\n \"computer\",\n \"concierge-bell\",\n \"cone\",\n \"construction\",\n \"contact-round\",\n \"contact-2\",\n \"contact\",\n \"container\",\n \"contrast\",\n \"cookie\",\n \"cooking-pot\",\n \"copy-check\",\n \"copy-minus\",\n \"copy-plus\",\n \"copy-slash\",\n \"copy-x\",\n \"copy\",\n \"copyleft\",\n \"copyright\",\n \"corner-down-left\",\n \"corner-down-right\",\n \"corner-left-down\",\n \"corner-left-up\",\n \"corner-right-down\",\n \"corner-right-up\",\n \"corner-up-left\",\n \"corner-up-right\",\n \"cpu\",\n \"creative-commons\",\n \"credit-card\",\n \"croissant\",\n \"crop\",\n \"cross\",\n \"crosshair\",\n \"crown\",\n \"cuboid\",\n \"cup-soda\",\n \"currency\",\n \"cylinder\",\n \"dam\",\n \"database-backup\",\n \"database-search\",\n \"database-zap\",\n \"database\",\n \"decimals-arrow-left\",\n \"decimals-arrow-right\",\n \"delete\",\n \"dessert\",\n \"diameter\",\n \"diamond-minus\",\n \"diamond-percent\",\n \"percent-diamond\",\n \"diamond-plus\",\n \"diamond\",\n \"dice-1\",\n \"dice-2\",\n \"dice-3\",\n \"dice-4\",\n \"dice-5\",\n \"dice-6\",\n \"dices\",\n \"diff\",\n \"disc-2\",\n \"disc-3\",\n \"disc-album\",\n \"disc\",\n \"divide\",\n \"dna-off\",\n \"dna\",\n \"dock\",\n \"dog\",\n \"dollar-sign\",\n \"donut\",\n \"door-closed-locked\",\n \"door-closed\",\n \"door-open\",\n \"dot\",\n \"download\",\n \"drafting-compass\",\n \"drama\",\n \"drill\",\n \"drone\",\n \"droplet-off\",\n \"droplet\",\n \"droplets\",\n \"drum\",\n \"drumstick\",\n \"dumbbell\",\n \"ear-off\",\n \"ear\",\n \"earth-lock\",\n \"earth\",\n \"globe-2\",\n \"eclipse\",\n \"egg-fried\",\n \"egg-off\",\n \"egg\",\n \"ellipse\",\n \"ellipsis-vertical\",\n \"more-vertical\",\n \"ellipsis\",\n \"more-horizontal\",\n \"equal-approximately\",\n \"equal-not\",\n \"equal\",\n \"eraser\",\n \"ethernet-port\",\n \"euro\",\n \"ev-charger\",\n \"expand\",\n \"external-link\",\n \"eye-closed\",\n \"eye-off\",\n \"eye\",\n \"factory\",\n \"fan\",\n \"fast-forward\",\n \"feather\",\n \"fence\",\n \"ferris-wheel\",\n \"file-archive\",\n \"file-axis-3d\",\n \"file-axis-3-d\",\n \"file-badge\",\n \"file-badge-2\",\n \"file-box\",\n \"file-braces-corner\",\n \"file-json-2\",\n \"file-braces\",\n \"file-json\",\n \"file-chart-column-increasing\",\n \"file-bar-chart\",\n \"file-chart-column\",\n \"file-bar-chart-2\",\n \"file-chart-line\",\n \"file-line-chart\",\n \"file-chart-pie\",\n \"file-pie-chart\",\n \"file-check-corner\",\n \"file-check-2\",\n \"file-check\",\n \"file-clock\",\n \"file-code-corner\",\n \"file-code-2\",\n \"file-code\",\n \"file-cog\",\n \"file-cog-2\",\n \"file-diff\",\n \"file-digit\",\n \"file-down\",\n \"file-exclamation-point\",\n \"file-warning\",\n \"file-headphone\",\n \"file-audio\",\n \"file-audio-2\",\n \"file-heart\",\n \"file-image\",\n \"file-input\",\n \"file-key\",\n \"file-key-2\",\n \"file-lock\",\n \"file-lock-2\",\n \"file-minus-corner\",\n \"file-minus-2\",\n \"file-minus\",\n \"file-music\",\n \"file-output\",\n \"file-pen-line\",\n \"file-signature\",\n \"file-pen\",\n \"file-edit\",\n \"file-play\",\n \"file-video\",\n \"file-plus-corner\",\n \"file-plus-2\",\n \"file-plus\",\n \"file-question-mark\",\n \"file-question\",\n \"file-scan\",\n \"file-search-corner\",\n \"file-search-2\",\n \"file-search\",\n \"file-signal\",\n \"file-volume-2\",\n \"file-sliders\",\n \"file-spreadsheet\",\n \"file-stack\",\n \"file-symlink\",\n \"file-terminal\",\n \"file-text\",\n \"file-type-corner\",\n \"file-type-2\",\n \"file-type\",\n \"file-up\",\n \"file-user\",\n \"file-video-camera\",\n \"file-video-2\",\n \"file-volume\",\n \"file-x-corner\",\n \"file-x-2\",\n \"file-x\",\n \"file\",\n \"files\",\n \"film\",\n \"fingerprint-pattern\",\n \"fingerprint\",\n \"fire-extinguisher\",\n \"fish-off\",\n \"fish-symbol\",\n \"fish\",\n \"fishing-hook\",\n \"fishing-rod\",\n \"flag-off\",\n \"flag-triangle-left\",\n \"flag-triangle-right\",\n \"flag\",\n \"flame-kindling\",\n \"flame\",\n \"flashlight-off\",\n \"flashlight\",\n \"flask-conical-off\",\n \"flask-conical\",\n \"flask-round\",\n \"flip-horizontal-2\",\n \"flip-vertical-2\",\n \"flower-2\",\n \"flower\",\n \"focus\",\n \"fold-horizontal\",\n \"fold-vertical\",\n \"folder-archive\",\n \"folder-check\",\n \"folder-clock\",\n \"folder-closed\",\n \"folder-code\",\n \"folder-cog\",\n \"folder-cog-2\",\n \"folder-dot\",\n \"folder-down\",\n \"folder-git-2\",\n \"folder-git\",\n \"folder-heart\",\n \"folder-input\",\n \"folder-kanban\",\n \"folder-key\",\n \"folder-lock\",\n \"folder-minus\",\n \"folder-open-dot\",\n \"folder-open\",\n \"folder-output\",\n \"folder-pen\",\n \"folder-edit\",\n \"folder-plus\",\n \"folder-root\",\n \"folder-search-2\",\n \"folder-search\",\n \"folder-symlink\",\n \"folder-sync\",\n \"folder-tree\",\n \"folder-up\",\n \"folder-x\",\n \"folder\",\n \"folders\",\n \"footprints\",\n \"forklift\",\n \"form\",\n \"forward\",\n \"frame\",\n \"frown\",\n \"fuel\",\n \"fullscreen\",\n \"funnel-plus\",\n \"funnel-x\",\n \"filter-x\",\n \"funnel\",\n \"filter\",\n \"gallery-horizontal-end\",\n \"gallery-horizontal\",\n \"gallery-thumbnails\",\n \"gallery-vertical-end\",\n \"gallery-vertical\",\n \"gamepad-2\",\n \"gamepad-directional\",\n \"gamepad\",\n \"gauge\",\n \"gavel\",\n \"gem\",\n \"georgian-lari\",\n \"ghost\",\n \"gift\",\n \"git-branch-minus\",\n \"git-branch-plus\",\n \"git-branch\",\n \"git-commit-horizontal\",\n \"git-commit\",\n \"git-commit-vertical\",\n \"git-compare-arrows\",\n \"git-compare\",\n \"git-fork\",\n \"git-graph\",\n \"git-merge-conflict\",\n \"git-merge\",\n \"git-pull-request-arrow\",\n \"git-pull-request-closed\",\n \"git-pull-request-create-arrow\",\n \"git-pull-request-create\",\n \"git-pull-request-draft\",\n \"git-pull-request\",\n \"glass-water\",\n \"glasses\",\n \"globe-lock\",\n \"globe-off\",\n \"globe-x\",\n \"globe\",\n \"goal\",\n \"gpu\",\n \"graduation-cap\",\n \"grape\",\n \"grid-2x2-check\",\n \"grid-2-x-2-check\",\n \"grid-2x2-plus\",\n \"grid-2-x-2-plus\",\n \"grid-2x2-x\",\n \"grid-2-x-2-x\",\n \"grid-2x2\",\n \"grid-2-x-2\",\n \"grid-3x2\",\n \"grid-3x3\",\n \"grid\",\n \"grid-3-x-3\",\n \"grip-horizontal\",\n \"grip-vertical\",\n \"grip\",\n \"group\",\n \"guitar\",\n \"ham\",\n \"hamburger\",\n \"hammer\",\n \"hand-coins\",\n \"hand-fist\",\n \"hand-grab\",\n \"grab\",\n \"hand-heart\",\n \"hand-helping\",\n \"helping-hand\",\n \"hand-metal\",\n \"hand-platter\",\n \"hand\",\n \"handbag\",\n \"handshake\",\n \"hard-drive-download\",\n \"hard-drive-upload\",\n \"hard-drive\",\n \"hard-hat\",\n \"hash\",\n \"hat-glasses\",\n \"haze\",\n \"hd\",\n \"hdmi-port\",\n \"heading-1\",\n \"heading-2\",\n \"heading-3\",\n \"heading-4\",\n \"heading-5\",\n \"heading-6\",\n \"heading\",\n \"headphone-off\",\n \"headphones\",\n \"headset\",\n \"heart-crack\",\n \"heart-handshake\",\n \"heart-minus\",\n \"heart-off\",\n \"heart-plus\",\n \"heart-pulse\",\n \"heart\",\n \"heater\",\n \"helicopter\",\n \"hexagon\",\n \"highlighter\",\n \"history\",\n \"hop-off\",\n \"hop\",\n \"hospital\",\n \"hotel\",\n \"hourglass\",\n \"house-heart\",\n \"house-plug\",\n \"house-plus\",\n \"house-wifi\",\n \"house\",\n \"home\",\n \"ice-cream-bowl\",\n \"ice-cream-2\",\n \"ice-cream-cone\",\n \"ice-cream\",\n \"id-card-lanyard\",\n \"id-card\",\n \"image-down\",\n \"image-minus\",\n \"image-off\",\n \"image-play\",\n \"image-plus\",\n \"image-up\",\n \"image-upscale\",\n \"image\",\n \"images\",\n \"import\",\n \"inbox\",\n \"indian-rupee\",\n \"infinity\",\n \"info\",\n \"inspection-panel\",\n \"italic\",\n \"iteration-ccw\",\n \"iteration-cw\",\n \"japanese-yen\",\n \"joystick\",\n \"kanban\",\n \"kayak\",\n \"key-round\",\n \"key-square\",\n \"key\",\n \"keyboard-music\",\n \"keyboard-off\",\n \"keyboard\",\n \"lamp-ceiling\",\n \"lamp-desk\",\n \"lamp-floor\",\n \"lamp-wall-down\",\n \"lamp-wall-up\",\n \"lamp\",\n \"land-plot\",\n \"landmark\",\n \"languages\",\n \"laptop-minimal-check\",\n \"laptop-minimal\",\n \"laptop-2\",\n \"laptop\",\n \"lasso-select\",\n \"lasso\",\n \"laugh\",\n \"layers-2\",\n \"layers-plus\",\n \"layers\",\n \"layers-3\",\n \"layout-dashboard\",\n \"layout-grid\",\n \"layout-list\",\n \"layout-panel-left\",\n \"layout-panel-top\",\n \"layout-template\",\n \"leaf\",\n \"leafy-green\",\n \"lectern\",\n \"lens-concave\",\n \"lens-convex\",\n \"library-big\",\n \"library\",\n \"life-buoy\",\n \"ligature\",\n \"lightbulb-off\",\n \"lightbulb\",\n \"line-dot-right-horizontal\",\n \"line-squiggle\",\n \"line-style\",\n \"link-2-off\",\n \"link-2\",\n \"link\",\n \"list-check\",\n \"list-checks\",\n \"list-chevrons-down-up\",\n \"list-chevrons-up-down\",\n \"list-collapse\",\n \"list-end\",\n \"list-filter-plus\",\n \"list-filter\",\n \"list-indent-decrease\",\n \"outdent\",\n \"indent-decrease\",\n \"list-indent-increase\",\n \"indent\",\n \"indent-increase\",\n \"list-minus\",\n \"list-music\",\n \"list-ordered\",\n \"list-plus\",\n \"list-restart\",\n \"list-start\",\n \"list-todo\",\n \"list-tree\",\n \"list-video\",\n \"list-x\",\n \"list\",\n \"loader-circle\",\n \"loader-2\",\n \"loader-pinwheel\",\n \"loader\",\n \"locate-fixed\",\n \"locate-off\",\n \"locate\",\n \"lock-keyhole-open\",\n \"unlock-keyhole\",\n \"lock-keyhole\",\n \"lock-open\",\n \"unlock\",\n \"lock\",\n \"log-in\",\n \"log-out\",\n \"logs\",\n \"lollipop\",\n \"luggage\",\n \"magnet\",\n \"mail-check\",\n \"mail-minus\",\n \"mail-open\",\n \"mail-plus\",\n \"mail-question-mark\",\n \"mail-question\",\n \"mail-search\",\n \"mail-warning\",\n \"mail-x\",\n \"mail\",\n \"mailbox\",\n \"mails\",\n \"map-minus\",\n \"map-pin-check-inside\",\n \"map-pin-check\",\n \"map-pin-house\",\n \"map-pin-minus-inside\",\n \"map-pin-minus\",\n \"map-pin-off\",\n \"map-pin-pen\",\n \"location-edit\",\n \"map-pin-plus-inside\",\n \"map-pin-plus\",\n \"map-pin-search\",\n \"map-pin-x-inside\",\n \"map-pin-x\",\n \"map-pin\",\n \"map-pinned\",\n \"map-plus\",\n \"map\",\n \"mars-stroke\",\n \"mars\",\n \"martini\",\n \"maximize-2\",\n \"maximize\",\n \"medal\",\n \"megaphone-off\",\n \"megaphone\",\n \"meh\",\n \"memory-stick\",\n \"menu\",\n \"merge\",\n \"message-circle-check\",\n \"message-circle-code\",\n \"message-circle-dashed\",\n \"message-circle-heart\",\n \"message-circle-more\",\n \"message-circle-off\",\n \"message-circle-plus\",\n \"message-circle-question-mark\",\n \"message-circle-question\",\n \"message-circle-reply\",\n \"message-circle-warning\",\n \"message-circle-x\",\n \"message-circle\",\n \"message-square-check\",\n \"message-square-code\",\n \"message-square-dashed\",\n \"message-square-diff\",\n \"message-square-dot\",\n \"message-square-heart\",\n \"message-square-lock\",\n \"message-square-more\",\n \"message-square-off\",\n \"message-square-plus\",\n \"message-square-quote\",\n \"message-square-reply\",\n \"message-square-share\",\n \"message-square-text\",\n \"message-square-warning\",\n \"message-square-x\",\n \"message-square\",\n \"messages-square\",\n \"metronome\",\n \"mic-off\",\n \"mic-vocal\",\n \"mic-2\",\n \"mic\",\n \"microchip\",\n \"microscope\",\n \"microwave\",\n \"milestone\",\n \"milk-off\",\n \"milk\",\n \"minimize-2\",\n \"minimize\",\n \"minus\",\n \"mirror-rectangular\",\n \"mirror-round\",\n \"monitor-check\",\n \"monitor-cloud\",\n \"monitor-cog\",\n \"monitor-dot\",\n \"monitor-down\",\n \"monitor-off\",\n \"monitor-pause\",\n \"monitor-play\",\n \"monitor-smartphone\",\n \"monitor-speaker\",\n \"monitor-stop\",\n \"monitor-up\",\n \"monitor-x\",\n \"monitor\",\n \"moon-star\",\n \"moon\",\n \"motorbike\",\n \"mountain-snow\",\n \"mountain\",\n \"mouse-left\",\n \"mouse-off\",\n \"mouse-pointer-2-off\",\n \"mouse-pointer-2\",\n \"mouse-pointer-ban\",\n \"mouse-pointer-click\",\n \"mouse-pointer\",\n \"mouse-right\",\n \"mouse\",\n \"move-3d\",\n \"move-3-d\",\n \"move-diagonal-2\",\n \"move-diagonal\",\n \"move-down-left\",\n \"move-down-right\",\n \"move-down\",\n \"move-horizontal\",\n \"move-left\",\n \"move-right\",\n \"move-up-left\",\n \"move-up-right\",\n \"move-up\",\n \"move-vertical\",\n \"move\",\n \"music-2\",\n \"music-3\",\n \"music-4\",\n \"music\",\n \"navigation-2-off\",\n \"navigation-2\",\n \"navigation-off\",\n \"navigation\",\n \"network\",\n \"newspaper\",\n \"nfc\",\n \"non-binary\",\n \"notebook-pen\",\n \"notebook-tabs\",\n \"notebook-text\",\n \"notebook\",\n \"notepad-text-dashed\",\n \"notepad-text\",\n \"nut-off\",\n \"nut\",\n \"octagon-alert\",\n \"alert-octagon\",\n \"octagon-minus\",\n \"octagon-pause\",\n \"pause-octagon\",\n \"octagon-x\",\n \"x-octagon\",\n \"octagon\",\n \"omega\",\n \"option\",\n \"orbit\",\n \"origami\",\n \"package-2\",\n \"package-check\",\n \"package-minus\",\n \"package-open\",\n \"package-plus\",\n \"package-search\",\n \"package-x\",\n \"package\",\n \"paint-bucket\",\n \"paint-roller\",\n \"paintbrush-vertical\",\n \"paintbrush-2\",\n \"paintbrush\",\n \"palette\",\n \"panda\",\n \"panel-bottom-close\",\n \"panel-bottom-dashed\",\n \"panel-bottom-inactive\",\n \"panel-bottom-open\",\n \"panel-bottom\",\n \"panel-left-close\",\n \"sidebar-close\",\n \"panel-left-dashed\",\n \"panel-left-inactive\",\n \"panel-left-open\",\n \"sidebar-open\",\n \"panel-left-right-dashed\",\n \"panel-left\",\n \"sidebar\",\n \"panel-right-close\",\n \"panel-right-dashed\",\n \"panel-right-inactive\",\n \"panel-right-open\",\n \"panel-right\",\n \"panel-top-bottom-dashed\",\n \"panel-top-close\",\n \"panel-top-dashed\",\n \"panel-top-inactive\",\n \"panel-top-open\",\n \"panel-top\",\n \"panels-left-bottom\",\n \"panels-right-bottom\",\n \"panels-top-left\",\n \"layout\",\n \"paperclip\",\n \"parentheses\",\n \"parking-meter\",\n \"party-popper\",\n \"pause\",\n \"paw-print\",\n \"pc-case\",\n \"pen-line\",\n \"edit-3\",\n \"pen-off\",\n \"pen-tool\",\n \"pen\",\n \"edit-2\",\n \"pencil-line\",\n \"pencil-off\",\n \"pencil-ruler\",\n \"pencil\",\n \"pentagon\",\n \"percent\",\n \"person-standing\",\n \"philippine-peso\",\n \"phone-call\",\n \"phone-forwarded\",\n \"phone-incoming\",\n \"phone-missed\",\n \"phone-off\",\n \"phone-outgoing\",\n \"phone\",\n \"pi\",\n \"piano\",\n \"pickaxe\",\n \"picture-in-picture-2\",\n \"picture-in-picture\",\n \"piggy-bank\",\n \"pilcrow-left\",\n \"pilcrow-right\",\n \"pilcrow\",\n \"pill-bottle\",\n \"pill\",\n \"pin-off\",\n \"pin\",\n \"pipette\",\n \"pizza\",\n \"plane-landing\",\n \"plane-takeoff\",\n \"plane\",\n \"play\",\n \"plug-2\",\n \"plug-zap\",\n \"plug-zap-2\",\n \"plug\",\n \"plus\",\n \"pocket-knife\",\n \"podcast\",\n \"pointer-off\",\n \"pointer\",\n \"popcorn\",\n \"popsicle\",\n \"pound-sterling\",\n \"power-off\",\n \"power\",\n \"presentation\",\n \"printer-check\",\n \"printer-x\",\n \"printer\",\n \"projector\",\n \"proportions\",\n \"puzzle\",\n \"pyramid\",\n \"qr-code\",\n \"quote\",\n \"rabbit\",\n \"radar\",\n \"radiation\",\n \"radical\",\n \"radio-off\",\n \"radio-receiver\",\n \"radio-tower\",\n \"radio\",\n \"radius\",\n \"rainbow\",\n \"rat\",\n \"ratio\",\n \"receipt-cent\",\n \"receipt-euro\",\n \"receipt-indian-rupee\",\n \"receipt-japanese-yen\",\n \"receipt-pound-sterling\",\n \"receipt-russian-ruble\",\n \"receipt-swiss-franc\",\n \"receipt-text\",\n \"receipt-turkish-lira\",\n \"receipt\",\n \"rectangle-circle\",\n \"rectangle-ellipsis\",\n \"form-input\",\n \"rectangle-goggles\",\n \"rectangle-horizontal\",\n \"rectangle-vertical\",\n \"recycle\",\n \"redo-2\",\n \"redo-dot\",\n \"redo\",\n \"refresh-ccw-dot\",\n \"refresh-ccw\",\n \"refresh-cw-off\",\n \"refresh-cw\",\n \"refrigerator\",\n \"regex\",\n \"remove-formatting\",\n \"repeat-1\",\n \"repeat-2\",\n \"repeat\",\n \"replace-all\",\n \"replace\",\n \"reply-all\",\n \"reply\",\n \"rewind\",\n \"ribbon\",\n \"road\",\n \"rocket\",\n \"rocking-chair\",\n \"roller-coaster\",\n \"rose\",\n \"rotate-3d\",\n \"rotate-3-d\",\n \"rotate-ccw-key\",\n \"rotate-ccw-square\",\n \"rotate-ccw\",\n \"rotate-cw-square\",\n \"rotate-cw\",\n \"route-off\",\n \"route\",\n \"router\",\n \"rows-2\",\n \"rows\",\n \"rows-3\",\n \"panels-top-bottom\",\n \"rows-4\",\n \"rss\",\n \"ruler-dimension-line\",\n \"ruler\",\n \"russian-ruble\",\n \"sailboat\",\n \"salad\",\n \"sandwich\",\n \"satellite-dish\",\n \"satellite\",\n \"saudi-riyal\",\n \"save-all\",\n \"save-off\",\n \"save\",\n \"scale-3d\",\n \"scale-3-d\",\n \"scale\",\n \"scaling\",\n \"scan-barcode\",\n \"scan-eye\",\n \"scan-face\",\n \"scan-heart\",\n \"scan-line\",\n \"scan-qr-code\",\n \"scan-search\",\n \"scan-text\",\n \"scan\",\n \"school\",\n \"scissors-line-dashed\",\n \"scissors\",\n \"scooter\",\n \"screen-share-off\",\n \"screen-share\",\n \"scroll-text\",\n \"scroll\",\n \"search-alert\",\n \"search-check\",\n \"search-code\",\n \"search-slash\",\n \"search-x\",\n \"search\",\n \"section\",\n \"send-horizontal\",\n \"send-horizonal\",\n \"send-to-back\",\n \"send\",\n \"separator-horizontal\",\n \"separator-vertical\",\n \"server-cog\",\n \"server-crash\",\n \"server-off\",\n \"server\",\n \"settings-2\",\n \"settings\",\n \"shapes\",\n \"share-2\",\n \"share\",\n \"sheet\",\n \"shell\",\n \"shelving-unit\",\n \"shield-alert\",\n \"shield-ban\",\n \"shield-check\",\n \"shield-cog-corner\",\n \"shield-cog\",\n \"shield-ellipsis\",\n \"shield-half\",\n \"shield-minus\",\n \"shield-off\",\n \"shield-plus\",\n \"shield-question-mark\",\n \"shield-question\",\n \"shield-user\",\n \"shield-x\",\n \"shield-close\",\n \"shield\",\n \"ship-wheel\",\n \"ship\",\n \"shirt\",\n \"shopping-bag\",\n \"shopping-basket\",\n \"shopping-cart\",\n \"shovel\",\n \"shower-head\",\n \"shredder\",\n \"shrimp\",\n \"shrink\",\n \"shrub\",\n \"shuffle\",\n \"sigma\",\n \"signal-high\",\n \"signal-low\",\n \"signal-medium\",\n \"signal-zero\",\n \"signal\",\n \"signature\",\n \"signpost-big\",\n \"signpost\",\n \"siren\",\n \"skip-back\",\n \"skip-forward\",\n \"skull\",\n \"slash\",\n \"slice\",\n \"sliders-horizontal\",\n \"sliders-vertical\",\n \"sliders\",\n \"smartphone-charging\",\n \"smartphone-nfc\",\n \"smartphone\",\n \"smile-plus\",\n \"smile\",\n \"snail\",\n \"snowflake\",\n \"soap-dispenser-droplet\",\n \"sofa\",\n \"solar-panel\",\n \"soup\",\n \"space\",\n \"spade\",\n \"sparkle\",\n \"sparkles\",\n \"stars\",\n \"speaker\",\n \"speech\",\n \"spell-check-2\",\n \"spell-check\",\n \"spline-pointer\",\n \"spline\",\n \"split\",\n \"spool\",\n \"sport-shoe\",\n \"spotlight\",\n \"spray-can\",\n \"sprout\",\n \"square-activity\",\n \"activity-square\",\n \"square-arrow-down-left\",\n \"arrow-down-left-square\",\n \"square-arrow-down-right\",\n \"arrow-down-right-square\",\n \"square-arrow-down\",\n \"arrow-down-square\",\n \"square-arrow-left\",\n \"arrow-left-square\",\n \"square-arrow-out-down-left\",\n \"arrow-down-left-from-square\",\n \"square-arrow-out-down-right\",\n \"arrow-down-right-from-square\",\n \"square-arrow-out-up-left\",\n \"arrow-up-left-from-square\",\n \"square-arrow-out-up-right\",\n \"arrow-up-right-from-square\",\n \"square-arrow-right-enter\",\n \"square-arrow-right-exit\",\n \"square-arrow-right\",\n \"arrow-right-square\",\n \"square-arrow-up-left\",\n \"arrow-up-left-square\",\n \"square-arrow-up-right\",\n \"arrow-up-right-square\",\n \"square-arrow-up\",\n \"arrow-up-square\",\n \"square-asterisk\",\n \"asterisk-square\",\n \"square-bottom-dashed-scissors\",\n \"scissors-square-dashed-bottom\",\n \"square-centerline-dashed-horizontal\",\n \"flip-horizontal\",\n \"square-centerline-dashed-vertical\",\n \"flip-vertical\",\n \"square-chart-gantt\",\n \"gantt-chart-square\",\n \"square-gantt-chart\",\n \"square-check-big\",\n \"check-square\",\n \"square-check\",\n \"check-square-2\",\n \"square-chevron-down\",\n \"chevron-down-square\",\n \"square-chevron-left\",\n \"chevron-left-square\",\n \"square-chevron-right\",\n \"chevron-right-square\",\n \"square-chevron-up\",\n \"chevron-up-square\",\n \"square-code\",\n \"code-square\",\n \"square-dashed-bottom-code\",\n \"square-dashed-bottom\",\n \"square-dashed-kanban\",\n \"kanban-square-dashed\",\n \"square-dashed-mouse-pointer\",\n \"mouse-pointer-square-dashed\",\n \"square-dashed-text\",\n \"text-selection\",\n \"text-select\",\n \"square-dashed-top-solid\",\n \"square-dashed\",\n \"box-select\",\n \"square-divide\",\n \"divide-square\",\n \"square-dot\",\n \"dot-square\",\n \"square-equal\",\n \"equal-square\",\n \"square-function\",\n \"function-square\",\n \"square-kanban\",\n \"kanban-square\",\n \"square-library\",\n \"library-square\",\n \"square-m\",\n \"m-square\",\n \"square-menu\",\n \"menu-square\",\n \"square-minus\",\n \"minus-square\",\n \"square-mouse-pointer\",\n \"inspect\",\n \"square-parking-off\",\n \"parking-square-off\",\n \"square-parking\",\n \"parking-square\",\n \"square-pause\",\n \"square-pen\",\n \"pen-box\",\n \"edit\",\n \"pen-square\",\n \"square-percent\",\n \"percent-square\",\n \"square-pi\",\n \"pi-square\",\n \"square-pilcrow\",\n \"pilcrow-square\",\n \"square-play\",\n \"play-square\",\n \"square-plus\",\n \"plus-square\",\n \"square-power\",\n \"power-square\",\n \"square-radical\",\n \"square-round-corner\",\n \"square-scissors\",\n \"scissors-square\",\n \"square-sigma\",\n \"sigma-square\",\n \"square-slash\",\n \"slash-square\",\n \"square-split-horizontal\",\n \"split-square-horizontal\",\n \"square-split-vertical\",\n \"split-square-vertical\",\n \"square-square\",\n \"square-stack\",\n \"square-star\",\n \"square-stop\",\n \"square-terminal\",\n \"terminal-square\",\n \"square-user-round\",\n \"user-square-2\",\n \"square-user\",\n \"user-square\",\n \"square-x\",\n \"x-square\",\n \"square\",\n \"squares-exclude\",\n \"squares-intersect\",\n \"squares-subtract\",\n \"squares-unite\",\n \"squircle-dashed\",\n \"squircle\",\n \"squirrel\",\n \"stamp\",\n \"star-half\",\n \"star-off\",\n \"star\",\n \"step-back\",\n \"step-forward\",\n \"stethoscope\",\n \"sticker\",\n \"sticky-note\",\n \"stone\",\n \"store\",\n \"stretch-horizontal\",\n \"stretch-vertical\",\n \"strikethrough\",\n \"subscript\",\n \"sun-dim\",\n \"sun-medium\",\n \"sun-moon\",\n \"sun-snow\",\n \"sun\",\n \"sunrise\",\n \"sunset\",\n \"superscript\",\n \"swatch-book\",\n \"swiss-franc\",\n \"switch-camera\",\n \"sword\",\n \"swords\",\n \"syringe\",\n \"table-2\",\n \"table-cells-merge\",\n \"table-cells-split\",\n \"table-columns-split\",\n \"table-of-contents\",\n \"table-properties\",\n \"table-rows-split\",\n \"table\",\n \"tablet-smartphone\",\n \"tablet\",\n \"tablets\",\n \"tag\",\n \"tags\",\n \"tally-1\",\n \"tally-2\",\n \"tally-3\",\n \"tally-4\",\n \"tally-5\",\n \"tangent\",\n \"target\",\n \"telescope\",\n \"tent-tree\",\n \"tent\",\n \"terminal\",\n \"test-tube-diagonal\",\n \"test-tube-2\",\n \"test-tube\",\n \"test-tubes\",\n \"text-align-center\",\n \"align-center\",\n \"text-align-end\",\n \"align-right\",\n \"text-align-justify\",\n \"align-justify\",\n \"text-align-start\",\n \"text\",\n \"align-left\",\n \"text-cursor-input\",\n \"text-cursor\",\n \"text-initial\",\n \"letter-text\",\n \"text-quote\",\n \"text-search\",\n \"text-wrap\",\n \"wrap-text\",\n \"theater\",\n \"thermometer-snowflake\",\n \"thermometer-sun\",\n \"thermometer\",\n \"thumbs-down\",\n \"thumbs-up\",\n \"ticket-check\",\n \"ticket-minus\",\n \"ticket-percent\",\n \"ticket-plus\",\n \"ticket-slash\",\n \"ticket-x\",\n \"ticket\",\n \"tickets-plane\",\n \"tickets\",\n \"timer-off\",\n \"timer-reset\",\n \"timer\",\n \"toggle-left\",\n \"toggle-right\",\n \"toilet\",\n \"tool-case\",\n \"toolbox\",\n \"tornado\",\n \"torus\",\n \"touchpad-off\",\n \"touchpad\",\n \"towel-rack\",\n \"tower-control\",\n \"toy-brick\",\n \"tractor\",\n \"traffic-cone\",\n \"train-front-tunnel\",\n \"train-front\",\n \"train-track\",\n \"tram-front\",\n \"train\",\n \"transgender\",\n \"trash-2\",\n \"trash\",\n \"tree-deciduous\",\n \"tree-palm\",\n \"palmtree\",\n \"tree-pine\",\n \"trees\",\n \"trending-down\",\n \"trending-up-down\",\n \"trending-up\",\n \"triangle-alert\",\n \"alert-triangle\",\n \"triangle-dashed\",\n \"triangle-right\",\n \"triangle\",\n \"trophy\",\n \"truck-electric\",\n \"truck\",\n \"turkish-lira\",\n \"turntable\",\n \"turtle\",\n \"tv-minimal-play\",\n \"tv-minimal\",\n \"tv-2\",\n \"tv\",\n \"type-outline\",\n \"type\",\n \"umbrella-off\",\n \"umbrella\",\n \"underline\",\n \"undo-2\",\n \"undo-dot\",\n \"undo\",\n \"unfold-horizontal\",\n \"unfold-vertical\",\n \"ungroup\",\n \"university\",\n \"school-2\",\n \"unlink-2\",\n \"unlink\",\n \"unplug\",\n \"upload\",\n \"usb\",\n \"user-check\",\n \"user-cog\",\n \"user-key\",\n \"user-lock\",\n \"user-minus\",\n \"user-pen\",\n \"user-plus\",\n \"user-round-check\",\n \"user-check-2\",\n \"user-round-cog\",\n \"user-cog-2\",\n \"user-round-key\",\n \"user-round-minus\",\n \"user-minus-2\",\n \"user-round-pen\",\n \"user-round-plus\",\n \"user-plus-2\",\n \"user-round-search\",\n \"user-round-x\",\n \"user-x-2\",\n \"user-round\",\n \"user-2\",\n \"user-search\",\n \"user-star\",\n \"user-x\",\n \"user\",\n \"users-round\",\n \"users-2\",\n \"users\",\n \"utensils-crossed\",\n \"fork-knife-crossed\",\n \"utensils\",\n \"fork-knife\",\n \"utility-pole\",\n \"van\",\n \"variable\",\n \"vault\",\n \"vector-square\",\n \"vegan\",\n \"venetian-mask\",\n \"venus-and-mars\",\n \"venus\",\n \"vibrate-off\",\n \"vibrate\",\n \"video-off\",\n \"video\",\n \"videotape\",\n \"view\",\n \"voicemail\",\n \"volleyball\",\n \"volume-1\",\n \"volume-2\",\n \"volume-off\",\n \"volume-x\",\n \"volume\",\n \"vote\",\n \"wallet-cards\",\n \"wallet-minimal\",\n \"wallet-2\",\n \"wallet\",\n \"wallpaper\",\n \"wand-sparkles\",\n \"wand-2\",\n \"wand\",\n \"warehouse\",\n \"washing-machine\",\n \"watch\",\n \"waves-arrow-down\",\n \"waves-arrow-up\",\n \"waves-ladder\",\n \"waves\",\n \"waypoints\",\n \"webcam\",\n \"webhook-off\",\n \"webhook\",\n \"weight-tilde\",\n \"weight\",\n \"wheat-off\",\n \"wheat\",\n \"whole-word\",\n \"wifi-cog\",\n \"wifi-high\",\n \"wifi-low\",\n \"wifi-off\",\n \"wifi-pen\",\n \"wifi-sync\",\n \"wifi-zero\",\n \"wifi\",\n \"wind-arrow-down\",\n \"wind\",\n \"wine-off\",\n \"wine\",\n \"workflow\",\n \"worm\",\n \"wrench\",\n \"x-line-top\",\n \"x\",\n \"zap-off\",\n \"zap\",\n \"zodiac-aquarius\",\n \"zodiac-aries\",\n \"zodiac-cancer\",\n \"zodiac-capricorn\",\n \"zodiac-gemini\",\n \"zodiac-leo\",\n \"zodiac-libra\",\n \"zodiac-ophiuchus\",\n \"zodiac-pisces\",\n \"zodiac-sagittarius\",\n \"zodiac-scorpio\",\n \"zodiac-taurus\",\n \"zodiac-virgo\",\n \"zoom-in\",\n \"zoom-out\",\n]);\n\nexport const LAYOUT_SECTION_ICON_SET: ReadonlySet<string> = new Set(LAYOUT_SECTION_ICONS);\nexport type LayoutSectionIcon = string;\n","/** Stable identifiers used by every project and page layout document. */\nexport const PAGE_CONTENT_ANCHOR_ID = \"page-content\" as const;\nexport const NAVIGATION_SECTION_ID = \"navigation\" as const;\nexport const FOOTER_SECTION_ID = \"footer\" as const;\n\n/** Locked transport/validation set shared by authoring surfaces and the server. */\nexport {\n LAYOUT_SECTION_ICONS,\n LAYOUT_SECTION_ICON_SET,\n type LayoutSectionIcon,\n} from \"./layout-lucide-icons.js\";\nimport type { LayoutSectionIcon } from \"./layout-lucide-icons.js\";\n\nexport type LayoutZone = \"above-page-content\" | \"below-page-content\";\nexport type ReservedLayoutSection = \"navigation\" | \"footer\";\n\nexport type LayoutScalarFieldType =\n | \"text\"\n | \"longtext\"\n | \"richtext\"\n | \"number\"\n | \"toggle\"\n | \"date\"\n | \"image\"\n | \"file\"\n | \"link\"\n | \"email\"\n | \"phone\"\n | \"select\"\n | \"color\"\n | \"json\"\n | \"reference\"\n | \"multi-reference\";\n\nexport type LayoutFieldType = LayoutScalarFieldType | \"group\" | \"repeater\";\n\n/** A recursive, stable-ID field contract shared by Sections and variant inputs. */\nexport interface LayoutFieldDefinition {\n id: string;\n slug: string;\n label: string;\n type: LayoutFieldType;\n required?: boolean;\n defaultValue?: unknown;\n config?: {\n options?: Array<{ label: string; value: string }>;\n referenceModelId?: string;\n minItems?: number;\n maxItems?: number;\n } & Record<string, unknown>;\n /** Required for group/repeater; forbidden for scalar fields. */\n fields?: LayoutFieldDefinition[];\n}\n\n/** The canonical public input contract all variants in a group implement. */\nexport type CanonicalInputDefinition = LayoutFieldDefinition;\n\n/** Maps one canonical input onto one or more internal component prop paths. */\nexport interface VariantInputMapping {\n inputId: string;\n targets: Array<{ blockId: string; path: string }>;\n}\n\nexport interface ComponentVariantGroup {\n id: string;\n workspaceId: string;\n projectId?: string | null;\n name: string;\n slug: string;\n canonicalInputs: CanonicalInputDefinition[];\n status: \"draft\" | \"published\";\n}\n\nexport interface LayoutFieldItem {\n id: string;\n kind: \"field\";\n fieldId: string;\n}\n\nexport interface LayoutComponentItem {\n id: string;\n kind: \"component\";\n componentId: string;\n variantGroupId?: string;\n bindings: Array<{ inputId: string; fieldId: string }>;\n literalValues?: Record<string, unknown>;\n}\n\nexport type LayoutSectionItem = LayoutFieldItem | LayoutComponentItem;\n\nexport interface LayoutSection {\n id: string;\n name: string;\n slug: string;\n icon: string;\n zone: LayoutZone;\n orderKey: string;\n reserved?: ReservedLayoutSection;\n fields: LayoutFieldDefinition[];\n items: LayoutSectionItem[];\n}\n\nexport interface LayoutStructureDocument {\n version: 1;\n pageContentAnchor: { id: typeof PAGE_CONTENT_ANCHOR_ID };\n sections: LayoutSection[];\n}\n\nexport interface LayoutDataDocument {\n version: 1;\n sections: Record<string, { fields: Record<string, unknown> }>;\n}\n\nexport type PageLayoutOverrideState =\n | \"inherit\"\n | \"override-content\"\n | \"customize-structure\"\n | \"disable\";\n\nexport interface PageSectionPlacement {\n zone: LayoutZone;\n afterSectionId?: string;\n beforeSectionId?: string;\n localOrderKey: string;\n}\n\nexport type PageLayoutSectionOverride =\n | { sectionId: string; state: \"inherit\" }\n | { sectionId: string; state: \"override-content\"; values: Record<string, unknown> }\n | {\n sectionId: string;\n state: \"customize-structure\";\n section: LayoutSection;\n data: { fields: Record<string, unknown> };\n /** Retained when the inherited Section is later deleted. */\n placement: PageSectionPlacement;\n }\n | { sectionId: string; state: \"disable\" };\n\nexport interface PageOnlyLayoutSection {\n section: LayoutSection;\n data: { fields: Record<string, unknown> };\n placement: PageSectionPlacement;\n}\n\nexport type PageLayoutSectionStructureOverride =\n | { sectionId: string; state: \"inherit\" }\n | { sectionId: string; state: \"override-content\" }\n | { sectionId: string; state: \"customize-structure\"; section: LayoutSection; placement: PageSectionPlacement }\n | { sectionId: string; state: \"disable\" };\n\n/** Persisted in pages.layout_override_structure_json. */\nexport interface PageLayoutOverrideStructureDocument {\n version: 1;\n sections: PageLayoutSectionStructureOverride[];\n pageOnlySections: Array<{ section: LayoutSection; placement: PageSectionPlacement }>;\n}\n\n/** Persisted independently so values can be patched without rewriting structure. */\nexport interface PageLayoutOverrideDataDocument {\n version: 1;\n sections: Record<string, { fields: Record<string, unknown> }>;\n pageOnlySections: Record<string, { fields: Record<string, unknown> }>;\n}\n\n/** Canonical in-memory form consumed by the pure resolver. */\nexport interface PageLayoutOverrideDocument {\n version: 1;\n sections: PageLayoutSectionOverride[];\n pageOnlySections: PageOnlyLayoutSection[];\n}\n\n/** Canonical, discriminated Management/MCP authoring transport. Authority is derived from type. */\nexport type ManagementLayoutCommand =\n | { type: \"set-section-values\"; sectionId: string; values: Record<string, unknown> }\n | { type: \"set-field-value\"; sectionId: string; fieldId: string; value: unknown }\n | { type: \"add-component\"; sectionId: string; componentId: string; variantGroupId?: string; bindings?: LayoutComponentItem[\"bindings\"]; literalValues?: Record<string, unknown> }\n | { type: \"remove-item\"; sectionId: string; itemId: string }\n | { type: \"move-component\"; sectionId: string; itemId: string; index: number }\n | { type: \"move-item\"; sectionId: string; itemId: string; index: number }\n | { type: \"swap-component-variant\"; sectionId: string; itemId: string; componentId: string }\n | { type: \"set-page-state\"; sectionId: string; state: PageLayoutOverrideState | \"reset\" }\n | { type: \"set-section-state\"; sectionId: string; state: PageLayoutOverrideState | \"reset\" }\n | { type: \"add-section\"; name: string; icon: LayoutSectionIcon; zone: \"before_page\" | \"after_page\" }\n | { type: \"restore-section\"; section: LayoutSection; data: { fields: Record<string, unknown> }; placement?: PageSectionPlacement }\n | { type: \"update-section\"; sectionId: string; name?: string; icon?: LayoutSectionIcon; slug?: string; zone?: LayoutZone; orderKey?: string }\n | { type: \"remove-section\"; sectionId: string }\n | { type: \"move-section\"; sectionId: string; afterId?: string | null; beforeId?: string | null }\n | { type: \"add-field\"; sectionId: string; parentFieldId?: string; field?: LayoutFieldDefinition; fieldType?: LayoutFieldType }\n | { type: \"update-field\"; sectionId: string; fieldId: string; patch: Partial<Omit<LayoutFieldDefinition, \"id\">> }\n | { type: \"remove-field\"; sectionId: string; fieldId: string }\n | { type: \"move-field\"; sectionId: string; itemId: string; index: number }\n | { type: \"set-bindings\"; sectionId: string; itemId: string; bindings: LayoutComponentItem[\"bindings\"]; literalValues?: Record<string, unknown> };\n\nexport type ResolvedLayoutNode =\n | { kind: \"page-content\"; id: typeof PAGE_CONTENT_ANCHOR_ID }\n | {\n kind: \"section\";\n id: string;\n section: LayoutSection;\n data: { fields: Record<string, unknown> };\n source: \"inherit\" | \"override-content\" | \"customize-structure\" | \"page-only\" | \"detached\";\n };\n\nexport interface DeliveredLayout {\n version: 1;\n nodes: Array<\n | { kind: \"page-content\"; id: typeof PAGE_CONTENT_ANCHOR_ID }\n | { kind: \"section\"; id: string; slug: string; name: string; source: Extract<ResolvedLayoutNode, { kind: \"section\" }>[\"source\"] }\n >;\n sections: Record<string, {\n id: string;\n slug: string;\n name: string;\n fields: Record<string, unknown>;\n items: Array<\n | { id: string; kind: \"field\"; fieldId: string; value: unknown }\n | {\n id: string;\n kind: \"component\";\n componentId: string;\n variantGroupId?: string;\n canonicalInputs: CanonicalInputDefinition[];\n bindings: LayoutComponentItem[\"bindings\"];\n canonicalValues: Record<string, unknown>;\n resolvedProps: Record<string, unknown>;\n /**\n * `prop.key` → canonical `inputId` — the relation `resolvedProps` consumes and throws\n * away (`output[prop.key] = canonicalValues[mapping.inputId]`).\n *\n * Without it a renderer holds a component prop key and NO address: `logoAlt`/`links`/\n * `cta` are the component's own bare keys, and nothing relates them back to the layout\n * field a write must land on. With it the chain closes — `prop.key` → `inputId` →\n * (`bindings`, already delivered above) → `fieldId` → `set-field-value(sectionId,\n * fieldId)`. That is what makes global chrome click-to-edit (FLO-1179).\n *\n * Additive and always present (`{}` when the item has no variant mappings), so an\n * older consumer that ignores it is byte-identical to before.\n */\n propInputs: Record<string, string>;\n blocks: unknown[];\n }\n >;\n }>;\n}\n","/**\n * WHERE an element was on a built page, so a later pass can find it again.\n *\n * This lives in the shared package because BOTH ends of the comparison have to spell an address\n * the same way: the backend derives it from a JSDOM tree at import time, the dashboard computes\n * it from a live iframe tree when a person clicks an unbound element. Two implementations of\n * \"the ancestor chain down from the nearest landmark\" is one implementation too many — the first\n * time they disagree by one tag, a click binds the wrong element.\n *\n * The DOM is typed STRUCTURALLY (`ElementLike`, `LandmarkHost`) so this package needs no DOM lib\n * and stays importable from a node-only build.\n */\n\n/** The landmark tags an address is anchored at, as one CSS selector and as one tag set. */\nexport const LANDMARK_SELECTOR = \"header,nav,footer\";\nconst LANDMARK_TAGS = new Set([\"HEADER\", \"NAV\", \"FOOTER\"]);\n\n/**\n * The THIRD region — a modal, a cookie banner, a pop-up — behind a per-project gate.\n *\n * A `<dialog>` or a `[role=\"dialog\"]` sits at BODY level, outside every landmark, so a banner\n * byte-identical on twelve routes derived twelve copies of itself. It is NOT a stop for\n * `locatorFor`: `region` already names which dialog an element is in, and a second gated rule\n * about where the ancestor chain ends would make the same element's locator differ between a\n * project that derived it as chrome and one that did not.\n */\nexport const DIALOG_SELECTOR = 'dialog,[role=\"dialog\"]';\n\n/**\n * Best-effort by construction — built-DOM positions do not survive component expansion or\n * conditional rendering — so a consumer that finds no exact match, or finds several, falls back\n * to ambiguity rather than to a guess. The ancestor chain is compared EXACTLY (`atLocator`,\n * annotate-static.ts): a chain that merely contains the stored one is a different element.\n */\nexport interface DerivedLocator {\n /** The landmark it lives in — `header#0`, `nav#1`, `footer#0` — or null for the page body. */\n region: string | null;\n /** Tag names from the nearest landmark (or `<body>`) down to the element's parent. */\n ancestors: string[];\n /** Its index among its parent's element children. */\n siblingIndex: number;\n /**\n * The element's own lower-cased tag name.\n *\n * The cheapest fact that separates two elements a chain-and-index pair calls identical — a\n * `<h2>` and the `<a>` beside it in a rebuilt layout — and the only one a resolver can use to\n * NARROW its candidate list before comparing anything. Absent on locators stored before it\n * existed; a comparer must treat a missing tag as \"matches\".\n */\n tag: string;\n /**\n * The repeater row this value belongs to.\n *\n * On a leaf's field DEFINITION the index is 0 — one definition serves every row — and the\n * brief overrides it with the row it is actually describing (`cards[2].title` → index 2).\n */\n repeat?: { groupKey: string; index: number };\n}\n\n/** The DOM surface `locatorFor` reads. `Element` satisfies it; so does a plain object. */\nexport interface ElementLike {\n tagName: string;\n parentElement: ElementLike | null;\n children: ArrayLike<ElementLike>;\n}\n\n/**\n * The structural address of one element: its ancestor tags and its position among its siblings.\n *\n * Stops at the nearest LANDMARK because that is where a page's structure stops being comparable\n * — a header's internals are the same on every route while the body's are not — and `region`\n * already names which landmark it was.\n */\nexport function locatorFor(el: ElementLike, region: string | null): DerivedLocator {\n const ancestors: string[] = [];\n for (\n let parent = el.parentElement;\n parent && parent.tagName !== \"BODY\" && !LANDMARK_TAGS.has(parent.tagName);\n parent = parent.parentElement\n ) {\n ancestors.unshift(parent.tagName.toLowerCase());\n }\n const siblings = el.parentElement ? Array.from(el.parentElement.children) : [];\n return {\n region,\n ancestors,\n siblingIndex: Math.max(siblings.indexOf(el), 0),\n tag: el.tagName.toLowerCase(),\n };\n}\n\n/** The DOM surface `landmarkRegions` reads of each element it considers. */\nexport interface LandmarkElement {\n tagName: string;\n parentElement: { closest(selectors: string): unknown } | null;\n matches(selectors: string): boolean;\n}\n\n/**\n * A page's landmark regions: the OUTERMOST `header`/`nav`/`footer` elements, in document order.\n *\n * Outermost, because a `<nav>` inside a `<header>` is one region a visitor sees as one thing —\n * and promoting the two separately would let a site's masthead be half layout, half page.\n */\nexport function landmarkRegions<E extends LandmarkElement>(\n doc: { querySelectorAll(selectors: string): Iterable<E> },\n /**\n * Count a dialog as a region too — the per-project chrome grammar.\n *\n * OFF by default, and not merely for symmetry: a region name is part of every field's LOCATOR,\n * and a project whose stored locators say `region: null` for a modal's copy must keep being\n * read the same way.\n */\n dialogs = false,\n): { slot: string; el: E }[] {\n const counts = new Map<string, number>();\n const out: { slot: string; el: E }[] = [];\n const selector = dialogs ? `${LANDMARK_SELECTOR},${DIALOG_SELECTOR}` : LANDMARK_SELECTOR;\n for (const el of doc.querySelectorAll(selector)) {\n if (el.parentElement?.closest(selector)) continue;\n // The NAME, not the tag: a `[role=\"dialog\"]` is usually a `<div>`, and slotting it as\n // `div#0` would make one site's modal and another's wrapper the same kind of region.\n const name = !LANDMARK_TAGS.has(el.tagName) && el.matches(DIALOG_SELECTOR)\n ? \"dialog\"\n : el.tagName.toLowerCase();\n const n = counts.get(name) ?? 0;\n counts.set(name, n + 1);\n out.push({ slot: `${name}#${n}`, el });\n }\n return out;\n}\n"],"mappings":";AAmfO,SAAS,QAAQ,OAAuC;AAC7D,SACE,OAAO,UAAU,YACjB,UAAU,QACV,UAAU,SACV,OAAQ,MAAkC,MAAM,MAAM;AAE1D;AAUO,SAAS,aAAa,OAAkC;AAC7D,MAAI,QAAQ,KAAK,EAAG,QAAO,MAAM;AACjC,SAAO;AACT;;;AC3bO,IAAM,iBAAsE;AAAA,EACjF,SAAS,CAAC,EAAE,MAAM,QAAQ,MAAM,OAAO,CAAC;AAAA,EACxC,MAAM,CAAC,EAAE,MAAM,QAAQ,MAAM,WAAW,CAAC;AAAA,EACzC,UAAU,CAAC,EAAE,MAAM,QAAQ,MAAM,WAAW,CAAC;AAAA,EAC7C,OAAO;AAAA,IACL,EAAE,MAAM,OAAO,MAAM,QAAQ;AAAA,IAC7B,EAAE,MAAM,WAAW,MAAM,OAAO;AAAA,IAChC,EAAE,MAAM,OAAO,MAAM,QAAQ,MAAM,MAAM;AAAA,EAC3C;AAAA,EACA,QAAQ;AAAA,IACN,EAAE,MAAM,QAAQ,MAAM,OAAO;AAAA,IAC7B,EAAE,MAAM,QAAQ,MAAM,OAAO,MAAM,OAAO;AAAA,EAC5C;AAAA,EACA,OAAO;AAAA,IACL,EAAE,MAAM,OAAO,MAAM,OAAO,MAAM,MAAM;AAAA,IACxC,EAAE,MAAM,UAAU,MAAM,OAAO,MAAM,SAAS;AAAA,EAChD;AAAA,EACA,QAAQ;AAAA,IACN,EAAE,MAAM,YAAY,MAAM,QAAQ;AAAA,IAClC,EAAE,MAAM,YAAY,MAAM,QAAQ,MAAM,MAAM;AAAA,IAC9C,EAAE,MAAM,iBAAiB,MAAM,OAAO;AAAA,IACtC,EAAE,MAAM,gBAAgB,MAAM,OAAO,MAAM,OAAO;AAAA,IAClD,EAAE,MAAM,YAAY,MAAM,OAAO;AAAA,IACjC,EAAE,MAAM,YAAY,MAAM,OAAO,MAAM,OAAO;AAAA,EAChD;AAAA,EACA,QAAQ;AAAA,IACN,EAAE,MAAM,aAAa,MAAM,OAAO;AAAA,IAClC,EAAE,MAAM,qBAAqB,MAAM,OAAO;AAAA,IAC1C,EAAE,MAAM,2BAA2B,MAAM,OAAO;AAAA,IAChD,EAAE,MAAM,0BAA0B,MAAM,OAAO,MAAM,OAAO;AAAA,EAC9D;AAAA,EACA,MAAM,CAAC,EAAE,MAAM,gBAAgB,MAAM,OAAO,CAAC;AAC/C;AAQA,IAAM,WAAW,CAAC,MAChB,OAAO,MAAM,YAAY,MAAM,QAAQ,CAAC,MAAM,QAAQ,CAAC;AAgBlD,SAAS,SAAS,MAAe,MAAuB;AAC7D,MAAI,SAAkB;AACtB,aAAW,WAAW,KAAK,MAAM,GAAG,GAAG;AACrC,QAAI,CAAC,QAAS,QAAO;AACrB,UAAM,MAAM,QAAQ,QAAQ,YAAY,EAAE;AAC1C,QAAI,KAAK;AACP,UAAI,CAAC,SAAS,MAAM,EAAG,QAAO;AAC9B,eAAS,OAAO,GAAG;AAAA,IACrB;AACA,eAAW,SAAS,QAAQ,SAAS,YAAY,GAAG;AAClD,UAAI,CAAC,MAAM,QAAQ,MAAM,EAAG,QAAO;AACnC,eAAS,OAAO,OAAO,MAAM,CAAC,CAAC,CAAC;AAAA,IAClC;AAAA,EACF;AACA,SAAO;AACT;AAGA,SAAS,eAAe,SAAuB,OAAgB,MAAiC;AAC9F,QAAM,KAAK,KAAK,QAAQ,IAAI;AAC5B,MAAI,KAAK,EAAG,QAAO,CAAC,EAAE,GAAG,SAAS,KAAK,CAAC;AAExC,QAAM,OAAO,KAAK,MAAM,GAAG,EAAE;AAC7B,QAAM,OAAO,KAAK,MAAM,KAAK,CAAC;AAC9B,QAAM,QAAQ,SAAS,OAAO,IAAI;AAClC,MAAI,CAAC,MAAM,QAAQ,KAAK,EAAG,QAAO,CAAC;AAEnC,SAAO,MAAM;AAAA,IAAQ,CAAC,OAAO,UAC3B,eAAe,SAAS,OAAO,GAAG,IAAI,IAAI,KAAK,IAAI,IAAI,EAAE;AAAA,EAC3D;AACF;AAiBO,SAAS,oBAAoB,OAAwC;AAC1E,QAAM,WAAW,eAAe,MAAM,IAAI;AAC1C,MAAI,CAAC,SAAU,QAAO,CAAC;AACvB,QAAM,QAAS,MAA8B;AAC7C,MAAI,CAAC,SAAS,KAAK,EAAG,QAAO,CAAC;AAC9B,SAAO,SACJ,QAAQ,CAAC,YAAY,eAAe,SAAS,OAAO,QAAQ,IAAI,CAAC,EACjE,OAAO,CAAC,YAAY,SAAS,OAAO,QAAQ,IAAI,MAAM,MAAS;AACpE;AAGO,SAAS,qBACd,SACQ;AACR,SAAO,QAAQ,IAAI,CAAC,MAAM,GAAG,EAAE,OAAO,IAAI,EAAE,IAAI,IAAI,EAAE,IAAI,EAAE,EAAE,KAAK,GAAG;AACxE;AAGO,SAAS,oBACd,OACwD;AACxD,MAAI,CAAC,MAAO,QAAO,CAAC;AACpB,SAAO,MACJ,MAAM,GAAG,EACT,IAAI,CAAC,UAAU,MAAM,MAAM,GAAG,CAAC,EAC/B,OAAO,CAAC,UAAkD,MAAM,WAAW,KAAK,MAAM,MAAM,OAAO,CAAC,EACpG,IAAI,CAAC,CAAC,SAAS,MAAM,IAAI,OAAO,EAAE,SAAS,MAAM,KAAK,EAAE;AAC7D;AAiCO,SAAS,uBAAuB,MAA6C;AAClF,MAAI,CAAC,MAAM,OAAO,CAAC,KAAK,QAAQ,QAAS,QAAO;AAChD,SAAO,GAAG,KAAK,OAAO,OAAO,KAAK,OAAO,KAAK,OAAO,QAAQ,EAAE,EAAE,QAAQ,YAAY,EAAE,CAAC;AAC1F;AAOO,SAAS,2BACd,iBACA,OACA,OACqB;AACrB,QAAM,WAAW,QAAQ,GAAG,KAAK,IAAI,eAAe,KAAK;AACzD,QAAM,MAAM,oBAAI,IAAoB;AACpC,aAAW,QAAQ,SAAS,CAAC,GAAG;AAC9B,QAAI,CAAC,MAAM,OAAO,CAAC,KAAK,QAAQ,QAAS;AACzC,UAAM,OAAO,uBAAuB,IAAI;AAGxC,QAAI,CAAC,IAAI,IAAI,IAAI,EAAG,KAAI,IAAI,MAAM,GAAG,QAAQ,eAAe,KAAK,GAAG,EAAE;AAAA,EACxE;AACA,SAAO;AACT;;;ACjQA,IAAM,WAAmC,EAAE,MAAM,KAAK,IAAI,OAAO,IAAI,OAAO,IAAI,QAAQ,IAAI,QAAQ,IAAI,OAAO;AAC/G,IAAM,gBAAwC,EAAE,IAAI,YAAY,MAAM,QAAQ,IAAI,WAAW,IAAI,UAAU,OAAO,OAAO;AACzH,IAAM,SAAiC,EAAE,QAAQ,KAAK,QAAQ,KAAK,UAAU,KAAK,MAAM,IAAI;AAC5F,IAAM,YAAoC,EAAE,MAAM,KAAK,IAAI,OAAO,IAAI,OAAO,IAAI,QAAQ,MAAM,SAAS;AACxG,IAAM,YAAoC,EAAE,OAAO,WAAW,OAAO,WAAW,OAAO,WAAW,SAAS,WAAW,SAAS,WAAW,QAAQ,UAAU;AAGrJ,SAAS,gBAAgB,OAA4E;AAC1G,MAAI,CAAC,SAAS,OAAO,UAAU,SAAU,QAAO;AAChD,QAAM,IAAI;AACV,QAAM,MAAuC,CAAC;AAC9C,MAAI,EAAE,YAAY,SAAS,EAAE,QAAQ,KAAK,MAAM;AAAE,QAAI,aAAa,SAAS,EAAE,QAAQ;AAAI,QAAI,gBAAgB,SAAS,EAAE,QAAQ;AAAA,EAAI;AACrI,MAAI,EAAE,YAAY,SAAS,EAAE,QAAQ,KAAK,MAAM;AAAE,QAAI,cAAc,SAAS,EAAE,QAAQ;AAAI,QAAI,eAAe,SAAS,EAAE,QAAQ;AAAA,EAAI;AACrI,MAAI,EAAE,aAAa,SAAS,EAAE,SAAS,KAAK,KAAM,KAAI,YAAY,SAAS,EAAE,SAAS;AACtF,MAAI,EAAE,gBAAgB,SAAS,EAAE,YAAY,KAAK,KAAM,KAAI,eAAe,SAAS,EAAE,YAAY;AAClG,MAAI,EAAE,cAAc,UAAU,EAAE,UAAU,EAAG,KAAI,aAAa,UAAU,EAAE,UAAU;AACpF,MAAI,EAAE,aAAa,UAAU,EAAE,SAAS,EAAG,KAAI,QAAQ,UAAU,EAAE,SAAS;AAC5E,MAAI,EAAE,UAAU,UAAU,EAAE,UAAU,YAAY,EAAE,UAAU,QAAS,KAAI,YAAY,EAAE;AACzF,MAAI,EAAE,YAAY,cAAc,EAAE,QAAQ,EAAG,KAAI,WAAW,cAAc,EAAE,QAAQ;AACpF,MAAI,EAAE,UAAU,OAAO,EAAE,MAAM,KAAK,KAAM,KAAI,aAAa,OAAO,EAAE,MAAM;AAC1E,MAAI,EAAE,UAAU,UAAU,EAAE,MAAM,KAAK,KAAM,KAAI,eAAe,UAAU,EAAE,MAAM;AAClF,SAAO,OAAO,KAAK,GAAG,EAAE,SAAS,MAAM;AACzC;;;ACOO,IAAM,mBACX;AAiCK,IAAM,uBAAuB;AAAA,EAClC;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AACF;;;AC/EO,IAAM,uBAA0C,OAAO,OAAO;AAAA,EACnE;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AACF,CAAC;AAEM,IAAM,0BAA+C,IAAI,IAAI,oBAAoB;;;AC36DjF,IAAM,yBAAyB;AAC/B,IAAM,wBAAwB;AAC9B,IAAM,oBAAoB;;;ACW1B,IAAM,oBAAoB;AACjC,IAAM,gBAAgB,oBAAI,IAAI,CAAC,UAAU,OAAO,QAAQ,CAAC;AAWlD,IAAM,kBAAkB;AA+CxB,SAAS,WAAW,IAAiB,QAAuC;AACjF,QAAM,YAAsB,CAAC;AAC7B,WACM,SAAS,GAAG,eAChB,UAAU,OAAO,YAAY,UAAU,CAAC,cAAc,IAAI,OAAO,OAAO,GACxE,SAAS,OAAO,eAChB;AACA,cAAU,QAAQ,OAAO,QAAQ,YAAY,CAAC;AAAA,EAChD;AACA,QAAM,WAAW,GAAG,gBAAgB,MAAM,KAAK,GAAG,cAAc,QAAQ,IAAI,CAAC;AAC7E,SAAO;AAAA,IACL;AAAA,IACA;AAAA,IACA,cAAc,KAAK,IAAI,SAAS,QAAQ,EAAE,GAAG,CAAC;AAAA,IAC9C,KAAK,GAAG,QAAQ,YAAY;AAAA,EAC9B;AACF;AAeO,SAAS,gBACd,KAQA,UAAU,OACiB;AAC3B,QAAM,SAAS,oBAAI,IAAoB;AACvC,QAAM,MAAiC,CAAC;AACxC,QAAM,WAAW,UAAU,GAAG,iBAAiB,IAAI,eAAe,KAAK;AACvE,aAAW,MAAM,IAAI,iBAAiB,QAAQ,GAAG;AAC/C,QAAI,GAAG,eAAe,QAAQ,QAAQ,EAAG;AAGzC,UAAM,OAAO,CAAC,cAAc,IAAI,GAAG,OAAO,KAAK,GAAG,QAAQ,eAAe,IACrE,WACA,GAAG,QAAQ,YAAY;AAC3B,UAAM,IAAI,OAAO,IAAI,IAAI,KAAK;AAC9B,WAAO,IAAI,MAAM,IAAI,CAAC;AACtB,QAAI,KAAK,EAAE,MAAM,GAAG,IAAI,IAAI,CAAC,IAAI,GAAG,CAAC;AAAA,EACvC;AACA,SAAO;AACT;","names":[]}
1
+ {"version":3,"sources":["../src/block.ts","../src/block-bindings.ts","../src/blockStyle.ts","../src/component.ts","../src/layout-lucide-icons.ts","../src/layout.ts","../src/locator.ts"],"sourcesContent":["/**\n * ContentBlock — a discriminated union of all CMS block types.\n * Each block has a `type` discriminator and a `props` object\n * whose shape matches the block type.\n */\n\n// ── Block style (FLO-264) ──────────────────────────────────────────────────────\n// A uniform, BOUNDED set of design tokens any block may carry (sibling to `props`).\n// Tokens map to fixed CSS values in the renderer (`styleTokensToCss`) so styling\n// reaches the live site WITHOUT arbitrary CSS. Additive + fully optional.\n\nexport type SpaceToken = \"none\" | \"xs\" | \"sm\" | \"md\" | \"lg\" | \"xl\";\nexport type ColorToken = \"none\" | \"white\" | \"black\" | \"muted\" | \"mutedBg\" | \"primary\" | \"accent\";\nexport type AlignToken = \"left\" | \"center\" | \"right\";\nexport type FontSizeToken = \"sm\" | \"base\" | \"lg\" | \"xl\" | \"2xl\";\nexport type WeightToken = \"normal\" | \"medium\" | \"semibold\" | \"bold\";\nexport type RadiusToken = \"none\" | \"sm\" | \"md\" | \"lg\" | \"full\";\n\n// Section design (task 4) — the per-instance design a section carries on the page.\nexport type ThemeToken = \"inherit\" | \"light\" | \"dark\";\nexport type BgToken = \"none\" | \"surface\" | \"muted\" | \"accent\" | \"dark\" | \"custom\";\nexport type ContentWidthToken = \"narrow\" | \"default\" | \"wide\" | \"full\";\nexport type CornerToken = \"0\" | \"s\" | \"m\" | \"l\" | \"xl\" | \"2xl\";\nexport type ShadowToken = \"0\" | \"s\" | \"m\" | \"l\" | \"xl\";\n\nexport interface BlockStyle {\n // Legacy token set (FLO-264). Where these overlap the section fields below\n // (background, radius, padding), the section field WINS in the renderer.\n paddingY?: SpaceToken;\n paddingX?: SpaceToken;\n marginTop?: SpaceToken;\n marginBottom?: SpaceToken;\n background?: ColorToken;\n textColor?: ColorToken;\n align?: AlignToken;\n fontSize?: FontSizeToken;\n weight?: WeightToken;\n radius?: RadiusToken;\n\n // Section design (task 4).\n theme?: ThemeToken;\n bg?: BgToken;\n /** Only read when `bg === \"custom\"`. Hex only. */\n bgCustom?: string;\n /** Padding sliders, in px (0–240). */\n paddingTop?: number;\n paddingBottom?: number;\n paddingSides?: number;\n contentWidth?: ContentWidthToken;\n /**\n * Where the constrained content column sits, when `contentWidth` constrains it.\n *\n * Split out of `align`, which still means text alignment and is still the fallback when this\n * is unset — so everything written before the split renders byte-identically. The two were one\n * token until anything MEASURED a section's text alignment: copying a source site's\n * `text-align: left` would otherwise also shove its column to the page edge.\n */\n contentAlign?: AlignToken;\n fullHeight?: boolean;\n /** 0–100. */\n opacity?: number;\n corner?: CornerToken;\n shadow?: ShadowToken;\n borderTop?: boolean;\n borderBottom?: boolean;\n /** All four sides, `1px solid currentColor` — an outline button's border follows its text colour. */\n border?: boolean;\n /** 🔴 The one free-form string. MUST go through `safeCssUrl()` before reaching CSS. */\n bgImage?: string;\n}\n\n// ── Heading ──────────────────────────────────────────────────────────────────\n\nexport interface HeadingProps {\n text: string;\n level?: 1 | 2 | 3;\n}\n\nexport interface HeadingBlock {\n type: \"heading\";\n id: string;\n style?: BlockStyle;\n /** Editor-facing display name for this block's dock card. Not rendered. */\n label?: string;\n props: HeadingProps;\n}\n\n// ── Text ─────────────────────────────────────────────────────────────────────\n\nexport interface TextProps {\n html: string;\n /** @see RichTextProps.level — the same payload takes the same level. */\n level?: 1 | 2 | 3 | 4 | 5 | 6;\n}\n\nexport interface TextBlock {\n type: \"text\";\n id: string;\n style?: BlockStyle;\n /** Editor-facing display name for this block's dock card. Not rendered. */\n label?: string;\n props: TextProps;\n}\n\n/**\n * A rich-text block: the same HTML payload as `text`, authored through a real editor.\n *\n * WHY A SEPARATE TYPE RATHER THAN CHANGING `text`. Every `text` block already on a live page\n * holds an HTML string that the delivery renderer injects as-is. Repurposing that type would\n * mean migrating published content, and getting it wrong renders visible markup to visitors.\n * A new type costs nothing at rest and leaves existing pages untouched.\n *\n * The payload is deliberately IDENTICAL to TextProps (an HTML string) so the two are\n * interchangeable at the renderer: delivery treats them the same, and the difference is\n * entirely in how an author edits them — `text` is a plain field, `richtext` gets the\n * formatting surface.\n */\n/**\n * A Portable Text node — the structured form of rich text.\n *\n * Kept alongside `html` rather than replacing it, so nothing already published moves. The\n * structure exists because an HTML string cannot carry INTENT: a colour is a hex with no\n * notion of which brand token produced it, an embedded component is a div with no reference\n * to resolve, and neither can be read back by tooling. Nodes can carry all of that.\n */\nexport interface PortableTextNode {\n _type: string;\n _key?: string;\n /** Block style — \"normal\", \"h2\", \"blockquote\". */\n style?: string;\n text?: string;\n children?: PortableTextNode[];\n /** Marks on a span: \"strong\", \"em\", or a token reference like \"color:brand-accent\". */\n marks?: string[];\n /** An embedded component or reference resolves through these. */\n schemaKey?: string;\n _ref?: string;\n fields?: Record<string, unknown>;\n}\n\nexport interface PortableTextDocument {\n version: 1;\n content: PortableTextNode[];\n}\n\nexport interface RichTextProps {\n /**\n * The RENDERED CACHE. Delivery reads this, so the fast path stays a string interpolation\n * and every page published before `content` existed keeps rendering byte-identically.\n */\n html: string;\n /**\n * The SOURCE OF TRUTH, when present — `content` always wins over `html`.\n *\n * Optional on purpose: this is the same envelope the field values already use\n * (`{ format, value, html }`), where `html` is likewise derived. Any writer that sets\n * `html` alone on a block that HAS `content` must delete `content` in the same write, or\n * the stale string silently shadows the newer structure.\n */\n content?: PortableTextDocument;\n /**\n * Render the rich copy AS `<h1>`–`<h6>` instead of a paragraph container, so a title keeps\n * its inline marks (a brand-coloured span) AND its heading semantics. Absent ⇒ ordinary rich\n * text, as before. Set ⇒ the value must be ONE line of inline copy; the write schema refuses\n * more. A component prop of type `number` or `select` can target `props.level`.\n */\n level?: 1 | 2 | 3 | 4 | 5 | 6;\n}\n\nexport interface RichTextBlock {\n type: \"richtext\";\n id: string;\n style?: BlockStyle;\n /** Editor-facing display name for this block's dock card. Not rendered. */\n label?: string;\n props: RichTextProps;\n}\n\n// ── Image ────────────────────────────────────────────────────────────────────\n\nexport interface ImageProps {\n src: string;\n alt: string;\n width?: number;\n height?: number;\n caption?: string;\n}\n\nexport interface ImageBlock {\n type: \"image\";\n id: string;\n style?: BlockStyle;\n /** Editor-facing display name for this block's dock card. Not rendered. */\n label?: string;\n props: ImageProps;\n}\n\n// ── Button ───────────────────────────────────────────────────────────────────\n\nexport interface ButtonProps {\n text: string;\n href: string;\n variant?: \"primary\" | \"secondary\";\n}\n\nexport interface ButtonBlock {\n type: \"button\";\n id: string;\n style?: BlockStyle;\n /** Editor-facing display name for this block's dock card. Not rendered. */\n label?: string;\n props: ButtonProps;\n}\n\n// ── Spacer ───────────────────────────────────────────────────────────────────\n\nexport interface SpacerProps {\n height: number; // in px\n}\n\nexport interface SpacerBlock {\n type: \"spacer\";\n id: string;\n style?: BlockStyle;\n /** Editor-facing display name for this block's dock card. Not rendered. */\n label?: string;\n props: SpacerProps;\n}\n\n// ── Columns ───────────────────────────────────────────────────────────────────\n\nexport interface ColumnsProps {\n columns: ContentBlock[][]; // array of column slots, each slot is an array of blocks\n gap?: number; // in px\n}\n\nexport interface ColumnsBlock {\n type: \"columns\";\n id: string;\n style?: BlockStyle;\n /** Editor-facing display name for this block's dock card. Not rendered. */\n label?: string;\n props: ColumnsProps;\n}\n\n// ── Video ────────────────────────────────────────────────────────────────────\n\nexport interface VideoProps {\n url: string;\n poster?: string;\n autoplay?: boolean;\n loop?: boolean;\n /**\n * What is said in the video (CPO-093). The block carries its own because its url may be a\n * pasted provider link with no library asset to hang one from. Rendered as <details> after\n * the player and published in the .md twin.\n */\n transcript?: string;\n}\n\nexport interface VideoBlock {\n type: \"video\";\n id: string;\n style?: BlockStyle;\n /** Editor-facing display name for this block's dock card. Not rendered. */\n label?: string;\n props: VideoProps;\n}\n\n// ── Form ─────────────────────────────────────────────────────────────────────\n\nexport interface FormProps {\n formId: string; // references forms.id (a nanoid). Resolved against delivered forms at render time.\n}\n\nexport interface FormBlock {\n type: \"form\";\n id: string;\n style?: BlockStyle;\n /** Editor-facing display name for this block's dock card. Not rendered. */\n label?: string;\n props: FormProps;\n}\n\n// ── Section (recursive container) ──────────────────────────────────────────────\n\nexport interface SectionProps {\n children: ContentBlock[];\n background?: string;\n paddingY?: number; // in px\n maxWidth?: number; // in px\n}\n\nexport interface SectionBlock {\n type: \"section\";\n id: string;\n style?: BlockStyle;\n /** Editor-facing display name for this block's dock card. Not rendered. */\n label?: string;\n props: SectionProps;\n}\n\n// ── Navbar ─────────────────────────────────────────────────────────────────────\n\nexport interface NavLink {\n label: string;\n href: string;\n}\n\nexport interface NavbarProps {\n logo?: { src: string; alt: string; href?: string };\n logoAlt?: string;\n links: NavLink[];\n mobileMenu?: boolean;\n cta?: { text: string; href: string };\n}\n\nexport interface NavbarBlock {\n type: \"navbar\";\n id: string;\n style?: BlockStyle;\n /** Editor-facing display name for this block's dock card. Not rendered. */\n label?: string;\n props: NavbarProps;\n}\n\n// ── Footer ─────────────────────────────────────────────────────────────────────\n\nexport interface FooterColumn {\n heading?: string;\n links: NavLink[];\n}\n\nexport interface FooterProps {\n columns: FooterColumn[];\n copyright?: string;\n}\n\nexport interface FooterBlock {\n type: \"footer\";\n id: string;\n style?: BlockStyle;\n /** Editor-facing display name for this block's dock card. Not rendered. */\n label?: string;\n props: FooterProps;\n}\n\n// ── Slider / Carousel (recursive container, client-hydrated) ────────────────────\n\nexport interface SlideItem {\n id: string;\n children: ContentBlock[];\n}\n\nexport interface SliderProps {\n slides: SlideItem[];\n autoplay?: boolean;\n interval?: number; // in ms\n loop?: boolean;\n}\n\nexport interface SliderBlock {\n type: \"slider\";\n id: string;\n style?: BlockStyle;\n /** Editor-facing display name for this block's dock card. Not rendered. */\n label?: string;\n props: SliderProps;\n}\n\n// ── Tabs (recursive container, client-hydrated) ─────────────────────────────────\n\nexport interface TabItem {\n id: string;\n label: string;\n children: ContentBlock[];\n}\n\nexport interface TabsProps {\n tabs: TabItem[];\n}\n\nexport interface TabsBlock {\n type: \"tabs\";\n id: string;\n style?: BlockStyle;\n /** Editor-facing display name for this block's dock card. Not rendered. */\n label?: string;\n props: TabsProps;\n}\n\n// ── Component instance (Webflow-style reusable symbol) ──────────────────────────\n// References a reusable component by id. `overrides` maps a component prop key\n// (declared in the component's `props[]` allowlist) to a value, applied to the\n// component's block tree at render time. Resolved against delivered components.\n\nexport interface ComponentProps {\n componentId: string;\n overrides?: Record<string, unknown>;\n /** Phase A: the page field group this placement renders (its copy + bindings live there). */\n bind?: string;\n /**\n * Phase B: where each override's copy CAME FROM — `{ <propKey>: \"<page field path>\" }`.\n *\n * Written when a placement takes ownership of its copy (`bind` is deleted at the same moment),\n * and it is not decoration:\n * - the COVERAGE METER counts a block-lane declaration\n * (`data-bcms-block=\"<id>\"` + `data-bcms-field=\"<id>__overrides.<propKey>\"`) as bound for\n * the page path named here, so a converted page does not read as a site that lost its\n * bindings;\n * - it is how the componentize lane still recognises WHICH GROUP an instance renders once\n * `bind` is gone — without it a second run would mint a second instance for the same band.\n * A `table` prop names its repeater's path (`faq.items`); every row path under it is that one\n * declaration's, because the prop holds every row.\n */\n source?: Record<string, string>;\n}\n\nexport interface ComponentBlock {\n type: \"component\";\n id: string;\n style?: BlockStyle;\n /** Editor-facing display name for this block's dock card. Not rendered. */\n label?: string;\n props: ComponentProps;\n}\n\n// ── Collection (the entries of the page this block sits on) ─────────────────────\n//\n// LANE-AWARE, and that is the whole idea. A dynamic page's `blockJson` is BOTH what\n// `/blog` renders and the template interpolated into every `/blog/<slug>`. One array\n// cannot be an index and a post layout — unless the one block that differs between them\n// knows which lane it is in. The route supplies that (see CollectionCtx in render-page.ts):\n//\n// /blog → this block renders a card per published entry\n// /blog/my-post → this block renders THAT entry's detail; every other block in the\n// array is interpolated with {{placeholders}} exactly as before\n//\n// So no second template column, no migration, and a page without a collection block\n// behaves byte-identically to before.\n//\n// Scope is IMPLIED, never configured: a collection lists the entries of the page it sits\n// on, which is precisely the set whose detail URLs are /<thisPage>/<slug>. There is no\n// model picker because there is no other correct answer.\n\nexport interface CollectionProps {\n /** Component rendered once per entry, interpolated with {{field}} and {{url}}. Omit for a built-in card. */\n cardComponentId?: string;\n /** Component rendered for the single entry on a detail URL. Omit to fall back to the generic field layout. */\n detailComponentId?: string;\n /** Built-in card only. Defaults to \"title\" / no excerpt. */\n titleField?: string;\n excerptField?: string;\n /** Max cards to render. Defaults to 20. */\n limit?: number;\n /** \"newest\" (default) reverses the reader's created_at ordering. */\n order?: \"newest\" | \"oldest\";\n emptyText?: string;\n}\n\nexport interface CollectionBlock {\n type: \"collection\";\n id: string;\n style?: BlockStyle;\n /** Editor-facing display name for this block's dock card. Not rendered. */\n label?: string;\n props: CollectionProps;\n}\n\n// ── Union ─────────────────────────────────────────────────────────────────────\n\nexport type ContentBlock =\n | CollectionBlock\n | HeadingBlock\n | TextBlock\n | RichTextBlock\n | ImageBlock\n | ButtonBlock\n | SpacerBlock\n | ColumnsBlock\n | VideoBlock\n | FormBlock\n | SectionBlock\n | NavbarBlock\n | FooterBlock\n | SliderBlock\n | TabsBlock\n | ComponentBlock;\n\n/** Literal union of all block type discriminators. */\nexport type BlockType = ContentBlock[\"type\"];\n\n/**\n * Type guard — narrows an unknown block to `ContentBlock`.\n *\n * @example\n * const block = maybeBlock as unknown;\n * if (isBlock(block)) {\n * // block is ContentBlock here\n * }\n */\nexport function isBlock(value: unknown): value is ContentBlock {\n return (\n typeof value === \"object\" &&\n value !== null &&\n \"type\" in value &&\n typeof (value as Record<string, unknown>)[\"type\"] === \"string\"\n );\n}\n\n/**\n * Extract the `type` discriminator from a block, or `null` if not a block.\n *\n * @example\n * const block = { type: \"heading\", id: \"1\", props: { text: \"Hi\" } };\n * getBlockType(block); // \"heading\"\n * getBlockType({ not: \"a block\" }); // null\n */\nexport function getBlockType(value: unknown): BlockType | null {\n if (isBlock(value)) return value.type;\n return null;\n}\n","/**\n * The ONE declaration of which block props the Visual Editor can address.\n *\n * Four renderers stamp `data-bcms-field` — the hosted renderer, the Next SDK, the Astro SDK\n * and (for minting keys rather than markup) the dashboard's `buildBlockPageDoc`. Until this\n * file existed each carried its own hand-written list, they disagreed by two props, and the\n * dashboard's copy said so in a comment while having nothing to enforce it. A block listed in\n * one and missing from another does not error: it simply never binds, or it binds to a node\n * that resolves to no field. Both failures are silent, which is why they survived.\n *\n * This file is the declaration. The renderers remain the implementation — only they know which\n * ELEMENT carries a value — and `block-binding-coverage.test.ts` asserts the two agree.\n *\n * ── Two kinds of address, because an element is not an attribute ────────────────────────────\n *\n * `data-bcms-field` addresses ONE element. That is enough for a heading's text or an image's\n * src, and not enough for an image's `alt`: the `<img>` already carries a binding, and an\n * element cannot hold two. Entries that name an `attr` are therefore emitted on a SECOND\n * attribute, `data-bcms-props`, whose grammar is:\n *\n * <address>|<kind>|<domAttribute>[;<address>|<kind>|<domAttribute>]*\n *\n * No JSON, because the values are already constrained: an address is grammar A\n * (`[A-Za-z0-9_$-]`, `.`, `[n]`), and kinds and attributes are plain identifiers. A split on\n * two characters parses it, in any language, with no escaping.\n *\n * ── Path templates ──────────────────────────────────────────────────────────────────────────\n *\n * `[]` marks an array the renderer walks. `expandBlockBindings` substitutes real indices from a\n * block's actual props, so `links[].label` on a three-link navbar yields three concrete\n * addresses and on an empty one yields none. `parseFieldPath`/`setFieldPath` in the dashboard\n * have handled N indices since FLO-949; the cap was in what the renderer offered, not in what\n * the writer could persist.\n */\nimport type { ContentBlock, BlockType } from \"./block.js\";\n\n/**\n * How the editor paints a value, and whether it may take a caret.\n *\n * `text`/`richtext` are inline-editable. `image` selects and swaps through the media picker.\n * `url` never takes a caret — a URL typed onto the page has nowhere to report a malformed\n * value — so it is edited in the element toolbar. `array` is a repeater slot: selectable and\n * locatable, edited in the dock.\n *\n * `document` is a whole Portable Text body: selectable as ONE container, repainted whole from the\n * form, and edited per keyed block inside it. It is not a longer `richtext` — a Body stamped\n * `richtext` goes into the rich-text lane, where an opt-out rewrites the value as an `{html}`\n * envelope and the document's own block structure is destroyed.\n */\nexport type BindingKind = \"text\" | \"richtext\" | \"image\" | \"document\" | \"url\" | \"number\" | \"array\";\n\nexport interface BlockBinding {\n /** Path template in grammar A, relative to the block's `props`. `[]` = an array to walk. */\n readonly path: string;\n readonly kind: BindingKind;\n /**\n * The DOM attribute this value lives in, when it is not the element's own text or `src`.\n * Present ⇒ the renderer emits it on `data-bcms-props`, never on `data-bcms-field`.\n */\n readonly attr?: string;\n}\n\n/**\n * Props deliberately absent, and still absent for the original reason:\n *\n * `spacer.height`, `columns.gap`, `section.background` and every `style` token — design, not\n * content. They are edited in the Design accordion, where a slider can express a bounded\n * range that free typing on the page cannot.\n *\n * `text.html` when Portable Text is present — `html` is a cache derived from `content`, so\n * advertising it would persist an ignored sibling and the next frame would read as a revert.\n * The renderer suppresses it; the expander cannot see `content`, so the branch stays there.\n *\n * `component.overrides.*` — instance-scoped, so it cannot be a static template. The renderer\n * derives those addresses per instance from the definition's declared props.\n */\nexport const BLOCK_BINDINGS: Partial<Record<BlockType, readonly BlockBinding[]>> = {\n heading: [{ path: \"text\", kind: \"text\" }],\n text: [{ path: \"html\", kind: \"richtext\" }],\n richtext: [{ path: \"html\", kind: \"richtext\" }],\n image: [\n { path: \"src\", kind: \"image\" },\n { path: \"caption\", kind: \"text\" },\n { path: \"alt\", kind: \"text\", attr: \"alt\" },\n ],\n button: [\n { path: \"text\", kind: \"text\" },\n { path: \"href\", kind: \"url\", attr: \"href\" },\n ],\n video: [\n { path: \"url\", kind: \"url\", attr: \"src\" },\n { path: \"poster\", kind: \"url\", attr: \"poster\" },\n ],\n navbar: [\n { path: \"logo.src\", kind: \"image\" },\n { path: \"logo.alt\", kind: \"text\", attr: \"alt\" },\n { path: \"links[].label\", kind: \"text\" },\n { path: \"links[].href\", kind: \"url\", attr: \"href\" },\n { path: \"cta.text\", kind: \"text\" },\n { path: \"cta.href\", kind: \"url\", attr: \"href\" },\n ],\n footer: [\n { path: \"copyright\", kind: \"text\" },\n { path: \"columns[].heading\", kind: \"text\" },\n { path: \"columns[].links[].label\", kind: \"text\" },\n { path: \"columns[].links[].href\", kind: \"url\", attr: \"href\" },\n ],\n tabs: [{ path: \"tabs[].label\", kind: \"text\" }],\n};\n\n/** One concrete, writable address on one block. */\nexport interface ExpandedBinding extends BlockBinding {\n /** The template with every `[]` replaced by a real index, e.g. `links[2].href`. */\n readonly path: string;\n}\n\nconst isRecord = (v: unknown): v is Record<string, unknown> =>\n typeof v === \"object\" && v !== null && !Array.isArray(v);\n\n/**\n * Read a grammar-A path — dotted object keys and zero or more `[n]` indices.\n *\n * Positional, exactly like the dashboard's `parseFieldPath`: a dotted segment is always an\n * object key and a bracketed one always an index, so `links.0` reads the string key \"0\" and\n * misses, rather than being quietly treated as `links[0]`. Any miss returns undefined; nothing\n * here throws, because a template that does not resolve must yield no address, not an error.\n *\n * EXPORTED because a second reader of this grammar now exists: `@bettercms-ai/convert` commits a\n * build-time helper into a customer's repository, and that helper must resolve a path exactly the\n * way the editor does or a converted template renders a fallback where a value exists. The helper\n * itself carries an inlined copy (it lands in a repo where our packages do not exist) and a parity\n * test pins the copy to this original.\n */\nexport function readPath(root: unknown, path: string): unknown {\n let cursor: unknown = root;\n for (const segment of path.split(\".\")) {\n if (!segment) return undefined;\n const key = segment.replace(/\\[\\d+\\]/g, \"\");\n if (key) {\n if (!isRecord(cursor)) return undefined;\n cursor = cursor[key];\n }\n for (const index of segment.matchAll(/\\[(\\d+)\\]/g)) {\n if (!Array.isArray(cursor)) return undefined;\n cursor = cursor[Number(index[1])];\n }\n }\n return cursor;\n}\n\n/** Substitute the FIRST `[]` with every real index, then recurse for any deeper array. */\nfunction expandTemplate(binding: BlockBinding, props: unknown, path: string): ExpandedBinding[] {\n const at = path.indexOf(\"[]\");\n if (at < 0) return [{ ...binding, path }];\n\n const head = path.slice(0, at);\n const tail = path.slice(at + 2);\n const array = readPath(props, head);\n if (!Array.isArray(array)) return [];\n\n return array.flatMap((_item, index) =>\n expandTemplate(binding, props, `${head}[${index}]${tail}`),\n );\n}\n\n/**\n * Every concrete address a block actually offers right now.\n *\n * Array templates expand against the array's real length, so an address is only ever minted\n * for an element that exists. That is the load-bearing property: `setFieldPath` refuses to\n * fabricate an array member, so an address for `links[3]` on a two-link navbar would be a\n * binding the writer rejects — the \"advertises an edit that silently fails\" failure this whole\n * grammar exists to avoid.\n *\n * A prop whose KEY is absent does NOT expand, and that is not a nicety. `setFieldPath` refuses\n * to create a final key unless `createMissingObjects` is set, which only component overrides\n * pass — so an address for a key the block does not carry is a write the editor would reject.\n * An empty string still expands: `\"\"` is a value, and clearing a heading must not make it\n * uneditable.\n */\nexport function expandBlockBindings(block: ContentBlock): ExpandedBinding[] {\n const declared = BLOCK_BINDINGS[block.type];\n if (!declared) return [];\n const props = (block as { props?: unknown }).props;\n if (!isRecord(props)) return [];\n return declared\n .flatMap((binding) => expandTemplate(binding, props, binding.path))\n .filter((binding) => readPath(props, binding.path) !== undefined);\n}\n\n/** The `data-bcms-props` value for a block's attribute bindings, or \"\" when it has none. */\nexport function formatPropsAttribute(\n entries: readonly { address: string; kind: BindingKind; attr: string }[],\n): string {\n return entries.map((e) => `${e.address}|${e.kind}|${e.attr}`).join(\";\");\n}\n\n/** Parse a `data-bcms-props` value. Malformed entries are dropped, never guessed at. */\nexport function parsePropsAttribute(\n value: string | null | undefined,\n): { address: string; kind: BindingKind; attr: string }[] {\n if (!value) return [];\n return value\n .split(\";\")\n .map((entry) => entry.split(\"|\"))\n .filter((parts): parts is [string, BindingKind, string] => parts.length === 3 && parts.every(Boolean))\n .map(([address, kind, attr]) => ({ address, kind, attr }));\n}\n\n/** The shape of a declared component prop this module needs: where it points, and its key. */\ninterface PropTarget {\n key?: string;\n target?: { blockId?: string; path?: string };\n}\n\n/**\n * `<defBlockId>__<prop>` → `<instanceBlockId>__overrides.<propKey>`, for one placed component.\n *\n * Shared by every renderer, because the mapping is a property of the DEFINITION and not of any\n * one output format. A component's block ids belong to the definition and are shared by every\n * instance of it, so `<defBlockId>__text` addresses no instance's value — which is why component\n * subtrees used to render unannotated, and why the SDKs (which never had that suppression)\n * stamped definition-scoped addresses that resolve to no field and, on a component placed twice,\n * collide into a duplicate that drops BOTH copies.\n *\n * The definition already states the mapping in `props[].target`. This only re-keys that\n * statement into the address the editor writes through. Nothing is inferred: a prop with no\n * target produces no entry, so it keeps its dock control and stays uneditable on the canvas,\n * which is the truthful outcome rather than a broken one.\n */\n/**\n * The definition-scoped key a declared prop POINTS AT — `<defBlockId>__<path>`, the same\n * grammar `expandBlockBindings` produces for a block's own bindings.\n *\n * Exported so the \"which leaves does no prop reach?\" check and the address minter below read\n * the key from ONE place. They ask opposite questions of the same mapping, and two spellings\n * of `.replace(/^props\\./, \"\")` is precisely how a leaf ends up counted as bound by one and\n * unbound by the other. Null when the prop declares no target — which is the honest answer:\n * such a prop reaches nothing.\n */\nexport function componentPropTargetKey(prop: PropTarget | undefined): string | null {\n if (!prop?.key || !prop.target?.blockId) return null;\n return `${prop.target.blockId}__${String(prop.target.path ?? \"\").replace(/^props\\./, \"\")}`;\n}\n\n/**\n * `owner` is the address of the rich-text field an instance is EMBEDDED in. Its `_key` is unique\n * only within that field, so the instance is named `<owner>#<_key>` — the same grammar a\n * rich-text node's own address uses — giving `<owner>#<_key>__overrides.<propKey>`.\n */\nexport function componentInstanceAddresses(\n instanceBlockId: string,\n props: readonly PropTarget[] | undefined,\n owner?: string,\n): Map<string, string> {\n const instance = owner ? `${owner}#${instanceBlockId}` : instanceBlockId;\n const out = new Map<string, string>();\n for (const prop of props ?? []) {\n if (!prop?.key || !prop.target?.blockId) continue;\n const from = componentPropTargetKey(prop)!;\n // Two props aimed at one target would make the address ambiguous; first declaration wins\n // and the duplicate is dropped rather than silently overwriting it.\n if (!out.has(from)) out.set(from, `${instance}__overrides.${prop.key}`);\n }\n return out;\n}\n","/**\n * FLO-264 — bounded block-style tokens → CSS. Framework-agnostic (returns a plain\n * declaration object, no React types) so every renderer shares ONE mapping: the\n * headless @bettercms-ai/next adapter, @bettercms-ai/ui, and (string form) the hosted\n * render-page.ts. Unknown tokens are dropped — closed set, no arbitrary CSS.\n */\nimport type { BlockStyle } from \"./block.js\";\n\nconst SPACE_PX: Record<string, string> = { none: \"0\", xs: \"4px\", sm: \"8px\", md: \"16px\", lg: \"32px\", xl: \"64px\" };\nconst FONT_SIZE_REM: Record<string, string> = { sm: \"0.875rem\", base: \"1rem\", lg: \"1.25rem\", xl: \"1.5rem\", \"2xl\": \"2rem\" };\nconst WEIGHT: Record<string, number> = { normal: 400, medium: 500, semibold: 600, bold: 700 };\nconst RADIUS_PX: Record<string, string> = { none: \"0\", sm: \"4px\", md: \"8px\", lg: \"16px\", full: \"9999px\" };\nconst COLOR_HEX: Record<string, string> = { white: \"#ffffff\", black: \"#111111\", muted: \"#6b7280\", mutedBg: \"#f3f4f6\", primary: \"#111111\", accent: \"#4f46e5\" };\n\n/** A CSS declaration object (key → value) usable as a React `style` prop, or undefined when empty. */\nexport function blockStyleToCss(style: BlockStyle | undefined): Record<string, string | number> | undefined {\n if (!style || typeof style !== \"object\") return undefined;\n const s = style as Record<string, string>;\n const css: Record<string, string | number> = {};\n if (s.paddingY && SPACE_PX[s.paddingY] != null) { css.paddingTop = SPACE_PX[s.paddingY]!; css.paddingBottom = SPACE_PX[s.paddingY]!; }\n if (s.paddingX && SPACE_PX[s.paddingX] != null) { css.paddingLeft = SPACE_PX[s.paddingX]!; css.paddingRight = SPACE_PX[s.paddingX]!; }\n if (s.marginTop && SPACE_PX[s.marginTop] != null) css.marginTop = SPACE_PX[s.marginTop]!;\n if (s.marginBottom && SPACE_PX[s.marginBottom] != null) css.marginBottom = SPACE_PX[s.marginBottom]!;\n if (s.background && COLOR_HEX[s.background]) css.background = COLOR_HEX[s.background]!;\n if (s.textColor && COLOR_HEX[s.textColor]) css.color = COLOR_HEX[s.textColor]!;\n if (s.align === \"left\" || s.align === \"center\" || s.align === \"right\") css.textAlign = s.align;\n if (s.fontSize && FONT_SIZE_REM[s.fontSize]) css.fontSize = FONT_SIZE_REM[s.fontSize]!;\n if (s.weight && WEIGHT[s.weight] != null) css.fontWeight = WEIGHT[s.weight]!;\n if (s.radius && RADIUS_PX[s.radius] != null) css.borderRadius = RADIUS_PX[s.radius]!;\n if ((style as BlockStyle).border === true) css.border = \"1px solid currentColor\";\n return Object.keys(css).length ? css : undefined;\n}\n","/**\n * Component — a reusable, Webflow-style block tree (a \"symbol\").\n *\n * A component is authored once and placed across pages via `component` blocks\n * (see `ComponentBlock` in `./block.ts`). Its definition lives in `blockJson`;\n * `props` declares a flat allowlist of values an instance may override.\n */\nimport type { ContentBlock } from \"./block.js\";\nimport type { ContentModelFieldUi } from \"./content-model.js\";\nimport type { VariantInputMapping } from \"./layout.js\";\n\n/**\n * The category a component belongs to (drives library grouping + icons). The first eight\n * are structural (what the component IS); the last four are the \"Add a section\" library\n * tabs (where it appears). One varchar column, not a PG enum — widening is code-only.\n */\n/**\n * 🔴 THE STRUCTURE DOCTRINE — one sentence, one home, spliced into every surface that builds a page.\n *\n * It lives HERE, beside the component contract it describes, because there are THREE places that teach\n * an agent how to build a page and they drifted apart:\n * • `packages/mcp/src/tools.ts` — the MCP tool descriptions (external agents)\n * • `src/lib/ai/agent.ts` — the in-product Studio Agent's system prompt\n * • `packages/mcp/src/prompts.ts` — the authoring playbook, which a tool call does not carry\n *\n * Only the playbook explained sections. `create_page` taught the SCHEMA axis in detail (\"each visual\n * section becomes a nested field\") and said nothing about STRUCTURE; the Studio Agent's prompt named\n * \"pages & reusable components (structure/layout)\" without ever mentioning `sectionType`.\n *\n * Measured consequence, production 2026-08-18: project `acme` has three components, ALL with\n * `section_type = (none)`, and its home page is 18 loose top-level blocks with ZERO sections. Every\n * generated page came out flat, so the visual editor's section lane — outline, name, move, duplicate,\n * delete, variant swap — had nothing to attach to. The editor was faithfully showing pages that were\n * never built out of sections.\n *\n * A constant rather than three paraphrases, because updating some of them is exactly how this happened.\n */\nexport const SECTION_DOCTRINE =\n \"STRUCTURE (separate from schema): a page is composed of SECTIONS. NEVER build a page out of loose top-level heading/text/image/button/spacer blocks — they cannot be moved, duplicated or swapped as a unit, the visual editor cannot outline or name them, and every one of them becomes its own section in the editor. A hero of a headline, a lede and two CTAs is ONE section, not four. TWO SHAPES, and the choice is about REUSE. (1) A band that appears on more than one page, or that needs layout variants, is a COMPONENT with a `sectionType` — see create_component. Components sharing a `sectionType` are that section's VARIANTS (one Hero: 'Centered' for the home page and 'Two-column' for about, same prop keys so a swap keeps the content). This is also the only shape the editor's 'Add a section' picker can insert, and the only one that gets a family name and a variant switcher. (2) A genuinely one-off band on a single page is a `section` BLOCK whose `props.children` hold its blocks. THE TRADEOFF, stated in the present tense because it is real today: inside a component, ONLY the leaves a declared prop TARGETS are click-to-edit on the canvas — each declared prop's `target` is re-keyed to that PLACEMENT's own override address, so editing it changes this page and not the shared definition. A prop with no `target` still SHOWS as a dock control, but its override reaches no rendered slot, so editing it changes nothing on the page. Copy that no prop points at is worse still: no binding and no control, unreachable from click-to-edit AND from the dock, changeable only by editing the component definition, which rewrites every page that places it. A `section` block's children stay click-to-edit unconditionally. So when you choose a component, DECLARE A PROP — WITH A `target` — for every string, link and image a marketer will ever touch; a component with un-propped editable copy is the defect, not the component. In the dock an unset prop shows EMPTY and inherits the definition's default, so set props explicitly when you want the current copy visible there. Do not hand-write a band's JSON: start from a built-in section blueprint (list_components returns locked `builtin:*` blueprints with no projectId — hero-centered, hero-split, feature-grid-three, cta-banner and nine more), each already rooted in a `section` block with its editable leaves declared as props. INLINE its blockJson as a `section` block for a one-off band; for a recurring band, materialize the blueprint with create_component so it becomes project-scoped before implementation validation, Output or publication. Direct `builtin:*` component references exist only for legacy delivery compatibility. Two consecutive call-to-action buttons are two sibling `button` blocks inside the same section — never a `columns` block, which is a `repeat(N,1fr)` grid and would stretch each CTA to half the container. Buttons are inline-level and flow side by side on their own.\";\n\nexport type ComponentCategory =\n | \"navbar\"\n | \"footer\"\n | \"button\"\n | \"section\"\n | \"slider\"\n | \"tabs\"\n | \"form\"\n | \"custom\"\n | \"hero\"\n | \"content\"\n | \"social-proof\"\n | \"conversion\";\n\n/**\n * A single overridable field on a component. `target` points at the block + JSON\n * path inside `blockJson` the override writes to (e.g. blockId \"cta\", path\n * \"props.text\"). Keeping overrides a declared allowlist (not arbitrary nested\n * rewrites) keeps instance data small and the contract explicit.\n */\n/**\n * THE prop vocabulary. One list, imported everywhere a prop type is enumerated.\n *\n * It exists as a value (not just a union) because four places used to spell it out by hand —\n * this file, the Drizzle schema, `COMPONENT_PROP_TYPES` in the backend's Zod schemas, and the\n * MCP tool shape — and the MCP copy is the dangerous one: `update_component` REPLACES the whole\n * `props` array, so a type its enum omits cannot be echoed back, and an agent that reads a\n * component and writes it straight back DESTROYS every prop of that type with a 200.\n *\n * Order is not semantic; append rather than re-sort, so a diff stays readable.\n */\nexport const COMPONENT_PROP_TYPES = [\n \"text\",\n \"richtext\",\n \"image\",\n \"url\",\n \"boolean\",\n \"number\",\n \"select\",\n \"group\",\n \"table\",\n \"slot\",\n \"form\",\n] as const;\n\nexport type ComponentPropType = (typeof COMPONENT_PROP_TYPES)[number];\n\n/**\n * The value a `form` prop STORES: just the id. The form itself is a Form document and stays the\n * single source of truth for its fields — a component references one, it never re-declares it.\n *\n * `.strict()` at the write boundary, so a client that POSTs a hydrated form object alongside the\n * id gets a 400 rather than a silent strip.\n *\n * There is deliberately NO resolved twin of this shape. Every renderer already receives forms the\n * same way — a catalogue beside the blocks (`BcmsBlocks({blocks, forms})`, the site renderer's\n * forms map) — and looks the id up in it. A hydrated `{formId, form}` prop value would be a shape\n * that exists nowhere in delivery.\n */\nexport interface ComponentFormPropRef {\n formId: string;\n}\n\nexport interface ComponentPropDef {\n key: string;\n label: string;\n target: { blockId: string; path: string };\n /**\n * `slot` holds ONE nested component instance — the component-level twin of the\n * content-model field type `component-ref` (see content-model.ts), named differently for\n * the same reason that one is: `component` already means a BLOCK type. Its value is\n * `{ componentId, overrides }` and its `target.path` is `props`, so filling a slot writes\n * that object over an empty `component` block's props.\n *\n * On a PAGE a slot fill is a LIVE reference; a published ENTRY freezes it (resolveDeep).\n */\n /**\n * The EDITOR contract, not a storage one: `applyOverrides` writes the value at\n * `target.path` whatever its shape, so `type` decides which control the inspector renders\n * and what shape that control produces (FLO-1020).\n *\n * number → a number (heading.level, columns.count)\n * select → one string from `config.options`\n * group → an object keyed by `config.fields`\n * table → an array of such objects (slider.slides)\n *\n * `reference` is absent on purpose: nothing resolves a content-entry id at component render\n * time, so such a prop would save cleanly and render as nothing.\n */\n type: ComponentPropType;\n defaultValue?: unknown;\n /**\n * EDITOR HINTS (playbook §12). Stored in the props JSON, so no migration.\n *\n * 🔴 `required` IS NOT ENFORCED AT WRITE TIME, deliberately. Nothing on the write path\n * refuses an override that omits a required prop — a placement saves either way — because\n * the alternative is a component definition that can retroactively make already-saved pages\n * unsaveable. It is a marker the dashboard renders and `get_site_composition` counts, which\n * is the honest shape: the receipt names what is missing instead of the write refusing it.\n */\n required?: boolean;\n /** Hint shown under the control, muted. */\n helpText?: string;\n /** Ghost text inside a text-ish control. */\n placeholder?: string;\n /** Per-type settings; the save schema enforces that each is present on the type needing it. */\n config?: {\n /** `slot` — a pick allowlist. */\n componentIds?: string[];\n /**\n * `select` — the choices. Required, and a default must be one of them. `{ label, value }`\n * when the stored value is not what an author should read (a component id, for instance).\n */\n options?: Array<string | { label: string; value: string }>;\n /** `group` / `table` — the sub-shape, nestable to 3 levels. */\n fields?: ComponentSubField[];\n /** `number` — bounds for the control. */\n min?: number;\n max?: number;\n step?: number;\n } & Record<string, unknown>;\n /**\n * AUTHORING CHROME — the same object a content-model FIELD carries ({@link ContentModelFieldUi}),\n * deliberately: an agent that has learned `ui` once has learned it on both lanes.\n *\n * A SIBLING of `config`, not a member of it. `config` is a loose bag, so a `config.ui` already\n * survived the write — and that is the problem this key fixes: surviving is not declared, and\n * an undeclared prop is a typo that saves cleanly and renders as nothing.\n *\n * WHERE EACH KEY IS LEGAL differs from the field lane, because the vocabulary does:\n * `preview`/`layout` on `group`, `table` and `slot`; `reorderable` on `table` ALONE, the only\n * prop type whose value is a list. The save schema refuses the rest with the valid set named.\n */\n ui?: ContentModelFieldUi;\n}\n\n/** One field inside a `group` prop or a `table` row. Recursive, capped at 3 levels deep. */\nexport interface ComponentSubField {\n key: string;\n label: string;\n /** No `slot`: a nested component instance belongs on the prop itself, not inside a row. */\n // `slot` and `form` are reference-shaped props: they belong ON a prop, never inside a row of\n // one. A form in a table row would mean N form documents per component with no way to author\n // them — the second field model this design exists to avoid.\n type: Exclude<ComponentPropDef[\"type\"], \"slot\" | \"form\">;\n defaultValue?: unknown;\n /** The same editor hints as the prop above, one level down. @see ComponentPropDef */\n required?: boolean;\n helpText?: string;\n placeholder?: string;\n options?: string[];\n /** CANONICAL. A nested `group`/`table`'s own sub-shape. */\n fields?: ComponentSubField[];\n /**\n * A READ-ONLY MIRROR of `options`/`fields`, in the shape `ComponentPropDef` puts them in.\n *\n * 🔴 WHY A SECOND COPY EXISTS AT ALL. A `group`/`table` PROP declares its sub-shape under\n * `config.fields`; a sub-field of one declares its own under a bare `fields`. So a consumer\n * walking a nested table has to switch shape after the first level, and the componentize lane's\n * repo half (`@bettercms-ai/convert --componentize`) walks exactly that — it reads one node\n * shape at every depth. Mirroring the sub-shape here lets it, without the CMS having to\n * describe a nested table differently from a top-level one.\n *\n * `fields` is the authority. The save schema REFUSES a node whose mirror disagrees with it\n * (`componentPropDefSchema`), because two copies that may drift are worse than one awkward\n * shape — an editor that rewrote `fields` alone would leave a stale row description behind.\n */\n config?: { fields?: ComponentSubField[]; options?: string[] } & Record<string, unknown>;\n}\n\n/** The value a `slot` prop holds — the draft half of a `component-ref`, deliberately. */\nexport interface SlotValue {\n componentId: string;\n overrides?: Record<string, unknown>;\n}\n\n/**\n * A component is a DRAFT until published; only the published copy reaches a visitor.\n * Mirrors pages and entries. See migration 0186_component_draft_live_split.sql.\n */\nexport type ComponentStatus = \"draft\" | \"published\";\n\n/**\n * Archive state (FLO-1012), deliberately SEPARATE from `ComponentStatus`.\n *\n * Archive takes a component out of the working set — hidden from the components list by\n * default, not offered in the visual editor's insert surfaces — while every existing usage\n * keeps serving. It is not unpublish (which pulls the live copy and re-bakes every page that\n * embeds it) and it is not delete.\n *\n * It is a timestamp rather than a third `status` value because a component can be published\n * AND archived; collapsing the two would lose the bit restore has to put back.\n */\n\nexport interface Component {\n id: string;\n workspaceId: string;\n projectId?: string | null;\n name: string;\n slug: string;\n category: ComponentCategory;\n /**\n * Section library: the family this component is a LAYOUT of, e.g. \"Hero\". `name` is the\n * layout label (\"Centered\"), so components sharing a sectionType are selectable variants\n * of one section. Null/absent = an ordinary component, not shown in the section library.\n */\n sectionType?: string | null;\n /** First-class variant family membership; exact workspace/project scope is enforced in DB. */\n variantGroupId?: string | null;\n variantInputMappings?: VariantInputMapping[];\n /** Placement governance: `*`, `slug:<page-slug>`, and/or `type:<page-type>`. */\n allowedOn: string[];\n description?: string | null;\n /** The DRAFT definition. Every builder/autosave/import write path targets these two. */\n blockJson: ContentBlock[];\n props: ComponentPropDef[];\n status: ComponentStatus;\n /** When it left the working set, or null/absent while active. @see ComponentStatus */\n archivedAt?: string | Date | null;\n /** Derived from `archivedAt`, so a client never has to know the column. */\n archived?: boolean;\n /**\n * The LIVE snapshot get_components_by_handle() serves. Null until the first publish.\n * Returned by GET-one (the Compare view needs it), omitted from list rows for payload.\n */\n publishedBlockJson?: ContentBlock[] | null;\n publishedProps?: ComponentPropDef[] | null;\n publishedAt?: string | null; // ISO 8601\n /**\n * Computed in SQL on list/get, never stored:\n * status='published' AND (blockJson or props has diverged from its published copy).\n * An exact jsonb compare, so it self-clears when an edit is reverted.\n */\n pendingChanges?: boolean;\n thumbnail?: string | null;\n createdAt: string; // ISO 8601\n updatedAt: string; // ISO 8601\n}\n\n/**\n * Public/delivery projection — the fields a renderer needs to resolve instances.\n *\n * DELIBERATELY UNCHANGED by the 0186 draft/live split: delivery aliases\n * publishedBlockJson -> blockJson, so every already-deployed site and every\n * bcms-content.json on disk keeps a byte-identical wire shape. Do not add `status` here —\n * delivery only ever returns published rows, so it would always be the same constant.\n */\nexport interface DeliveryComponent {\n id: string;\n name: string;\n slug: string;\n category: ComponentCategory;\n sectionType?: string | null;\n blockJson: ContentBlock[];\n props: ComponentPropDef[];\n}\n","/**\n * Generated from lucide-react@1.8.0 dynamic icon names.\n * Legacy CamelCase identifiers remain valid for existing Layout documents.\n */\nexport const LAYOUT_SECTION_ICONS: readonly string[] = Object.freeze([\n \"LayoutPanelTop\",\n \"PanelTop\",\n \"PanelBottom\",\n \"Menu\",\n \"Navigation\",\n \"Megaphone\",\n \"GalleryHorizontal\",\n \"Rows3\",\n \"Grid2X2\",\n \"FileText\",\n \"Link\",\n \"Contact\",\n \"BadgeInfo\",\n \"Sparkles\",\n \"a-arrow-down\",\n \"a-arrow-up\",\n \"a-large-small\",\n \"accessibility\",\n \"activity\",\n \"air-vent\",\n \"airplay\",\n \"alarm-clock-check\",\n \"alarm-check\",\n \"alarm-clock-minus\",\n \"alarm-minus\",\n \"alarm-clock-off\",\n \"alarm-clock-plus\",\n \"alarm-plus\",\n \"alarm-clock\",\n \"alarm-smoke\",\n \"album\",\n \"align-center-horizontal\",\n \"align-center-vertical\",\n \"align-end-horizontal\",\n \"align-end-vertical\",\n \"align-horizontal-distribute-center\",\n \"align-horizontal-distribute-end\",\n \"align-horizontal-distribute-start\",\n \"align-horizontal-justify-center\",\n \"align-horizontal-justify-end\",\n \"align-horizontal-justify-start\",\n \"align-horizontal-space-around\",\n \"align-horizontal-space-between\",\n \"align-start-horizontal\",\n \"align-start-vertical\",\n \"align-vertical-distribute-center\",\n \"align-vertical-distribute-end\",\n \"align-vertical-distribute-start\",\n \"align-vertical-justify-center\",\n \"align-vertical-justify-end\",\n \"align-vertical-justify-start\",\n \"align-vertical-space-around\",\n \"align-vertical-space-between\",\n \"ambulance\",\n \"ampersand\",\n \"ampersands\",\n \"amphora\",\n \"anchor\",\n \"angry\",\n \"annoyed\",\n \"antenna\",\n \"anvil\",\n \"aperture\",\n \"app-window-mac\",\n \"app-window\",\n \"apple\",\n \"archive-restore\",\n \"archive-x\",\n \"archive\",\n \"armchair\",\n \"arrow-big-down-dash\",\n \"arrow-big-down\",\n \"arrow-big-left-dash\",\n \"arrow-big-left\",\n \"arrow-big-right-dash\",\n \"arrow-big-right\",\n \"arrow-big-up-dash\",\n \"arrow-big-up\",\n \"arrow-down-0-1\",\n \"arrow-down-01\",\n \"arrow-down-1-0\",\n \"arrow-down-10\",\n \"arrow-down-a-z\",\n \"arrow-down-az\",\n \"arrow-down-from-line\",\n \"arrow-down-left\",\n \"arrow-down-narrow-wide\",\n \"arrow-down-right\",\n \"arrow-down-to-dot\",\n \"arrow-down-to-line\",\n \"arrow-down-up\",\n \"arrow-down-wide-narrow\",\n \"sort-desc\",\n \"arrow-down-z-a\",\n \"arrow-down-za\",\n \"arrow-down\",\n \"arrow-left-from-line\",\n \"arrow-left-right\",\n \"arrow-left-to-line\",\n \"arrow-left\",\n \"arrow-right-from-line\",\n \"arrow-right-left\",\n \"arrow-right-to-line\",\n \"arrow-right\",\n \"arrow-up-0-1\",\n \"arrow-up-01\",\n \"arrow-up-1-0\",\n \"arrow-up-10\",\n \"arrow-up-a-z\",\n \"arrow-up-az\",\n \"arrow-up-down\",\n \"arrow-up-from-dot\",\n \"arrow-up-from-line\",\n \"arrow-up-left\",\n \"arrow-up-narrow-wide\",\n \"sort-asc\",\n \"arrow-up-right\",\n \"arrow-up-to-line\",\n \"arrow-up-wide-narrow\",\n \"arrow-up-z-a\",\n \"arrow-up-za\",\n \"arrow-up\",\n \"arrows-up-from-line\",\n \"asterisk\",\n \"at-sign\",\n \"atom\",\n \"audio-lines\",\n \"audio-waveform\",\n \"award\",\n \"axe\",\n \"axis-3d\",\n \"axis-3-d\",\n \"baby\",\n \"backpack\",\n \"badge-alert\",\n \"badge-cent\",\n \"badge-check\",\n \"verified\",\n \"badge-dollar-sign\",\n \"badge-euro\",\n \"badge-indian-rupee\",\n \"badge-info\",\n \"badge-japanese-yen\",\n \"badge-minus\",\n \"badge-percent\",\n \"badge-plus\",\n \"badge-pound-sterling\",\n \"badge-question-mark\",\n \"badge-help\",\n \"badge-russian-ruble\",\n \"badge-swiss-franc\",\n \"badge-turkish-lira\",\n \"badge-x\",\n \"badge\",\n \"baggage-claim\",\n \"balloon\",\n \"ban\",\n \"banana\",\n \"bandage\",\n \"banknote-arrow-down\",\n \"banknote-arrow-up\",\n \"banknote-x\",\n \"banknote\",\n \"barcode\",\n \"barrel\",\n \"baseline\",\n \"bath\",\n \"battery-charging\",\n \"battery-full\",\n \"battery-low\",\n \"battery-medium\",\n \"battery-plus\",\n \"battery-warning\",\n \"battery\",\n \"beaker\",\n \"bean-off\",\n \"bean\",\n \"bed-double\",\n \"bed-single\",\n \"bed\",\n \"beef-off\",\n \"beef\",\n \"beer-off\",\n \"beer\",\n \"bell-dot\",\n \"bell-electric\",\n \"bell-minus\",\n \"bell-off\",\n \"bell-plus\",\n \"bell-ring\",\n \"bell\",\n \"between-horizontal-end\",\n \"between-horizonal-end\",\n \"between-horizontal-start\",\n \"between-horizonal-start\",\n \"between-vertical-end\",\n \"between-vertical-start\",\n \"biceps-flexed\",\n \"bike\",\n \"binary\",\n \"binoculars\",\n \"biohazard\",\n \"bird\",\n \"birdhouse\",\n \"bitcoin\",\n \"blend\",\n \"blinds\",\n \"blocks\",\n \"bluetooth-connected\",\n \"bluetooth-off\",\n \"bluetooth-searching\",\n \"bluetooth\",\n \"bold\",\n \"bolt\",\n \"bomb\",\n \"bone\",\n \"book-a\",\n \"book-alert\",\n \"book-audio\",\n \"book-check\",\n \"book-copy\",\n \"book-dashed\",\n \"book-template\",\n \"book-down\",\n \"book-headphones\",\n \"book-heart\",\n \"book-image\",\n \"book-key\",\n \"book-lock\",\n \"book-marked\",\n \"book-minus\",\n \"book-open-check\",\n \"book-open-text\",\n \"book-open\",\n \"book-plus\",\n \"book-search\",\n \"book-text\",\n \"book-type\",\n \"book-up-2\",\n \"book-up\",\n \"book-user\",\n \"book-x\",\n \"book\",\n \"bookmark-check\",\n \"bookmark-minus\",\n \"bookmark-off\",\n \"bookmark-plus\",\n \"bookmark-x\",\n \"bookmark\",\n \"boom-box\",\n \"bot-message-square\",\n \"bot-off\",\n \"bot\",\n \"bottle-wine\",\n \"bow-arrow\",\n \"box\",\n \"boxes\",\n \"braces\",\n \"curly-braces\",\n \"brackets\",\n \"brain-circuit\",\n \"brain-cog\",\n \"brain\",\n \"brick-wall-fire\",\n \"brick-wall-shield\",\n \"brick-wall\",\n \"briefcase-business\",\n \"briefcase-conveyor-belt\",\n \"briefcase-medical\",\n \"briefcase\",\n \"bring-to-front\",\n \"brush-cleaning\",\n \"brush\",\n \"bubbles\",\n \"bug-off\",\n \"bug-play\",\n \"bug\",\n \"building-2\",\n \"building\",\n \"bus-front\",\n \"bus\",\n \"cable-car\",\n \"cable\",\n \"cake-slice\",\n \"cake\",\n \"calculator\",\n \"calendar-1\",\n \"calendar-arrow-down\",\n \"calendar-arrow-up\",\n \"calendar-check-2\",\n \"calendar-check\",\n \"calendar-clock\",\n \"calendar-cog\",\n \"calendar-days\",\n \"calendar-fold\",\n \"calendar-heart\",\n \"calendar-minus-2\",\n \"calendar-minus\",\n \"calendar-off\",\n \"calendar-plus-2\",\n \"calendar-plus\",\n \"calendar-range\",\n \"calendar-search\",\n \"calendar-sync\",\n \"calendar-x-2\",\n \"calendar-x\",\n \"calendar\",\n \"calendars\",\n \"camera-off\",\n \"camera\",\n \"candy-cane\",\n \"candy-off\",\n \"candy\",\n \"cannabis-off\",\n \"cannabis\",\n \"captions-off\",\n \"captions\",\n \"subtitles\",\n \"car-front\",\n \"car-taxi-front\",\n \"car\",\n \"caravan\",\n \"card-sim\",\n \"carrot\",\n \"case-lower\",\n \"case-sensitive\",\n \"case-upper\",\n \"cassette-tape\",\n \"cast\",\n \"castle\",\n \"cat\",\n \"cctv-off\",\n \"cctv\",\n \"chart-area\",\n \"area-chart\",\n \"chart-bar-big\",\n \"bar-chart-horizontal-big\",\n \"chart-bar-decreasing\",\n \"chart-bar-increasing\",\n \"chart-bar-stacked\",\n \"chart-bar\",\n \"bar-chart-horizontal\",\n \"chart-candlestick\",\n \"candlestick-chart\",\n \"chart-column-big\",\n \"bar-chart-big\",\n \"chart-column-decreasing\",\n \"chart-column-increasing\",\n \"bar-chart-4\",\n \"chart-column-stacked\",\n \"chart-column\",\n \"bar-chart-3\",\n \"chart-gantt\",\n \"chart-line\",\n \"line-chart\",\n \"chart-network\",\n \"chart-no-axes-column-decreasing\",\n \"chart-no-axes-column-increasing\",\n \"bar-chart\",\n \"chart-no-axes-column\",\n \"bar-chart-2\",\n \"chart-no-axes-combined\",\n \"chart-no-axes-gantt\",\n \"gantt-chart\",\n \"chart-pie\",\n \"pie-chart\",\n \"chart-scatter\",\n \"scatter-chart\",\n \"chart-spline\",\n \"check-check\",\n \"check-line\",\n \"check\",\n \"chef-hat\",\n \"cherry\",\n \"chess-bishop\",\n \"chess-king\",\n \"chess-knight\",\n \"chess-pawn\",\n \"chess-queen\",\n \"chess-rook\",\n \"chevron-down\",\n \"chevron-first\",\n \"chevron-last\",\n \"chevron-left\",\n \"chevron-right\",\n \"chevron-up\",\n \"chevrons-down-up\",\n \"chevrons-down\",\n \"chevrons-left-right-ellipsis\",\n \"chevrons-left-right\",\n \"chevrons-left\",\n \"chevrons-right-left\",\n \"chevrons-right\",\n \"chevrons-up-down\",\n \"chevrons-up\",\n \"church\",\n \"cigarette-off\",\n \"cigarette\",\n \"circle-alert\",\n \"alert-circle\",\n \"circle-arrow-down\",\n \"arrow-down-circle\",\n \"circle-arrow-left\",\n \"arrow-left-circle\",\n \"circle-arrow-out-down-left\",\n \"arrow-down-left-from-circle\",\n \"circle-arrow-out-down-right\",\n \"arrow-down-right-from-circle\",\n \"circle-arrow-out-up-left\",\n \"arrow-up-left-from-circle\",\n \"circle-arrow-out-up-right\",\n \"arrow-up-right-from-circle\",\n \"circle-arrow-right\",\n \"arrow-right-circle\",\n \"circle-arrow-up\",\n \"arrow-up-circle\",\n \"circle-check-big\",\n \"check-circle\",\n \"circle-check\",\n \"check-circle-2\",\n \"circle-chevron-down\",\n \"chevron-down-circle\",\n \"circle-chevron-left\",\n \"chevron-left-circle\",\n \"circle-chevron-right\",\n \"chevron-right-circle\",\n \"circle-chevron-up\",\n \"chevron-up-circle\",\n \"circle-dashed\",\n \"circle-divide\",\n \"divide-circle\",\n \"circle-dollar-sign\",\n \"circle-dot-dashed\",\n \"circle-dot\",\n \"circle-ellipsis\",\n \"circle-equal\",\n \"circle-fading-arrow-up\",\n \"circle-fading-plus\",\n \"circle-gauge\",\n \"gauge-circle\",\n \"circle-minus\",\n \"minus-circle\",\n \"circle-off\",\n \"circle-parking-off\",\n \"parking-circle-off\",\n \"circle-parking\",\n \"parking-circle\",\n \"circle-pause\",\n \"pause-circle\",\n \"circle-percent\",\n \"percent-circle\",\n \"circle-pile\",\n \"circle-play\",\n \"play-circle\",\n \"circle-plus\",\n \"plus-circle\",\n \"circle-pound-sterling\",\n \"circle-power\",\n \"power-circle\",\n \"circle-question-mark\",\n \"help-circle\",\n \"circle-help\",\n \"circle-slash-2\",\n \"circle-slashed\",\n \"circle-slash\",\n \"circle-small\",\n \"circle-star\",\n \"circle-stop\",\n \"stop-circle\",\n \"circle-user-round\",\n \"user-circle-2\",\n \"circle-user\",\n \"user-circle\",\n \"circle-x\",\n \"x-circle\",\n \"circle\",\n \"circuit-board\",\n \"citrus\",\n \"clapperboard\",\n \"clipboard-check\",\n \"clipboard-clock\",\n \"clipboard-copy\",\n \"clipboard-list\",\n \"clipboard-minus\",\n \"clipboard-paste\",\n \"clipboard-pen-line\",\n \"clipboard-signature\",\n \"clipboard-pen\",\n \"clipboard-edit\",\n \"clipboard-plus\",\n \"clipboard-type\",\n \"clipboard-x\",\n \"clipboard\",\n \"clock-1\",\n \"clock-10\",\n \"clock-11\",\n \"clock-12\",\n \"clock-2\",\n \"clock-3\",\n \"clock-4\",\n \"clock-5\",\n \"clock-6\",\n \"clock-7\",\n \"clock-8\",\n \"clock-9\",\n \"clock-alert\",\n \"clock-arrow-down\",\n \"clock-arrow-up\",\n \"clock-check\",\n \"clock-fading\",\n \"clock-plus\",\n \"clock\",\n \"closed-caption\",\n \"cloud-alert\",\n \"cloud-backup\",\n \"cloud-check\",\n \"cloud-cog\",\n \"cloud-download\",\n \"download-cloud\",\n \"cloud-drizzle\",\n \"cloud-fog\",\n \"cloud-hail\",\n \"cloud-lightning\",\n \"cloud-moon-rain\",\n \"cloud-moon\",\n \"cloud-off\",\n \"cloud-rain-wind\",\n \"cloud-rain\",\n \"cloud-snow\",\n \"cloud-sun-rain\",\n \"cloud-sun\",\n \"cloud-sync\",\n \"cloud-upload\",\n \"upload-cloud\",\n \"cloud\",\n \"cloudy\",\n \"clover\",\n \"club\",\n \"code-xml\",\n \"code-2\",\n \"code\",\n \"coffee\",\n \"cog\",\n \"coins\",\n \"columns-2\",\n \"columns\",\n \"columns-3-cog\",\n \"columns-settings\",\n \"table-config\",\n \"columns-3\",\n \"panels-left-right\",\n \"columns-4\",\n \"combine\",\n \"command\",\n \"compass\",\n \"component\",\n \"computer\",\n \"concierge-bell\",\n \"cone\",\n \"construction\",\n \"contact-round\",\n \"contact-2\",\n \"contact\",\n \"container\",\n \"contrast\",\n \"cookie\",\n \"cooking-pot\",\n \"copy-check\",\n \"copy-minus\",\n \"copy-plus\",\n \"copy-slash\",\n \"copy-x\",\n \"copy\",\n \"copyleft\",\n \"copyright\",\n \"corner-down-left\",\n \"corner-down-right\",\n \"corner-left-down\",\n \"corner-left-up\",\n \"corner-right-down\",\n \"corner-right-up\",\n \"corner-up-left\",\n \"corner-up-right\",\n \"cpu\",\n \"creative-commons\",\n \"credit-card\",\n \"croissant\",\n \"crop\",\n \"cross\",\n \"crosshair\",\n \"crown\",\n \"cuboid\",\n \"cup-soda\",\n \"currency\",\n \"cylinder\",\n \"dam\",\n \"database-backup\",\n \"database-search\",\n \"database-zap\",\n \"database\",\n \"decimals-arrow-left\",\n \"decimals-arrow-right\",\n \"delete\",\n \"dessert\",\n \"diameter\",\n \"diamond-minus\",\n \"diamond-percent\",\n \"percent-diamond\",\n \"diamond-plus\",\n \"diamond\",\n \"dice-1\",\n \"dice-2\",\n \"dice-3\",\n \"dice-4\",\n \"dice-5\",\n \"dice-6\",\n \"dices\",\n \"diff\",\n \"disc-2\",\n \"disc-3\",\n \"disc-album\",\n \"disc\",\n \"divide\",\n \"dna-off\",\n \"dna\",\n \"dock\",\n \"dog\",\n \"dollar-sign\",\n \"donut\",\n \"door-closed-locked\",\n \"door-closed\",\n \"door-open\",\n \"dot\",\n \"download\",\n \"drafting-compass\",\n \"drama\",\n \"drill\",\n \"drone\",\n \"droplet-off\",\n \"droplet\",\n \"droplets\",\n \"drum\",\n \"drumstick\",\n \"dumbbell\",\n \"ear-off\",\n \"ear\",\n \"earth-lock\",\n \"earth\",\n \"globe-2\",\n \"eclipse\",\n \"egg-fried\",\n \"egg-off\",\n \"egg\",\n \"ellipse\",\n \"ellipsis-vertical\",\n \"more-vertical\",\n \"ellipsis\",\n \"more-horizontal\",\n \"equal-approximately\",\n \"equal-not\",\n \"equal\",\n \"eraser\",\n \"ethernet-port\",\n \"euro\",\n \"ev-charger\",\n \"expand\",\n \"external-link\",\n \"eye-closed\",\n \"eye-off\",\n \"eye\",\n \"factory\",\n \"fan\",\n \"fast-forward\",\n \"feather\",\n \"fence\",\n \"ferris-wheel\",\n \"file-archive\",\n \"file-axis-3d\",\n \"file-axis-3-d\",\n \"file-badge\",\n \"file-badge-2\",\n \"file-box\",\n \"file-braces-corner\",\n \"file-json-2\",\n \"file-braces\",\n \"file-json\",\n \"file-chart-column-increasing\",\n \"file-bar-chart\",\n \"file-chart-column\",\n \"file-bar-chart-2\",\n \"file-chart-line\",\n \"file-line-chart\",\n \"file-chart-pie\",\n \"file-pie-chart\",\n \"file-check-corner\",\n \"file-check-2\",\n \"file-check\",\n \"file-clock\",\n \"file-code-corner\",\n \"file-code-2\",\n \"file-code\",\n \"file-cog\",\n \"file-cog-2\",\n \"file-diff\",\n \"file-digit\",\n \"file-down\",\n \"file-exclamation-point\",\n \"file-warning\",\n \"file-headphone\",\n \"file-audio\",\n \"file-audio-2\",\n \"file-heart\",\n \"file-image\",\n \"file-input\",\n \"file-key\",\n \"file-key-2\",\n \"file-lock\",\n \"file-lock-2\",\n \"file-minus-corner\",\n \"file-minus-2\",\n \"file-minus\",\n \"file-music\",\n \"file-output\",\n \"file-pen-line\",\n \"file-signature\",\n \"file-pen\",\n \"file-edit\",\n \"file-play\",\n \"file-video\",\n \"file-plus-corner\",\n \"file-plus-2\",\n \"file-plus\",\n \"file-question-mark\",\n \"file-question\",\n \"file-scan\",\n \"file-search-corner\",\n \"file-search-2\",\n \"file-search\",\n \"file-signal\",\n \"file-volume-2\",\n \"file-sliders\",\n \"file-spreadsheet\",\n \"file-stack\",\n \"file-symlink\",\n \"file-terminal\",\n \"file-text\",\n \"file-type-corner\",\n \"file-type-2\",\n \"file-type\",\n \"file-up\",\n \"file-user\",\n \"file-video-camera\",\n \"file-video-2\",\n \"file-volume\",\n \"file-x-corner\",\n \"file-x-2\",\n \"file-x\",\n \"file\",\n \"files\",\n \"film\",\n \"fingerprint-pattern\",\n \"fingerprint\",\n \"fire-extinguisher\",\n \"fish-off\",\n \"fish-symbol\",\n \"fish\",\n \"fishing-hook\",\n \"fishing-rod\",\n \"flag-off\",\n \"flag-triangle-left\",\n \"flag-triangle-right\",\n \"flag\",\n \"flame-kindling\",\n \"flame\",\n \"flashlight-off\",\n \"flashlight\",\n \"flask-conical-off\",\n \"flask-conical\",\n \"flask-round\",\n \"flip-horizontal-2\",\n \"flip-vertical-2\",\n \"flower-2\",\n \"flower\",\n \"focus\",\n \"fold-horizontal\",\n \"fold-vertical\",\n \"folder-archive\",\n \"folder-check\",\n \"folder-clock\",\n \"folder-closed\",\n \"folder-code\",\n \"folder-cog\",\n \"folder-cog-2\",\n \"folder-dot\",\n \"folder-down\",\n \"folder-git-2\",\n \"folder-git\",\n \"folder-heart\",\n \"folder-input\",\n \"folder-kanban\",\n \"folder-key\",\n \"folder-lock\",\n \"folder-minus\",\n \"folder-open-dot\",\n \"folder-open\",\n \"folder-output\",\n \"folder-pen\",\n \"folder-edit\",\n \"folder-plus\",\n \"folder-root\",\n \"folder-search-2\",\n \"folder-search\",\n \"folder-symlink\",\n \"folder-sync\",\n \"folder-tree\",\n \"folder-up\",\n \"folder-x\",\n \"folder\",\n \"folders\",\n \"footprints\",\n \"forklift\",\n \"form\",\n \"forward\",\n \"frame\",\n \"frown\",\n \"fuel\",\n \"fullscreen\",\n \"funnel-plus\",\n \"funnel-x\",\n \"filter-x\",\n \"funnel\",\n \"filter\",\n \"gallery-horizontal-end\",\n \"gallery-horizontal\",\n \"gallery-thumbnails\",\n \"gallery-vertical-end\",\n \"gallery-vertical\",\n \"gamepad-2\",\n \"gamepad-directional\",\n \"gamepad\",\n \"gauge\",\n \"gavel\",\n \"gem\",\n \"georgian-lari\",\n \"ghost\",\n \"gift\",\n \"git-branch-minus\",\n \"git-branch-plus\",\n \"git-branch\",\n \"git-commit-horizontal\",\n \"git-commit\",\n \"git-commit-vertical\",\n \"git-compare-arrows\",\n \"git-compare\",\n \"git-fork\",\n \"git-graph\",\n \"git-merge-conflict\",\n \"git-merge\",\n \"git-pull-request-arrow\",\n \"git-pull-request-closed\",\n \"git-pull-request-create-arrow\",\n \"git-pull-request-create\",\n \"git-pull-request-draft\",\n \"git-pull-request\",\n \"glass-water\",\n \"glasses\",\n \"globe-lock\",\n \"globe-off\",\n \"globe-x\",\n \"globe\",\n \"goal\",\n \"gpu\",\n \"graduation-cap\",\n \"grape\",\n \"grid-2x2-check\",\n \"grid-2-x-2-check\",\n \"grid-2x2-plus\",\n \"grid-2-x-2-plus\",\n \"grid-2x2-x\",\n \"grid-2-x-2-x\",\n \"grid-2x2\",\n \"grid-2-x-2\",\n \"grid-3x2\",\n \"grid-3x3\",\n \"grid\",\n \"grid-3-x-3\",\n \"grip-horizontal\",\n \"grip-vertical\",\n \"grip\",\n \"group\",\n \"guitar\",\n \"ham\",\n \"hamburger\",\n \"hammer\",\n \"hand-coins\",\n \"hand-fist\",\n \"hand-grab\",\n \"grab\",\n \"hand-heart\",\n \"hand-helping\",\n \"helping-hand\",\n \"hand-metal\",\n \"hand-platter\",\n \"hand\",\n \"handbag\",\n \"handshake\",\n \"hard-drive-download\",\n \"hard-drive-upload\",\n \"hard-drive\",\n \"hard-hat\",\n \"hash\",\n \"hat-glasses\",\n \"haze\",\n \"hd\",\n \"hdmi-port\",\n \"heading-1\",\n \"heading-2\",\n \"heading-3\",\n \"heading-4\",\n \"heading-5\",\n \"heading-6\",\n \"heading\",\n \"headphone-off\",\n \"headphones\",\n \"headset\",\n \"heart-crack\",\n \"heart-handshake\",\n \"heart-minus\",\n \"heart-off\",\n \"heart-plus\",\n \"heart-pulse\",\n \"heart\",\n \"heater\",\n \"helicopter\",\n \"hexagon\",\n \"highlighter\",\n \"history\",\n \"hop-off\",\n \"hop\",\n \"hospital\",\n \"hotel\",\n \"hourglass\",\n \"house-heart\",\n \"house-plug\",\n \"house-plus\",\n \"house-wifi\",\n \"house\",\n \"home\",\n \"ice-cream-bowl\",\n \"ice-cream-2\",\n \"ice-cream-cone\",\n \"ice-cream\",\n \"id-card-lanyard\",\n \"id-card\",\n \"image-down\",\n \"image-minus\",\n \"image-off\",\n \"image-play\",\n \"image-plus\",\n \"image-up\",\n \"image-upscale\",\n \"image\",\n \"images\",\n \"import\",\n \"inbox\",\n \"indian-rupee\",\n \"infinity\",\n \"info\",\n \"inspection-panel\",\n \"italic\",\n \"iteration-ccw\",\n \"iteration-cw\",\n \"japanese-yen\",\n \"joystick\",\n \"kanban\",\n \"kayak\",\n \"key-round\",\n \"key-square\",\n \"key\",\n \"keyboard-music\",\n \"keyboard-off\",\n \"keyboard\",\n \"lamp-ceiling\",\n \"lamp-desk\",\n \"lamp-floor\",\n \"lamp-wall-down\",\n \"lamp-wall-up\",\n \"lamp\",\n \"land-plot\",\n \"landmark\",\n \"languages\",\n \"laptop-minimal-check\",\n \"laptop-minimal\",\n \"laptop-2\",\n \"laptop\",\n \"lasso-select\",\n \"lasso\",\n \"laugh\",\n \"layers-2\",\n \"layers-plus\",\n \"layers\",\n \"layers-3\",\n \"layout-dashboard\",\n \"layout-grid\",\n \"layout-list\",\n \"layout-panel-left\",\n \"layout-panel-top\",\n \"layout-template\",\n \"leaf\",\n \"leafy-green\",\n \"lectern\",\n \"lens-concave\",\n \"lens-convex\",\n \"library-big\",\n \"library\",\n \"life-buoy\",\n \"ligature\",\n \"lightbulb-off\",\n \"lightbulb\",\n \"line-dot-right-horizontal\",\n \"line-squiggle\",\n \"line-style\",\n \"link-2-off\",\n \"link-2\",\n \"link\",\n \"list-check\",\n \"list-checks\",\n \"list-chevrons-down-up\",\n \"list-chevrons-up-down\",\n \"list-collapse\",\n \"list-end\",\n \"list-filter-plus\",\n \"list-filter\",\n \"list-indent-decrease\",\n \"outdent\",\n \"indent-decrease\",\n \"list-indent-increase\",\n \"indent\",\n \"indent-increase\",\n \"list-minus\",\n \"list-music\",\n \"list-ordered\",\n \"list-plus\",\n \"list-restart\",\n \"list-start\",\n \"list-todo\",\n \"list-tree\",\n \"list-video\",\n \"list-x\",\n \"list\",\n \"loader-circle\",\n \"loader-2\",\n \"loader-pinwheel\",\n \"loader\",\n \"locate-fixed\",\n \"locate-off\",\n \"locate\",\n \"lock-keyhole-open\",\n \"unlock-keyhole\",\n \"lock-keyhole\",\n \"lock-open\",\n \"unlock\",\n \"lock\",\n \"log-in\",\n \"log-out\",\n \"logs\",\n \"lollipop\",\n \"luggage\",\n \"magnet\",\n \"mail-check\",\n \"mail-minus\",\n \"mail-open\",\n \"mail-plus\",\n \"mail-question-mark\",\n \"mail-question\",\n \"mail-search\",\n \"mail-warning\",\n \"mail-x\",\n \"mail\",\n \"mailbox\",\n \"mails\",\n \"map-minus\",\n \"map-pin-check-inside\",\n \"map-pin-check\",\n \"map-pin-house\",\n \"map-pin-minus-inside\",\n \"map-pin-minus\",\n \"map-pin-off\",\n \"map-pin-pen\",\n \"location-edit\",\n \"map-pin-plus-inside\",\n \"map-pin-plus\",\n \"map-pin-search\",\n \"map-pin-x-inside\",\n \"map-pin-x\",\n \"map-pin\",\n \"map-pinned\",\n \"map-plus\",\n \"map\",\n \"mars-stroke\",\n \"mars\",\n \"martini\",\n \"maximize-2\",\n \"maximize\",\n \"medal\",\n \"megaphone-off\",\n \"megaphone\",\n \"meh\",\n \"memory-stick\",\n \"menu\",\n \"merge\",\n \"message-circle-check\",\n \"message-circle-code\",\n \"message-circle-dashed\",\n \"message-circle-heart\",\n \"message-circle-more\",\n \"message-circle-off\",\n \"message-circle-plus\",\n \"message-circle-question-mark\",\n \"message-circle-question\",\n \"message-circle-reply\",\n \"message-circle-warning\",\n \"message-circle-x\",\n \"message-circle\",\n \"message-square-check\",\n \"message-square-code\",\n \"message-square-dashed\",\n \"message-square-diff\",\n \"message-square-dot\",\n \"message-square-heart\",\n \"message-square-lock\",\n \"message-square-more\",\n \"message-square-off\",\n \"message-square-plus\",\n \"message-square-quote\",\n \"message-square-reply\",\n \"message-square-share\",\n \"message-square-text\",\n \"message-square-warning\",\n \"message-square-x\",\n \"message-square\",\n \"messages-square\",\n \"metronome\",\n \"mic-off\",\n \"mic-vocal\",\n \"mic-2\",\n \"mic\",\n \"microchip\",\n \"microscope\",\n \"microwave\",\n \"milestone\",\n \"milk-off\",\n \"milk\",\n \"minimize-2\",\n \"minimize\",\n \"minus\",\n \"mirror-rectangular\",\n \"mirror-round\",\n \"monitor-check\",\n \"monitor-cloud\",\n \"monitor-cog\",\n \"monitor-dot\",\n \"monitor-down\",\n \"monitor-off\",\n \"monitor-pause\",\n \"monitor-play\",\n \"monitor-smartphone\",\n \"monitor-speaker\",\n \"monitor-stop\",\n \"monitor-up\",\n \"monitor-x\",\n \"monitor\",\n \"moon-star\",\n \"moon\",\n \"motorbike\",\n \"mountain-snow\",\n \"mountain\",\n \"mouse-left\",\n \"mouse-off\",\n \"mouse-pointer-2-off\",\n \"mouse-pointer-2\",\n \"mouse-pointer-ban\",\n \"mouse-pointer-click\",\n \"mouse-pointer\",\n \"mouse-right\",\n \"mouse\",\n \"move-3d\",\n \"move-3-d\",\n \"move-diagonal-2\",\n \"move-diagonal\",\n \"move-down-left\",\n \"move-down-right\",\n \"move-down\",\n \"move-horizontal\",\n \"move-left\",\n \"move-right\",\n \"move-up-left\",\n \"move-up-right\",\n \"move-up\",\n \"move-vertical\",\n \"move\",\n \"music-2\",\n \"music-3\",\n \"music-4\",\n \"music\",\n \"navigation-2-off\",\n \"navigation-2\",\n \"navigation-off\",\n \"navigation\",\n \"network\",\n \"newspaper\",\n \"nfc\",\n \"non-binary\",\n \"notebook-pen\",\n \"notebook-tabs\",\n \"notebook-text\",\n \"notebook\",\n \"notepad-text-dashed\",\n \"notepad-text\",\n \"nut-off\",\n \"nut\",\n \"octagon-alert\",\n \"alert-octagon\",\n \"octagon-minus\",\n \"octagon-pause\",\n \"pause-octagon\",\n \"octagon-x\",\n \"x-octagon\",\n \"octagon\",\n \"omega\",\n \"option\",\n \"orbit\",\n \"origami\",\n \"package-2\",\n \"package-check\",\n \"package-minus\",\n \"package-open\",\n \"package-plus\",\n \"package-search\",\n \"package-x\",\n \"package\",\n \"paint-bucket\",\n \"paint-roller\",\n \"paintbrush-vertical\",\n \"paintbrush-2\",\n \"paintbrush\",\n \"palette\",\n \"panda\",\n \"panel-bottom-close\",\n \"panel-bottom-dashed\",\n \"panel-bottom-inactive\",\n \"panel-bottom-open\",\n \"panel-bottom\",\n \"panel-left-close\",\n \"sidebar-close\",\n \"panel-left-dashed\",\n \"panel-left-inactive\",\n \"panel-left-open\",\n \"sidebar-open\",\n \"panel-left-right-dashed\",\n \"panel-left\",\n \"sidebar\",\n \"panel-right-close\",\n \"panel-right-dashed\",\n \"panel-right-inactive\",\n \"panel-right-open\",\n \"panel-right\",\n \"panel-top-bottom-dashed\",\n \"panel-top-close\",\n \"panel-top-dashed\",\n \"panel-top-inactive\",\n \"panel-top-open\",\n \"panel-top\",\n \"panels-left-bottom\",\n \"panels-right-bottom\",\n \"panels-top-left\",\n \"layout\",\n \"paperclip\",\n \"parentheses\",\n \"parking-meter\",\n \"party-popper\",\n \"pause\",\n \"paw-print\",\n \"pc-case\",\n \"pen-line\",\n \"edit-3\",\n \"pen-off\",\n \"pen-tool\",\n \"pen\",\n \"edit-2\",\n \"pencil-line\",\n \"pencil-off\",\n \"pencil-ruler\",\n \"pencil\",\n \"pentagon\",\n \"percent\",\n \"person-standing\",\n \"philippine-peso\",\n \"phone-call\",\n \"phone-forwarded\",\n \"phone-incoming\",\n \"phone-missed\",\n \"phone-off\",\n \"phone-outgoing\",\n \"phone\",\n \"pi\",\n \"piano\",\n \"pickaxe\",\n \"picture-in-picture-2\",\n \"picture-in-picture\",\n \"piggy-bank\",\n \"pilcrow-left\",\n \"pilcrow-right\",\n \"pilcrow\",\n \"pill-bottle\",\n \"pill\",\n \"pin-off\",\n \"pin\",\n \"pipette\",\n \"pizza\",\n \"plane-landing\",\n \"plane-takeoff\",\n \"plane\",\n \"play\",\n \"plug-2\",\n \"plug-zap\",\n \"plug-zap-2\",\n \"plug\",\n \"plus\",\n \"pocket-knife\",\n \"podcast\",\n \"pointer-off\",\n \"pointer\",\n \"popcorn\",\n \"popsicle\",\n \"pound-sterling\",\n \"power-off\",\n \"power\",\n \"presentation\",\n \"printer-check\",\n \"printer-x\",\n \"printer\",\n \"projector\",\n \"proportions\",\n \"puzzle\",\n \"pyramid\",\n \"qr-code\",\n \"quote\",\n \"rabbit\",\n \"radar\",\n \"radiation\",\n \"radical\",\n \"radio-off\",\n \"radio-receiver\",\n \"radio-tower\",\n \"radio\",\n \"radius\",\n \"rainbow\",\n \"rat\",\n \"ratio\",\n \"receipt-cent\",\n \"receipt-euro\",\n \"receipt-indian-rupee\",\n \"receipt-japanese-yen\",\n \"receipt-pound-sterling\",\n \"receipt-russian-ruble\",\n \"receipt-swiss-franc\",\n \"receipt-text\",\n \"receipt-turkish-lira\",\n \"receipt\",\n \"rectangle-circle\",\n \"rectangle-ellipsis\",\n \"form-input\",\n \"rectangle-goggles\",\n \"rectangle-horizontal\",\n \"rectangle-vertical\",\n \"recycle\",\n \"redo-2\",\n \"redo-dot\",\n \"redo\",\n \"refresh-ccw-dot\",\n \"refresh-ccw\",\n \"refresh-cw-off\",\n \"refresh-cw\",\n \"refrigerator\",\n \"regex\",\n \"remove-formatting\",\n \"repeat-1\",\n \"repeat-2\",\n \"repeat\",\n \"replace-all\",\n \"replace\",\n \"reply-all\",\n \"reply\",\n \"rewind\",\n \"ribbon\",\n \"road\",\n \"rocket\",\n \"rocking-chair\",\n \"roller-coaster\",\n \"rose\",\n \"rotate-3d\",\n \"rotate-3-d\",\n \"rotate-ccw-key\",\n \"rotate-ccw-square\",\n \"rotate-ccw\",\n \"rotate-cw-square\",\n \"rotate-cw\",\n \"route-off\",\n \"route\",\n \"router\",\n \"rows-2\",\n \"rows\",\n \"rows-3\",\n \"panels-top-bottom\",\n \"rows-4\",\n \"rss\",\n \"ruler-dimension-line\",\n \"ruler\",\n \"russian-ruble\",\n \"sailboat\",\n \"salad\",\n \"sandwich\",\n \"satellite-dish\",\n \"satellite\",\n \"saudi-riyal\",\n \"save-all\",\n \"save-off\",\n \"save\",\n \"scale-3d\",\n \"scale-3-d\",\n \"scale\",\n \"scaling\",\n \"scan-barcode\",\n \"scan-eye\",\n \"scan-face\",\n \"scan-heart\",\n \"scan-line\",\n \"scan-qr-code\",\n \"scan-search\",\n \"scan-text\",\n \"scan\",\n \"school\",\n \"scissors-line-dashed\",\n \"scissors\",\n \"scooter\",\n \"screen-share-off\",\n \"screen-share\",\n \"scroll-text\",\n \"scroll\",\n \"search-alert\",\n \"search-check\",\n \"search-code\",\n \"search-slash\",\n \"search-x\",\n \"search\",\n \"section\",\n \"send-horizontal\",\n \"send-horizonal\",\n \"send-to-back\",\n \"send\",\n \"separator-horizontal\",\n \"separator-vertical\",\n \"server-cog\",\n \"server-crash\",\n \"server-off\",\n \"server\",\n \"settings-2\",\n \"settings\",\n \"shapes\",\n \"share-2\",\n \"share\",\n \"sheet\",\n \"shell\",\n \"shelving-unit\",\n \"shield-alert\",\n \"shield-ban\",\n \"shield-check\",\n \"shield-cog-corner\",\n \"shield-cog\",\n \"shield-ellipsis\",\n \"shield-half\",\n \"shield-minus\",\n \"shield-off\",\n \"shield-plus\",\n \"shield-question-mark\",\n \"shield-question\",\n \"shield-user\",\n \"shield-x\",\n \"shield-close\",\n \"shield\",\n \"ship-wheel\",\n \"ship\",\n \"shirt\",\n \"shopping-bag\",\n \"shopping-basket\",\n \"shopping-cart\",\n \"shovel\",\n \"shower-head\",\n \"shredder\",\n \"shrimp\",\n \"shrink\",\n \"shrub\",\n \"shuffle\",\n \"sigma\",\n \"signal-high\",\n \"signal-low\",\n \"signal-medium\",\n \"signal-zero\",\n \"signal\",\n \"signature\",\n \"signpost-big\",\n \"signpost\",\n \"siren\",\n \"skip-back\",\n \"skip-forward\",\n \"skull\",\n \"slash\",\n \"slice\",\n \"sliders-horizontal\",\n \"sliders-vertical\",\n \"sliders\",\n \"smartphone-charging\",\n \"smartphone-nfc\",\n \"smartphone\",\n \"smile-plus\",\n \"smile\",\n \"snail\",\n \"snowflake\",\n \"soap-dispenser-droplet\",\n \"sofa\",\n \"solar-panel\",\n \"soup\",\n \"space\",\n \"spade\",\n \"sparkle\",\n \"sparkles\",\n \"stars\",\n \"speaker\",\n \"speech\",\n \"spell-check-2\",\n \"spell-check\",\n \"spline-pointer\",\n \"spline\",\n \"split\",\n \"spool\",\n \"sport-shoe\",\n \"spotlight\",\n \"spray-can\",\n \"sprout\",\n \"square-activity\",\n \"activity-square\",\n \"square-arrow-down-left\",\n \"arrow-down-left-square\",\n \"square-arrow-down-right\",\n \"arrow-down-right-square\",\n \"square-arrow-down\",\n \"arrow-down-square\",\n \"square-arrow-left\",\n \"arrow-left-square\",\n \"square-arrow-out-down-left\",\n \"arrow-down-left-from-square\",\n \"square-arrow-out-down-right\",\n \"arrow-down-right-from-square\",\n \"square-arrow-out-up-left\",\n \"arrow-up-left-from-square\",\n \"square-arrow-out-up-right\",\n \"arrow-up-right-from-square\",\n \"square-arrow-right-enter\",\n \"square-arrow-right-exit\",\n \"square-arrow-right\",\n \"arrow-right-square\",\n \"square-arrow-up-left\",\n \"arrow-up-left-square\",\n \"square-arrow-up-right\",\n \"arrow-up-right-square\",\n \"square-arrow-up\",\n \"arrow-up-square\",\n \"square-asterisk\",\n \"asterisk-square\",\n \"square-bottom-dashed-scissors\",\n \"scissors-square-dashed-bottom\",\n \"square-centerline-dashed-horizontal\",\n \"flip-horizontal\",\n \"square-centerline-dashed-vertical\",\n \"flip-vertical\",\n \"square-chart-gantt\",\n \"gantt-chart-square\",\n \"square-gantt-chart\",\n \"square-check-big\",\n \"check-square\",\n \"square-check\",\n \"check-square-2\",\n \"square-chevron-down\",\n \"chevron-down-square\",\n \"square-chevron-left\",\n \"chevron-left-square\",\n \"square-chevron-right\",\n \"chevron-right-square\",\n \"square-chevron-up\",\n \"chevron-up-square\",\n \"square-code\",\n \"code-square\",\n \"square-dashed-bottom-code\",\n \"square-dashed-bottom\",\n \"square-dashed-kanban\",\n \"kanban-square-dashed\",\n \"square-dashed-mouse-pointer\",\n \"mouse-pointer-square-dashed\",\n \"square-dashed-text\",\n \"text-selection\",\n \"text-select\",\n \"square-dashed-top-solid\",\n \"square-dashed\",\n \"box-select\",\n \"square-divide\",\n \"divide-square\",\n \"square-dot\",\n \"dot-square\",\n \"square-equal\",\n \"equal-square\",\n \"square-function\",\n \"function-square\",\n \"square-kanban\",\n \"kanban-square\",\n \"square-library\",\n \"library-square\",\n \"square-m\",\n \"m-square\",\n \"square-menu\",\n \"menu-square\",\n \"square-minus\",\n \"minus-square\",\n \"square-mouse-pointer\",\n \"inspect\",\n \"square-parking-off\",\n \"parking-square-off\",\n \"square-parking\",\n \"parking-square\",\n \"square-pause\",\n \"square-pen\",\n \"pen-box\",\n \"edit\",\n \"pen-square\",\n \"square-percent\",\n \"percent-square\",\n \"square-pi\",\n \"pi-square\",\n \"square-pilcrow\",\n \"pilcrow-square\",\n \"square-play\",\n \"play-square\",\n \"square-plus\",\n \"plus-square\",\n \"square-power\",\n \"power-square\",\n \"square-radical\",\n \"square-round-corner\",\n \"square-scissors\",\n \"scissors-square\",\n \"square-sigma\",\n \"sigma-square\",\n \"square-slash\",\n \"slash-square\",\n \"square-split-horizontal\",\n \"split-square-horizontal\",\n \"square-split-vertical\",\n \"split-square-vertical\",\n \"square-square\",\n \"square-stack\",\n \"square-star\",\n \"square-stop\",\n \"square-terminal\",\n \"terminal-square\",\n \"square-user-round\",\n \"user-square-2\",\n \"square-user\",\n \"user-square\",\n \"square-x\",\n \"x-square\",\n \"square\",\n \"squares-exclude\",\n \"squares-intersect\",\n \"squares-subtract\",\n \"squares-unite\",\n \"squircle-dashed\",\n \"squircle\",\n \"squirrel\",\n \"stamp\",\n \"star-half\",\n \"star-off\",\n \"star\",\n \"step-back\",\n \"step-forward\",\n \"stethoscope\",\n \"sticker\",\n \"sticky-note\",\n \"stone\",\n \"store\",\n \"stretch-horizontal\",\n \"stretch-vertical\",\n \"strikethrough\",\n \"subscript\",\n \"sun-dim\",\n \"sun-medium\",\n \"sun-moon\",\n \"sun-snow\",\n \"sun\",\n \"sunrise\",\n \"sunset\",\n \"superscript\",\n \"swatch-book\",\n \"swiss-franc\",\n \"switch-camera\",\n \"sword\",\n \"swords\",\n \"syringe\",\n \"table-2\",\n \"table-cells-merge\",\n \"table-cells-split\",\n \"table-columns-split\",\n \"table-of-contents\",\n \"table-properties\",\n \"table-rows-split\",\n \"table\",\n \"tablet-smartphone\",\n \"tablet\",\n \"tablets\",\n \"tag\",\n \"tags\",\n \"tally-1\",\n \"tally-2\",\n \"tally-3\",\n \"tally-4\",\n \"tally-5\",\n \"tangent\",\n \"target\",\n \"telescope\",\n \"tent-tree\",\n \"tent\",\n \"terminal\",\n \"test-tube-diagonal\",\n \"test-tube-2\",\n \"test-tube\",\n \"test-tubes\",\n \"text-align-center\",\n \"align-center\",\n \"text-align-end\",\n \"align-right\",\n \"text-align-justify\",\n \"align-justify\",\n \"text-align-start\",\n \"text\",\n \"align-left\",\n \"text-cursor-input\",\n \"text-cursor\",\n \"text-initial\",\n \"letter-text\",\n \"text-quote\",\n \"text-search\",\n \"text-wrap\",\n \"wrap-text\",\n \"theater\",\n \"thermometer-snowflake\",\n \"thermometer-sun\",\n \"thermometer\",\n \"thumbs-down\",\n \"thumbs-up\",\n \"ticket-check\",\n \"ticket-minus\",\n \"ticket-percent\",\n \"ticket-plus\",\n \"ticket-slash\",\n \"ticket-x\",\n \"ticket\",\n \"tickets-plane\",\n \"tickets\",\n \"timer-off\",\n \"timer-reset\",\n \"timer\",\n \"toggle-left\",\n \"toggle-right\",\n \"toilet\",\n \"tool-case\",\n \"toolbox\",\n \"tornado\",\n \"torus\",\n \"touchpad-off\",\n \"touchpad\",\n \"towel-rack\",\n \"tower-control\",\n \"toy-brick\",\n \"tractor\",\n \"traffic-cone\",\n \"train-front-tunnel\",\n \"train-front\",\n \"train-track\",\n \"tram-front\",\n \"train\",\n \"transgender\",\n \"trash-2\",\n \"trash\",\n \"tree-deciduous\",\n \"tree-palm\",\n \"palmtree\",\n \"tree-pine\",\n \"trees\",\n \"trending-down\",\n \"trending-up-down\",\n \"trending-up\",\n \"triangle-alert\",\n \"alert-triangle\",\n \"triangle-dashed\",\n \"triangle-right\",\n \"triangle\",\n \"trophy\",\n \"truck-electric\",\n \"truck\",\n \"turkish-lira\",\n \"turntable\",\n \"turtle\",\n \"tv-minimal-play\",\n \"tv-minimal\",\n \"tv-2\",\n \"tv\",\n \"type-outline\",\n \"type\",\n \"umbrella-off\",\n \"umbrella\",\n \"underline\",\n \"undo-2\",\n \"undo-dot\",\n \"undo\",\n \"unfold-horizontal\",\n \"unfold-vertical\",\n \"ungroup\",\n \"university\",\n \"school-2\",\n \"unlink-2\",\n \"unlink\",\n \"unplug\",\n \"upload\",\n \"usb\",\n \"user-check\",\n \"user-cog\",\n \"user-key\",\n \"user-lock\",\n \"user-minus\",\n \"user-pen\",\n \"user-plus\",\n \"user-round-check\",\n \"user-check-2\",\n \"user-round-cog\",\n \"user-cog-2\",\n \"user-round-key\",\n \"user-round-minus\",\n \"user-minus-2\",\n \"user-round-pen\",\n \"user-round-plus\",\n \"user-plus-2\",\n \"user-round-search\",\n \"user-round-x\",\n \"user-x-2\",\n \"user-round\",\n \"user-2\",\n \"user-search\",\n \"user-star\",\n \"user-x\",\n \"user\",\n \"users-round\",\n \"users-2\",\n \"users\",\n \"utensils-crossed\",\n \"fork-knife-crossed\",\n \"utensils\",\n \"fork-knife\",\n \"utility-pole\",\n \"van\",\n \"variable\",\n \"vault\",\n \"vector-square\",\n \"vegan\",\n \"venetian-mask\",\n \"venus-and-mars\",\n \"venus\",\n \"vibrate-off\",\n \"vibrate\",\n \"video-off\",\n \"video\",\n \"videotape\",\n \"view\",\n \"voicemail\",\n \"volleyball\",\n \"volume-1\",\n \"volume-2\",\n \"volume-off\",\n \"volume-x\",\n \"volume\",\n \"vote\",\n \"wallet-cards\",\n \"wallet-minimal\",\n \"wallet-2\",\n \"wallet\",\n \"wallpaper\",\n \"wand-sparkles\",\n \"wand-2\",\n \"wand\",\n \"warehouse\",\n \"washing-machine\",\n \"watch\",\n \"waves-arrow-down\",\n \"waves-arrow-up\",\n \"waves-ladder\",\n \"waves\",\n \"waypoints\",\n \"webcam\",\n \"webhook-off\",\n \"webhook\",\n \"weight-tilde\",\n \"weight\",\n \"wheat-off\",\n \"wheat\",\n \"whole-word\",\n \"wifi-cog\",\n \"wifi-high\",\n \"wifi-low\",\n \"wifi-off\",\n \"wifi-pen\",\n \"wifi-sync\",\n \"wifi-zero\",\n \"wifi\",\n \"wind-arrow-down\",\n \"wind\",\n \"wine-off\",\n \"wine\",\n \"workflow\",\n \"worm\",\n \"wrench\",\n \"x-line-top\",\n \"x\",\n \"zap-off\",\n \"zap\",\n \"zodiac-aquarius\",\n \"zodiac-aries\",\n \"zodiac-cancer\",\n \"zodiac-capricorn\",\n \"zodiac-gemini\",\n \"zodiac-leo\",\n \"zodiac-libra\",\n \"zodiac-ophiuchus\",\n \"zodiac-pisces\",\n \"zodiac-sagittarius\",\n \"zodiac-scorpio\",\n \"zodiac-taurus\",\n \"zodiac-virgo\",\n \"zoom-in\",\n \"zoom-out\",\n]);\n\nexport const LAYOUT_SECTION_ICON_SET: ReadonlySet<string> = new Set(LAYOUT_SECTION_ICONS);\nexport type LayoutSectionIcon = string;\n","/** Stable identifiers used by every project and page layout document. */\nexport const PAGE_CONTENT_ANCHOR_ID = \"page-content\" as const;\nexport const NAVIGATION_SECTION_ID = \"navigation\" as const;\nexport const FOOTER_SECTION_ID = \"footer\" as const;\n\n/** Locked transport/validation set shared by authoring surfaces and the server. */\nexport {\n LAYOUT_SECTION_ICONS,\n LAYOUT_SECTION_ICON_SET,\n type LayoutSectionIcon,\n} from \"./layout-lucide-icons.js\";\nimport type { LayoutSectionIcon } from \"./layout-lucide-icons.js\";\n\nexport type LayoutZone = \"above-page-content\" | \"below-page-content\";\nexport type ReservedLayoutSection = \"navigation\" | \"footer\";\n\nexport type LayoutScalarFieldType =\n | \"text\"\n | \"longtext\"\n | \"richtext\"\n | \"number\"\n | \"toggle\"\n | \"date\"\n | \"image\"\n | \"file\"\n | \"link\"\n | \"email\"\n | \"phone\"\n | \"select\"\n | \"color\"\n | \"json\"\n | \"reference\"\n | \"multi-reference\";\n\nexport type LayoutFieldType = LayoutScalarFieldType | \"group\" | \"repeater\";\n\n/** A recursive, stable-ID field contract shared by Sections and variant inputs. */\nexport interface LayoutFieldDefinition {\n id: string;\n slug: string;\n label: string;\n type: LayoutFieldType;\n required?: boolean;\n defaultValue?: unknown;\n config?: {\n options?: Array<{ label: string; value: string }>;\n referenceModelId?: string;\n minItems?: number;\n maxItems?: number;\n } & Record<string, unknown>;\n /** Required for group/repeater; forbidden for scalar fields. */\n fields?: LayoutFieldDefinition[];\n}\n\n/** The canonical public input contract all variants in a group implement. */\nexport type CanonicalInputDefinition = LayoutFieldDefinition;\n\n/** Maps one canonical input onto one or more internal component prop paths. */\nexport interface VariantInputMapping {\n inputId: string;\n targets: Array<{ blockId: string; path: string }>;\n}\n\nexport interface ComponentVariantGroup {\n id: string;\n workspaceId: string;\n projectId?: string | null;\n name: string;\n slug: string;\n canonicalInputs: CanonicalInputDefinition[];\n status: \"draft\" | \"published\";\n}\n\nexport interface LayoutFieldItem {\n id: string;\n kind: \"field\";\n fieldId: string;\n}\n\nexport interface LayoutComponentItem {\n id: string;\n kind: \"component\";\n componentId: string;\n variantGroupId?: string;\n bindings: Array<{ inputId: string; fieldId: string }>;\n literalValues?: Record<string, unknown>;\n}\n\nexport type LayoutSectionItem = LayoutFieldItem | LayoutComponentItem;\n\nexport interface LayoutSection {\n id: string;\n name: string;\n slug: string;\n icon: string;\n zone: LayoutZone;\n orderKey: string;\n reserved?: ReservedLayoutSection;\n fields: LayoutFieldDefinition[];\n items: LayoutSectionItem[];\n}\n\nexport interface LayoutStructureDocument {\n version: 1;\n pageContentAnchor: { id: typeof PAGE_CONTENT_ANCHOR_ID };\n sections: LayoutSection[];\n}\n\nexport interface LayoutDataDocument {\n version: 1;\n sections: Record<string, { fields: Record<string, unknown> }>;\n}\n\nexport type PageLayoutOverrideState =\n | \"inherit\"\n | \"override-content\"\n | \"customize-structure\"\n | \"disable\";\n\nexport interface PageSectionPlacement {\n zone: LayoutZone;\n afterSectionId?: string;\n beforeSectionId?: string;\n localOrderKey: string;\n}\n\nexport type PageLayoutSectionOverride =\n | { sectionId: string; state: \"inherit\" }\n | { sectionId: string; state: \"override-content\"; values: Record<string, unknown> }\n | {\n sectionId: string;\n state: \"customize-structure\";\n section: LayoutSection;\n data: { fields: Record<string, unknown> };\n /** Retained when the inherited Section is later deleted. */\n placement: PageSectionPlacement;\n }\n | { sectionId: string; state: \"disable\" };\n\nexport interface PageOnlyLayoutSection {\n section: LayoutSection;\n data: { fields: Record<string, unknown> };\n placement: PageSectionPlacement;\n}\n\nexport type PageLayoutSectionStructureOverride =\n | { sectionId: string; state: \"inherit\" }\n | { sectionId: string; state: \"override-content\" }\n | { sectionId: string; state: \"customize-structure\"; section: LayoutSection; placement: PageSectionPlacement }\n | { sectionId: string; state: \"disable\" };\n\n/** Persisted in pages.layout_override_structure_json. */\nexport interface PageLayoutOverrideStructureDocument {\n version: 1;\n sections: PageLayoutSectionStructureOverride[];\n pageOnlySections: Array<{ section: LayoutSection; placement: PageSectionPlacement }>;\n}\n\n/** Persisted independently so values can be patched without rewriting structure. */\nexport interface PageLayoutOverrideDataDocument {\n version: 1;\n sections: Record<string, { fields: Record<string, unknown> }>;\n pageOnlySections: Record<string, { fields: Record<string, unknown> }>;\n}\n\n/** Canonical in-memory form consumed by the pure resolver. */\nexport interface PageLayoutOverrideDocument {\n version: 1;\n sections: PageLayoutSectionOverride[];\n pageOnlySections: PageOnlyLayoutSection[];\n}\n\n/** Canonical, discriminated Management/MCP authoring transport. Authority is derived from type. */\nexport type ManagementLayoutCommand =\n | { type: \"set-section-values\"; sectionId: string; values: Record<string, unknown> }\n | { type: \"set-field-value\"; sectionId: string; fieldId: string; value: unknown }\n | { type: \"add-component\"; sectionId: string; componentId: string; variantGroupId?: string; bindings?: LayoutComponentItem[\"bindings\"]; literalValues?: Record<string, unknown> }\n | { type: \"remove-item\"; sectionId: string; itemId: string }\n | { type: \"move-component\"; sectionId: string; itemId: string; index: number }\n | { type: \"move-item\"; sectionId: string; itemId: string; index: number }\n | { type: \"swap-component-variant\"; sectionId: string; itemId: string; componentId: string }\n | { type: \"set-page-state\"; sectionId: string; state: PageLayoutOverrideState | \"reset\" }\n | { type: \"set-section-state\"; sectionId: string; state: PageLayoutOverrideState | \"reset\" }\n | { type: \"add-section\"; name: string; icon: LayoutSectionIcon; zone: \"before_page\" | \"after_page\" }\n | { type: \"restore-section\"; section: LayoutSection; data: { fields: Record<string, unknown> }; placement?: PageSectionPlacement }\n | { type: \"update-section\"; sectionId: string; name?: string; icon?: LayoutSectionIcon; slug?: string; zone?: LayoutZone; orderKey?: string }\n | { type: \"remove-section\"; sectionId: string }\n | { type: \"move-section\"; sectionId: string; afterId?: string | null; beforeId?: string | null }\n | { type: \"add-field\"; sectionId: string; parentFieldId?: string; field?: LayoutFieldDefinition; fieldType?: LayoutFieldType }\n | { type: \"update-field\"; sectionId: string; fieldId: string; patch: Partial<Omit<LayoutFieldDefinition, \"id\">> }\n | { type: \"remove-field\"; sectionId: string; fieldId: string }\n | { type: \"move-field\"; sectionId: string; itemId: string; index: number }\n | { type: \"set-bindings\"; sectionId: string; itemId: string; bindings: LayoutComponentItem[\"bindings\"]; literalValues?: Record<string, unknown> };\n\nexport type ResolvedLayoutNode =\n | { kind: \"page-content\"; id: typeof PAGE_CONTENT_ANCHOR_ID }\n | {\n kind: \"section\";\n id: string;\n section: LayoutSection;\n data: { fields: Record<string, unknown> };\n source: \"inherit\" | \"override-content\" | \"customize-structure\" | \"page-only\" | \"detached\";\n };\n\nexport interface DeliveredLayout {\n version: 1;\n nodes: Array<\n | { kind: \"page-content\"; id: typeof PAGE_CONTENT_ANCHOR_ID }\n | { kind: \"section\"; id: string; slug: string; name: string; source: Extract<ResolvedLayoutNode, { kind: \"section\" }>[\"source\"] }\n >;\n sections: Record<string, {\n id: string;\n slug: string;\n name: string;\n fields: Record<string, unknown>;\n items: Array<\n | { id: string; kind: \"field\"; fieldId: string; value: unknown }\n | {\n id: string;\n kind: \"component\";\n componentId: string;\n variantGroupId?: string;\n canonicalInputs: CanonicalInputDefinition[];\n bindings: LayoutComponentItem[\"bindings\"];\n canonicalValues: Record<string, unknown>;\n resolvedProps: Record<string, unknown>;\n /**\n * `prop.key` → canonical `inputId` — the relation `resolvedProps` consumes and throws\n * away (`output[prop.key] = canonicalValues[mapping.inputId]`).\n *\n * Without it a renderer holds a component prop key and NO address: `logoAlt`/`links`/\n * `cta` are the component's own bare keys, and nothing relates them back to the layout\n * field a write must land on. With it the chain closes — `prop.key` → `inputId` →\n * (`bindings`, already delivered above) → `fieldId` → `set-field-value(sectionId,\n * fieldId)`. That is what makes global chrome click-to-edit (FLO-1179).\n *\n * Additive and always present (`{}` when the item has no variant mappings), so an\n * older consumer that ignores it is byte-identical to before.\n */\n propInputs: Record<string, string>;\n blocks: unknown[];\n }\n >;\n }>;\n}\n","/**\n * WHERE an element was on a built page, so a later pass can find it again.\n *\n * This lives in the shared package because BOTH ends of the comparison have to spell an address\n * the same way: the backend derives it from a JSDOM tree at import time, the dashboard computes\n * it from a live iframe tree when a person clicks an unbound element. Two implementations of\n * \"the ancestor chain down from the nearest landmark\" is one implementation too many — the first\n * time they disagree by one tag, a click binds the wrong element.\n *\n * The DOM is typed STRUCTURALLY (`ElementLike`, `LandmarkHost`) so this package needs no DOM lib\n * and stays importable from a node-only build.\n */\n\n/** The landmark tags an address is anchored at, as one CSS selector and as one tag set. */\nexport const LANDMARK_SELECTOR = \"header,nav,footer\";\nconst LANDMARK_TAGS = new Set([\"HEADER\", \"NAV\", \"FOOTER\"]);\n\n/**\n * The THIRD region — a modal, a cookie banner, a pop-up — behind a per-project gate.\n *\n * A `<dialog>` or a `[role=\"dialog\"]` sits at BODY level, outside every landmark, so a banner\n * byte-identical on twelve routes derived twelve copies of itself. It is NOT a stop for\n * `locatorFor`: `region` already names which dialog an element is in, and a second gated rule\n * about where the ancestor chain ends would make the same element's locator differ between a\n * project that derived it as chrome and one that did not.\n */\nexport const DIALOG_SELECTOR = 'dialog,[role=\"dialog\"]';\n\n/**\n * Best-effort by construction — built-DOM positions do not survive component expansion or\n * conditional rendering — so a consumer that finds no exact match, or finds several, falls back\n * to ambiguity rather than to a guess. The ancestor chain is compared EXACTLY (`atLocator`,\n * annotate-static.ts): a chain that merely contains the stored one is a different element.\n */\nexport interface DerivedLocator {\n /** The landmark it lives in — `header#0`, `nav#1`, `footer#0` — or null for the page body. */\n region: string | null;\n /** Tag names from the nearest landmark (or `<body>`) down to the element's parent. */\n ancestors: string[];\n /** Its index among its parent's element children. */\n siblingIndex: number;\n /**\n * The element's own lower-cased tag name.\n *\n * The cheapest fact that separates two elements a chain-and-index pair calls identical — a\n * `<h2>` and the `<a>` beside it in a rebuilt layout — and the only one a resolver can use to\n * NARROW its candidate list before comparing anything. Absent on locators stored before it\n * existed; a comparer must treat a missing tag as \"matches\".\n */\n tag: string;\n /**\n * The repeater row this value belongs to.\n *\n * On a leaf's field DEFINITION the index is 0 — one definition serves every row — and the\n * brief overrides it with the row it is actually describing (`cards[2].title` → index 2).\n */\n repeat?: { groupKey: string; index: number };\n}\n\n/** The DOM surface `locatorFor` reads. `Element` satisfies it; so does a plain object. */\nexport interface ElementLike {\n tagName: string;\n parentElement: ElementLike | null;\n children: ArrayLike<ElementLike>;\n}\n\n/**\n * The structural address of one element: its ancestor tags and its position among its siblings.\n *\n * Stops at the nearest LANDMARK because that is where a page's structure stops being comparable\n * — a header's internals are the same on every route while the body's are not — and `region`\n * already names which landmark it was.\n */\nexport function locatorFor(el: ElementLike, region: string | null): DerivedLocator {\n const ancestors: string[] = [];\n for (\n let parent = el.parentElement;\n parent && parent.tagName !== \"BODY\" && !LANDMARK_TAGS.has(parent.tagName);\n parent = parent.parentElement\n ) {\n ancestors.unshift(parent.tagName.toLowerCase());\n }\n const siblings = el.parentElement ? Array.from(el.parentElement.children) : [];\n return {\n region,\n ancestors,\n siblingIndex: Math.max(siblings.indexOf(el), 0),\n tag: el.tagName.toLowerCase(),\n };\n}\n\n/** The DOM surface `landmarkRegions` reads of each element it considers. */\nexport interface LandmarkElement {\n tagName: string;\n parentElement: { closest(selectors: string): unknown } | null;\n matches(selectors: string): boolean;\n}\n\n/**\n * A page's landmark regions: the OUTERMOST `header`/`nav`/`footer` elements, in document order.\n *\n * Outermost, because a `<nav>` inside a `<header>` is one region a visitor sees as one thing —\n * and promoting the two separately would let a site's masthead be half layout, half page.\n */\nexport function landmarkRegions<E extends LandmarkElement>(\n doc: { querySelectorAll(selectors: string): Iterable<E> },\n /**\n * Count a dialog as a region too — the per-project chrome grammar.\n *\n * OFF by default, and not merely for symmetry: a region name is part of every field's LOCATOR,\n * and a project whose stored locators say `region: null` for a modal's copy must keep being\n * read the same way.\n */\n dialogs = false,\n): { slot: string; el: E }[] {\n const counts = new Map<string, number>();\n const out: { slot: string; el: E }[] = [];\n const selector = dialogs ? `${LANDMARK_SELECTOR},${DIALOG_SELECTOR}` : LANDMARK_SELECTOR;\n for (const el of doc.querySelectorAll(selector)) {\n if (el.parentElement?.closest(selector)) continue;\n // The NAME, not the tag: a `[role=\"dialog\"]` is usually a `<div>`, and slotting it as\n // `div#0` would make one site's modal and another's wrapper the same kind of region.\n const name = !LANDMARK_TAGS.has(el.tagName) && el.matches(DIALOG_SELECTOR)\n ? \"dialog\"\n : el.tagName.toLowerCase();\n const n = counts.get(name) ?? 0;\n counts.set(name, n + 1);\n out.push({ slot: `${name}#${n}`, el });\n }\n return out;\n}\n"],"mappings":";AAqfO,SAAS,QAAQ,OAAuC;AAC7D,SACE,OAAO,UAAU,YACjB,UAAU,QACV,UAAU,SACV,OAAQ,MAAkC,MAAM,MAAM;AAE1D;AAUO,SAAS,aAAa,OAAkC;AAC7D,MAAI,QAAQ,KAAK,EAAG,QAAO,MAAM;AACjC,SAAO;AACT;;;AC7bO,IAAM,iBAAsE;AAAA,EACjF,SAAS,CAAC,EAAE,MAAM,QAAQ,MAAM,OAAO,CAAC;AAAA,EACxC,MAAM,CAAC,EAAE,MAAM,QAAQ,MAAM,WAAW,CAAC;AAAA,EACzC,UAAU,CAAC,EAAE,MAAM,QAAQ,MAAM,WAAW,CAAC;AAAA,EAC7C,OAAO;AAAA,IACL,EAAE,MAAM,OAAO,MAAM,QAAQ;AAAA,IAC7B,EAAE,MAAM,WAAW,MAAM,OAAO;AAAA,IAChC,EAAE,MAAM,OAAO,MAAM,QAAQ,MAAM,MAAM;AAAA,EAC3C;AAAA,EACA,QAAQ;AAAA,IACN,EAAE,MAAM,QAAQ,MAAM,OAAO;AAAA,IAC7B,EAAE,MAAM,QAAQ,MAAM,OAAO,MAAM,OAAO;AAAA,EAC5C;AAAA,EACA,OAAO;AAAA,IACL,EAAE,MAAM,OAAO,MAAM,OAAO,MAAM,MAAM;AAAA,IACxC,EAAE,MAAM,UAAU,MAAM,OAAO,MAAM,SAAS;AAAA,EAChD;AAAA,EACA,QAAQ;AAAA,IACN,EAAE,MAAM,YAAY,MAAM,QAAQ;AAAA,IAClC,EAAE,MAAM,YAAY,MAAM,QAAQ,MAAM,MAAM;AAAA,IAC9C,EAAE,MAAM,iBAAiB,MAAM,OAAO;AAAA,IACtC,EAAE,MAAM,gBAAgB,MAAM,OAAO,MAAM,OAAO;AAAA,IAClD,EAAE,MAAM,YAAY,MAAM,OAAO;AAAA,IACjC,EAAE,MAAM,YAAY,MAAM,OAAO,MAAM,OAAO;AAAA,EAChD;AAAA,EACA,QAAQ;AAAA,IACN,EAAE,MAAM,aAAa,MAAM,OAAO;AAAA,IAClC,EAAE,MAAM,qBAAqB,MAAM,OAAO;AAAA,IAC1C,EAAE,MAAM,2BAA2B,MAAM,OAAO;AAAA,IAChD,EAAE,MAAM,0BAA0B,MAAM,OAAO,MAAM,OAAO;AAAA,EAC9D;AAAA,EACA,MAAM,CAAC,EAAE,MAAM,gBAAgB,MAAM,OAAO,CAAC;AAC/C;AAQA,IAAM,WAAW,CAAC,MAChB,OAAO,MAAM,YAAY,MAAM,QAAQ,CAAC,MAAM,QAAQ,CAAC;AAgBlD,SAAS,SAAS,MAAe,MAAuB;AAC7D,MAAI,SAAkB;AACtB,aAAW,WAAW,KAAK,MAAM,GAAG,GAAG;AACrC,QAAI,CAAC,QAAS,QAAO;AACrB,UAAM,MAAM,QAAQ,QAAQ,YAAY,EAAE;AAC1C,QAAI,KAAK;AACP,UAAI,CAAC,SAAS,MAAM,EAAG,QAAO;AAC9B,eAAS,OAAO,GAAG;AAAA,IACrB;AACA,eAAW,SAAS,QAAQ,SAAS,YAAY,GAAG;AAClD,UAAI,CAAC,MAAM,QAAQ,MAAM,EAAG,QAAO;AACnC,eAAS,OAAO,OAAO,MAAM,CAAC,CAAC,CAAC;AAAA,IAClC;AAAA,EACF;AACA,SAAO;AACT;AAGA,SAAS,eAAe,SAAuB,OAAgB,MAAiC;AAC9F,QAAM,KAAK,KAAK,QAAQ,IAAI;AAC5B,MAAI,KAAK,EAAG,QAAO,CAAC,EAAE,GAAG,SAAS,KAAK,CAAC;AAExC,QAAM,OAAO,KAAK,MAAM,GAAG,EAAE;AAC7B,QAAM,OAAO,KAAK,MAAM,KAAK,CAAC;AAC9B,QAAM,QAAQ,SAAS,OAAO,IAAI;AAClC,MAAI,CAAC,MAAM,QAAQ,KAAK,EAAG,QAAO,CAAC;AAEnC,SAAO,MAAM;AAAA,IAAQ,CAAC,OAAO,UAC3B,eAAe,SAAS,OAAO,GAAG,IAAI,IAAI,KAAK,IAAI,IAAI,EAAE;AAAA,EAC3D;AACF;AAiBO,SAAS,oBAAoB,OAAwC;AAC1E,QAAM,WAAW,eAAe,MAAM,IAAI;AAC1C,MAAI,CAAC,SAAU,QAAO,CAAC;AACvB,QAAM,QAAS,MAA8B;AAC7C,MAAI,CAAC,SAAS,KAAK,EAAG,QAAO,CAAC;AAC9B,SAAO,SACJ,QAAQ,CAAC,YAAY,eAAe,SAAS,OAAO,QAAQ,IAAI,CAAC,EACjE,OAAO,CAAC,YAAY,SAAS,OAAO,QAAQ,IAAI,MAAM,MAAS;AACpE;AAGO,SAAS,qBACd,SACQ;AACR,SAAO,QAAQ,IAAI,CAAC,MAAM,GAAG,EAAE,OAAO,IAAI,EAAE,IAAI,IAAI,EAAE,IAAI,EAAE,EAAE,KAAK,GAAG;AACxE;AAGO,SAAS,oBACd,OACwD;AACxD,MAAI,CAAC,MAAO,QAAO,CAAC;AACpB,SAAO,MACJ,MAAM,GAAG,EACT,IAAI,CAAC,UAAU,MAAM,MAAM,GAAG,CAAC,EAC/B,OAAO,CAAC,UAAkD,MAAM,WAAW,KAAK,MAAM,MAAM,OAAO,CAAC,EACpG,IAAI,CAAC,CAAC,SAAS,MAAM,IAAI,OAAO,EAAE,SAAS,MAAM,KAAK,EAAE;AAC7D;AAiCO,SAAS,uBAAuB,MAA6C;AAClF,MAAI,CAAC,MAAM,OAAO,CAAC,KAAK,QAAQ,QAAS,QAAO;AAChD,SAAO,GAAG,KAAK,OAAO,OAAO,KAAK,OAAO,KAAK,OAAO,QAAQ,EAAE,EAAE,QAAQ,YAAY,EAAE,CAAC;AAC1F;AAOO,SAAS,2BACd,iBACA,OACA,OACqB;AACrB,QAAM,WAAW,QAAQ,GAAG,KAAK,IAAI,eAAe,KAAK;AACzD,QAAM,MAAM,oBAAI,IAAoB;AACpC,aAAW,QAAQ,SAAS,CAAC,GAAG;AAC9B,QAAI,CAAC,MAAM,OAAO,CAAC,KAAK,QAAQ,QAAS;AACzC,UAAM,OAAO,uBAAuB,IAAI;AAGxC,QAAI,CAAC,IAAI,IAAI,IAAI,EAAG,KAAI,IAAI,MAAM,GAAG,QAAQ,eAAe,KAAK,GAAG,EAAE;AAAA,EACxE;AACA,SAAO;AACT;;;ACjQA,IAAM,WAAmC,EAAE,MAAM,KAAK,IAAI,OAAO,IAAI,OAAO,IAAI,QAAQ,IAAI,QAAQ,IAAI,OAAO;AAC/G,IAAM,gBAAwC,EAAE,IAAI,YAAY,MAAM,QAAQ,IAAI,WAAW,IAAI,UAAU,OAAO,OAAO;AACzH,IAAM,SAAiC,EAAE,QAAQ,KAAK,QAAQ,KAAK,UAAU,KAAK,MAAM,IAAI;AAC5F,IAAM,YAAoC,EAAE,MAAM,KAAK,IAAI,OAAO,IAAI,OAAO,IAAI,QAAQ,MAAM,SAAS;AACxG,IAAM,YAAoC,EAAE,OAAO,WAAW,OAAO,WAAW,OAAO,WAAW,SAAS,WAAW,SAAS,WAAW,QAAQ,UAAU;AAGrJ,SAAS,gBAAgB,OAA4E;AAC1G,MAAI,CAAC,SAAS,OAAO,UAAU,SAAU,QAAO;AAChD,QAAM,IAAI;AACV,QAAM,MAAuC,CAAC;AAC9C,MAAI,EAAE,YAAY,SAAS,EAAE,QAAQ,KAAK,MAAM;AAAE,QAAI,aAAa,SAAS,EAAE,QAAQ;AAAI,QAAI,gBAAgB,SAAS,EAAE,QAAQ;AAAA,EAAI;AACrI,MAAI,EAAE,YAAY,SAAS,EAAE,QAAQ,KAAK,MAAM;AAAE,QAAI,cAAc,SAAS,EAAE,QAAQ;AAAI,QAAI,eAAe,SAAS,EAAE,QAAQ;AAAA,EAAI;AACrI,MAAI,EAAE,aAAa,SAAS,EAAE,SAAS,KAAK,KAAM,KAAI,YAAY,SAAS,EAAE,SAAS;AACtF,MAAI,EAAE,gBAAgB,SAAS,EAAE,YAAY,KAAK,KAAM,KAAI,eAAe,SAAS,EAAE,YAAY;AAClG,MAAI,EAAE,cAAc,UAAU,EAAE,UAAU,EAAG,KAAI,aAAa,UAAU,EAAE,UAAU;AACpF,MAAI,EAAE,aAAa,UAAU,EAAE,SAAS,EAAG,KAAI,QAAQ,UAAU,EAAE,SAAS;AAC5E,MAAI,EAAE,UAAU,UAAU,EAAE,UAAU,YAAY,EAAE,UAAU,QAAS,KAAI,YAAY,EAAE;AACzF,MAAI,EAAE,YAAY,cAAc,EAAE,QAAQ,EAAG,KAAI,WAAW,cAAc,EAAE,QAAQ;AACpF,MAAI,EAAE,UAAU,OAAO,EAAE,MAAM,KAAK,KAAM,KAAI,aAAa,OAAO,EAAE,MAAM;AAC1E,MAAI,EAAE,UAAU,UAAU,EAAE,MAAM,KAAK,KAAM,KAAI,eAAe,UAAU,EAAE,MAAM;AAClF,MAAK,MAAqB,WAAW,KAAM,KAAI,SAAS;AACxD,SAAO,OAAO,KAAK,GAAG,EAAE,SAAS,MAAM;AACzC;;;ACMO,IAAM,mBACX;AAiCK,IAAM,uBAAuB;AAAA,EAClC;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AACF;;;AC/EO,IAAM,uBAA0C,OAAO,OAAO;AAAA,EACnE;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AAAA,EACA;AACF,CAAC;AAEM,IAAM,0BAA+C,IAAI,IAAI,oBAAoB;;;AC36DjF,IAAM,yBAAyB;AAC/B,IAAM,wBAAwB;AAC9B,IAAM,oBAAoB;;;ACW1B,IAAM,oBAAoB;AACjC,IAAM,gBAAgB,oBAAI,IAAI,CAAC,UAAU,OAAO,QAAQ,CAAC;AAWlD,IAAM,kBAAkB;AA+CxB,SAAS,WAAW,IAAiB,QAAuC;AACjF,QAAM,YAAsB,CAAC;AAC7B,WACM,SAAS,GAAG,eAChB,UAAU,OAAO,YAAY,UAAU,CAAC,cAAc,IAAI,OAAO,OAAO,GACxE,SAAS,OAAO,eAChB;AACA,cAAU,QAAQ,OAAO,QAAQ,YAAY,CAAC;AAAA,EAChD;AACA,QAAM,WAAW,GAAG,gBAAgB,MAAM,KAAK,GAAG,cAAc,QAAQ,IAAI,CAAC;AAC7E,SAAO;AAAA,IACL;AAAA,IACA;AAAA,IACA,cAAc,KAAK,IAAI,SAAS,QAAQ,EAAE,GAAG,CAAC;AAAA,IAC9C,KAAK,GAAG,QAAQ,YAAY;AAAA,EAC9B;AACF;AAeO,SAAS,gBACd,KAQA,UAAU,OACiB;AAC3B,QAAM,SAAS,oBAAI,IAAoB;AACvC,QAAM,MAAiC,CAAC;AACxC,QAAM,WAAW,UAAU,GAAG,iBAAiB,IAAI,eAAe,KAAK;AACvE,aAAW,MAAM,IAAI,iBAAiB,QAAQ,GAAG;AAC/C,QAAI,GAAG,eAAe,QAAQ,QAAQ,EAAG;AAGzC,UAAM,OAAO,CAAC,cAAc,IAAI,GAAG,OAAO,KAAK,GAAG,QAAQ,eAAe,IACrE,WACA,GAAG,QAAQ,YAAY;AAC3B,UAAM,IAAI,OAAO,IAAI,IAAI,KAAK;AAC9B,WAAO,IAAI,MAAM,IAAI,CAAC;AACtB,QAAI,KAAK,EAAE,MAAM,GAAG,IAAI,IAAI,CAAC,IAAI,GAAG,CAAC;AAAA,EACvC;AACA,SAAO;AACT;","names":[]}
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "@bettercms-ai/types",
3
- "version": "1.20.0",
3
+ "version": "1.21.0",
4
4
  "type": "module",
5
5
  "sideEffects": false,
6
6
  "main": "./dist/index.js",