Fix auth token not persisting over HTTP (non-TLS) deployments (#47076)
<!-- Add the related story/sub-task/bug number, like Resolves #123, or remove if NA --> **Related issue:** Resolves #41641 & Resolves #44276 When Fleet is served over plain HTTP from a non-localhost host (e.g. a Docker deployment accessed by IP), login fails with an "Authentication Required" error. To reproduce this, I ran the server as follows: ``` ./build/fleet serve --dev --dev_license --server_tls=false --server_address=0.0.0.0:8080 ``` And then, go to the Fleet UI using my private IP: ``` http://<my-lan-ip>:8080 ``` https://github.com/user-attachments/assets/09543b9b-b9ee-4d1c-b47e-ebd49c20c699 The auth token is stored client-side in a `__Host-token` cookie with the `Secure` attribute, and browsers silently drop `__Host-`/`Secure` cookies on insecure, non-localhost origins. So, the token was never persisted and the follow-up `GET /config` (and every subsequent request) went out without it. This change keeps the `__Host-token` + `Secure` cookie on HTTPS, and falls back to a plain `token` cookie over HTTP so the token persists. TL;DR: this restores the pre [#40504](https://github.com/fleetdm/fleet/pull/40504) behavior for non-TLS deployments and leaves HTTPS behavior unchanged. # Checklist for submitter - [x] Changes file added for user-visible changes in `changes/`, `orbit/changes/` or `ee/fleetd-chrome/changes`. See [Changes files](https://github.com/fleetdm/fleet/blob/main/docs/Contributing/guides/committing-changes.md#changes-files) for more information. ## Testing - [x] QA'd all new/changed functionality manually https://github.com/user-attachments/assets/e7e838f3-f423-4e28-aebd-5f921af08b00 <!-- This is an auto-generated comment: release notes by coderabbit.ai --> ## Summary by CodeRabbit * **Bug Fixes** * Fixed an issue where login requests would fail with an "Authentication Required" error when Fleet is served over HTTP. <!-- end of auto-generated comment: release notes by coderabbit.ai -->
This commit is contained in:
@@ -0,0 +1 @@
|
||||
- Fixed login failing with an "Authentication Required" error when Fleet is served over HTTP, by storing the auth token in a non-secure cookie outside of HTTPS contexts.
|
||||
@@ -6,23 +6,36 @@ import Cookie from "js-cookie";
|
||||
|
||||
const DEFAULT_EXPIRATION_DAYS = 5;
|
||||
|
||||
// The `__Host-` cookie name prefix and the `Secure` attribute both require the
|
||||
// cookie to be set from a secure (HTTPS) context. When Fleet is served over
|
||||
// plain HTTP (e.g. a Docker deployment without TLS), the browser silently
|
||||
// refuses to store such a cookie, leaving the user unable to authenticate
|
||||
// because the token is never persisted and therefore never attached to
|
||||
// subsequent requests. Detect the context and fall back to a regular,
|
||||
// non-secure cookie when not served over HTTPS.
|
||||
const isSecure = (): boolean => window.location.protocol === "https:";
|
||||
|
||||
// `__Host-` prefixed names are only valid on secure cookies, so the cookie name
|
||||
// must match the context it was stored in for get/remove to find it.
|
||||
const getTokenName = (): string => (isSecure() ? "__Host-token" : "token");
|
||||
|
||||
const save = (token: string, expiresAt?: Date): void => {
|
||||
Cookie.set("__Host-token", token, {
|
||||
secure: true,
|
||||
Cookie.set(getTokenName(), token, {
|
||||
secure: isSecure(),
|
||||
sameSite: "lax",
|
||||
expires: expiresAt ?? DEFAULT_EXPIRATION_DAYS,
|
||||
});
|
||||
};
|
||||
|
||||
const get = (): string | null => {
|
||||
return Cookie.get("__Host-token") || null;
|
||||
return Cookie.get(getTokenName()) || null;
|
||||
};
|
||||
|
||||
const remove = (): void => {
|
||||
// NOTE: the secure and sameSite from the cookie must be provided
|
||||
// to correctly remove. That is why we include the options here as well.
|
||||
Cookie.remove("__Host-token", {
|
||||
secure: true,
|
||||
Cookie.remove(getTokenName(), {
|
||||
secure: isSecure(),
|
||||
sameSite: "lax",
|
||||
});
|
||||
};
|
||||
|
||||
Reference in New Issue
Block a user