docs, allowed hosts stuff

[ci skip]
This commit is contained in:
shamoon
2026-01-20 22:54:59 -08:00
parent 0660b91d94
commit f0e65a6ac8
6 changed files with 14 additions and 42 deletions

View File

@@ -15,8 +15,6 @@ services:
volumes: volumes:
- /path/to/config:/app/config # Make sure your local config directory exists - /path/to/config:/app/config # Make sure your local config directory exists
- /var/run/docker.sock:/var/run/docker.sock:ro # (optional) For docker integrations - /var/run/docker.sock:/var/run/docker.sock:ro # (optional) For docker integrations
environment:
HOMEPAGE_ALLOWED_HOSTS: gethomepage.dev # required, may need port. See gethomepage.dev/installation/#homepage_allowed_hosts
``` ```
### Running as non-root ### Running as non-root
@@ -38,7 +36,6 @@ services:
- /path/to/config:/app/config # Make sure your local config directory exists - /path/to/config:/app/config # Make sure your local config directory exists
- /var/run/docker.sock:/var/run/docker.sock:ro # (optional) For docker integrations, see alternative methods - /var/run/docker.sock:/var/run/docker.sock:ro # (optional) For docker integrations, see alternative methods
environment: environment:
HOMEPAGE_ALLOWED_HOSTS: gethomepage.dev # required, may need port. See gethomepage.dev/installation/#homepage_allowed_hosts
PUID: $PUID PUID: $PUID
PGID: $PGID PGID: $PGID
``` ```
@@ -46,7 +43,7 @@ services:
### With Docker Run ### With Docker Run
```bash ```bash
docker run -p 3000:3000 -e HOMEPAGE_ALLOWED_HOSTS=gethomepage.dev -v /path/to/config:/app/config -v /var/run/docker.sock:/var/run/docker.sock ghcr.io/gethomepage/homepage:latest docker run -p 3000:3000 -v /path/to/config:/app/config -v /var/run/docker.sock:/var/run/docker.sock ghcr.io/gethomepage/homepage:latest
``` ```
### Using Environment Secrets ### Using Environment Secrets

View File

@@ -27,21 +27,9 @@ You have a few options for deploying homepage, depending on your needs. We offer
</div> </div>
### `HOMEPAGE_ALLOWED_HOSTS` ### Authentication
As of v1.0 there is one required environment variable to access homepage via a URL other than `localhost`, <code>HOMEPAGE_ALLOWED_HOSTS</code>. The setting helps prevent certain kinds of attacks when retrieving data from the homepage API proxy. Public deployments of Homepage should be secured via a reverse proxy, VPN, or similar. As of version 2.0, Homepage supports a simple OIDC login flow for built-in authorization. Enable it with the following environment variables:
The value is a comma-separated (no spaces) list of allowed hosts (sometimes with the port) that can host your homepage install. See the [docker](docker.md), [kubernetes](k8s.md) and [source](source.md) installation pages for more information about where / how to set the variable.
`localhost:3000` and `127.0.0.1:3000` are always included, but you can add a domain or IP address to this list to allow that host such as `HOMEPAGE_ALLOWED_HOSTS=gethomepage.dev,192.168.1.2:1234`, etc.
If you are seeing errors about host validation, check the homepage logs and ensure that the host exactly as output in the logs is in the `HOMEPAGE_ALLOWED_HOSTS` list.
This can be disabled by setting `HOMEPAGE_ALLOWED_HOSTS` to `*` but this is not recommended. Public deployments must rely on a reverse proxy (and/or VPN) that enforces authentication, TLS, and blocks direct-IP access and unexpected Host headers; the built-in host check is a best-effort guard for local setups and is not a substitute for edge protections.
### Built-in OIDC authentication (optional, opt-in)
Homepage now supports a minimal OIDC login flow (no per-user roles or personalization) so you can deploy without a reverse proxy handling auth. Enable it with:
- `HOMEPAGE_AUTH_ENABLED=true` - `HOMEPAGE_AUTH_ENABLED=true`
- `HOMEPAGE_OIDC_ISSUER` (OIDC issuer URL, e.g., `https://auth.example.com/realms/homepage`) - `HOMEPAGE_OIDC_ISSUER` (OIDC issuer URL, e.g., `https://auth.example.com/realms/homepage`)

View File

@@ -223,9 +223,6 @@ spec:
- name: homepage - name: homepage
image: "ghcr.io/gethomepage/homepage:latest" image: "ghcr.io/gethomepage/homepage:latest"
imagePullPolicy: Always imagePullPolicy: Always
env:
- name: HOMEPAGE_ALLOWED_HOSTS
value: gethomepage.dev # required, may need port. See gethomepage.dev/installation/#homepage_allowed_hosts
ports: ports:
- name: http - name: http
containerPort: 3000 containerPort: 3000

View File

