Datastar Integration
Datastar is an ultra-lightweight declarative frontend enhancement library. It provides a minimalist way to manage frontend state through data-signals attributes and works seamlessly with Nex’s Action mechanism.
1. Core Philosophy
The heart of Datastar lies in Signals. It doesn’t use a Virtual DOM; instead, it establishes reactive bindings by scanning HTML attributes.
- Zero Build: No Node.js required, included directly via CDN.
- Extreme Transparency: State is declared directly on HTML tags.
-
Nex Synergy: Use
@getand@postexpressions to call Nex Actions directly for partial DOM updates (Morphing).
2. Integration Method
Include the Datastar script in your src/layouts.ex:
<script type="module" src="https://cdn.jsdelivr.net/gh/starfederation/datastar/dist/datastar.js"></script>
3. Core Application Patterns
A. Reactive Signals and Binding
Use data-signals to define state, data-bind for two-way binding, and data-text to display values.
~H"""
<div data-signals="{ name: 'Nex' }">
<input type="text" data-bind:name class="border p-2">
<p class="mt-2">Hello, <span data-text="$name"></span>!</p>
</div>
"""
B. Backend Requests and Morphing (Crucial)
Datastar allows using @get or @post in data-on attributes to initiate asynchronous requests. You can pass signal values as parameters. Nex returns HTML fragments with matching ids, and Datastar automatically performs the Morph update.
# Page Module
~H"""
<div data-signals="{ inputValue: '' }">
<input type="text" data-bind:inputValue class="border">
<!-- Send POST request with parameters -->
<button data-on:click="@post('/process', { text: $inputValue })" class="btn">
Process
</button>
<div id="result" class="mt-4 p-4 bg-gray-50">Waiting for result...</div>
</div>
"""
C. Merge Strategies
Control how backend responses are merged into the existing DOM using the data-merge attribute.
- morph (default): Smart diff-based update.
- append: Append to the end.
- prepend: Prepend to the beginning.
~H"""
<div id="logs" data-merge="append" class="space-y-2">
<button data-on:click="@post('/add_log')">Add Log</button>
<div class="text-sm text-gray-500 italic">Logs will be appended here...</div>
</div>
"""
D. JavaScript Expressions
Datastar supports standard JavaScript expressions directly within attributes. You can use this for string manipulation, mathematical operations, or array handling.
~H"""
<div data-signals="{ x: 5, y: 3, text: 'hello' }">
<!-- Math -->
<div data-text="$x + $y"></div>
<!-- String Methods -->
<div data-text="$text.toUpperCase()"></div>
<!-- Ternary Logic -->
<div data-text="$x > $y ? 'X is larger' : 'Y is larger'"></div>
</div>
"""
4. The Tao of Datastar
When integrating Datastar with Nex, follow these core principles:
- Hypermedia First: Prefer returning HTML fragments from the server instead of JSON whenever possible.
- Frontend Reactivity: Use Datastar signals for UI state that doesn’t need persistence (e.g., tabs, modal visibility).
-
Minimal JavaScript: Use
data-*attributes to declare behavior rather than writing imperative JS. -
Smart Morphing: Leverage Datastar’s Morphing mechanism (via
idmatching) to update only changed DOM elements, preserving form focus and animations.
5. Datastar Directive Cheat Sheet
| Directive | Description |
|---|---|
data-signals |
Defines reactive state (JSON format). |
data-text |
Binds element text content to expression results. |
data-bind |
Establishes two-way binding between input and signal. |
data-on |
Listens for events and executes expressions (supports @get, @post, etc.). |
data-show |
Decides visibility based on expression result. |
data-class |
Dynamically adds or removes CSS classes based on signals. |
data-attr |
Binds HTML attributes (e.g., disabled). |
data-computed |
Defines derived signals (computed properties). |
data-merge |
Defines the merge strategy for backend responses (morph, append, prepend). |
6. Complete Example Project: Datastar Tutorial
We provide a complete, step-by-step tutorial project covering all core scenarios from basic binding to AI streaming chat:
Tutorial Content and Feature Distribution:
📍 Basic (Lessons 1-3)
-
Quick Start (
index.ex): Learndata-onevent listening and simple@postbackend Morphing updates. -
Reactive Signals (
signals.ex): Masterdata-signals(state definition),data-bind(two-way binding),data-show(visibility), anddata-computed(computed properties). -
JS Expressions (
expressions.ex): Demonstrates how to use JS directly in attributes to handle strings, arrays, and logical operations.
📍 Intermediate (Lessons 4-5)
-
Requests and Merging (
requests.ex): Deep dive into passing parameters via@get/@post, and list merging strategies likedata-merge="append". -
The Tao of Datastar (
tao.ex): Summarizes the 6 design principles, including Hypermedia First and Backend as Source of Truth.
📍 Real-world (Advanced & Apps)
-
Advanced Features (
advanced.ex):-
data-init: Automatically execute on page load (e.g., initializing long-lived connections). -
data-on-intersect: Triggered when scrolling into viewport (implements infinite scroll/lazy loading). -
data-indicator: Fully automatic request loading state display. -
data-ref: Direct DOM element reference for complex interactions (e.g., auto-focusing).
-
-
AI Chatbot (
chat.ex): Combined with Nex’sNex.stream(fn}return value to implement AI word-by-word streaming responses. -
Real-time Form Validation (
form.ex): Complex validation logic driven by pure frontend signals, no backend round-trips required. -
Todo MVC (
todos.ex): A comprehensive showcase of CRUD operations, client-side list filtering, and dynamic style switching.
7. Best Practices (Nex + Datastar)
- Fine-Grained Updates: Leverage Datastar’s Morphing to return only the smallest necessary HTML fragments.
-
Avoid Redundant State: For pure UI interactions (toggles, input previews), prioritize Datastar signals; for business data (saving to DB), use
@postto call Nex Actions. -
Computed Properties: Use simple JavaScript expressions directly in
data-textfor logic composition.
6. Datastar vs Alpine.js
- Alpine.js: Better suited for traditional UI interactions (modals, collapse menus, simple logic).
- Datastar: Advantageous in handling large-scale state sharing across components and complex frontend business logic.
In a Nex project, you can choose either based on your team’s preference. Nex’s file system routing and Action mechanism coordinate perfectly with both.