diff options
author | Anna Larch <anna@nextcloud.com> | 2022-11-03 12:51:29 +0100 |
---|---|---|
committer | Anna (Rebase PR Action) <miaulalala@users.noreply.github.com> | 2022-11-28 11:52:55 +0000 |
commit | 7c4ceb444cb22f519cd30af5cd22304b960c8818 (patch) | |
tree | 99007ffe7cdc0a7f7360f4793cb92a6f18b98c52 /lib/private/Group | |
parent | 08587c9de681f3335d81c327fd524f229380067a (diff) | |
download | nextcloud-server-7c4ceb444cb22f519cd30af5cd22304b960c8818.tar.gz nextcloud-server-7c4ceb444cb22f519cd30af5cd22304b960c8818.zip |
Add group display name cache
Signed-off-by: Anna Larch <anna@nextcloud.com>
Diffstat (limited to 'lib/private/Group')
-rw-r--r-- | lib/private/Group/DisplayNameCache.php | 87 | ||||
-rw-r--r-- | lib/private/Group/Group.php | 2 | ||||
-rw-r--r-- | lib/private/Group/Manager.php | 17 |
3 files changed, 104 insertions, 2 deletions
diff --git a/lib/private/Group/DisplayNameCache.php b/lib/private/Group/DisplayNameCache.php new file mode 100644 index 00000000000..d724b6caf0e --- /dev/null +++ b/lib/private/Group/DisplayNameCache.php @@ -0,0 +1,87 @@ +<?php + +declare(strict_types=1); + +/** + * @copyright 2022 Anna Larch <anna.larch@gmx.net> + * @author Anna Larch <anna.larch@gmx.net> + * + * @license AGPL-3.0-or-later + * + * This code is free software: you can redistribute it and/or modify + * it under the terms of the GNU Affero General Public License, version 3, + * as published by the Free Software Foundation. + * + * This program is distributed in the hope that it will be useful, + * but WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the + * GNU Affero General Public License for more details. + * + * You should have received a copy of the GNU Affero General Public License, version 3, + * along with this program. If not, see <http://www.gnu.org/licenses/> + * + */ + + +namespace OC\Group; + +use OCP\Cache\CappedMemoryCache; +use OCP\EventDispatcher\Event; +use OCP\EventDispatcher\IEventListener; +use OCP\Group\Events\GroupChangedEvent; +use OCP\ICache; +use OCP\ICacheFactory; +use OCP\IGroupManager; + +/** + * Class that cache the relation Group ID -> Display name + * + * This saves fetching the group from the backend for "just" the display name + */ +class DisplayNameCache implements IEventListener { + private CappedMemoryCache $cache; + private ICache $memCache; + private IGroupManager $groupManager; + + public function __construct(ICacheFactory $cacheFactory, IGroupManager $groupManager) { + $this->cache = new CappedMemoryCache(); + $this->memCache = $cacheFactory->createDistributed('groupDisplayNameMappingCache'); + $this->groupManager = $groupManager; + } + + public function getDisplayName(string $groupId): ?string { + if (isset($this->cache[$groupId])) { + return $this->cache[$groupId]; + } + $displayName = $this->memCache->get($groupId); + if ($displayName) { + $this->cache[$groupId] = $displayName; + return $displayName; + } + + $group = $this->groupManager->get($groupId); + if ($group) { + $displayName = $group->getDisplayName(); + } else { + $displayName = null; + } + $this->cache[$groupId] = $displayName; + $this->memCache->set($groupId, $displayName, 60 * 10); // 10 minutes + + return $displayName; + } + + public function clear(): void { + $this->cache = new CappedMemoryCache(); + $this->memCache->clear(); + } + + public function handle(Event $event): void { + if ($event instanceof GroupChangedEvent && $event->getFeature() === 'displayName') { + $groupId = $event->getGroup()->getGID(); + $newDisplayName = $event->getValue(); + $this->cache[$groupId] = $newDisplayName; + $this->memCache->set($groupId, $newDisplayName, 60 * 10); // 10 minutes + } + } +} diff --git a/lib/private/Group/Group.php b/lib/private/Group/Group.php index 2ef4d2ee23f..ae70a611e4e 100644 --- a/lib/private/Group/Group.php +++ b/lib/private/Group/Group.php @@ -38,6 +38,7 @@ use OCP\Group\Backend\IGetDisplayNameBackend; use OCP\Group\Backend\IHideFromCollaborationBackend; use OCP\Group\Backend\INamedBackend; use OCP\Group\Backend\ISetDisplayNameBackend; +use OCP\Group\Events\GroupChangedEvent; use OCP\GroupInterface; use OCP\IGroup; use OCP\IUser; @@ -112,6 +113,7 @@ class Group implements IGroup { if (($backend instanceof ISetDisplayNameBackend) && $backend->setDisplayName($this->gid, $displayName)) { $this->displayName = $displayName; + $this->dispatcher->dispatch(new GroupChangedEvent($this, 'displayName', $displayName, '')); return true; } } diff --git a/lib/private/Group/Manager.php b/lib/private/Group/Manager.php index 28f7a400b41..b718afa5168 100644 --- a/lib/private/Group/Manager.php +++ b/lib/private/Group/Manager.php @@ -42,6 +42,7 @@ namespace OC\Group; use OC\Hooks\PublicEmitter; use OCP\EventDispatcher\IEventDispatcher; use OCP\GroupInterface; +use OCP\ICacheFactory; use OCP\IGroup; use OCP\IGroupManager; use OCP\IUser; @@ -82,12 +83,16 @@ class Manager extends PublicEmitter implements IGroupManager { /** @var \OC\SubAdmin */ private $subAdmin = null; + private DisplayNameCache $displayNameCache; + public function __construct(\OC\User\Manager $userManager, EventDispatcherInterface $dispatcher, - LoggerInterface $logger) { + LoggerInterface $logger, + ICacheFactory $cacheFactory) { $this->userManager = $userManager; $this->dispatcher = $dispatcher; $this->logger = $logger; + $this->displayNameCache = new DisplayNameCache($cacheFactory, $this); $cachedGroups = &$this->cachedGroups; $cachedUserGroups = &$this->cachedUserGroups; @@ -339,6 +344,14 @@ class Manager extends PublicEmitter implements IGroupManager { } /** + * @param string $groupId + * @return ?string + */ + public function getDisplayName(string $groupId): ?string { + return $this->displayNameCache->getDisplayName($groupId); + } + + /** * get an array of groupid and displayName for a user * * @param IUser $user @@ -346,7 +359,7 @@ class Manager extends PublicEmitter implements IGroupManager { */ public function getUserGroupNames(IUser $user) { return array_map(function ($group) { - return ['displayName' => $group->getDisplayName()]; + return ['displayName' => $this->displayNameCache->getDisplayName($group->getGID())]; }, $this->getUserGroups($user)); } |