DEV Community

Alex Spinov
Alex Spinov

Posted on

htmx Has a Free API: Build Modern Web Apps Without JavaScript Frameworks

What if you could build interactive web apps using just HTML attributes? No React. No build step. No npm install.

That's htmx.

What Is htmx?

htmx gives any HTML element the ability to make HTTP requests and update the DOM. It extends HTML instead of replacing it.

<script src="https://unpkg.com/htmx.org@2.0.0"></script>

<!-- Click button → GET request → replace #results -->
<button hx-get="/api/users" hx-target="#results">
  Load Users
</button>
<div id="results"></div>
Enter fullscreen mode Exit fullscreen mode

That's a complete AJAX interaction. No JavaScript written.

The Core Attributes

<!-- Any element can make requests -->
<button hx-get="/api/data">GET request</button>
<form hx-post="/api/users">POST on submit</form>
<button hx-delete="/api/users/1">DELETE request</button>

<!-- Control what gets updated -->
<button hx-get="/search" hx-target="#results">Search</button>
<button hx-get="/row" hx-swap="afterbegin">Prepend</button>
<button hx-get="/row" hx-swap="outerHTML">Replace self</button>

<!-- Trigger on any event -->
<input hx-get="/search" hx-trigger="keyup changed delay:300ms" name="q">
<div hx-get="/news" hx-trigger="every 30s">Live feed</div>
Enter fullscreen mode Exit fullscreen mode

Real Example: Live Search

<input type="search"
       name="q"
       hx-get="/search"
       hx-trigger="input changed delay:300ms"
       hx-target="#search-results"
       placeholder="Search users...">

<table>
  <tbody id="search-results">
    <!-- Results appear here -->
  </tbody>
</table>
Enter fullscreen mode Exit fullscreen mode

Server returns HTML fragments, not JSON. Your server template renders the <tr> rows. htmx drops them in.

Why Developers Are Switching

1. No build step — Add one <script> tag. Done.

2. Server renders HTML — Use Django, Rails, Flask, Express, Go — whatever. Return HTML, not JSON.

3. Progressive enhancement — Works without JavaScript (forms still submit).

4. Tiny — 14KB minified+gzipped vs React 42KB + ReactDOM 130KB.

5. Simplicity — A junior developer can be productive in 30 minutes.

htmx + Any Backend

# Flask
@app.route("/search")
def search():
    q = request.args.get("q", "")
    users = User.query.filter(User.name.contains(q)).all()
    return render_template("partials/user_rows.html", users=users)
Enter fullscreen mode Exit fullscreen mode
// Go
func searchHandler(w http.ResponseWriter, r *http.Request) {
    q := r.URL.Query().Get("q")
    users := searchUsers(q)
    tmpl.ExecuteTemplate(w, "user_rows", users)
}
Enter fullscreen mode Exit fullscreen mode

The server returns an HTML fragment. htmx handles the swap. That's the whole architecture.


Need data tools or custom web solutions? Check out my scraping toolkit or email spinov001@gmail.com.

Top comments (0)