Skip to main content

Datastar HTML Attributes

The zio-http-datastar-sdk provides extensions to the templating module that allow you to easily add type-safe Datastar attributes to your HTML elements:

ZIO HTTP AttributeDatastar HTML AttributeDescription
dataAttrdata-attrSet arbitrary attributes.
dataBinddata-bindBinds signal name to input/select/textarea values.
dataClassdata-classToggle classes.
dataComputeddata-computedComputed values from expressions.
dataEffectdata-effectSide effects from expressions.
dataIgnoredata-ignoreIgnore this element and its children.
dataIgnoreSelfdata-ignore__selfIgnore only this element, not children.
dataIgnoreMorphdata-ignore-morphIgnore morphing for this element.
dataIndicatordata-indicatorLoading indicator.
dataJsonSignalsdata-json-signalsJSON signal declarations.
dataOndata-onEvent listeners (click, input, etc.).
dataOnIntersectdata-on-intersectExecute when element intersects viewport.
dataOnIntervaldata-on-intervalExecute on interval.
dataOnLoaddata-init (deprecated)Execute when element loads (generates data-init).
dataOnSignalPatchdata-on-signal-patchExecute when signal patches.
dataOnSignalPatchFilterdata-on-signal-patch-filterFilter signal patch events.
dataPreserveAttrdata-preserve-attrPreserve attributes during morphing.
dataRefdata-refAssign a local reference.
dataShowdata-showShow element when expression is truthy.
dataSignalsdata-signalsDeclare/expose signals.
dataStyle("styleName")data-styleSets inline style.
dataTextdata-textSets element text content from expression.

Using Attributes

Most of these attributes have a := dsl method that takes a Js value representing the Datastar expression in which you can use signals, JavaScript code, or special @ commands to interact with the server. You can use the Js helper to create these expressions or use the js interpolator which has compile-time checking of the expressions.

For example, you can use the dataOnLoad attribute to trigger a server request when the page loads:

import zio.http._
import zio.http.datastar._
import zio.http.template2._
import zio.http.endpoint.Endpoint

body(
dataOnLoad := js"@get('/hello-world')",
dataOn.load := Endpoint(Method.GET / "hello-world").out[String].datastarRequest(()),
div(
className := "container",
h1("Hello World Example"),
div(id("message"))
)
)

If you want a type-safe DSL, we recommend using the Endpoint API instead of a JavaScript expression when using the dataOn attribute to define a Datastar server request:

import zio.http.datastar._
import zio.http.endpoint.Endpoint

body(
dataOn.load := Endpoint(Method.GET / "hello-world").out[String].datastarRequest(()),
div(
className := "container",
h1("Hello World Example"),
div(id("message"))
)
)

The dataOn attribute has several event listeners that you can use to handle different events on elements. For example, the dataOnLoad can be written as dataOn.load; there are many other events available, such as click, input, submit, change, focus, blur, etc.

Each of the attributes may have a couple of modifiers, about which you can learn in their respective sections in the Datastar documentation. They are all modeled as a type-safe DSL in the zio-http-datastar-sdk module. For example, you can use the debounce modifier on the dataOn.input attribute to debounce input events:

import zio._

dataOn.input.debounce(300.millis) := Js("@get('/search?q=' + $query)")
// datastar equivalent: <p data-on-input__debounce.300ms="@get('/search?q=' + $query)"></p>

Working with Signals

Another important attribute is dataSignals, which allows you to declare signals that can be used in the Datastar expressions. You can declare a signal using the dataSignals attribute as follows:

val $currentTime = Signal[String]("currentTime")

dataSignals($currentTime) := js"'--:--:--'"

This declares a signal named currentTime of type String with an initial value of 00:00:00. You can then use this signal in other Datastar attributes. For example, you can use dataText to display the current time:

span(
dataSignals($currentTime) := js"'--:--:--'",
dataText := $currentTime,
dataOn.load := Endpoint(Method.GET / "server-time").out[String].datastarRequest(()),
)

In this example, the dataText attribute binds the text content of the span element to the currentTime signal, and the dataOn.load attribute triggers a server request to update the signal when the page loads.

Server-side updates to signals are sent using the ServerSentEventGenerator#patchSignals method.