re-frame.ui¶
re-frame.ui is the first-party compiled-view substrate (Maven coordinate
day8/re-frame2-ui). Views are authored as defview + hiccup; the compiler lowers
templates to direct React construction (browser) and a versioned structural tree
(JVM). There is no hiccup interpreter in production bundles on the compiled path.
This namespace is not re-exported from re-frame.core. Require it explicitly and
install its adapter at boot:
Concept teaching lives in the UI guide (when published under docs/ui/) and the
substrate design suite. This page is the contract surface for public symbols.
Stage honesty. Front-porch symbols below are the ruled public API. Some runtime behaviours (committed DOM handlers, full lease semantics, hydration manifests) land with later substrate stages; the names and signatures are the v1 surface. Where a direct call is only a compile-time resolution symbol, the description says so.
Boot¶
adapter¶
- Kind: Var (adapter map)
- Signature: pass to
(rf/init! ui/adapter) - Description: The
re-frame.uisubstrate adapter. CLJS installs the native React observation substrate (no Reagent / UIx / Helix). JVM uses the headless atom realisation of the same closed adapter contract. Discriminator:rf.adapter/ui. Destroying the adapter tears down every public compiled Root, then the generic React spine. - Example:
Views¶
defview¶
- Kind: macro
- Signature:
- Description: The one component form. A pure function of zero or one props map to a hiccup template, compiled to direct React (browser) and the JVM structural tree. Header destructuring lowers to per-slot reads. Closed options map:
:props— Malli schema (dev-checked; compile-time when the call site is literal):id— registry override:display-name— React display name Every view is memoised on a per-slotrf=comparator and registers under the registrar's:viewkind. No Form-2 / Form-3 / positional args.- Example:
custom-element¶
- Kind: macro
- Signature:
- Description: Declares a custom-element tag and which kebab-case prop names are JS properties (camelCased on the client). Undeclared names are attributes; undeclared elements need no declaration (all-attributes default). JVM emits attributes only; property props apply at hydration.
- Example:
Template forms (compiler-owned)¶
These symbols resolve in templates so the compiler can lower them. A direct call from ordinary Clojure code fails loud (they are not runtime helpers).
sub¶
- Kind: function (compile-time authoring form)
- Signature:
(sub query-vector) → value(inside a compiled view only) - Description: Lexical subscription read site. Returns the current value; the view
re-renders when it changes. Conditional sites are legal; sites inside
forare a compile error (extract a keyed child view). Not a one-shot helper — use coresubscribe/subscribe-onceoutside views. - Errors: direct call →
:rf.error/ui-tree-malformed.
lease¶
- Kind: function (compile-time authoring form)
- Signature:
(lease descriptor) - Description: Declares resource interest while the view is mounted/visible. Does
not return data and does not fetch; read status via
(sub [:rf/resource …]). Leading declaration form in adefviewbody. Direct calls fail loud.
frame¶
- Kind: function (compile-time authoring form)
- Signature:
(frame) → {:frame :dispatch :dispatch-sync :subscribe} - Description: Inside a compiled view, returns the capture-frame-shaped ops bundle
bound to the committed frame. Ops fail loud after the frame incarnation dies
(
:rf.error/frame-destroyed). Outside views userf/capture-frame.
raw¶
- Kind: function (template interop form)
- Signature:
(raw react-element) - Description: Embed an existing React element in child position. On the JVM a
rendered
rawchild is a host-op error.
html¶
- Kind: function (template interop form)
- Signature:
(html string) - Description: Trusted markup bypass — the sole child of a DOM element
(
[:div (ui/html s)]). Visible at the call site; both emitters treat it identically.
raw-fn¶
- Kind: function
- Signature:
(raw-fn f) → f - Description: Identity-as-protocol callback marker (also the explicit callback-ref form). Passes the function through to the host untouched.
spread¶
- Kind: function (template interop form)
- Signature:
(spread base overrides) - Description: Runtime prop-map merge through the same conversion rule table
as the compiler. Legal in a DOM element's props position only:
[:div (ui/spread base attrs)]. Direct call →:rf.error/ui-spread-outside-template.
Roots and mounting¶
mount¶
- Kind: macro
- Signature:
- Description: One-shot client mount: create-root + frame preflight +
render!. Idempotent per root (same root-id + container re-renders; live frames are not re-seeded).root-formmust be a literal vector. Identity opts (:root-id,:disambiguator,:identifier-prefix) are compile-time literals. Host error callbacks (:on-uncaught-error, …) are plain fns. Returns the Root. - Example:
create-root¶
- Kind: macro
- Signature:
(create-root dom-node opts) → Root - Description: Fix root identity for the Root's lifetime without rendering.
Authored
:root-idis required (no root form to derive from). Prefermountfor the one-liner path.
render!¶
- Kind: macro
- Signature:
(render! root root-form) - Description: Render / re-render a literal root form into an existing Root. Frame plans in the top region preflight before render. Identity is unchanged.
hydrate-root¶
- Kind: macro
- Signature:
- Description: Hydrating mount. Identity comes from the server manifest, not
client identity opts (passing
:root-id/:identifier-prefixis an error). Full hydration lands with SSR roots; earlier stages fail loud with:rf.error/root-manifest-invalidwhen no valid manifest is present.
unmount!¶
- Kind: function
- Signature:
(unmount! root) → nil - Description: Total teardown: unmount the React root and unregister the root-id. Idempotent. Client-only; JVM host-op error.
frame-root¶
- Kind: function (root-form template symbol)
- Signature:
(frame-root {:id … :initial-events …} & children) - Description: Static ENSURE plan wrapper, legal only in the top region of
a root form passed to
mount/render!/hydrate-root.:idmust be a compile-time keyword. Creates the frame if absent, seeds:initial-eventsonce, never destroys on unmount. Compiles away — direct call fails with:rf.error/ui-frame-root-outside-root-form. To scope an already-live frame inside a view tree, useframe-provider.
frame-provider¶
- Kind: function (template symbol)
- Signature:
(frame-provider {:frame f} & children) - Description: Scope a subtree to an already-live frame through React
context. Creates nothing, seeds nothing, destroys nothing.
:frameis a runtime frame id or live frame value. Absent frame →:rf.error/frame-provider-frame-absent. Direct call fails with:rf.error/ui-frame-provider-outside-template.
See also¶
re-frame.core— events, subs, frames (make-frame,capture-frame), boot (init!)- Introduction — the pure dataflow loop this substrate plugs into
- Substrate design / UI guide under the synthesis suite (force-tracked findings) when
reader-facing
docs/ui/is not yet landed