open-webui: do not login when not belonging to user or admin group

This commit is contained in:
ibizaman 2025-10-06 23:39:09 +02:00 committed by Pierre Penninckx
parent 81dc4f280d
commit a536ee141e
3 changed files with 87 additions and 15 deletions

View file

@ -4,6 +4,9 @@ let
contracts = pkgs.callPackage ../contracts {};
shblib = pkgs.callPackage ../../lib {};
roleClaim = "openwebui_groups";
oauthScopes = [ "openid" "email" "profile" "groups" "${roleClaim}" ];
in
{
options.shb.open-webui = {
@ -191,21 +194,11 @@ in
${cfg.ldap.adminGroup} = {};
};
shb.authelia.oidcClients = [
{
client_id = cfg.sso.clientID;
client_secret.source = cfg.sso.sharedSecretForAuthelia.result.path;
scopes = [ "openid" "email" "profile" ];
authorization_policy = cfg.sso.authorization_policy;
redirect_uris = [
"https://${cfg.subdomain}.${cfg.domain}/oauth/oidc/callback"
];
}
];
services.open-webui = {
package = pkgs.open-webui.overrideAttrs (finalAttrs: {
patches = [
../../patches/0001-selfhostblocks-never-onboard.patch
../../patches/0002-selfhostblocks-do-not-allow-unauthorized-roles.patch
];
});
environment = {
@ -217,13 +210,43 @@ in
OAUTH_CLIENT_ID = cfg.sso.clientID;
OPENID_PROVIDER_URL = "${cfg.sso.authEndpoint}/.well-known/openid-configuration";
OAUTH_PROVIDER_NAME = "Single Sign-On";
OAUTH_SCOPES = "openid email profile";
OAUTH_ALLOWED_ROLES = cfg.ldap.userGroup;
OAUTH_ADMIN_ROLES = cfg.ldap.adminGroup;
OAUTH_USERNAME_CLAIM = "preferred_username";
ENABLE_OAUTH_ROLE_MANAGEMENT = "True";
OAUTH_ALLOWED_ROLES = "user,admin";
OAUTH_ADMIN_ROLES = "admin";
OAUTH_ROLES_CLAIM = roleClaim;
OAUTH_SCOPES = lib.concatStringsSep " " oauthScopes;
};
};
shb.authelia.extraDefinitions = {
user_attributes.${roleClaim}.expression =
''"${cfg.ldap.adminGroup}" in groups ? ["admin"] : ("${cfg.ldap.userGroup}" in groups ? ["user"] : [""])'';
};
shb.authelia.extraOidcClaimsPolicies.${roleClaim} = {
custom_claims = {
"${roleClaim}" = {};
};
};
shb.authelia.extraOidcScopes."${roleClaim}" = {
claims = [ "${roleClaim}" ];
};
shb.authelia.oidcClients = [
{
client_id = cfg.sso.clientID;
client_name = "Open WebUI";
client_secret.source = cfg.sso.sharedSecretForAuthelia.result.path;
claims_policy = "${roleClaim}";
public = false;
authorization_policy = cfg.sso.authorization_policy;
redirect_uris = [
"https://${cfg.subdomain}.${cfg.domain}/oauth/oidc/callback"
];
scopes = oauthScopes;
}
];
systemd.services.open-webui.serviceConfig.EnvironmentFile = "/run/open-webui/secrets.env";
systemd.tmpfiles.rules = [
"d '/run/open-webui' 0750 root root - -"

View file

@ -11,12 +11,13 @@ This service sets up [Open WebUI][] which provides a frontend to various LLMs.
## Features {#services-open-webui-features}
- Telemetry disabled.
- Skip onboarding.
- Skip onboarding through custom patch.
- Declarative [LDAP](#services-open-webui-options-shb.open-webui.ldap) Configuration.
Needed LDAP groups are created automatically.
- Declarative [SSO](#services-open-webui-options-shb.open-webui.sso) Configuration.
When SSO is enabled, login with user and password is disabled.
Registration is enabled through SSO.
Correct error message for unauthorized user through custom patch.
- Access through [subdomain](#services-open-webui-options-shb.open-webui.subdomain) using reverse proxy.
- Access through [HTTPS](#services-open-webui-options-shb.open-webui.ssl) using reverse proxy.
- [Backup](#services-open-webui-options-shb.open-webui.sso) through the [backup block](./blocks-backup.html).

View file

@ -0,0 +1,48 @@
From fed4cfab1f66e6a2a46dbdd20ad52aee664f06b1 Mon Sep 17 00:00:00 2001
From: ibizaman <ibizaman@tiserbox.com>
Date: Thu, 9 Oct 2025 01:37:43 +0200
Subject: [PATCH] selfhostblocks: do not allow unauthorized roles
---
backend/open_webui/constants.py | 2 +-
backend/open_webui/utils/oauth.py | 5 +++--
2 files changed, 4 insertions(+), 3 deletions(-)
diff --git a/backend/open_webui/constants.py b/backend/open_webui/constants.py
index 59ee6aaac..5a42f1805 100644
--- a/backend/open_webui/constants.py
+++ b/backend/open_webui/constants.py
@@ -51,7 +51,7 @@ class ERROR_MESSAGES(str, Enum):
EXISTING_USERS = "You can't turn off authentication because there are existing users. If you want to disable WEBUI_AUTH, make sure your web interface doesn't have any existing users and is a fresh installation."
- UNAUTHORIZED = "401 Unauthorized"
+ UNAUTHORIZED = "Unauthorized"
ACCESS_PROHIBITED = "You do not have permission to access this resource. Please contact your administrator for assistance."
ACTION_PROHIBITED = (
"The requested action has been restricted as a security measure."
diff --git a/backend/open_webui/utils/oauth.py b/backend/open_webui/utils/oauth.py
index 9090c38ce..3c68dead4 100644
--- a/backend/open_webui/utils/oauth.py
+++ b/backend/open_webui/utils/oauth.py
@@ -336,8 +336,7 @@ class OAuthManager:
oauth_allowed_roles = auth_manager_config.OAUTH_ALLOWED_ROLES
oauth_admin_roles = auth_manager_config.OAUTH_ADMIN_ROLES
oauth_roles = []
- # Default/fallback role if no matching roles are found
- role = auth_manager_config.DEFAULT_USER_ROLE
+ role = None
# Next block extracts the roles from the user data, accepting nested claims of any depth
if oauth_claim and oauth_allowed_roles and oauth_admin_roles:
@@ -373,6 +372,8 @@ class OAuthManager:
log.debug("Assigned user the admin role")
role = "admin"
break
+ if role is None:
+ raise HTTPException(403, detail=ERROR_MESSAGES.UNAUTHORIZED)
else:
if not user:
# If role management is disabled, use the default role for new users
--
2.50.1