aboutsummaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
authorCôme Chilliet <come.chilliet@nextcloud.com>2023-09-12 12:15:30 +0200
committerCôme Chilliet <come.chilliet@nextcloud.com>2023-10-12 10:13:43 +0200
commit05efbf11d95109c7905a554b92ee7924cc6115e6 (patch)
tree46e4c32aa5c75df3edeebf44783f9ae864b4ef77
parent800b1b703195e494d980b741ee566ba2b19d9b3f (diff)
downloadnextcloud-server-05efbf11d95109c7905a554b92ee7924cc6115e6.tar.gz
nextcloud-server-05efbf11d95109c7905a554b92ee7924cc6115e6.zip
Fix LDAP LoginListener by adding new group relationships to caches before firing the event
Signed-off-by: Côme Chilliet <come.chilliet@nextcloud.com>
-rw-r--r--apps/user_ldap/lib/Group_LDAP.php35
-rw-r--r--apps/user_ldap/lib/Group_Proxy.php4
-rw-r--r--apps/user_ldap/lib/LoginListener.php2
3 files changed, 38 insertions, 3 deletions
diff --git a/apps/user_ldap/lib/Group_LDAP.php b/apps/user_ldap/lib/Group_LDAP.php
index b3ff63d3b5c..544c7f151ac 100644
--- a/apps/user_ldap/lib/Group_LDAP.php
+++ b/apps/user_ldap/lib/Group_LDAP.php
@@ -56,9 +56,9 @@ use Psr\Log\LoggerInterface;
class Group_LDAP extends ABackend implements GroupInterface, IGroupLDAP, IGetDisplayNameBackend, IDeleteGroupBackend {
protected bool $enabled = false;
- /** @var CappedMemoryCache<string[]> $cachedGroupMembers array of users with gid as key */
+ /** @var CappedMemoryCache<string[]> $cachedGroupMembers array of user DN with gid as key */
protected CappedMemoryCache $cachedGroupMembers;
- /** @var CappedMemoryCache<array[]> $cachedGroupsByMember array of groups with uid as key */
+ /** @var CappedMemoryCache<array[]> $cachedGroupsByMember array of groups with user DN as key */
protected CappedMemoryCache $cachedGroupsByMember;
/** @var CappedMemoryCache<string[]> $cachedNestedGroups array of groups with gid (DN) as key */
protected CappedMemoryCache $cachedNestedGroups;
@@ -1357,4 +1357,35 @@ class Group_LDAP extends ABackend implements GroupInterface, IGroupLDAP, IGetDis
public function dn2GroupName(string $dn): string|false {
return $this->access->dn2groupname($dn);
}
+
+ public function addRelationshipToCaches(string $uid, ?string $dnUser, string $gid): void {
+ $dnGroup = $this->access->groupname2dn($gid);
+ $dnUser ??= $this->access->username2dn($uid);
+ if ($dnUser === false || $dnGroup === false) {
+ return;
+ }
+ if (isset($this->cachedGroupMembers[$gid])) {
+ $this->cachedGroupMembers[$gid] = array_merge($this->cachedGroupMembers[$gid], [$dnUser]);
+ }
+ unset($this->cachedGroupsByMember[$dnUser]);
+ unset($this->cachedNestedGroups[$gid]);
+ $cacheKey = 'inGroup' . $uid . ':' . $gid;
+ $this->access->connection->writeToCache($cacheKey, true);
+ $cacheKeyMembers = 'inGroup-members:' . $gid;
+ if (!is_null($data = $this->access->connection->getFromCache($cacheKeyMembers))) {
+ $this->access->connection->writeToCache($cacheKeyMembers, array_merge($data, [$dnUser]));
+ }
+ $cacheKey = '_groupMembers' . $dnGroup;
+ if (!is_null($data = $this->access->connection->getFromCache($cacheKey))) {
+ $this->access->connection->writeToCache($cacheKey, array_merge($data, [$dnUser]));
+ }
+ $cacheKey = 'getUserGroups' . $uid;
+ if (!is_null($data = $this->access->connection->getFromCache($cacheKey))) {
+ $this->access->connection->writeToCache($cacheKey, array_merge($data, [$gid]));
+ }
+ // These cache keys cannot be easily updated:
+ // $cacheKey = 'usersInGroup-' . $gid . '-' . $search . '-' . $limit . '-' . $offset;
+ // $cacheKey = 'usersInGroup-' . $gid . '-' . $search;
+ // $cacheKey = 'countUsersInGroup-' . $gid . '-' . $search;
+ }
}
diff --git a/apps/user_ldap/lib/Group_Proxy.php b/apps/user_ldap/lib/Group_Proxy.php
index 114902ff9ba..bb394156572 100644
--- a/apps/user_ldap/lib/Group_Proxy.php
+++ b/apps/user_ldap/lib/Group_Proxy.php
@@ -384,4 +384,8 @@ class Group_Proxy extends Proxy implements \OCP\GroupInterface, IGroupLDAP, IGet
public function searchInGroup(string $gid, string $search = '', int $limit = -1, int $offset = 0): array {
return $this->handleRequest($gid, 'searchInGroup', [$gid, $search, $limit, $offset]);
}
+
+ public function addRelationshipToCaches(string $uid, ?string $dnUser, string $gid): void {
+ $this->handleRequest($gid, 'addRelationshipToCaches', [$uid, $dnUser, $gid]);
+ }
}
diff --git a/apps/user_ldap/lib/LoginListener.php b/apps/user_ldap/lib/LoginListener.php
index b9c3c3c1742..ac5b32635c8 100644
--- a/apps/user_ldap/lib/LoginListener.php
+++ b/apps/user_ldap/lib/LoginListener.php
@@ -93,7 +93,7 @@ class LoginListener implements IEventListener {
continue;
}
$this->groupMembershipMapper->insert(GroupMembership::fromParams(['groupid' => $groupId,'userid' => $userId]));
- // TODO: empty cache to avoid crash
+ $this->groupBackend->addRelationshipToCaches($userId, null, $groupId);
$this->dispatcher->dispatchTyped(new UserAddedEvent($groupObject, $userObject));
$this->logger->info(
__CLASS__ . ' – {user} added to {group}',