Skip to content

Commit 0274364

Browse files
susnuxbackportbot[bot]
authored andcommitted
fix: Skip users that still exist in backend
Signed-off-by: Ferdinand Thiessen <opensource@fthiessen.de> [skip ci]
1 parent 3a4dea5 commit 0274364

5 files changed

Lines changed: 30 additions & 11 deletions

File tree

lib/composer/composer/autoload_classmap.php

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -1808,14 +1808,14 @@
18081808
'OC\\User\\BackgroundJobs\\CleanupDeletedUsers' => $baseDir . '/lib/private/User/BackgroundJobs/CleanupDeletedUsers.php',
18091809
'OC\\User\\Database' => $baseDir . '/lib/private/User/Database.php',
18101810
'OC\\User\\DisplayNameCache' => $baseDir . '/lib/private/User/DisplayNameCache.php',
1811-
'OC\\User\\FailedUsersBackend' => $baseDir . '/lib/private/User/FailedUsersBackend.php',
18121811
'OC\\User\\LazyUser' => $baseDir . '/lib/private/User/LazyUser.php',
18131812
'OC\\User\\Listeners\\BeforeUserDeletedListener' => $baseDir . '/lib/private/User/Listeners/BeforeUserDeletedListener.php',
18141813
'OC\\User\\Listeners\\UserChangedListener' => $baseDir . '/lib/private/User/Listeners/UserChangedListener.php',
18151814
'OC\\User\\LoginException' => $baseDir . '/lib/private/User/LoginException.php',
18161815
'OC\\User\\Manager' => $baseDir . '/lib/private/User/Manager.php',
18171816
'OC\\User\\NoUserException' => $baseDir . '/lib/private/User/NoUserException.php',
18181817
'OC\\User\\OutOfOfficeData' => $baseDir . '/lib/private/User/OutOfOfficeData.php',
1818+
'OC\\User\\PartiallyDeletedUsersBackend' => $baseDir . '/lib/private/User/PartiallyDeletedUsersBackend.php',
18191819
'OC\\User\\Session' => $baseDir . '/lib/private/User/Session.php',
18201820
'OC\\User\\User' => $baseDir . '/lib/private/User/User.php',
18211821
'OC_API' => $baseDir . '/lib/private/legacy/OC_API.php',

lib/composer/composer/autoload_static.php

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -1841,14 +1841,14 @@ class ComposerStaticInit749170dad3f5e7f9ca158f5a9f04f6a2
18411841
'OC\\User\\BackgroundJobs\\CleanupDeletedUsers' => __DIR__ . '/../../..' . '/lib/private/User/BackgroundJobs/CleanupDeletedUsers.php',
18421842
'OC\\User\\Database' => __DIR__ . '/../../..' . '/lib/private/User/Database.php',
18431843
'OC\\User\\DisplayNameCache' => __DIR__ . '/../../..' . '/lib/private/User/DisplayNameCache.php',
1844-
'OC\\User\\FailedUsersBackend' => __DIR__ . '/../../..' . '/lib/private/User/FailedUsersBackend.php',
18451844
'OC\\User\\LazyUser' => __DIR__ . '/../../..' . '/lib/private/User/LazyUser.php',
18461845
'OC\\User\\Listeners\\BeforeUserDeletedListener' => __DIR__ . '/../../..' . '/lib/private/User/Listeners/BeforeUserDeletedListener.php',
18471846
'OC\\User\\Listeners\\UserChangedListener' => __DIR__ . '/../../..' . '/lib/private/User/Listeners/UserChangedListener.php',
18481847
'OC\\User\\LoginException' => __DIR__ . '/../../..' . '/lib/private/User/LoginException.php',
18491848
'OC\\User\\Manager' => __DIR__ . '/../../..' . '/lib/private/User/Manager.php',
18501849
'OC\\User\\NoUserException' => __DIR__ . '/../../..' . '/lib/private/User/NoUserException.php',
18511850
'OC\\User\\OutOfOfficeData' => __DIR__ . '/../../..' . '/lib/private/User/OutOfOfficeData.php',
1851+
'OC\\User\\PartiallyDeletedUsersBackend' => __DIR__ . '/../../..' . '/lib/private/User/PartiallyDeletedUsersBackend.php',
18521852
'OC\\User\\Session' => __DIR__ . '/../../..' . '/lib/private/User/Session.php',
18531853
'OC\\User\\User' => __DIR__ . '/../../..' . '/lib/private/User/User.php',
18541854
'OC_API' => __DIR__ . '/../../..' . '/lib/private/legacy/OC_API.php',

lib/private/User/BackgroundJobs/CleanupDeletedUsers.php

Lines changed: 13 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -8,10 +8,11 @@
88
*/
99
namespace OC\User\BackgroundJobs;
1010

