Hacker News new | ask | show | jobs
by rmbyrro 826 days ago
I don't know, every time I see people sneaking html into Python feels weird and wrong to me...
7 comments

Until you try it out and realize the benefits!

- Type safe HTML: you get an exception instead of malformed HTML

- Truly reusable components: any Python web framework, component packages are truly reusable in any other projects. I never seen this with template engines.

- Huge productivity boost: not even close! No hunting for templates, no jumping between files, everything is in Python functions.

- Composable elements: you can nest things as much as you want, refactor very easily. Doing this with templates is not even possible, or such a pain I never did it.

- Storybook: There are a couple ones for Django, but they are clunky and not reusable at all.

I felt the same for a long time, but started thinking about a nice API. It took me months, but I finally got it: https://github.com/kissgyorgy/compone

Yes, I quite like the idea of being able to run pyflakes/flake8/black/pytest/mypy over my "html templates", and benefiting from all the power that entails.
Try ruff [0] and get rid of flake and black

[0]: https://github.com/astral-sh/ruff

I'm aware of it, but it obscures functionality for my previous statement.
Insightful summary. Thx.
It feels weird at the beginning, but after a bit of practice I found it pretty nice to write HTML in Python.

Here is an example of a HTML page layout written with the DOMinate [1] library for example, in a "JSX-like" way:

https://github.com/olivierphi/zakuchess/blob/main/src/apps/w...

It may hurt your eyes at first sight, for sure... But similarly to technologies like Tailwind CSS, it's mostly a matter of getting used to it - and after a while it end ups feeling very natural to use :-)

1: https://github.com/Knio/dominate#readme

Dominate is quite fast as well. I did a few tests vs jinja for my flask app and it beat the pants off it.
I imagine a lot of this comes down to personal preference. In the early days of Mountaineer [^1] (gee, almost two months ago at this point), I played around with the idea of embedding html into python instead of needing a JS layer. Eventually my consensus was:

- The most flexible shim approaches typically end up wrapping JS/React components anyway (like Reflex/Pinecone)

- We really need better IDE support for html strings that are within python strings. The editing problem is a big setback.

The ergonomics of Python + JS in separate code files won out and the user experience has been better than forcing them both into a common language would be.

This has the benefit of leveraging whatever the two languages are best at, in native code, so you have access to all the native APIs without having to learn a shim on top of it. Way more longevity to that approach too. Context switching between two languages isn't that bad if you minimize the glue layer that you have to write between them.

[^1]: https://github.com/piercefreeman/mountaineer

I agree and I don't fully understand the why of it.

I remember coding PL/SQL to emmit HTML in Oracle around 1999 or 2000 and using functions to code the various elements.

That got old and repetitive very quickly - for instance, everytime I had to correct a spelling error, I had to recompile the code.

To get around it I used one or two tables to hold html snippets to decouple the business/backend logic from the frontend, and stopped using the PL/SQL functions completely.

My speed of developmet skyrocketed, and separating and abstracting the frontend from the backend made so much sense.

A few years later, I was doing web developemt with Python using the Zope framework (not many people know about it tiday, I think).

It uses a specialised serverside templating language called TAL (Template Attribute Language)[1] that basically builds the front end dynamically, and then you feed it data from the backend.

Very neat and allowed me to build reusable compoments as well as collections of a schema definition (basically a dict), html template(s) and the code to validate that the input matched the schema and could be rendered.

Or something like that - its been 2 employers and almost 20 years since I worked with that :)

I did build a small extension for Wordpress using a PHP implementation[2] of TAL a few years ago, and TAL still works like a charm :)

My point is that I still believe there is value in keeping python out of the html-templating, and in keeping the front end logic apart from the backend logic.

There is something I am not understanding about the renewal of mixing HTML/GUI template with code, but I haven't fully found it yet.

[1] https://en.m.wikipedia.org/wiki/Template_Attribute_Language

[2] I believe it was this one https://phptal.org/

Yeah, I understand that. Now that Python 3.12 has better support for f-strings, I thought there might be a way to make it possible. But I am still not sure it will work. There is a pretty weird hack to make f-strings work while avoiding the possibility of rendering unsafe user input.
It's nice for small hacks, but for anything longer than a couple dozen characters you're probably still better off making jinja2 (or similar) templates as painless as possible.
Do you feel the same about sneaking html into javascript? Just curious if it's a Python-specific objection.
In general, this usually results in front-end logic being very tightly coupled with back-end logic. In some of the examples given, you even have database access in the same line that is generating the HTML document.

https://github.com/paveldedik/ludic/blob/main/examples/click...

It's the kind of thing that looks very cool and concise in small examples, but tends to become a nightmare when you are working on larger projects.

> In some of the examples given, you even have database access in the same line that is generating the HTML document.

Python template engines have the exact same problem, just way less obvious.

It doesn't have to be that way. Make all the queries up-front and pass the result the same way as you would pass context to templates. This way, all your components are pure. The difference is explicitness. Much easier to spot where side-effects happen than in templates.

I think the issue is orthogonal. I'm not a huge fan of react but it's an example of an architecture where the structure that is (imposed/encouraged) helps avoid the problem you're talking about.

I don't think the issue is "markup expressed in another language" - I think it's "poor application architecture". I don't dispute there might be a correlation between libraries and frameworks that do poorly on each - but that doesn't mean it's intrinsic.

same feeling there tbh. Though generally, when it's done in javascript it's done completely in a string, without javascript objects.
recall python server pages ... good old index.psp