-
-
Notifications
You must be signed in to change notification settings - Fork 5.5k
New issue
Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.
By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.
Already on GitHub? Sign in to your account
Decide to use htmx or not #28880
Comments
I think adding htmx is a good idea. The pull requests speak for themselves, they are small and easy to maintain. htmx fits Gitea very well. |
HTMX makes it easier to develop interactive UI using our already present template structure. And I think it is better to introduce something we can use to make existing UI better than to wait for someone to rebuild everything using a new framework. |
My question is: does htmx really help and will be widely used in Gitea? I have been following htmx for some time. My feeling is:
The samples PRs #28871 and #28872 are good demo for htmx, but they are too simple and didn't handle error messages / loading indicators. Are there some complex samples for showing how htmx would work for a complex case in Gitea? For example, comment editing, PR merging? So, IMO the only useful part of htmx at the moment is the "replacing inner/outer html by ajax", while it is quite simple and could (should) be implemented by existing "link-action" and "form-fetch-action". Other htmx features are unlikely useful in foreseeable future. (I don't mean objection, while I think these questions needs to be clearly answered and some should be written into the guideline / devtest.tmpl if most people would like to use htmx) |
I would be for using htmx over our home-rolled solutions, and for slowly increasing its usage where it would be beneficial. |
From https://htmx.org/docs/#requests: In the event of an error response from the server (e.g. a 404 or a 501), htmx will trigger the htmx:responseError event, which you can handle. In the event of a connection error, the htmx:sendError event will be triggered.
https://htmx.org/docs/#indicators
Why would we recreate the logic htmx excels at and maintain it?
We can use https://htmx.org/docs/#inheritance to set it on a root tag, that way all requests include it
I don't have experience creating modals. I don't think that the fact htmx has features we already implemented should block us from using it, or any other library that implements functionality we have. I wouldn't use htmx with Vue, I'd use htmx when I don't need the power of Vue.
What do you mean by fragile? Yes, linting is missing in htmx, what kind of rules would you like to enforce?
What's wrong with their error handling? I can work to change it. Just like the previous behavior of the buttons I changed, there were no loading indicators.
It's not supposed to be used in complex cases, at least I won't force it to.
I don't think you've considered the varying possibilities to "replacing inner/outer html by ajax". Are we going to reimplement
I am very new to htmx. Those PRs are the first time I used it. We should try it out and play with it instead of immediately enforcing some prematurely written guidelines. |
Thank you for the detailed answers.
That's a complex question, and I do not think it could be easily answered by yes or no. Let's see some examples:
Gitea is not a small project, so there are a lot of details which are not easy to be satisfied by 3rdparty library, they need to be customized somewhat. For "htmx": I am just showing a choice for "not introducing if there are some foreseeable problems". And I have a feeling that "replacing inner/outer html by ajax" is not that complex in Gitea, no need to fully "reimplement hx-target, hx-swap, and hx-select" like htmx or reinvent the wheel again. (I just would like to express the background, don't mean yes / no here)
I didn't mean they were wrong, but the previous behavior is not ideal doesn't mean the new behavior is right. And actually the behaviors are changed, that why I asked the questions about error handling / loading indicator:
Since we are improving the UI, I think it is a good chance to give end users better UI responses. In my mind, our
If let us predict, after introducing htmx, in which case the |
Having experience with both htmx and vuejs, I currently utilize htmx for smaller applications. However, I've encountered limitations when integrating it into big project, especially on complex screens such as code review and the front landing page, where various UI elements are in play. Considering the challenges faced, I believe using to Vue3 would be a more favorable option. It allows us to leverage existing solutions and avoid reinventing the wheel. I leave the final decision to the TOC/maintainers for their consideration. |
Thanks for the detailed comment.
Sure, but we have more libraries we don't customize than ones we do.
I'd love to see the sample PRs recreated in
Regarding the error handling and loading indicator, I am open to add changes, I don't see these as blockers to use htmx.
The distinction seems pretty clear to me, |
I am not sure whether I have enough time recently to work on a sample. So feel free to continue the htmx related design. I think there might be some htmx options or mechanisms to make the error handling / loading indicator easier (no need to write them everytime).
I think it is feasible. And at the moment we had better forbid some htmx features like "htmx modal" / "htmx script" to make sure there are consistent designs in code base (unless there is another complete plan to refactor existing code to a new framework). My opinion: I could vote for htmx if the standards could be defined (including: general error handling, avoid some unnecessary features like htmx script). |
@go-gitea/technical-oversight-committee please write here your official decision if we can add |
I will take "no comment" as silent approval |
My comment is largely as it was above. I would be for an exploratory PR (similar to the one we recently had and reverted) and we should use that PR to try and define some guardrails around its usage moving forward, as well as giving the opportunity for anyone to be critical of any tradeoffs. I love (the idea of) htmx, my main concern is more fracturing of our frontend framework(s). |
So, the overall consensus I sense is the following: |
I created #28908 with error handling and request indicators |
Just notice this closed. I concens following questions.
|
I abstain and respect others' choice since it's the first time I've heard of htmx. Sorry to bother, but I meant to read others' discussions and learn 😄, not give silent approval. |
Hi, chiming in as well. While I am a fan of htmx and use it elsewhere, I am cautious to include it in Gitea itself regardless of benefits for the following reasons:
I'd be interested in hearing @silverwind's thoughts due to their contributions to the frontend, and being the top voted person in the latest TOC election. I do see the benefits of it though (see reasons others have listed above). I realize this isn't a yes/no to the question, but I think it is a valuable discussion to have with any big change of direction (similar to how we did with changing the routing library to chi) |
No, vue3 is more powerful. htmx is for simple interactions.
By order of reactivity:
If I compare it with #28914 it seems using ajax/fetch with vue3 is more lines and overall more complex.
Yes but the number of lines needed to achieve the same is drastically different, with vue3 using much more.
If htmx can't provide something, use vue3. I believe htmx covers a lot of use cases, but not all. |
The code lines are not much more than htmx. I think the Cons is the layout will be blink, maybe I need some css to fix the height and width. |
vue3 is nice if you have complex things ... but if we use it everywhere we will loose the ability to have static rendered things. e.g. at the moment server side rendered HTML can be crawled, saved in the wayback machine, used on JS-restricted browsers ... with htmx ... we can still program as we do with templates on the server-side while archiving "modern website feeling" summaryvue3: client-side rendering only |
All views are same and pointing in the same direction. Let's introduce the htmx. |
(Accidentally posted this originally on #28908) Looks like a pretty promising approach using htmx for gitea. One thing I would like to throw into the discussions is how updating UI through events send from the server (websocket / sse) would be handled in the future for things like #2287 or #25661. There seems to be https://htmx.org/extensions/web-sockets/. If not would it mean that gitea would use:
|
We want to ged rid of jQuery ... else yes thats what at least i have in mind :) |
We cannot get rid of jQuery real soon, honestly. We are too much jQuery. |
Did a first attempt on implementing how the websocket "realtime" updating could look like #28958 |
I don't have much of an opionion on htmx really. Overall it seems to be suited for some limited use cases like content replacement from fetch/ws. But for many complex user cases, we will certainly have to resort to JS and Vue. It seems reasonably small, though, so I guess the performance impact of loading it shouldn't be too much. |
It's unclear for small and big. There is no clear rule for which should use vue+js and which should use htmx. |
It looks to me currently like there are much more pros than possible cons of adopting HTMX. It seems to fit well into our current template structure, lowers the amount of development needed for interactive components, lowers the amount of client side rendering, and also seems to make it easier to implement features like websockets. @lunny I'd do htmx as long as it is possible because it allows us to continue using go templates. Of course there are pages like the action run view where the whole page has to be interactive, but as long as this isn't the case and the htmx implementation is easier than the vue one, I'd go with htmx. |
looking at lunnys example pull just for the simple change ... the JS got way more conplex and we got way more lines of code ... |
But it's not too much. And it will keep the frontend users only one consistent technique to contribute to Gitea. I'm not a frontend guy, I think it can be shorter for frontend guys. |
I think we can say htmx is accepted at this point? |
…`Follow` (#28908) - Closes #28880 This change introduces htmx with the hope we could use it to make Gitea more reactive while keeping our "HTML rendered on the server" approach. - Add `htmx.js` that imports `htmx.org` and initializes error toasts - Place `hx-headers='{"x-csrf-token": "{{.CsrfToken}}"}'` on the `<body>` tag so every request that htmx sends is authenticated - Place `hx-swap="outerHTML"` on the `<body>` tag so the response of each htmx request replaces the tag it targets (as opposed to its inner content) - Place `hx-push-url="false"` on the `<body>` tag so no changes to the URL happen in `<form>` tags - Add the `is-loading` class during request ### Error toasts in action ![errors](https://github.com/go-gitea/gitea/assets/20454870/181a1beb-1cb8-4858-abe8-fa1fc3f5b8f3) ## Don't do a full page load when clicking the subscribe button - Refactor the form around the subscribe button into its own template - Use htmx to perform the form submission - `hx-boost="true"` to prevent the default form submission behavior of a full page load - `hx-sync="this:replace"` to replace the current request (in case the button is clicked again before the response is returned) - `hx-target="this"` to replace the form tag with the new form tag - Change the backend response to return a `<form>` tag instead of a redirect to the issue page ### Before ![subscribe_before](https://github.com/go-gitea/gitea/assets/20454870/cb2439a2-c3c0-425c-8d3c-5d646b1cdc28) ### After ![subscribe_after](https://github.com/go-gitea/gitea/assets/20454870/6fcd77d8-7b11-40b0-af4f-b152aaad787c) ## Don't do a full page load when clicking the follow button - Use htmx to perform the button request - `hx-post="{{.ContextUser.HomeLink}}?action=follow"` to send a POST request to follow the user - `hx-target="#profile-avatar-card"` to target the card div for replacement - `hx-indicator="#profile-avatar-card"` to place the loading indicator on the card - Change the backend response to return a `<div>` tag (the card) instead of a redirect to the user page ### Before ![follow_before](https://github.com/go-gitea/gitea/assets/20454870/a210b643-6e74-4ff9-8e61-d658c62edf1f) ### After ![follow_after](https://github.com/go-gitea/gitea/assets/20454870/5bb19ae9-0d59-4ae3-b538-4c83334e4722) --------- Signed-off-by: Yarden Shoham <[email protected]> Co-authored-by: 6543 <[email protected]> Co-authored-by: Giteabot <[email protected]>
…`Follow` (go-gitea#28908) - Closes go-gitea#28880 This change introduces htmx with the hope we could use it to make Gitea more reactive while keeping our "HTML rendered on the server" approach. - Add `htmx.js` that imports `htmx.org` and initializes error toasts - Place `hx-headers='{"x-csrf-token": "{{.CsrfToken}}"}'` on the `<body>` tag so every request that htmx sends is authenticated - Place `hx-swap="outerHTML"` on the `<body>` tag so the response of each htmx request replaces the tag it targets (as opposed to its inner content) - Place `hx-push-url="false"` on the `<body>` tag so no changes to the URL happen in `<form>` tags - Add the `is-loading` class during request ### Error toasts in action ![errors](https://github.com/go-gitea/gitea/assets/20454870/181a1beb-1cb8-4858-abe8-fa1fc3f5b8f3) ## Don't do a full page load when clicking the subscribe button - Refactor the form around the subscribe button into its own template - Use htmx to perform the form submission - `hx-boost="true"` to prevent the default form submission behavior of a full page load - `hx-sync="this:replace"` to replace the current request (in case the button is clicked again before the response is returned) - `hx-target="this"` to replace the form tag with the new form tag - Change the backend response to return a `<form>` tag instead of a redirect to the issue page ### Before ![subscribe_before](https://github.com/go-gitea/gitea/assets/20454870/cb2439a2-c3c0-425c-8d3c-5d646b1cdc28) ### After ![subscribe_after](https://github.com/go-gitea/gitea/assets/20454870/6fcd77d8-7b11-40b0-af4f-b152aaad787c) ## Don't do a full page load when clicking the follow button - Use htmx to perform the button request - `hx-post="{{.ContextUser.HomeLink}}?action=follow"` to send a POST request to follow the user - `hx-target="#profile-avatar-card"` to target the card div for replacement - `hx-indicator="#profile-avatar-card"` to place the loading indicator on the card - Change the backend response to return a `<div>` tag (the card) instead of a redirect to the user page ### Before ![follow_before](https://github.com/go-gitea/gitea/assets/20454870/a210b643-6e74-4ff9-8e61-d658c62edf1f) ### After ![follow_after](https://github.com/go-gitea/gitea/assets/20454870/5bb19ae9-0d59-4ae3-b538-4c83334e4722) --------- Signed-off-by: Yarden Shoham <[email protected]> Co-authored-by: 6543 <[email protected]> Co-authored-by: Giteabot <[email protected]>
…`Follow` (go-gitea#28908) - Closes go-gitea#28880 This change introduces htmx with the hope we could use it to make Gitea more reactive while keeping our "HTML rendered on the server" approach. - Add `htmx.js` that imports `htmx.org` and initializes error toasts - Place `hx-headers='{"x-csrf-token": "{{.CsrfToken}}"}'` on the `<body>` tag so every request that htmx sends is authenticated - Place `hx-swap="outerHTML"` on the `<body>` tag so the response of each htmx request replaces the tag it targets (as opposed to its inner content) - Place `hx-push-url="false"` on the `<body>` tag so no changes to the URL happen in `<form>` tags - Add the `is-loading` class during request ### Error toasts in action ![errors](https://github.com/go-gitea/gitea/assets/20454870/181a1beb-1cb8-4858-abe8-fa1fc3f5b8f3) ## Don't do a full page load when clicking the subscribe button - Refactor the form around the subscribe button into its own template - Use htmx to perform the form submission - `hx-boost="true"` to prevent the default form submission behavior of a full page load - `hx-sync="this:replace"` to replace the current request (in case the button is clicked again before the response is returned) - `hx-target="this"` to replace the form tag with the new form tag - Change the backend response to return a `<form>` tag instead of a redirect to the issue page ### Before ![subscribe_before](https://github.com/go-gitea/gitea/assets/20454870/cb2439a2-c3c0-425c-8d3c-5d646b1cdc28) ### After ![subscribe_after](https://github.com/go-gitea/gitea/assets/20454870/6fcd77d8-7b11-40b0-af4f-b152aaad787c) ## Don't do a full page load when clicking the follow button - Use htmx to perform the button request - `hx-post="{{.ContextUser.HomeLink}}?action=follow"` to send a POST request to follow the user - `hx-target="#profile-avatar-card"` to target the card div for replacement - `hx-indicator="#profile-avatar-card"` to place the loading indicator on the card - Change the backend response to return a `<div>` tag (the card) instead of a redirect to the user page ### Before ![follow_before](https://github.com/go-gitea/gitea/assets/20454870/a210b643-6e74-4ff9-8e61-d658c62edf1f) ### After ![follow_after](https://github.com/go-gitea/gitea/assets/20454870/5bb19ae9-0d59-4ae3-b538-4c83334e4722) --------- Signed-off-by: Yarden Shoham <[email protected]> Co-authored-by: 6543 <[email protected]> Co-authored-by: Giteabot <[email protected]>
We do a lot of server-side rendering. And if we want to keep it at least partially, we cannot fully use Vue 3 for that.
htmx fills the gap to do so while making the site more interactive. Though I'm not contributing much to the frontend lately, I did hear only good stuff about it. And if you look at the two pull requests, making the two components interactive in Vue 3 would have been more or less a complete rewrite. The pull requests only had to undergo minor code changes to make it work.
In terms of maintenance and refactoring, that is a huge advantage.
example pulls:
Subscribe
andFollow
#28908The text was updated successfully, but these errors were encountered: