# `AshUi.Patch.Skeleton`
[🔗](https://github.com/hyperbob-labs/ash_ui/blob/main/lib/ash_ui/patch/skeleton.ex#L1)

Target-specific static skeleton compiled from a resource's lowered view:
interleaved static markup + ordered dynamic refs, the exact
statics/dynamics contract the host bridge's `Rendered` structs consume.

Compilation renders the view ONCE through the ordinary render pipeline
(`ViewRender` → `RenderTree.render` → `RenderTarget.Html`) with unique
alphanumeric sentinels substituted at every dynamic position, then splits
the produced HTML on those sentinels. Statics are therefore byte-aligned
with the full renderer by construction — themes, parts, aria, event
bindings and attribute ordering all come from the same code path. The
compiled skeleton is pure data + evaluator closures; the runtime render
path never materializes a tree.

Dynamic refs (document order):

    {:text, addr, eval}                 — escaped text position
    {:attr_pair, addr, name, eval}      — whole ` name="value"` pair
    {:attr_value, addr, name, eval}     — value embedded in a merged attr
    {:branch, addr, cond_eval, arms}    — arms: %{true: skel|nil, false: skel|nil}
    {:keyed, addr, items_eval, item}    — item: %{skeleton, as, index}
    {:child, addr, resource}            — nested render(Resource, input)

`addr` is the SAME lowered address the patch table assigns its slots, so
the changed-address set from
`AshUi.Patch.Runtime.changed_addresses/3` gates re-emission
directly.

# `dyn`

```elixir
@type dyn() ::
  {:text, String.t(), (term() -&gt; term())}
  | {:attr_pair, String.t(), String.t(), (term() -&gt; term())}
  | {:attr_value, String.t(), String.t(), (term() -&gt; term())}
  | {:branch, String.t(), (term() -&gt; term()),
     %{true: t() | nil, false: t() | nil}}
  | {:keyed, String.t(), (term() -&gt; term()), map()}
  | {:child, String.t(), module()}
```

# `t`

```elixir
@type t() :: %AshUi.Patch.Skeleton{
  dynamics: [dyn()],
  fingerprint: term(),
  root?: term(),
  statics: [binary()]
}
```

# `compile`

```elixir
@spec compile(module(), map() | nil, keyword()) :: t()
```

Compile the skeleton for a lowered view node of `resource`. `base`
addresses the subtree: arm and item skeletons compile under their REAL
address prefix (`addr/t`, `addr/f`, `addr/*`) so element addresses are
unique across the whole table — binding keys depend on it.

---

*Consult [api-reference.md](api-reference.md) for complete listing*
