![]() |
|
![]() |
| I'm a big fan of Locality of Behavior (LoB): https://htmx.org/essays/locality-of-behaviour/ . I don't think this need be incompatible with SoC. But even if you did think so, I believe that it's better to have everything in one language as much as possible, with the simplest possible specification of marshalling over network boundaries. My view is that hypermedia is a better way to do both of these things.
(I think HTML templating is a historical accident for what it's worth, and I hope it dies.) |
![]() |
| My impression having done Django for over 15 years is that FastHTML allows for separation of concerns, albeit not within templates. Rather, most of the "presentation layer" is executed during the return statement. A common pattern in people building non-tiny FastHTML projects is to break out presentation into a components layer and business logic into a business layer.
Often we see "components.py" for presentation and "content|logic|models.py" broken out for business logic. You can see this pattern done in my as-yet-DNS-switched blog here: https://github.com/pydanny/daniel-blog-fasthtml Of course, it's still early in the project, it's going to be interesting to see what patterns emerge over time. :-) |
![]() |
| Very cool! After trying different approaches to render HTML from Python objects (including lxml, xml, etc.) I ended up liking htpy[0] the most, and the apps I built look similar to the examples in the FastHTML docs. I'll definitely try it.
One pattern I use is putting all the functions that generate HTML inside their own class. That way, I can more easily create and reuse components like:
Then `self.header()` can be reused in other parts, or to return partial HTML. It also makes it easy to pass the "request" object to the class, and do conditional rendering based on it (cookies, auth, language, etc).[0]: https://htpy.dev/ |
![]() |
| Yes htpy is nice! Other interesting examples of functional HTML include Elm-html (Elm), hiccl (Common Lisp), hiccup (Clojure), Falco.Markup (F#), Lucid (Haskell), and dream-html (OCaml). FastHTML's system, called "FastTag" (FT) is a bit of a mashup of all of them plus some extra bits. I seriously considered just using htpy actually -- but in the end decided I preferred something a little different.
I've wondered about a class-based approach like that -- interesting to hear it's worked for you. I should try it! I'm using a purely functional approach for re-use, as you see in this example of the code for about.fastht.ml: https://github.com/AnswerDotAI/fh-about/blob/main/overview.p... |
![]() |
| For what it's worth. One thing I really like about `htpy` is that the element attributes go before the child elements. I find this easier to write and read. Other things I like:
Having child elements as a list (i.e: the __getitem__ override) makes it convenient to build elements based on simple conditions + list comprehensions. This can be done with other frameworks, but it seems more natural to me when using `htpy`. I also like that you can just `print()` elements and get the final HTML without having to pass it through a different function. This is not something specific about FastHTML, but rather something I've found I also had to do when using `lxml` or similar tools (I wrote about my experiments here[0]) [0]: https://ricardoanderegg.com/posts/python-build-html-componen... |
![]() |
| FastHTML is very interesting and reading this thread has led me to discover htpy as well which I am shocked I have never seen before! The htpy website and docs are also great. So now I am a bit of a dilemma over which one to use.
I actually hate working in HTML with all those closing tags etc so I nearly always set up a build/make process to edit my templates in PUG format. When I paste my PUG->html output into https://h2x.answer.ai/, or run html2htpy over them, I get python code that basically looks the same as those PUG templates. What a realization that is! So I may as well create and edit them in python rather than PUG and exploit the power of my beloved python dev environment and tools (as nicely stated in that "Throw out your templates" essay https://github.com/tavisrudd/throw_out_your_templates reference from the htpy docs). Thanks very much Jeremy and Andreas for this fantastic insight :) |
![]() |
| Flask or Django users should be able to get started pretty quickly with FastHTML, and users of the preview that have switched over tell us that they're finding it easier and faster to create what they want in FastHTML.
Having said that, the people that will get the most out of it and folks that haven't got much prior web dev experience -- e.g. people who have just done some streamlit/gradio/etc apps, or maybe Python programmers that haven't written web apps at all. I mention this briefly on https://about.fastht.ml in the section "A new generation of coders": > "Coding is the key to turning the ideas in your head into products and services that can help people. AI has recently made it easier to get started with coding, which means there are more people than ever before who can create useful stuff. But this new generation of coders do not generally have the same background as full-time software engineers. They may have been trained in a different field, or they may have learned to code on their own. We hope that FastHTML will make it easier for this new generation of coders to turn their ideas into reality. To create maintainable and scalable solutions." |
![]() |
| It doesn't look like they use a formatter or linter. I hope I'm wrong but I feel like that and their use of nbdev are really going to hurt adoption. :( |
![]() |
| 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: https://github.com/AnswerDotAI/word2md/blob/main/main.py And here the JS code, which is just plain JS in a regular JS file: https://github.com/AnswerDotAI/word2md/blob/main/wordpaste.j... 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. |
![]() |
| > 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. |
![]() |
| In this case, it's a 1:1 mapping to what's on the page, so your concern doesn't apply here. Debugging and refactoring is far easier with Python functions than templates, and CSS programmers just use CSS the usual way.
To answer your question, I'll quote from https://about.fasht.ml: Templates were originally created for web development in the 1990s, back when web design required complex browser-specific HTML. By using templates, designers were able to work in a familiar language, and programmers could “fill in the blanks” with the data they needed. Today this is not needed, since we can create simple semantic HTML, and use CSS to style it. Templates have a number of disadvantages, for instance: - They require a separate language to write the templates, which is an additional learning curve - Template languages are generally less concise and powerful than Python - Refactoring a template into sub-components is harder than refactoring Python code - Templates generally require separate files - Templates generally do not support the Python debugger. By using Python as the HTML-generation language, we can avoid these disadvantages. More importantly, we can create a rich ecosystem of tools and frameworks available as pip-installable Python modules, which can be used to build web applications. |
![]() |
| > Maybe I'm missing something here.
I think you are missing how htmx (https://htmx.org/) is intended to be used. You still have your regular HTML page and by interacting with that HTML, you trigger server-side functions that return HTML. That HTML is used to update only a small part of your page. htmx works with HTML fragments while HTML templates work with entire pages. |
![]() |
| Which example? I see global vars in a couple of the demos. The game state for the Game of Life makes sense, since it is intended to be shared. The `messages` list in the Chatbot demo is definitely NOT how you'd build a multi-user application, that's mainly showing the styling aspect.
In general, you'd have an actual database and make it so users can only see their own data! See https://github.com/AnswerDotAI/fasthtml/blob/main/examples/a... which adds a filter to queries and DDL statements to ensure that the user can only see/edit their own todos. |
![]() |
| I love everything about this. I have been using HTMX heavily for a side project and glad to see it used in this project. Is fast.ai hiring? I would love to make contributions to their mission. |
![]() |
| Streamlit is for small, interactive, data-driven applets. FastHTML is for building entire websites with direct control over the HTML output. |
![]() |
| This looks very interesting.
Is it possible to inject custom JS wherever I want in the app? Also, is the generate html/css/javascript readable as the application scale up? |
![]() |
| Hi Jeremy, congratulations for the launch.
How does this compare to Dash? I've used Dash for many applications, so I'm wondering what are the advantages of FastHTML? |
![]() |
| That benchmark makes Go look good, and JS very good. The upper part of the table belongs to Go, and the very top is JS.
The bottom of the benchmark table are all slow Python implementations xD |
![]() |
| It's you!
Just wanted to say, nice job, love how much work has gone in to this and especially the site/docs to help people get going. |
![]() |
| Not a very good "ad" as your page is quite slow and skips many frames, especially when scrolling past "The fastest way to create a real web application."
"Fast" |
![]() |
| The only two langauges that have better error handling are golang and rust.
but not having to context switch from python to another language is worth it for 95% of applications. |
![]() |
| Yeah I also don't get it. Python is great and I really like it, but it never feels like a good choice for an app that runs 24/7 for years to come. So many wasted CPU cycles. |
![]() |
| This sounds exactly like what I was looking for. I settled on htbuilder[1], but it certainly does not feel right as it requires a fair bit of wrangling in order to fit with Django.
I'd love to help you with documentation and such; hit me up at [email protected] if you'd like a partner(: [1] https://github.com/tvst/htbuilder EDIT: Actually, scrolling further in this thread, it looks like https://htpy.dev fits the bill? It has explicit integration with Django, which is what I was looking for. |
![]() |
| This is fantastic and exactly what I wanted! A very neat idea about how you separate attributes and children.
How does the performance side of this thing look like? |
![]() |
| I did not measure performance yet, but I definitely will! My hunch is that it's faster than any templating library, because those are compiling from their own DSL, but it's completely ommitted here. |
![]() |
| Streamlit is fine for the first 20 minutes and then it sucks. I switched to NiceGUI and couldn't have been happier for my internal crud app with very specific ui/interactivity requirements. |
![]() |
| No. It's not in the spec, and in almost 30 years of web development, this might be the first time I've ever seen someone use a closing tag for it. |
![]() |
| HTML5's HTML syntax is no longer SGML-based. It's still invalid but no longer because of anything related to SGML; now it's simply because the HTML5 spec says so. |
![]() |
| I'm not sure if I'm alone in this, but I feel domains like this are a bit user hostile. It's cute but harder to commit to memory and it reads like fastht dot ml |
I wrote my first web app ~30 years ago, and have built some pretty big projects, including founding fastmail (written in Perl) and leading the first major production version of Kaggle (written in C#). Frankly, I've enjoyed creating web apps less and less over the last few years. So I decided to try to create something that I'd personally enjoy using. I like coding with Python, it's got a great ecosystem, and deployments like Dropbox and Instagram show that it can scale right up.
FastHTML brings together Python, hypermedia based apps with HTMX, the powerful and flexible ASGI/Uvicorn/Starlette trio, a new Python component system called FastTag (FT -- based on many similar projects from the functional programming world), an API design inspired by FastAPI, and a few more bits and pieces into something I've now written around a dozen apps with. I'm really loving it!
I hope some of you get a chance to try it out -- let me know what you think.