First, I welcome any project that enriches a software ecosystem, and this project no doubt does just that. However, I have two points which will deter me from using this (or any python->html/js framework) in a commercial production project:
1. It silos front end development in Python world. It might be great if your entire team are and always will be Python devs, but what happens when you want dedicated from end developers? What happens when you need to deviate out of what the framework gives you in a front-end context? What happens when you need to eject from "python" into a dedicated front end environment? All your front end code is now written in Python. Worst, you now might even have JavaScript code embedded inside Python code. I keep hearing "CoffeeScript" in the back of my mind...
2. Any python project using FastAPI (which is fantastic), flask, etc. and is growing in scope, will ultimately build Django. For example, FastAPI (which is great), has SqlModel (which is awesome) which makes SqlAlchemy less sucky and more like Django. Start to factor in all the other batteries we got used to getting with Django, and it starts adding up. If the project is smallish in scope and well defined to know it will stay such, sure it's a valid and excellent choice. The same applies here - unless batteries are included, or this is (as suggested in a comment) available as a Django app, you'll end up building Django.
Regarding (1), I think you might be misunderstanding how FastHTML works. If you want to write JS code in FastHTML, then you can just do that. But you can focus entirely on using it for the bits it works well for.
For instance, I wrote a little app (https://word2md.answer.ai/ ) which lets you copy/paste from MS word, and converts it to Markdown. I found that there's some nice existing JS code for cleaning up MS Word markup, so I used that on the client side, and used server-side python code for converting that to markdown. Here's the Python code, which is just plain python in a regular python file:
Regarding (2), I've heard the same basic argument nearly every time I've tried to create anything new, and I've heard it apply to lots of other people's projects too. Yes, if there's an existing product that's pretty good already, then it's likely the new thing won't be as good in every way. I don't think that's a reason to not try to make something better, however. I like Django a lot, have used it since its very early days, and I'm friends with one of the founders of it -- it's an amazing project. But it's not perfect, and hopefully it's OK if some people want to try different things too.
Regarding 2, I completely agree. A good existing project is no argument against new projects in the same space. It was more an observation (and very current experience of me reworking a fastapi project to Django+ninja because it simply grew in scope enough to merit it).
Regarding 1, I get it, although I do like my ends to be separate. Maybe it's a question of aesthetics and therefore completely subjective.
1. These folks on such a project will otherwise need to deal with templates with Python in them. Inside out or outside in, there’s some complexity.
Linted, formatted, optionally typed Python is likely going to be more maintainable than html templates in the long run and is one of the easier langs to pick up. css/js can be linked separately.
I don’t see any limitations that would prevent one from using a template on a new page.
I recently looked into these kind of html builder libs, pioneered by dominate. “htpy” was the only one where I was impressed with the source code.
I just don't see how a project beyond a small website can benefit from having it's front end generated in such a way. Once you grow beyond the "website" with simple interaction your front end becomes it's own universe. Coupling it all in the back end never ends well despite all good intentions. That has been my personal experience so far, so mileage varies etc.
As an aside, HTML is formatted in a very visual way in my opinion. The tag syntax makes it clear to visually identify blocks and layout elements. You lose this when you describe the layout in Python.
> Once you grow beyond the "website" with simple interaction your front end becomes it's own universe
I think this has been a major failing/pain point of web-dev that this MUST be the case. However, I think fastHTML for me is going to fix that. Naturally there is no approach that is ideal in every case, but for a ton of them fastHTML I think works. I've built several things with fastHTML and am very optimistic.
As far as the visual identification, I think python is just as clear to see visual blocks as HTML, but comes with many additional refactoring options (that you can choose when it makes sense to use for your use-case).
Try playing with https://h2x.answer.ai/ and putting in some HTML code and see how it looks in python. Maybe you'll disagree, but I find it quite refreshing.
I guess it's a personal preference. I tried it, and it looked a mess in my eyes.
Take a strong tag:
Div(
"If you click '",
Strong('Accept all'),
"', we and",
A('our partners', href='/v2/partners', target='_blank'),
...
It just verbose, very Java like, and feels like a step back in a commercial setting. It's absolutely fine if you're a single developer, HTML disgusts you, and Javascript is an abomination. I know people who think that way and I know they would love it. But I'm as comfortable with JS and I am with Python (after over 25 years using both). Someone likened JSX to it - but it's not even close - JSX brings the tag structure INTO JavaScript, not takes it away, to achieve the exact opposite result of fastHTML.
This is html building not js. It’s not any more verbose, in fact slightly less because no need for closing tags. Main difference is parens instead of angle brackets. Now you can use tools.
I do prefer lower case callables but that’s a minor nitpick, and “htpy” and other libs can do that.
Yes, it is HTML, and it loses all the benefits of HTML, by adding complexity of code and loss of structure. I'm uncomfortable with HTML and JS obfuscated by Python like that. I'm not using the word "verbose" as a character count comparison, but as an overall feel of weight when I see such code. It just takes me back to Java Swing, or ExtJS in the JavaScript world. It's not bad if it's the only way to describe an interface or layout. But there are better ways - HTML.
Please don't get my comments as criticism of the project itself, I think it's lovely and has a lot of merit. I've had to deal with the aftermath of these kind of things before, which makes me very aware of where it usually ends up at:
Devs in language X don't like Html/JavaScript/Y/Z, so they wrap it with language X until X is all there is. Then one day, the business realises they have a codebase nobody other than it's original creators can or want to deal with, and any change becomes a behemoth of a project. It always starts with the best of intentions.
The complexity and structure are near equivalent. S-expressions are an html precursor.
Python is one of the most popular languages and easy to read. People are more resilient than given credit.
I tend to agree with your closing comment about over abstraction in general, however you may have forgotten that a Jinja/html template is an abomination of conflicting concepts.
I’m more worried about the rest of this framework to be honest. :-D
In our company, where htpy was born, we are building a highly interactive application with htpy combined with Alpine.js+htmx. We have a couple of thousands lines of htpy code in production right now. We stick all HTML generation code into components/x.py or components.py files to keep it separate from other code. It is easy to grasp the structure. We use type hints so it is clear what data different components expect. "Goto defintion" just works so it is easy to navigate the code.
I agree about that HTML looks better with tags and it takes a bit of getting used to the python syntax. If something like JSX was possible in Python with all the tooling working, that would be great.
If you’re using backend templates it’s already coupled. The css as well. It’s a myth that separate langs in separate files == decoupled. I didn’t realize myself until recently—just got so used to it.
The main way around that is the SPA/API architecture, but that comes with huge complexity drawbacks as well.
Nothing special about html, at least as a Python string builder you can factor it and use tools. It can also be put into separate files. So many upsides and little to no downside besides initial surprise.
That's always the problem with these things. You can no longer leverage the bigger ecosystem (e.g. just copy HTML templates from libraries), and I can probably count on no fingers the number of decent designers I've met who knew python. So as soon as you want to grow your team you'll end up with a split.
Still, for projects that are only likely to stay small it might be fun. But then you'll have to remember how it works after coming back from your day job that uses a more mainstream framework.
1. It silos front end development in Python world. It might be great if your entire team are and always will be Python devs, but what happens when you want dedicated from end developers? What happens when you need to deviate out of what the framework gives you in a front-end context? What happens when you need to eject from "python" into a dedicated front end environment? All your front end code is now written in Python. Worst, you now might even have JavaScript code embedded inside Python code. I keep hearing "CoffeeScript" in the back of my mind...
2. Any python project using FastAPI (which is fantastic), flask, etc. and is growing in scope, will ultimately build Django. For example, FastAPI (which is great), has SqlModel (which is awesome) which makes SqlAlchemy less sucky and more like Django. Start to factor in all the other batteries we got used to getting with Django, and it starts adding up. If the project is smallish in scope and well defined to know it will stay such, sure it's a valid and excellent choice. The same applies here - unless batteries are included, or this is (as suggested in a comment) available as a Django app, you'll end up building Django.