11-
use OC\User\FailedUsersBackend;
1211
use OC\User\Manager;
12+
use OC\User\PartiallyDeletedUsersBackend;
1313
use OC\User\User;
1414
use OCP\AppFramework\Utility\ITimeFactory;
15+
use OCP\BackgroundJob\IJob;
1516
use OCP\BackgroundJob\TimedJob;
1617
use OCP\EventDispatcher\IEventDispatcher;
1718
use OCP\IConfig;
@@ -25,11 +26,12 @@ public function __construct(
2526
private LoggerInterface $logger,
2627
) {
2728
parent::__construct($time);
28-
$this->setInterval(3600);
29+
$this->setTimeSensitivity(IJob::TIME_INSENSITIVE);
30+
$this->setInterval(24 * 3600);
2931
}
3032

3133
protected function run($argument): void {
32-
$backend = new FailedUsersBackend($this->config);
34+
$backend = new PartiallyDeletedUsersBackend($this->config);
3335
$users = $backend->getUsers();
3436

3537
if (empty($users)) {
@@ -38,12 +40,19 @@ protected function run($argument): void {
3840
}
3941

4042
foreach ($users as $userId) {
43+
if ($this->userManager->userExists($userId)) {
44+
$this->logger->info('Skipping user {userId}, marked as deleted, as they still exists in user backend.', ['userId' => $userId]);
45+
$backend->unmarkUser($userId);
46+
continue;
47+
}
48+
4149
try {
4250
$user = new User(
4351
$userId,
4452
$backend,
4553
\OCP\Server::get(IEventDispatcher::class),
46-
config: $this->config,
54+
$this->userManager,
55+
$this->config,
4756
);
4857
$user->delete();
4958
$this->logger->info('Cleaned up deleted user {userId}', ['userId' => $userId]);

lib/private/User/FailedUsersBackend.php renamed to lib/private/User/PartiallyDeletedUsersBackend.php

Lines changed: 12 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -15,7 +15,7 @@
1515
* but not properly removed from Nextcloud (e.g. an exception occurred).
1616
* This backend is only needed because some APIs in user-deleted-events require a "real" user with backend.
1717
*/
18-
class FailedUsersBackend extends Backend implements IGetHomeBackend, IUserBackend {
18+
class PartiallyDeletedUsersBackend extends Backend implements IGetHomeBackend, IUserBackend {
1919

2020
public function __construct(
2121
private IConfig $config,
@@ -36,11 +36,21 @@ public function userExists($uid) {
3636
}
3737

3838
public function getHome(string $uid): string|false {
39-
return $this->config->getUserValue($uid, 'core', 'deleted.backup-home') ?: false;
39+
return $this->config->getUserValue($uid, 'core', 'deleted.home-path') ?: false;
4040
}
4141

4242
public function getUsers($search = '', $limit = null, $offset = null) {
4343
return $this->config->getUsersForUserValue('core', 'deleted', 'true');
4444
}
4545

46+
/**
47+
* Unmark a user as deleted.
48+
* This typically the case if the user deletion failed in the backend but before the backend deleted the user,
49+
* meaning the user still exists so we unmark them as it still can be accessed (and deleted) normally.
50+
*/
51+
public function unmarkUser(string $userId): void {
52+
$this->config->deleteUserValue($userId, 'core', 'deleted');
53+
$this->config->deleteUserValue($userId, 'core', 'deleted.home-path');
54+
}
55+
4656
}

lib/private/User/User.php

Lines changed: 3 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -272,7 +272,7 @@ public function delete() {
272272
// because we can not restore the user meaning we could not rollback to any stable state otherwise.
273273
$this->config->setUserValue($this->uid, 'core', 'deleted', 'true');
274274
// We also need to backup the home path as this can not be reconstructed later if the original backend uses custom home paths
275-
$this->config->setUserValue($this->uid, 'core', 'deleted.backup-home', $this->getHome());
275+
$this->config->setUserValue($this->uid, 'core', 'deleted.home-path', $this->getHome());
276276

277277
// Try to delete the user on the backend
278278
$result = $this->backend->deleteUser($this->uid);
@@ -350,15 +350,15 @@ public function delete() {
350350
$this->config->deleteAllUserValues($this->uid);
351351
// But again set flag that this user is about to be deleted
352352
$this->config->setUserValue($this->uid, 'core', 'deleted', 'true');
353-
$this->config->setUserValue($this->uid, 'core', 'deleted.backup-home', $this->getHome());
353+
$this->config->setUserValue($this->uid, 'core', 'deleted.home-path', $this->getHome());
354354
// Commit the transaction so we are in a defined state: either the preferences are removed or an exception occurred but the delete flag is still present
355355
$database->commit();
356356
} catch (\Throwable $e) {
357357
$database->rollback();
358358
throw $e;
359359
}
360360

361-
if ($this->emitter) {
361+
if ($this->emitter !== null) {
362362
/** @deprecated 21.0.0 use UserDeletedEvent event with the IEventDispatcher instead */
363363
$this->emitter->emit('\OC\User', 'postDelete', [$this]);
364364
}

0 commit comments

Comments
 (0)