SessionGuard + Guacamole 1.6 integration
The sessionguard-guacamole extension does not authenticate users. It decorates the UserContext produced by Guacamole's existing providers and asks the SessionGuard broker for connection parameter tokens at connect time.
1. Build Guacamole with the extension
Use Dockerfile.guacamole instead of the stock image directly. It builds guacamole-extension/ with Maven and copies the JAR to /etc/guacamole/extensions/.
The Guacamole container needs these additional environment variables:
SESSIONGUARD_MASTER_URL: http://sessionguard-master:8080
SESSIONGUARD_BROKER_API_KEY: ${SESSIONGUARD_BROKER_API_KEY}
SESSIONGUARD_BROKER_TIMEOUT_MS: "2500"
Use a private Docker network between Guacamole and SessionGuard Master where possible. The broker API key is independent from the agent enrollment token and PocketID client secret.
2. Configure Guacamole RDP connections
For a brokered desktop connection set the RDP hostname to:
${SESSIONGUARD_HOST}
For a brokered RemoteApp resource, these SessionGuard tokens can be used as connection parameters:
hostname: ${SESSIONGUARD_HOST}
remote-app: ${SESSIONGUARD_REMOTE_APP}
remote-app-dir: ${SESSIONGUARD_REMOTE_APP_DIR}
remote-app-args: ${SESSIONGUARD_REMOTE_APP_ARGS}
The extension identifies a SessionGuard resource by Guacamole connection ID or connection name. Create the corresponding mapping in SessionGuard under Published Resources. Unmapped Guacamole connections receive no SessionGuard tokens and remain untouched; this lets brokered and static/admin connections coexist.
3. Broker behavior
- Existing matching RDS session in the requested farm wins (if reconnect is enabled).
- Otherwise a valid SessionGuard user lease is reused.
- Otherwise only online,
online-mode farm members abovemin_health_scoreare considered. - Candidates are scored by health, active/disconnected sessions, CPU and memory pressure.
drainblocks new allocations but allows reconnects;maintenanceblocks both.
With single_session_per_user=true, the lease key is global per username. With it disabled, leases are scoped by user + farm + resource.
4. Header-auth boundary
If Guacamole uses HTTP_AUTH_HEADER=X-Guacamole-User, untrusted traffic must not be able to reach Guacamole directly and supply that header. Keep the reverse proxy/header scrubber as the only trusted ingress path. Prefer a dedicated proxy network instead of sharing Guacamole's port with unrelated containers.
5. SessionGuard Access Auth (0.5.0+)
SessionGuard Master can replace the separate traefik-forward-auth service for Guacamole. Keep Guacamole's header-auth extension (HTTP_AUTH_HEADER=X-Guacamole-User), but configure Traefik to call:
http://sessionguard-master:8080/auth/verify
Expose the Master's /auth/* routes on the Guacamole hostname through the reserved public prefix /_sessionguard/auth/*, with that router excluded from ForwardAuth. The recommended PocketID callback is therefore:
https://guacamole.example.org/_sessionguard/auth/oidc/callback
and the PocketID logout/back-channel callback is:
https://guacamole.example.org/_sessionguard/auth/backchannel-logout
Before ForwardAuth, strip any client-provided X-Guacamole-User and X-SessionGuard-* identity headers. After successful ForwardAuth, copy only SessionGuard's auth response headers to Guacamole.
See docs/ACCESS-AUTH.md for complete labels and migration steps.