Skip to content
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
29 changes: 22 additions & 7 deletions README.md
Original file line number Diff line number Diff line change
@@ -1,14 +1,14 @@
# user_oidc

OIDC connect user backend for Nextcloud
OpenID Connect user backend for Nextcloud

## General usage
See [Nextcloud and OpenID-Connect](https://www.schiessle.org/articles/2020/07/26/nextcloud-and-openid-connect/)
for a proper jumpstart.

### User IDs

The OIDC backend will ensure that user ids are unique even when multiple providers would report the same user
The OpenID Connect backend will ensure that user ids are unique even when multiple providers would report the same user
id to ensure that a user cannot identify for the same Nextcloud account through different providers.
Therefore, a hash of the provider id and the user id is used. This behaviour can be turned off in the provider options.

Expand Down Expand Up @@ -55,7 +55,7 @@ sudo -u www-data php /var/www/nextcloud/occ config:app:set --value=1 user_oidc i
```

### Disable other login methods
If there is only one OIDC provider configured, it can be made the default login
If there is only one OpenID Connect provider configured, it can be made the default login
method and the user would get redirected to the provider immediately for the
login. Admins can still use the regular login through adding the `?direct=1`
parameter to the login URL.
Expand All @@ -66,8 +66,8 @@ sudo -u www-data php var/www/nextcloud/occ config:app:set --value=0 user_oidc al

### Single logout

Single logout is enabled by default. When logging out of Nextcloud, the end_session_endpoint of the OIDC provider
is requested to end the session on this side.
Single logout is enabled by default. When logging out of Nextcloud,
the end_session_endpoint of the OpenID Connect provider is requested to end the session on this side.

It can be disabled in `config.php`:
``` php
Expand All @@ -78,8 +78,8 @@ It can be disabled in `config.php`:

### Auto provisioning

By default, this app provisions the users with the information contained in the OIDC ID token which means it gets
the user information (such as the display name or the email) from the OIDC provider.
By default, this app provisions the users with the information contained in the OIDC token
which means it gets the user information (such as the display name or the email) from the ID provider.
This also means that user_oidc takes care of creating the users when they first log in.

It is possible to disable auto provisioning to let other user backends (like LDAP)
Expand All @@ -93,6 +93,21 @@ Auto provisioning can be disabled in `config.php`:
],
```

:warning: When relying on the LDAP user backend for user provisioning, you need to adjust the
"Login Attributes" section and the Expert tab's "Internal Username" value of your LDAP settings.
Even if LDAP does not handle the login process,
the user_oidc app will trigger an LDAP search when logging in to make sure the user is created if it was
not synced already.
So it is essential that:
* the OpenID Connect "User ID mapping" attribute matches the LDAP Expert tab's "Internal Username".
The attribute names can be different but their values should match. Do not change the LDAP configuration,
simply adapt the OpenID Connect provider configuration.
* the OpenID Connect "User ID mapping" attribute can be used in the LDAP login query
defined in the "Login Attributes" tab.

In other words, make sure that your OpenID Connect provider's "User ID mapping" setting is set to an attribute
which provides the same values as the LDAP attribute set in "Internal Username" in your LDAP settings.

### UserInfo request for Bearer token validation

The OIDC tokens used to make API call to Nextcloud might have been generated by an external entity.
Expand Down
3 changes: 3 additions & 0 deletions lib/Controller/LoginController.php
Original file line number Diff line number Diff line change
Expand Up @@ -351,6 +351,9 @@ private function provisionUser(string $userId, int $providerId, object $idTokenP
$oidcSystemConfig = $this->config->getSystemValue('user_oidc', []);
$autoProvisionAllowed = (!isset($oidcSystemConfig['auto_provision']) || $oidcSystemConfig['auto_provision']);
if (!$autoProvisionAllowed) {
// in case user is provisioned by user_ldap, userManager->search() triggers an ldap search which syncs the results
// so new users will be directly available even if they were not synced before this login attempt
$this->userManager->search($userId);
// when auto provision is disabled, we assume the user has been created by another user backend (or manually)
return $this->userManager->get($userId);
}
Expand Down
16 changes: 14 additions & 2 deletions lib/User/Backend.php
Original file line number Diff line number Diff line change
Expand Up @@ -252,8 +252,20 @@ public function getCurrentUserId() {
if ($autoProvisionAllowed) {
$backendUser = $this->userMapper->getOrCreate($provider->getId(), $userId);
return $backendUser->getUserId();
} elseif ($this->userExists($userId) || $this->userManager->userExists($userId)) {
return $userId;
} else {
if ($this->userExists($userId)) {
return $userId;
}
// if the user exists locally
if ($this->userManager->userExists($userId)) {
return $userId;
}
// if not, this potentially triggers a user_ldap search
// to get the user if it has not been synced yet
$this->userManager->search($userId);
if ($this->userManager->userExists($userId)) {
return $userId;
}
}
return '';
}
Expand Down