bigskysoftware / htmx

</> htmx - high power tools for HTML
https://htmx.org
Other
37.59k stars 1.27k forks source link

Keep hmtx-request class while redirecting #1925

Open ouhndelof opened 11 months ago

ouhndelof commented 11 months ago

I am using the htmx-request class to show a loading indicator to the user when they issue a request. However, when the user receives the HX-Redirect header, a redirect is started and the browser takes over showing a loading indicator. Is there a simple way to keep the htmx-request class when the HX-Redirect header is received, so that the original loading indicator can be shown from the request is sent until the redirect has happened?

andryyy commented 11 months ago

It should work with the HX-Location header instead, as it uses a similar approach as an ajax() call.

A redirect is, iirc, a command for the browser to redirect itself to another location, which halts the current document while executing.

ouhndelof commented 11 months ago

Switching to HX-Location did indeed make the loading indicator stay until the redirect. But I need to swap out the whole page with the whole response, not just swap out some element with the body from the response. Is that possible to do with HX-Location?

phillip-haydon commented 3 months ago

Using HX-Location doesn't seem to be a good work-around. If there's a delay on the redirection url, there's still a period of time where the indicator or disabled state is reverted until the redirection occurs.

Currently the only way around this seems to be to re-apply those states manually by listening to htmx:afterRequest or applying my own class at htmx:configRequest

IMO this really should be something handled by htmx, i.e 'if the result of a request is HX-Redirect / HX-Location > Don't remove the state.

dwasyl commented 2 months ago

Just stumbled across this same issue. There's a slight delay on the redirect which gets confusing because the hx-indicator lifts once the redirect is received.

Is this something that could be changed?

webdevcody commented 1 month ago

I'm also running into this issue when using HX-Redirect. I'm not a fan of using HX-Location because it forces me to restructure my entire backend to know if it should return a full template or just the body. The issue is when using an HX-Redirect, the code calls removeRequestIndicators which will enable the button and remove the spinner; after, the code invokes the url change using a location.href due to the HX-Location header. This means there is a short period of time on slower network connections where to the user it seems like the button is clickable again.

I've tried adding some custom logic into HTMX to not call removeRequestIndicators if the response header includes HX-Location, but then you need to handle the scenario where a user clicks the back button in the browser which causes the old page to load and display spinners and disabled buttons. I then started looking into adding this code so I could go through the cached page and reset button / indicators, but it was starting to get more complex than I wanted to tackle.

window.addEventListener('pageshow', (event) => {
        if (event.persisted) {
           // do something to re-enable any buttons previously disabled by htmx and also hide any indicators
        }
    });

If I get more time I'll keep poking around at this.

webdevcody commented 1 month ago

This was my quick fix that I'm going to try rolling with on my own fork https://github.com/bigskysoftware/htmx/pull/2779

phillip-haydon commented 1 month ago

I assume the pageshow event is unrelated to the change, but if its as simple as adding that condition, I really hope it gets rolled in ASAP, cos this is the only thing I really hate about htmx.

webdevcody commented 1 month ago

@phillip-haydon the pageshow is needed because if you click back in your browser, all of your buttons will stay disabled and indicators displayed

this is without the pageshow logic

https://github.com/user-attachments/assets/82b5ab94-3222-47a8-9ec6-83d1c05f4103

phillip-haydon commented 1 month ago

Really really need to get this rolled into master!