]> source.dussan.org Git - nextcloud-server.git/commitdiff
Add ldap:reset-group command to unmap groups from LDAP
authorCôme Chilliet <come.chilliet@nextcloud.com>
Tue, 22 Mar 2022 11:31:44 +0000 (12:31 +0100)
committerCôme Chilliet (Rebase PR Action) <come-nc@users.noreply.github.com>
Fri, 1 Apr 2022 12:18:02 +0000 (12:18 +0000)
Signed-off-by: Côme Chilliet <come.chilliet@nextcloud.com>
apps/user_ldap/appinfo/info.xml
apps/user_ldap/composer/composer/autoload_classmap.php
apps/user_ldap/composer/composer/autoload_static.php
apps/user_ldap/lib/GroupPluginManager.php
apps/user_ldap/lib/Group_LDAP.php
apps/user_ldap/lib/Group_Proxy.php
apps/user_ldap/lib/UserPluginManager.php
core/Command/Group/Delete.php

index 2dae484524121130e897857c750597445ec347d5..d654d34d66ee6d91319b28adfbf9c29e35eff523 100644 (file)
@@ -50,6 +50,7 @@ A user logs into Nextcloud with their LDAP or AD credentials, and is granted acc
                <command>OCA\User_LDAP\Command\CheckUser</command>
                <command>OCA\User_LDAP\Command\CreateEmptyConfig</command>
                <command>OCA\User_LDAP\Command\DeleteConfig</command>
+               <command>OCA\User_LDAP\Command\ResetGroup</command>
                <command>OCA\User_LDAP\Command\ResetUser</command>
                <command>OCA\User_LDAP\Command\Search</command>
                <command>OCA\User_LDAP\Command\SetConfig</command>
