https://htmx.org/essays/when-to-use-hypermedia/
Also, please try unpoly:
It’s another excellent hypermedia oriented library
Edit: the article is actually not nearly as unreasonable as I thought based on the just-f*king-use template. Still prefer a chill vibe for htmx though.
> Another practical reason not to use htmx is that there are, rounding off, zero htmx jobs.
> I just did a search for htmx jobs on indeed and found a grand total of two: one at Microsoft and one at Oak Ridge National Laboratory.
> A search for “react”, on the other hand, gives 13,758 jobs.
> Seriously, developer, which of these two technologies do you want to hitch your career to?
I do not advocated for htmx; but this take is so bad!
Resume-driven development should not be a thing. If you are a professional developer, building a product for a user, your primary concern should not be the job market for when you quit the company you are working for, but rather making the best product possible for the user within the context of the current company. And if the product is such that it does not call for react, or some other javascript-rich client, then you shouldn't use it however many react jobs there may be on Indeed.
(In all seriousness, this entire article is facetious and is highlighting the strengths of HTMX. They are not sincerely advocating for 'resume driven development'.)
And the frameworks are churned continuously and are also bug-ridden nightmares, so that continuous development and support is needed to keep websites functioning and secure.
Any reduction in framework complexity threatens the whole edifice.
- How easy is it to hire people with experience in this?
- Relatedly, how easy will it be for the org to maintain this software after I (or the original team) leaves?
When NoRedInk switched to Elm, Richard Feldman, who was asked about whether this impacted their hiring experience in any negative way, said that on the contrary, hiring had never been better, because although the pool of candidates grew smaller, their quality (either prior experience of working with type-safe functional programming languages, or enthusiasm for learning them) got higher.
When Alex Russell announced several openings at Microsoft for development of design systems with web components, and certainly no react, he said this attracted a lot of really strong candidates.
I am not saying that a good web developer should be able to pick up any exotic language, such as elm, or purescript, or rescript, or clojurescript at no time; but what I am saying is that as far as web frameworks are concerned, they shouldn't be a criterion for hiring, and are unlikely to become an obstacle to it.
Pretend this is not about library choice, but rather about language choice. One language has 2 jobs, and the other language 13k jobs. I doubt you'd think for more than a second.
The Hacker News website runs on Lisp. How many jobs do you see on the market that ask for Lisp? And yet, for what it is, this site is amazing! I don't see them rushing to migrate to a python backend and a react-based frontend, no matter how many jobs there are for those.
In other words, HN does not have the problem that you are going to have if you use an unpopular language for your project.
If you choose LISP for your not-HN project, then you have a problem. The chances are very slim of finding any experienced LISP devs who are also in your salary range, within commute distance, want to work on your project, are a good fit for the team, etc.
You're probably going to have to hire a dev who is a good match on all those other things and train them up on LISP. Unless they've had experience with other functional languages (not that unusual, but not common either) then they're going to have to learn an entire new paradigm. All of which means that they'll spend the first six months going slow while they learn, and needing support from the rest of the team.
And you'll need to convince them to join you (probably by paying them more money) because if they spend a few years on your project learning LISP, they probably won't be able to use those skills for their next gig, and their current skills in a popular language will go out of date.
LISP is a great language, and if used well it will probably give you an advantage over the competition using other, more mundane, languages. But is that going to be enough of an advantage to counteract your slower onboarding, higher salaries, and greater recruitment workload?
It's a list of articles and comments. It would take like 3 pages from W3Schools to build this thing.
Firstly, because this site happily handles the amount of traffic that puts many hobbyist sites that happen to get on its front page into a hug of death; so its developers must have done something right on the backend that is probably above the web programming 101 level.
But secondly, because this was precisely my point. One does not need a super popular front-end framework to make an awesome web product, and the HackerNews site is a testament to that.
No you're not. You're just trying to respond with something witty.
It's a message board with 1% of the functionality most sites people are building with frameworks.
> Firstly, because this site happily handles the amount of traffic that puts many hobbyist sites that happen to get on its front page into a hug of death;
Lol are you really implying it's hard to scale a message board?
> One does not need a super popular front-end framework to make an awesome web product, and the HackerNews site is a testament to that.
IT'S A MESSAGE BOARD. Nobody is building message boards anymore. Using HN as an example for anything other than building a dirt simple message boardsays more about your refusal to recognize the need to these new technologies than it does about those technologies.
> awesome web product
A. Message. Board.
I am implying that it is beyond the "3 pages from W3Schools", as you put it.
> A. Message. Board.
Yes. A fast, reliable, accessible message board that I and many others thoroughly enjoy. An awesome product.
Again, I have never suggested that its ui is complex. In fact, it's glorious how simple it is. This is the point that those htmx people make: use simple tools for simple UIs; and also, try to make your UIs simple.
NO. IT. ISN'T.
lol. Anytime React is mentioned people like you rush in to tell others just how great stuff like...checks notes...a message board is. As if it in any, way, shape or form adds to the conversation.
You just couldn['t help yourself from rushing in to defend the simplest site on the planet (lol written in LISP) as if it demonstrates anything other than some rando building a w3 schools site in a language no one uses anymore.
This 'simplest site on the planet' does the job that it is tasked to do. Brilliantly. I am baffled by why you would scorn at simplicity.
> as if it demonstrates anything
It demonstrates that a great product (a product that many people use and love) can be built with simple tools. At least on the frontend.
You mean the message board? The website that has a grand total of 2 functions: post and comment?
> And yet, for what it is, this site is amazing!
It's 2 colors and text. That's it.
> ! I don't see them rushing to migrate to a python backend and a react-based frontend, no matter how many jobs there are for those.
It's A MESSAGE BOARD. A. MESSAGE. BOARD.
Have you seen how many blog or portfolio sites people build with react? Sometimes even adding nextjs into the mix? Blogs!
What is this an objection to? If you follow this thread upwards, where was it suggested that we should be talking about things so complex that nobody, or only very few, could build? The whole pitch of htmx is that it is proposed for building things that anybody could build. The article in the title assumes that the target audience isn't building Google Docs, Figma, video editors, or CAD tools.
> How many jobs do you see on the market that ask for Lisp? And yet, for what it is, this site is amazing! I don't see them rushing to migrate to a python backend and a react-based frontend, no matter how many jobs there are for those.
You pointing out that the dumb simple message board is written in LISP and doesn't need anymore more is a bit absurd.
No shit they aren't rushing to upgrade it. IT BARELY DOES ANYTHING TO BEGIN WITH.
Anytime a certain class of developer see the word "React" that end up saying the most ridiculous shit. Nobody, I mean nobody, thinks HN is a site worthy of replicating or achieving unless they're part of the .0000002% who couldn't find a prepackaged board from Google search results.
Wait what? You haven't seen all the hackernews clones that people make as an exercise of website building? You haven't seen lobste.rs?
All of those hacker news clones are by Hacker News people for Hacker News people, usually to implement features Hacker News never will.
Nobody outside of the HN community is holding up Hacker News as an exemplar of superior design or engineering, much less of a Lisp implementation. Anyone who's touched the Arc Lisp forum code knows how few fucks pg gave about the design of anything but the language itself. And still the original forum was so inefficient it would keel over and die under moderate traffic and internal links would time out and people's comments would just never post.
The other language - HTML - has over 30,000 jobs
I feel like only a backend developer trying to score "gotcha" points could make this argument and be confident about it.
You mean a real developer?
Survival is more important.
On the other hand htmx is nice to have, if it solves your problem. Still you should use what benefits you in the context of a customer.
If you ask me, I think the web is for viewing static content, download content, or share links that your browser should delegate to an app.
Reality is often disappointing. I'd love to be working deep in my Vulkan rendering knowledge, but it's clear right now with my lack of job that I need to grind leetcode instead and work on personal projects first. Graphics programming is already such a stiff bar to get into and it's only gotten stiffer as I go along.
I'm going a little bit on a limb by also cultivating Rust, so I'm not optimizing my RDD. But I still looked for a compromise of what I like and what's in demand.
Want to make a dropdown that updates a enumerated field on a record? Easy.
Want to make a modal dialog when users create a new content item? Easy.
Want a search box with autocomplete? Easy.
As I see it the basic problem of RIA front ends is that a piece of data changed and you have to update the front end accordingly. The complexity of this problem ranges from:
(1) One piece of information is updated on the page (Easy)
(2) Multiple pieces of information are updated but it's a static situation where the back end knows what has to be updated (Easy, HTMX can update more than one element at a time)
(3) Multiple pieces of information but it's dynamic (think of a productivity or decision support application which has lots of panes which may or may not be visible, property sheets, etc -- hard)
You do need some adaptations on the back end to really enjoy HTMX, particularly you have to have some answer to the problem that a partial might be drawn as part of a full page or drawn individually [1] and while you're there you might as well have something that makes it easy to update N partials together.
[1] ... I guess you could have HTMX suck them all down when the page loads but I'd be worried about speed and people seeing incomplete states
None of this mentions anything at all mentioned in the parent post.
Was it just a shameless way to ride on what would become a top comment?
I'm currently working on a side project in Rails using Stimulus but sometimes I wonder if Stimulus is overkill with all of the controllers and stuff as well. Do you have an opinion on when you should reach for something like Inertia or Stimulus over htmx?
htmx is lower level and focuses on generalizing the idea of hypermedia controls
I'm not yet sure whether this is a good thing or not -- I'll let you know once my latest iteration of my web framework is finally working as I envisioned, he-said sort-of-jokingly, which should be Soon Now.
But yeah, either alternative still beats React by a country mile, since everything related to that descends into madness right away.
Like, even just now, Claude Code with Opus 4-dot-latest, is absolutely convinced you need a bunch of fragile cascading Javascript listeners to dismiss a lower-level menu in case a dialog is opened, while the Unpoly docs, correctly and clearly, point out that 'shatter' exists for just that purpose.
And this is one of the use cases that I continue to highlight as the achilles heel of LLMs. I'm not holding it wrong: they're not reading it right.
Said the horse with laser eyes (¬_¬)
Third link on the page ("read the long story") points to https://triskweline.de/unpoly-rugb/, which renders as a blank page with NoScript enabled.
Sigh.
Still not perfect -- the demos should work too. I love the idea of a progressive framework and am willing to work around a few things to get it.
And if there was originally a harsher response which I missed, well then I hope it wasn't merited.
I'm pretty light-hearted about this topic! It's more fun that way.
The problem you've encountered is that people are annoying. I'm afraid that's not specific to any one technology or community. Fortunately, annoying blog posts are easily ignored and would never stop a useful tool from being adopted anyway.
Of course it will work. I can vibe code the most terrible web framework you have seen within 20 minutes and claim it is better than React, but what does it prove?
> You write zero JavaScript > The whole library is ~14kb gzipped
Oh sure, if there is nothing else in your UI, and if your Python/Go/whatever backend server has 0 dependency, which almost never happens.
I appreciate the basic demos, but I think what would really sell me is showing the extensibility story. Show me what it looks like when I need it to do something a bit beyond what it has in the box. Where do I add the JavaScript for that? Is it raw, inline, or are we back to packages and bundling and a build step? Am I building application JS, or some kind of extension or plugin to htmx itself? How chained am I going to be to its specific paradigms and opinions?
The page says htmx isn't for writing a true SPA like Google Docs, but where's the line? Show me an app that has pushed up against the limits of this system, and what happens in that scenario.
I'm not sure "fear" is exactly the right word here, but it's something I consciously evaluate for when looking at any new framework or library. Anything that has a lot of "magic" or "by-convention" type config is subject to this.
You start with the "hello world" example, and then you hit that wall. The test of an awesome framework vs a fundamentally limited (or even broken) one is: can you build on what you have with extensions, or do you have to rewrite everything you did? There's a lot of these where as soon as you want to do something slightly custom, you can't use _any_ of the magic and have to redo everything in a different way.
This isn't just libraries either. Another almost worse example is AWS Elastic Beanstalk. Simple way to get an app up and going, and it handles a lot of the boilerplate stuff for you. The problem is as soon as you want to extend it slightly, like have another custom load balancer route, you actually have to completely abandon the entire thing and do _everything_ yourself.
This is a really hard thing to get right, but in my view is one of the things that contributes to a framework's longevity. If you hit that wall and can't get past it, the next project you do will be in something else. Once enough people start posting about their experiences hitting the wall, other people won't even pick it up and the framework dwindles to a niche audience or dies completely.
I think this scenario would either be very apparent early on in the project, or wouldn't actually be that challenging. There are a couple ways you could run into the limits of HTMX:
1. You require purely client side interactivity. The right (IMO) way to use HTMX is as a replacement for sending JSON over the wire and rendering it into HTML on the client, so if your app has features that _wouldn't_ be done that way, you should reach for something else. Fortunately there's lots of solutions to this problem. You can use built in browser features to achieve a lot of the basics now (e.g. the <details> tag means you don't really need custom scripts if you just want an accordion), write simple vanila scripts, or adopt light weight libraries like alpinejs or the creator of HTMX's (only slightly deranged) hyperscript.
2. Maybe your purely client side interactivity needs are complex enough that you do need a SPA framework. At that point you can adopt the islands architecture and create interactive components in your fraemwork of choice, but continue to use hypermedia to communicate with the backend.
3. If you can't easily separate client side state (handled with javascript, potentially with the aid of frameworks) from server state (handled on the server and sent to the client via hypermedia), you can again adopt the islands architecture and have your islands manage their own network requests to the backend.
4. If the above applies to all of your app, then hypermedia/HTMX is a bad fit. But this should generally be pretty obvious early on, because it's about the basic, fundamental nature of the app. You probably know you're building google docs when you start build google docs, not mid-way through.
- No JSON serialization: HTMX sends form data natively no JSON.stringify() needed - Less JavaScript: Declarative hx-* attributes replace imperative fetch code. in my world declarative always wins. - Automatic headers: HTMX handles X-User-Id and other headers configured globally - Built-in error handling: hx-on::error instead of .catch() chains - Swapping flexibility: Can show success/error feedback via hx-swap without custom JS - Request indicators: Free loading states with hx-indicator - Debugging: HTMX events visible in browser devtools; fetch requires console.log
and most all: performance. multicardz goes like stink. 100/100 lighthouse scores, First Contentful Paint 0.4 s, Largest Contentful Paint 0.5 s, Total Blocking Time 0 ms, Cumulative Layout Shift 0, Speed Index, 0.5 s
still prerelease, but cautiously hope to go general availability by and of year.
I use pure front end manipulation to set state, then I send the state to the stateless back end with pure functions, and I get amazing performance: www.multicardz.com public test bed, 1M records, round trip usually around 160 ms for anywhere between 1 to 100K hits
- 1 Getting burned out by Nextjs slowness in a complex production project that shouldn't be that complex or slow on the dev side, (this was 2022 approx)
- 2 Taking a break from React
- 3 Moving back to classic server side rendering with python and Go and dealing now with template engines. Hyped with HTMX and loving it, but my conclusion after so many years of react was that template partials don't feel right to me and templates engines are somewhat not maintained and evolved as used to be. I found my self not feeling naturally inclined to reach for the htmx way and just let the coding agent do it the way they wanted AND stating to notice again the burn out.
- 4 Looking with some envy to co-workers using shadcn how fast they are getting things done and how good they look.
- 5 Wondering would be a way to use JSX with HTMX server side, I miss components, I don't want partial templates.
And then I found Astro, ahhh now I get it, Astro prioritizes generation over run time, and that unlocks a lot of gradual complexity where you can choose how to mix things ( islands ) you get something way more interesting than a template engine, and it uses JSX so you can benefit from React ecosystem.
This where I am now, but yet I have to complete a side project with it to know if I fully get it and love it.
So far seems to me is the answer I was looking for.
I can see the value of the "islands" concept when you have a huge front-end that's grown over generations of people working on it.
For my constrained front-end debugging Astro errors on top of React errors on top of whatever all the turtles down felt a like a step too far.
Am I in my Rust centered back-end driven brain missing something?
I'm playing with JSX, Hono, and Bun right now to do just that. It's early but will see how it goes.
That’s really your call to make. I’ve never went the full build step with it, but I’ve only built some internal dashboards and crud apps with it.
React is easy for small websites so why would I use a separate framework when I can use one framework for everything?
At least some of what you may not be getting in this space is how many developers right now seem to be hugely deprioritizing or just dropping SPA from their decision trees lately. Recent advances in CSS and ESM and Web Components such as View Transitions and vanilla/small-framework JS (ESM) tree-shaking/"unbundling"/importmaps give MPAs more of the benefits of a complex SPA with fewer of the downsides (less of a "mandatory" build process, smaller initial bundle load). It is easy to feel less of a need for "complex SPA" to be on your architecture options board.
You’re either doing something wrong or not actually doing a hello world.
Use the right tool for the job, instead of using the one tool you are comfortable with for everything.
Because most webpages don't need to be SPAs. I miss the days of jquery and html+css, where everything was snappy, and wasn't an SPA.
And I’m not saying every site needs to be an SPA. I’m saying if I can write everything from a simple site to an SPA in a single framework then why not use that for everything?
But have you tried it though? Don’t you think it’s time to give your story? Slam your needs to htmx and see what comes out of it’s ruins?
> Don’t you think it’s time to give your story?
I am afraid that's completely irrelevant to my comments here. If you read my posts carefully, you'll notice that I haven't said a single negative thing about htmx itself, because I want to very cautious in giving opinions. Everything I said was specifically about the horrible arguments in this article.
e.g. effect-ts which makes error handling, dependency injection, concurrency, retries, stack safety, interruptions, etc, simple but the hello world already hits people with "wait, it's 6 lines of code to print hello world!? Trash".
App (can take a few seconds to spin up if dormant): https://estimate.work/
More, but I don't think it's a mind-blowing difference and I wasn't playing code golf when I wrote it. I wouldn't have used redux if I was!
Did a quick test, since before this I also used some very ad-heavy p2p solution, and I see similar issues there. Not sure if you're looking for feedback, but these were all issues I considered before settling on a server-based HTMX long-interrupted-polling approach, which if you think about having server + client + realtime-ish features in the context of "just htmx" + tiny LoC is pretty cool (well I think it's pretty cool :D)
In the WebRTC p2p approach, without some sort of sync protocol that validates the state of data:
- the host must be online / already there to join a room; the host leaving the room means everyone gets kicked!
- if you rejoin a room and don't receive updates, you get a partial view of the data
- if you have data connectivity issues, you get a partial view of the data
- you must have a WebRTC capable browser and Internet connection
Having said that, I do still use this off and on and personally the limitations don't bug me too much. Would be a nightmare for more mission-critical software though
source: https://github.com/basecamp/fizzy
I don't think this is a better approach than React. It's just an approach. It's viable. It's fine
Like c'mon, if I'm using Vue, I'm using Vue. Same for React. Strap me into the native state management solution for your framework, your router, your preconfigured bundler. I'm not here to mess about or I'd have just stuck with vanilla.
Just like how easy jQuery was to get started with back in the day, but a whole framework
My startup did.
And now we’re going to rip it all out and move to a React front-end.
HTMX makes response handling much more complex. Every endpoint returns 3–5 different HTML fragments. Frontend and backend must agree on every scenario — success, validation errors, system errors, partial updates, full reloads.
And HTMX is still a fairly obscure library. The documentation and examples are lacking, there isn’t a real set of established best practices at scale, and not for nothing, LLMs aren’t great at it.
React is mature, used at scale, provides separation of concerns, and is great for agentic AI coding. HTMX has its place for simple projects, but for anything non-trivial, it’s a no for me.
Here is what my htmx apps have: - Single-purpose endpoints: Each endpoint returns ONE thing (a card list, a tag cloud, a form fragment) - Optimistic UI: Preferences like font/theme update the DOM immediately; the save is fire-and-forget with no response needed - Simple error handling: Most endpoints either succeed (return HTML) or fail (HTTP error code) - No fragment orchestration: Not returning 3-5 fragments; using hx-swap-oob sparingly
Here is how I update fonts on screen in user prefs: User selects font → JS updates body class immediately → htmx.ajax() saves in background → done
vs. the anti-pattern you're describing:
User submits form → backend validates → returns success fragment OR error fragment OR partial update OR redirect signal → frontend must handle all cases
No language or programming paradigm is perfect. All programming is an exercise in tradeoffs. The mark of a good CTO or architect is that ability to draw out the best of the technology selection and minimize the tradeoffs.
These days, I admit, though, the ship has sailed for me and htmx. My main app frontend is React and since the LLMs all know much more than I do about how to build out UIs and are 100x faster than me, I'll probably be sticking with React.
Here's the most complex app I've made with it. The most complex part of the app is the match page. I just use morphdom for that part of the app and it makes it super easy, I just send the whole main part of the page back and let a dom diff happen.
I find React to be really complex. What normally takes me just some HTML rendered from the back end and some interactivity on the front end can be done in just a few lines of code, but React takes 10s of lines of code for what I can write in a single line of code using vanilla js. The virtual dom causes it to make everything state. I always find it odd that people reach for that as their front end. I could understand something like Svelte, but even that is too complex for my needs. But I'm always writing CRUD apps, so there is some complexity but not that much, React just makes something that was simple, super complex.
Just curious because when I used HTMX I didn't enjoy this part.
Where appropriate, I use an extension that introduces hx-target-error and hx-swap-error, so I can put the message into an element. You can even use the CSS :empty selector to animate the error message as it appears and disappears.
Usually the default behavior, keeping the form as-is, is what you want, so users don’t lose their input and can just retry.
If it exceeds it, I returned 400. I had to add an event listener to check for the code (htmx:afterRequest) and show an alert(), but this gets difficult to manage if there's multiple requests to different endpoints on the page. Looking at it now, maybe I should have configured HTMX to swap for 4xx.
Allow the server to return a modal/toast in the response and, in your frontend, create a "global" listener that listens to `htmx:afterRequest` and check if the response contains a modal/toast. If it does, show the modal/toast. (or, if you want to keep it simple, show the content in an alert just like you already do)
This way you create a generic solution that you can also reuse for other endpoints too, instead of requiring to create a custom event listener on the client for each endpoint that may require special handling.
If you are on htmx's Discord server, I talked more about it on this message: https://discord.com/channels/725789699527933952/909436816388...
At the time I used headers to indicate if the body should be processed as a trigger, due to nginx header size limits and header compression limitations. Nowadays what I would do is serialize the toast/modal as a JSON inside the HTML response itself then, on `htmx:afterRequest`, parse any modals/toasts on the response and display them to the user.
Similar to wvbdmp's approach but without needing the extension
The problem with SPAs is the ecosystem. I recently found packages like this [1] and this [2] in my node_modules and that is insanity. But the architecture honestly makes way more sense than any other paradigm: server side is a well defined API and the client renders UI and handles local state.
Sun's NeWS also allowed something similar - but with a large amount of programmability using PostScript.
React has a lot going for it. It's simply that I prefer htmx; it feels cleaner to me.
Well, frontend and backend always need to agree on every scenario, that's why I prefer to do validation on backedn and frontend to just display it and not do any validation.
As someone who's been parsing everything entering the system from 2018, I don't believe you can have performance issues by parsing the data entering the system, the only exception I can name in a decade was real time trading app where the data coming in all time was just gargantuan that parsing it all the time was impacting UX and even then there should be an argument for the backend insisting on sending whole data instead of the latest value.
Definitely sad to see this everywhere nowadays, tech choices made because of AI
When is this not the case?
Thus, it’s considered normal that the backend team spits out some JSON and doesn’t know or care what the frontend team does with it.
With HTMX that distinction doesn’t exist so much (the frontend consists of fragments generated by the backend) so you will need a different organizational approach. The “frontend” folks will need to write a lot of “backend” code, but presumably in a separable layer.
The JS framework is the frontend, so you're still coordinating.
> If its returning HTML that's intended to go in a particular place on a page, the front-end has far less flexibility and pretty much has to put it in a specific place.
Well yes, because presumably that's what the app is supposed to do. If it's not supposed to put it in that place, why would that be the specified target?
If this kind of static assignment of targets is not flexible enough for some reason, then use OOB updates which lets you replace fragments by id attribute. That lets you decouple some of these kinds of decisions.
Although "endpoints can return 3-5 different versions of HTML" is also a bit of a red flag that you're not using htmx correctly, generally endpoints should be returning 1, maybe 2 fragments in unusual cases.
In any case, you might find DataStar more to your liking, it's partway between React and htmx.
A single, consistent, canonical response, generated by the server, taking into account all relevant state (which is stored on the server) is much cleaner. It's deterministic and therefore much more testable, predictable and easier to debug.
For pure UI-only logic (light/dark mode, etc) sure you can handle that entirely client-side, but my comment above applies to anything that reads or writes persistent data.
Most of the frontend stuff I do is for internal pages on embedded devices, and I'm very happy with a structure where I have the frontend being a full React fancy component lib SPA that is eventually just compiled down to a zip bundle of files that the backend needs to know nothing about and can serve as dumb files. The backend is a JSON API of sorts that I would need to build anyway for other use cases.
If you hang on to "possible states of the UI" that are client-side only then yes you'll have some difficulty implementing server-generated HTMX responses but more importantly, when your client has state that sometimes isn't in sync with, or shared with, or validated by your server, you're setting yourself up for errors and bugs that will exist regardless of framework.
In short, HTMX forces you to apply "single source of truth" concepts to your application.
Unless you’re saying the components returned by HTMX are using the shadow dom for isolation, you can very easily run into styling problems by changing a style and not realizing some injected fragment of HTML somewhere relies on it being a certain way. I hope you’re using a monorepo because unlike typescript APIs, those HTML fragments and CSS styles are not type checked.
Every backend framework, be it dotnet or Symphony or Rails, has a concept of components. It's a non-issue.
What would you return instead? It's easy to generate HTML, because that's what your server is already generating (and that's about all it should generate).
I kind of don't get why if you want to display something in a web browser you'd generate anything other than HTML.
The only exposure the back-end has to HTML is streaming the static files to the browser. Which can be done in small chunks.
If your back-end is rendering HTML with every request, it has to do a lot more work. It has to load HTML templates into memory and insert strings into them.
Just raw structs of data? Or do you turn that back into HTML?
Now you've got two sets of templates to cope with...
Why would I care about how much effort it is for the server to generate? It's already generating HTML from templates, and it's more-or-less infinitely capable of doing so.
In practice, I doubt this is much slower than serializing JSON. Keeping a couple kilobytes of HTML templates in memory is nothing. Conversely, running a whole vdom on the frontend (typically more resource-constrained than the server) is a much bigger performance issue.
So how do we still get a fancy SPA website? Build it all down to a simple zip bundle, the ARM can serve those static files just fine. The SPA talks to the ARM via a few JSON APIs. Very nice clean boundary.
This isn't a controversial idea and nobody would try to sell you on HTMX for your use case.
2. Who has a server with a weak, limited processor? HTML templates power Django, Rails, and PHP. This paradigm worked fine on the servers of 20 years ago, in the slowest languages we use. I could serve a Django app on my phone and see reasonable performance.
Read the OP's posts - he is talking about a "server" being an embedded device with 64mb of read-only storage. My assumption is that the data output format is basically hard-coded in the device's OS and doesn't even rely on JSON serialization.
> Three levels down and people have entirely forgotten what my post was.
I missed this reply entirely. Whoops.
That said, I do feel like you can do HTML templates on a tiny chip with 64 megs of memory. I've seen NASes with comparably tiny & terrible chips serve their web UIs this way: paper-thin html templates with <form>s for interactivity and <table>s for layout.
You draw a simple web page with very basic elements, tag them with an HTMX element, and let the client side javascript turn that into something that "does stuff".
I wrote a phone directory with find-as-you-type using Django (because it's what I had lying around) and HTMX (because I read somewhere that it was cool and fun and I should try it, and I bow easily to peer pressure), and then min.css to make it not look shit.
All totally vendored, just download the appropriate .js and .css file and check them into your source control.
When you type it hits an endpoint that returns a bit of HTML that contains a table, and swaps it into a div. The querying part and the drawing part is client-side and there's nothing stopping you passing a query string to the endpoint and getting just a bare table out.
Indeed there's nothing stopping you detecting if it's an HTMX request and only returning the fragment, or if it's "bare" returning a full valid page. You know what? I should do that, I'll log a feature request on my project for it.
I've gotten a little away from the original point.
You use HTMX on the client side, to turn a plain HTML page with no interactivity into something that will pull data from a backend and swap it into the DOM. If you want to return JSON and render that with yet another library you can, but you're probably already filling in the blanks in an HTML template as it is.
Why can't your code fill in the blanks in some HTML template instead of filling in the blanks in some JSON?
Why are you then offloading rendering HTML from JSON to a painfully slow scripting language on the client?
You're argument is fine assuming you wish to become another react frontend in a sea of react frontends.
But the documentation example is a terrible argument, the benefit of HTMX is it is easy to understand what is actually happening. There is no magic, you don't need to dive through millions of lines of code to figure out what this is doing like react. It's very basic javascript. Just read the library, frankly you don't even need any documentation. Just take 15 mins and read the entire library.
Whats the big deal here?
And why would that differ from React?
When I was building a website with React, I needed to model a "apply coupon" endpoint with different states (coupon applied, coupon does not exist, coupon exists but has reached its max usage limit) and it was so annoying because you needed to
1. The backend route that returns JSON with a different model depending on the coupon state
2. The JSON models for each response type
3. And then on the frontend you need to load the data, parse the JSON, figure out which "response state" it is (http status code? having a "type" field on the JSON?) convert the JSON to HTML and then display it to the user
In my experience it added a lot of extra "mental overhead". It is something that should be extremely simple that ends up being unnecessarily complex, especially when you need to do that for any new feature you want to add.
When using htmx, a simple implementation of that would be
1. A backend route that returns HTML depending on the coupon state
2. Some htmx attributes (hx-post, hx-swap) on the frontend to make the magic happen
Don't get me wrong, there are places that you wouldn't want to use htmx (heavily interactive components) but that's why htmx recommends the "islands of interactivity" pattern. This way you can make the boring things that would add unnecessary complexity when using React with htmx, and then you can spend the unused "mental overhead" with the interactive components. (which, IMO, makes it a more enjoyable experience)
At the end of the day it is just choices: Some people may prefer the React approach, some people may prefer the htmx approach. All of them have their own upsides and downsides and there isn't a real answer to which is better.
But for my use case, htmx (truth to be told: I use my own custom library that's heavily inspired by htmx on my website, but everything that I did could be done with htmx + some htmx extensions) worked wonderfully for me, and I don't plan on "ripping it all out" anytime soon.
Whereas with HTMX you learn a very, very basic concept in 15mins, and you're good to go for the next decade(s), and it will be more than enough for 80% of your projects.
Same as with vim and Emacs vs. proprietary IDEs and text editors.
It is not. React 18 changed damn near everything. You can't create a new React 17 project without jumping through serious hoops. React 19.5 introduced the compiler, so you can stop using useCallback and useMemo. Except for "common scenarios" where you still need it. Which are about as clear as mud.
I can only imagine what React 20 is going to introduce.
Because people don't like using heavyweight solutions needlessly. That's the logic that begat C++ and Ada and Multics and ASN.1 and CORBA. All of which were good solutions useful for "everything" in their domain. But people hate them, mostly.
Historically big "everything" solutuions end up losing in the market to lighter weight paradigms with more agility and flexibility. Almost every time. React[1] was such a solution once!
[1] Which really is a shorthand for "modern node-based web development with tens of thousands of npm dependencies and thirteen separately-documented API and deployment environemnts to learn".
Which is exactly why the uncool solutions persist in the market. They're useful and practical! If they weren't they never would have been successful at all. I'm just saying that that this is fundamentally the logic of the frumpy old curmudgeon, and the kids will always have something better to offer along with their confusing new ideas.
And to be clear, I'm also just saying that as someone looking in from the outside (I do firmware!) the front end webdev developer onboarding story has long since jumped the complexity shark and things are quite frankly an impenetrable disaster ripe for disruption.
Objection. Your React is ultimately turning into HTML so you DO have to learn HTML + CSS. You just have an abstraction over it.
Yet I know roughly what it is, but I couldn't begin to actually write the stuff myself.
Good abstractions mean you don't have to worry about the layer below.
Now of course it's not really the case that React holds up to being a good abstraction, especially when it comes to CSS and styling, but I don't think it's a forgone conclusion that abstractions force you to learn the level below.
Otherwise we'd all spend half our time learning assembly.
I do have sympathy though for a developer who just wants to focus on the higher level paradigm and let the library maintainers worry about the innards.
For a good part of your career this is true, but eventually you will need to justify your senior salary by being able to debug react via looking at library code itself, or understanding the event bubbling under the hood, or figure out why the output css isn't working.
Saw a video, wish I could remember who, someone developing a game in c-something. There was some bug they couldn't figure out so they jumped into I guess the assembly for that block of higher abstracted code, and was able to find some kind of memory issue. Vague, sorry, but point is I remember being really impressed, thinking oh shit yeah if I really want to be an expert in my field I better be able to really understand my stack all the way to the bones.
That's not a valid analogy, 99.99% of C# developers never see or touch CLR bytecode, where every React developer is still working with HTML+CSS.
In theory, react developers ought to be able to code against the react API in typescript, without seeing the "raw" HTML+JS that gets delivered to the browser.
So what's failing those developers? Is it the tooling, the abstraction itself, or something else?
You're failing to understand the difference between react and react-dom.
> be able to code against the react API in typescript
Probably helps a lot to keep abstractions from leaking.
if you care about have a solid UI, you should learn everything
you should learn css, react, svelte, vue, rails, tailwind, html
if you don't and you say you actually care about your UI, your opinion is actually irrelevant
No bundler required, no compilation step.
Alpine data objects can grow to be quite large, so you wind up inlining hundreds of lines of JS as strings within your HTML template, which often limits your editor's ability to do JS checks without additional config.
State management in Alpine is implicit and nested and not a serious solution for building commercial apps IMO.
And don't even get me started on unsafe-eval.
If it's your hobby app and you are the developer and the product owner, go for Alpine. If you're working at a company that is asking you to build a competitive web product in 2025, use a more robust tool. Hotwire and Stimulus has scaled much better from an organization standpoint in my experience.
And now I'm at the breaking point. So I'm planning to move to tailwind and Go templates, but honestly, i was hopeful for htmx, so I need to properly see the usecase. Which i don't know is this. It reminds me of Angular a lot...
It is otherwise a very simple website, and the framework and its SDKs are much simpler, yet more powerful, than HTMX
HTMX is less noisy if you integrate it into your backend framework.
A contact of mine build a python/flask app. To simplify coding, he wrote a file to extend the flask framework to support the HTMX patterns he needed with just a single line of boilerplate. Took him about a day, his team is happy with the results.
I'd love to hear more about that.
The reality is it's going to suit some people and some languages really well and others not so well. I think I like html/css/js and using AI to generate that. But I also like Go templates and trying to isolate that in a programmatic way. I find htmx in principle, a good idea, but when I actually tried to use it, fundamentally the wrong tool for me.
If your solution is actually good, it will get adopted eventually...
Forget React, there's still stuff written in jQuery and JSP.
Why the rush to convert everything - you're not a missionary on a mission, just build your stuff in stuff you like?
The attack on npm is ridiculous, when (apart from introducing a permanent vulnerability in the form of a runtime dependency on a third party site), you still need npm for htmx.
I used to believe this when I first started in tech. The truth is even something as seemingly innocent as javascript runtimes now have an incredible amount of money behind them. And sometimes even marketing budgets. Deno released a high-production trailer for their 2.0 release last year
https://www.youtube.com/watch?v=swXWUfufu2w
I've also seen some really cool and well-thought out technologies simply not gain any traction.
The truth is you ultimately do need some big company behind you or major personality writing blog posts to ultimately make it.
Techies don't like to admit it but we're just as reliant on influencers as anyone else.
This has never been more incorrect. The entire world of software is people using garbage solutions because the CTO is convinced Oracle/Microsoft/what ever new random software is the best thing since sliced bread. In no fashion has the best software solution ever been a factor.
I wish this were true.
Unfortunately, often the things that get adopted are the things hyped up the most, not the ones which are technically superior.
Popularity, marketing budgets and inertia often dictate what's popular.
As with all biases, we need to actively and deliberately work against these forces, if we value craftsmanship and professionalism.
Also, mobile apps often have different API needs than webapps, so they end up getting different APIs anyway.
The idea that HTMX removes all the complexity is false. However it does remove some of it, and moves the rest onto the backend.
I find the backend easier to work with, so that's a win for me.
And a batteries included framework (like Laravel or Django) makes HTMX even more appealing. They already have everything you need! :)