hay-kot / homebox

Homebox is the inventory and organization system built for the Home User
https://hay-kot.github.io/homebox/
GNU Affero General Public License v3.0
2.59k stars 176 forks source link

Reverse proxy with authentication though redirection not working with service worker #739

Open AmineI opened 4 months ago

AmineI commented 4 months ago

First Check

Homebox Version

0.10.3 / latest nightly

What is the issue you are experiencing?

Homebox does not work behind a reverse proxy performing authentication through redirection. When the user tries to access Homebox, if the service worker has been previously registered, the redirection to the authentication page silently errors (as it is the fetch/API calls that are redirected and fail.) 302 Errors appear in the console.

This problem seemed to be common when using service workers. This issue is related and quite clearly documents the scenario, challenges, and adopted solution.

What should happen is that the user is redirected to a login page by the reverse proxy. This login page can be Google's, Microsoft, Auth0, ... . Once the user logins there, they are redirected to homebox. Instead, the redirection never happens.

How can the maintainer reproduce the issue?

  1. Install and configure reverse proxy with authentication through redirection
  2. Log in with reverse proxy
  3. Access Homebox page
  4. Log out from reverse proxy (or clear the cookie that stores its login status)
  5. Refresh Homebox

The Homebox landing page might appear, but any action/data retrieval fail. It might also display a 500 offline error depending on the url accessed. The expected behavior is that the user is correctly redirected in browser.

Deployment

Docker (Linux)

Deployment Details

I have confirmed the behavior with nginx, vouch-proxy and many identity providers, including Azure AD & Auth0.

It can also be reproduced on Azure with easyauth as an authentication middleware to play the role of the reverse proxy.

AmineI commented 4 months ago

This one has been a pain for a very long while. It will likely unblock scenarios related to #345. I did a lot of research and ended up at the same conclusions as the friends at https://github.com/openhab/openhab-webui/issues/1207 , and their implementation. (Thanks !)

There is seemingly no 100% reliable way to handle this redirects through the service worker itself, especially when you add CORS and third party identity providers in the mix. By design, target URLs for the redirection are not exposed to our code, but only to the browser.

Using the fetch option redirect: manual, if a redirect happens we do get a specific response object however : with all fields empty except type: opaqueredirect. We are able to take advantage of this, and :

That materializes roughly like this :

[...] 
    payload.redirect = "manual";

    const response = await fetch(this.url(rargs.url), payload);
    this.callResponseInterceptors(response, payload);

    if (response.type === "opaqueredirect" && "serviceWorker" in navigator) {
        const swRegistration = await navigator.serviceWorker.getRegistration();
        await swRegistration.unregister();
        window.location.reload();
    }
[...]

in here https://github.com/hay-kot/homebox/blob/aace77ec408d05451dc4dcdcabc7867fd7926df3/frontend/lib/requests/requests.ts#L97-L100

This fixed the issue on my test scenarios, and had no impact on the asset-id redirects here https://github.com/hay-kot/homebox/blob/aace77ec408d05451dc4dcdcabc7867fd7926df3/frontend/pages/assets/%5Bid%5D.vue#L25

Hoping this can help. I'm too unfamiliar with Vue/Nuxt to confirm all options were explored on that side, but here is where I ended up after many attempts :). Thanks again for your time and work on this great project !