From cb56ae5f46ba0ef845b29c97664d726b06e5d3a7 Mon Sep 17 00:00:00 2001 From: Nash Kaminski <36900518+gs-kamnas@users.noreply.github.com> Date: Sat, 2 Oct 2021 08:02:42 -0500 Subject: [PATCH] Improvements to SSO Authorization and logout handling (#13311) * Improvements to SSO Authorization and logout handling Changes: * Adds support for a default access level in the SSO authorization plugin when group mapping is enabled. * Restore functionality of the auth_logout_handler configuration option, allowing the user to be redirected to a configured URL to complete logout from an external IdP. * Documentation and test coverage updates * Set sso.static_level to 0 in AuthSSOTest:testGroupParsing() * Simplify implementation to use default values in Config::get() --- LibreNMS/Authentication/SSOAuthorizer.php | 4 ++-- app/Http/Controllers/Auth/LoginController.php | 6 ++++++ doc/Extensions/Authentication.md | 18 ++++++++++++++---- tests/AuthSSOTest.php | 6 ++++++ 4 files changed, 28 insertions(+), 6 deletions(-) diff --git a/LibreNMS/Authentication/SSOAuthorizer.php b/LibreNMS/Authentication/SSOAuthorizer.php index 3d709ce7f0..e5384c165e 100644 --- a/LibreNMS/Authentication/SSOAuthorizer.php +++ b/LibreNMS/Authentication/SSOAuthorizer.php @@ -180,7 +180,7 @@ class SSOAuthorizer extends MysqlAuthorizer } /** - * Map a user to a permission level based on a table mapping, 0 if no matching group is found. + * Map a user to a permission level based on a table mapping, sso.static_level (default 0) if no matching group is found. * * @return int */ @@ -202,7 +202,7 @@ class SSOAuthorizer extends MysqlAuthorizer $groups = $valid_groups; } - $level = 0; + $level = (int) Config::get('sso.static_level', 0); $config_map = Config::get('sso.group_level_map'); diff --git a/app/Http/Controllers/Auth/LoginController.php b/app/Http/Controllers/Auth/LoginController.php index b5b1752f89..82ac831198 100644 --- a/app/Http/Controllers/Auth/LoginController.php +++ b/app/Http/Controllers/Auth/LoginController.php @@ -6,6 +6,7 @@ use App\Http\Controllers\Controller; use App\Models\Device; use App\Providers\RouteServiceProvider; use Illuminate\Foundation\Auth\AuthenticatesUsers; +use Illuminate\Http\Request; use LibreNMS\Config; class LoginController extends Controller @@ -55,4 +56,9 @@ class LoginController extends Controller return view('auth.login'); } + + protected function loggedOut(Request $request) + { + return redirect(Config::get('auth_redirect_handler', $this->redirectTo)); + } } diff --git a/doc/Extensions/Authentication.md b/doc/Extensions/Authentication.md index b7f20f2ac8..db4003e1f7 100644 --- a/doc/Extensions/Authentication.md +++ b/doc/Extensions/Authentication.md @@ -499,14 +499,20 @@ $config['sso']['group_level_map'] = ['librenms-admins' => 10, 'librenms-readers' $config['sso']['group_delimiter'] = ';'; ``` -The mechanism expects to find a delimited list of groups within the +This mechanism expects to find a delimited list of groups within the attribute that ___sso\_group\_attr___ points to. This should be an -associative array of group name keys, with privilege levels as +associative array of group name keys, with privilege levels as values. The mechanism will scan the list and find the ___highest___ privilege level that the user is entitled to, and assign that value to the user. -This format may be specific to Shibboleth; other relying party +If there are no matches between the user's groups and the +___sso\_group\_level\_map___, the user will be assigned the privilege level +specified in the ___sso\_static\_level___ variable, with a default of 0 (no access). +This feature can be used to provide a default access level (such as read-only) +to all authenticated users. + +Additionally, this format may be specific to Shibboleth; other relying party software may need changes to the mechanism (e.g. ___mod\_auth\_mellon___ may create pseudo arrays). @@ -527,7 +533,11 @@ If your Relying Party has a magic URL that needs to be called to end a session, you can configure LibreNMS to direct the user to it: ```php -$config['post_logout_action'] = '/Shibboleth.sso/Logout'; +# Example for Shibboleth +$config['auth_logout_handler'] = '/Shibboleth.sso/Logout'; + +# Example for oauth2-proxy +$config['auth_logout_handler'] = '/oauth2/sign_out'; ``` This option functions independently of the Single Sign-on mechanism. diff --git a/tests/AuthSSOTest.php b/tests/AuthSSOTest.php index 23ffeafc6d..2e388779af 100644 --- a/tests/AuthSSOTest.php +++ b/tests/AuthSSOTest.php @@ -397,6 +397,7 @@ class AuthSSOTest extends DBTestCase $this->basicEnvironmentEnv(); + Config::set('sso.static_level', 0); Config::set('sso.group_strategy', 'map'); Config::set('sso.group_delimiter', ';'); Config::set('sso.group_attr', 'member'); @@ -418,6 +419,11 @@ class AuthSSOTest extends DBTestCase $_SERVER['member'] = ''; $this->assertTrue($a->authSSOParseGroups() === 0); + // Empty with default access level + Config::set('sso.static_level', 5); + $this->assertTrue($a->authSSOParseGroups() === 5); + Config::forget('sso.static_level'); + // Null $_SERVER['member'] = null; $this->assertTrue($a->authSSOParseGroups() === 0);