@@ -27,9 +27,7 @@ If this is your first time starting, copy the `src/skeleton` directory to `confi
Finally, run the server: Finally, run the server:
```bash ```bash
HOMEPAGE_ALLOWED_HOSTS=gethomepage.dev:1234 pnpm start pnpm start
``` ```
When updating homepage versions you will need to re-build the static files i.e. repeat the process above. When updating homepage versions you will need to re-build the static files i.e. repeat the process above.
See [HOMEPAGE_ALLOWED_HOSTS](index.md#homepage_allowed_hosts) for more information on this environment variable.

View File

@@ -1,23 +1,17 @@
import { getToken } from "next-auth/jwt"; import { getToken } from "next-auth/jwt";
import { NextResponse } from "next/server"; import { NextResponse } from "next/server";
const authEnabled = process.env.HOMEPAGE_AUTH_ENABLED === "true"; const authEnabled = Boolean(process.env.HOMEPAGE_AUTH_ENABLED);
const authSecret = process.env.NEXTAUTH_SECRET || process.env.HOMEPAGE_AUTH_SECRET; const authSecret = process.env.NEXTAUTH_SECRET || process.env.HOMEPAGE_AUTH_SECRET;
let warnedAllowedHosts = false;
export async function middleware(req) { export async function middleware(req) {
// Host validation (status quo) if (!warnedAllowedHosts && process.env.HOMEPAGE_ALLOWED_HOSTS) {
const host = req.headers.get("host"); warnedAllowedHosts = true;
const port = process.env.PORT || 3000; // eslint-disable-next-line no-console
let allowedHosts = [`localhost:${port}`, `127.0.0.1:${port}`, `[::1]:${port}`]; console.warn(
const allowAll = process.env.HOMEPAGE_ALLOWED_HOSTS === "*"; "HOMEPAGE_ALLOWED_HOSTS is deprecated. To secure a publicly accessible homepage, configure authentication instead.",
if (process.env.HOMEPAGE_ALLOWED_HOSTS) {
allowedHosts = allowedHosts.concat(process.env.HOMEPAGE_ALLOWED_HOSTS.split(","));
}
if (!allowAll && (!host || !allowedHosts.includes(host))) {
console.error(
`Host validation failed for: ${host}. Hint: Set the HOMEPAGE_ALLOWED_HOSTS environment variable to allow requests from this host / port.`,
); );
return NextResponse.json({ error: "Host validation failed. See logs for more details." }, { status: 400 });
} }
if (authEnabled) { if (authEnabled) {

View File

@@ -1,13 +1,13 @@
import NextAuth from "next-auth"; import NextAuth from "next-auth";
const authEnabled = process.env.HOMEPAGE_AUTH_ENABLED === "true"; const authEnabled = Boolean(process.env.HOMEPAGE_AUTH_ENABLED);
const issuer = process.env.HOMEPAGE_OIDC_ISSUER; const issuer = process.env.HOMEPAGE_OIDC_ISSUER;
const clientId = process.env.HOMEPAGE_OIDC_CLIENT_ID; const clientId = process.env.HOMEPAGE_OIDC_CLIENT_ID;
const clientSecret = process.env.HOMEPAGE_OIDC_CLIENT_SECRET; const clientSecret = process.env.HOMEPAGE_OIDC_CLIENT_SECRET;
const homepageAuthSecret = process.env.HOMEPAGE_AUTH_SECRET; const homepageAuthSecret = process.env.HOMEPAGE_AUTH_SECRET;
const homepageExternalUrl = process.env.HOMEPAGE_EXTERNAL_URL; const homepageExternalUrl = process.env.HOMEPAGE_EXTERNAL_URL;
// Map HOMEPAGE_* envs to what NextAuth expects so users dont need NEXTAUTH_* explicitly. // Map HOMEPAGE_* envs to what NextAuth expects
if (!process.env.NEXTAUTH_SECRET && homepageAuthSecret) { if (!process.env.NEXTAUTH_SECRET && homepageAuthSecret) {
process.env.NEXTAUTH_SECRET = homepageAuthSecret; process.env.NEXTAUTH_SECRET = homepageAuthSecret;
} }
@@ -22,9 +22,7 @@ if (
authEnabled && authEnabled &&
(!issuer || !clientId || !clientSecret || !process.env.NEXTAUTH_SECRET || !process.env.NEXTAUTH_URL) (!issuer || !clientId || !clientSecret || !process.env.NEXTAUTH_SECRET || !process.env.NEXTAUTH_URL)
) { ) {
throw new Error( throw new Error("OIDC auth is enabled but required settings are missing.");
"OIDC auth is enabled but required settings are missing. Please set HOMEPAGE_OIDC_ISSUER, HOMEPAGE_OIDC_CLIENT_ID, HOMEPAGE_OIDC_CLIENT_SECRET, HOMEPAGE_AUTH_SECRET, and HOMEPAGE_EXTERNAL_URL.",
);
} }
let providers = []; let providers = [];