index 12ede37a941d0af86db596c0e9795d989456aa4a..1fca642fc9fbf6bf0aae779fe3c32e3a25a4d3d2 100644 (file)
@@ -14,6 +14,7 @@ return array(
     'OCA\\User_LDAP\\Command\\CheckUser' => $baseDir . '/../lib/Command/CheckUser.php',
     'OCA\\User_LDAP\\Command\\CreateEmptyConfig' => $baseDir . '/../lib/Command/CreateEmptyConfig.php',
     'OCA\\User_LDAP\\Command\\DeleteConfig' => $baseDir . '/../lib/Command/DeleteConfig.php',
+    'OCA\\User_LDAP\\Command\\ResetGroup' => $baseDir . '/../lib/Command/ResetGroup.php',
     'OCA\\User_LDAP\\Command\\ResetUser' => $baseDir . '/../lib/Command/ResetUser.php',
     'OCA\\User_LDAP\\Command\\Search' => $baseDir . '/../lib/Command/Search.php',
     'OCA\\User_LDAP\\Command\\SetConfig' => $baseDir . '/../lib/Command/SetConfig.php',
index ecf5e4167f615cb57e3d80142d9665ca1466247c..9d8c33406e88f8ef59126f9fab895a5a1112466e 100644 (file)
@@ -29,6 +29,7 @@ class ComposerStaticInitUser_LDAP
         'OCA\\User_LDAP\\Command\\CheckUser' => __DIR__ . '/..' . '/../lib/Command/CheckUser.php',
         'OCA\\User_LDAP\\Command\\CreateEmptyConfig' => __DIR__ . '/..' . '/../lib/Command/CreateEmptyConfig.php',
         'OCA\\User_LDAP\\Command\\DeleteConfig' => __DIR__ . '/..' . '/../lib/Command/DeleteConfig.php',
+        'OCA\\User_LDAP\\Command\\ResetGroup' => __DIR__ . '/..' . '/../lib/Command/ResetGroup.php',
         'OCA\\User_LDAP\\Command\\ResetUser' => __DIR__ . '/..' . '/../lib/Command/ResetUser.php',
         'OCA\\User_LDAP\\Command\\Search' => __DIR__ . '/..' . '/../lib/Command/Search.php',
         'OCA\\User_LDAP\\Command\\SetConfig' => __DIR__ . '/..' . '/../lib/Command/SetConfig.php',
index d23e9d4d443a7de742eb7ae51668c05a3308f177..a25665e4691bf02e93de457e9c7796f647175499 100644 (file)
@@ -26,9 +26,9 @@ namespace OCA\User_LDAP;
 use OCP\GroupInterface;
 
 class GroupPluginManager {
-       private $respondToActions = 0;
+       private int $respondToActions = 0;
 
-       private $which = [
+       private array $which = [
                GroupInterface::CREATE_GROUP => null,
                GroupInterface::DELETE_GROUP => null,
                GroupInterface::ADD_TO_GROUP => null,
@@ -37,6 +37,8 @@ class GroupPluginManager {
                GroupInterface::GROUP_DETAILS => null
        ];
 
+       private bool $suppressDeletion = false;
+
        /**
         * @return int All implemented actions
         */
@@ -84,6 +86,19 @@ class GroupPluginManager {
                throw new \Exception('No plugin implements createGroup in this LDAP Backend.');
        }
 
+       public function canDeleteGroup(): bool {
+               return !$this->suppressDeletion && ($this->which[GroupInterface::DELETE_GROUP] !== null);
+       }
+
+       /**
+        * @return bool – the value before the change
+        */
+       public function setSuppressDeletion(bool $value): bool {
+               $old = $this->suppressDeletion;
+               $this->suppressDeletion = $value;
+               return $old;
+       }
+
        /**
         * Delete a group
         * @param string $gid Group Id of the group to delete
@@ -94,6 +109,9 @@ class GroupPluginManager {
                $plugin = $this->which[GroupInterface::DELETE_GROUP];
 
                if ($plugin) {
+                       if ($this->suppressDeletion) {
+                               return false;
+                       }
                        return $plugin->deleteGroup($gid);
                }
                throw new \Exception('No plugin implements deleteGroup in this LDAP Backend.');
index 766b77bf52199c1418780c869de70db7a6dd4cf4..f9d9b06174303c5a1cc7e865c0a4c53121f251da 100644 (file)
@@ -48,10 +48,11 @@ use OC;
 use OC\Cache\CappedMemoryCache;
 use OC\ServerNotAvailableException;
 use OCP\Group\Backend\IGetDisplayNameBackend;
+use OCP\Group\Backend\IDeleteGroupBackend;
 use OCP\GroupInterface;
 use Psr\Log\LoggerInterface;
 
-class Group_LDAP extends BackendUtility implements GroupInterface, IGroupLDAP, IGetDisplayNameBackend {
+class Group_LDAP extends BackendUtility implements GroupInterface, IGroupLDAP, IGetDisplayNameBackend, IDeleteGroupBackend {
        protected $enabled = false;
 
        /** @var string[][] $cachedGroupMembers array of users with gid as key */
@@ -1204,6 +1205,7 @@ class Group_LDAP extends BackendUtility implements GroupInterface, IGroupLDAP, I
         */
        public function implementsActions($actions) {
                return (bool)((GroupInterface::COUNT_USERS |
+                               GroupInterface::DELETE_GROUP |
                                $this->groupPluginManager->getImplementedActions()) & $actions);
        }
 
@@ -1249,19 +1251,32 @@ class Group_LDAP extends BackendUtility implements GroupInterface, IGroupLDAP, I
         * delete a group
         *
         * @param string $gid gid of the group to delete
-        * @return bool
         * @throws Exception
         */
-       public function deleteGroup($gid) {
-               if ($this->groupPluginManager->implementsActions(GroupInterface::DELETE_GROUP)) {
+       public function deleteGroup(string $gid): bool {
+               if ($this->groupPluginManager->canDeleteGroup()) {
                        if ($ret = $this->groupPluginManager->deleteGroup($gid)) {
-                               #delete group in nextcloud internal db
+                               // Delete group in nextcloud internal db
                                $this->access->getGroupMapper()->unmap($gid);
                                $this->access->connection->writeToCache("groupExists" . $gid, false);
                        }
                        return $ret;
                }
-               throw new Exception('Could not delete group in LDAP backend.');
+
+               // Getting dn, if false the group is not mapped
+               $dn = $this->access->groupname2dn($gid);
+               if (!$dn) {
+                       throw new Exception('Could not delete unknown group '.$gid.' in LDAP backend.');
+               }
+
+               if (!$this->groupExists($gid)) {
+                       // The group does not exist in the LDAP, remove the mapping
+                       $this->access->getGroupMapper()->unmap($gid);
+                       $this->access->connection->writeToCache("groupExists" . $gid, false);
+                       return true;
+               }
+
+               throw new Exception('Could not delete existing group '.$gid.' in LDAP backend.');
        }
 
        /**
index 92a9041949e2cdb506511e227c6c17e762ce70b3..ea2fcce679c4a27d2c50a6a267aa258c4dc0688a 100644 (file)
  */
 namespace OCA\User_LDAP;
 
-use OCP\Group\Backend\INamedBackend;
+use OCP\Group\Backend\IDeleteGroupBackend;
 use OCP\Group\Backend\IGetDisplayNameBackend;
+use OCP\Group\Backend\INamedBackend;
 
-class Group_Proxy extends Proxy implements \OCP\GroupInterface, IGroupLDAP, IGetDisplayNameBackend, INamedBackend {
+class Group_Proxy extends Proxy implements \OCP\GroupInterface, IGroupLDAP, IGetDisplayNameBackend, INamedBackend, IDeleteGroupBackend {
        private $backends = [];
        private $refBackend = null;
 
@@ -171,11 +172,8 @@ class Group_Proxy extends Proxy implements \OCP\GroupInterface, IGroupLDAP, IGet
 
        /**
         * delete a group
-        *
-        * @param string $gid gid of the group to delete
-        * @return bool
         */
-       public function deleteGroup($gid) {
+       public function deleteGroup(string $gid): bool {
                return $this->handleRequest(
                        $gid, 'deleteGroup', [$gid]);
        }
index 035b7952dce657369978bf613d688c7187a34dbf..748a210cf60ad853e06cc6540fca2bb45b72c4c6 100644 (file)
@@ -28,9 +28,9 @@ namespace OCA\User_LDAP;
 use OC\User\Backend;
 
 class UserPluginManager {
-       private $respondToActions = 0;
+       private int $respondToActions = 0;
 
-       private $which = [
+       private array $which = [
                Backend::CREATE_USER => null,
                Backend::SET_PASSWORD => null,
                Backend::GET_HOME => null,
@@ -41,8 +41,7 @@ class UserPluginManager {
                'deleteUser' => null
        ];
 
-       /** @var bool */
-       private $suppressDeletion = false;
+       private bool $suppressDeletion = false;
 
        /**
         * @return int All implemented actions, except for 'deleteUser'
index 75202308944a989efa6d197bb2ecb070d21d06f3..be97be83407cc098c779b24b1d9bf0b432b7d216 100644 (file)
@@ -61,7 +61,7 @@ class Delete extends Base {
                        $output->writeln('<error>Group "' . $gid . '" could not be deleted.</error>');
                        return 1;
                }
-               if (! $this->groupManager->groupExists($gid)) {
+               if (!$this->groupManager->groupExists($gid)) {
                        $output->writeln('<error>Group "' . $gid . '" does not exist.</error>');
                        return 1;
                }