Skip to content

Commit 82e6977

Browse files
committed
feat: move file cache to a background job
Signed-off-by: Robin Appelman <robin@icewind.nl>
1 parent 2bb3d4e commit 82e6977

6 files changed

Lines changed: 98 additions & 22 deletions

File tree

Lines changed: 58 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,58 @@
1+
<?php
2+
3+
declare(strict_types=1);
4+
/**
5+
* SPDX-FileCopyrightText: 2025 Nextcloud GmbH and Nextcloud contributors
6+
* SPDX-License-Identifier: AGPL-3.0-or-later
7+
*/
8+
9+
namespace OC\Core\BackgroundJobs;
10+
11+
use OC\Cache\File;
12+
use OCP\AppFramework\Utility\ITimeFactory;
13+
use OCP\BackgroundJob\TimedJob;
14+
use OCP\IAppConfig;
15+
use OCP\IUserManager;
16+
use Psr\Log\LoggerInterface;
17+
18+
class FileCacheGcJob extends TimedJob {
19+
public function __construct(
20+
ITimeFactory $time,
21+
private readonly LoggerInterface $logger,
22+
private readonly IAppConfig $appConfig,
23+
private readonly IUserManager $userManager,
24+
) {
25+
parent::__construct($time);
26+
27+
$this->setTimeSensitivity(self::TIME_INSENSITIVE);
28+
$this->setInterval(24 * 60 * 60);
29+
}
30+
31+
protected function run(mixed $argument): void {
32+
$offset = $this->appConfig->getValueInt('core', 'files_gc_offset');
33+
34+
$users = $this->userManager->getSeenUsers($offset);
35+
$start = time();
36+
$count = 0;
37+
foreach ($users as $user) {
38+
$cache = new File();
39+
try {
40+
$cache->gc($user);
41+
} catch (\Exception $e) {
42+
$this->logger->warning('Exception when running cache gc.', [
43+
'app' => 'core',
44+
'exception' => $e,
45+
]);
46+
}
47+
$count++;
48+
$now = time();
49+
50+
// almost time for the next job run, stop early and save our location
51+
if ($now - $start > 23 * 60 * 60) {
52+
$this->appConfig->setValueInt('core', 'files_gc_offset', $offset + $count);
53+
return;
54+
}
55+
}
56+
$this->appConfig->setValueInt('core', 'files_gc_offset', 0);
57+
}
58+
}

lib/base.php

Lines changed: 0 additions & 17 deletions
Original file line numberDiff line numberDiff line change
@@ -980,23 +980,6 @@ public static function registerCleanupHooks(\OC\SystemConfig $systemConfig): voi
980980
$throttler = Server::get(IThrottler::class);
981981
$throttler->resetDelay($request->getRemoteAddress(), 'login', ['user' => $uid]);
982982
}
983-
984-
try {
985-
$cache = new \OC\Cache\File();
986-
$cache->gc();
987-
} catch (\OC\ServerNotAvailableException $e) {
988-
// not a GC exception, pass it on
989-
throw $e;
990-
} catch (\OC\ForbiddenException $e) {
991-
// filesystem blocked for this request, ignore
992-
} catch (\Exception $e) {
993-
// a GC exception should not prevent users from using OC,
994-
// so log the exception
995-
Server::get(LoggerInterface::class)->warning('Exception when running cache gc.', [
996-
'app' => 'core',
997-
'exception' => $e,
998-
]);
999-
}
1000983
});
1001984
}
1002985
}

lib/composer/composer/autoload_classmap.php

Lines changed: 2 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -1307,6 +1307,7 @@
13071307
'OC\\Core\\BackgroundJobs\\CheckForUserCertificates' => $baseDir . '/core/BackgroundJobs/CheckForUserCertificates.php',
13081308
'OC\\Core\\BackgroundJobs\\CleanupLoginFlowV2' => $baseDir . '/core/BackgroundJobs/CleanupLoginFlowV2.php',
13091309
'OC\\Core\\BackgroundJobs\\ExpirePreviewsJob' => $baseDir . '/core/BackgroundJobs/ExpirePreviewsJob.php',
1310+
'OC\\Core\\BackgroundJobs\\FileCacheGcJob' => $baseDir . '/core/BackgroundJobs/FileCacheGcJob.php',
13101311
'OC\\Core\\BackgroundJobs\\GenerateMetadataJob' => $baseDir . '/core/BackgroundJobs/GenerateMetadataJob.php',
13111312
'OC\\Core\\BackgroundJobs\\LookupServerSendCheckBackgroundJob' => $baseDir . '/core/BackgroundJobs/LookupServerSendCheckBackgroundJob.php',
13121313
'OC\\Core\\BackgroundJobs\\PreviewMigrationJob' => $baseDir . '/core/BackgroundJobs/PreviewMigrationJob.php',
@@ -2073,6 +2074,7 @@
20732074
'OC\\Repair\\NC29\\SanitizeAccountProperties' => $baseDir . '/lib/private/Repair/NC29/SanitizeAccountProperties.php',
20742075
'OC\\Repair\\NC29\\SanitizeAccountPropertiesJob' => $baseDir . '/lib/private/Repair/NC29/SanitizeAccountPropertiesJob.php',
20752076
'OC\\Repair\\NC30\\RemoveLegacyDatadirFile' => $baseDir . '/lib/private/Repair/NC30/RemoveLegacyDatadirFile.php',
2077+
'OC\\Repair\\NC34\\AddFileCacheGcBackgroundJob' => $baseDir . '/lib/private/Repair/NC34/AddFileCacheGcBackgroundJob.php',
20762078
'OC\\Repair\\OldGroupMembershipShares' => $baseDir . '/lib/private/Repair/OldGroupMembershipShares.php',
20772079
'OC\\Repair\\Owncloud\\CleanPreviews' => $baseDir . '/lib/private/Repair/Owncloud/CleanPreviews.php',
20782080
'OC\\Repair\\Owncloud\\CleanPreviewsBackgroundJob' => $baseDir . '/lib/private/Repair/Owncloud/CleanPreviewsBackgroundJob.php',

lib/composer/composer/autoload_static.php

Lines changed: 2 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -1348,6 +1348,7 @@ class ComposerStaticInit749170dad3f5e7f9ca158f5a9f04f6a2
13481348
'OC\\Core\\BackgroundJobs\\CheckForUserCertificates' => __DIR__ . '/../../..' . '/core/BackgroundJobs/CheckForUserCertificates.php',
13491349
'OC\\Core\\BackgroundJobs\\CleanupLoginFlowV2' => __DIR__ . '/../../..' . '/core/BackgroundJobs/CleanupLoginFlowV2.php',
13501350
'OC\\Core\\BackgroundJobs\\ExpirePreviewsJob' => __DIR__ . '/../../..' . '/core/BackgroundJobs/ExpirePreviewsJob.php',
1351+
'OC\\Core\\BackgroundJobs\\FileCacheGcJob' => __DIR__ . '/../../..' . '/core/BackgroundJobs/FileCacheGcJob.php',
13511352
'OC\\Core\\BackgroundJobs\\GenerateMetadataJob' => __DIR__ . '/../../..' . '/core/BackgroundJobs/GenerateMetadataJob.php',
13521353
'OC\\Core\\BackgroundJobs\\LookupServerSendCheckBackgroundJob' => __DIR__ . '/../../..' . '/core/BackgroundJobs/LookupServerSendCheckBackgroundJob.php',
13531354
'OC\\Core\\BackgroundJobs\\PreviewMigrationJob' => __DIR__ . '/../../..' . '/core/BackgroundJobs/PreviewMigrationJob.php',
@@ -2114,6 +2115,7 @@ class ComposerStaticInit749170dad3f5e7f9ca158f5a9f04f6a2
21142115
'OC\\Repair\\NC29\\SanitizeAccountProperties' => __DIR__ . '/../../..' . '/lib/private/Repair/NC29/SanitizeAccountProperties.php',
21152116
'OC\\Repair\\NC29\\SanitizeAccountPropertiesJob' => __DIR__ . '/../../..' . '/lib/private/Repair/NC29/SanitizeAccountPropertiesJob.php',
21162117
'OC\\Repair\\NC30\\RemoveLegacyDatadirFile' => __DIR__ . '/../../..' . '/lib/private/Repair/NC30/RemoveLegacyDatadirFile.php',
2118+
'OC\\Repair\\NC34\\AddFileCacheGcBackgroundJob' => __DIR__ . '/../../..' . '/lib/private/Repair/NC34/AddFileCacheGcBackgroundJob.php',
21172119
'OC\\Repair\\OldGroupMembershipShares' => __DIR__ . '/../../..' . '/lib/private/Repair/OldGroupMembershipShares.php',
21182120
'OC\\Repair\\Owncloud\\CleanPreviews' => __DIR__ . '/../../..' . '/lib/private/Repair/Owncloud/CleanPreviews.php',
21192121
'OC\\Repair\\Owncloud\\CleanPreviewsBackgroundJob' => __DIR__ . '/../../..' . '/lib/private/Repair/Owncloud/CleanPreviewsBackgroundJob.php',

lib/private/Cache/File.php

Lines changed: 7 additions & 5 deletions
Original file line numberDiff line numberDiff line change
@@ -33,12 +33,14 @@ class File implements ICache {
3333
* @throws ForbiddenException
3434
* @throws NoUserException
3535
*/
36-
protected function getStorage() {
36+
protected function getStorage(?IUser $user = null): Folder {
3737
if ($this->storage !== null) {
3838
return $this->storage;
3939
}
40-
$session = Server::get(IUserSession::class);
41-
$user = $session->getUser();
40+
if (!$user) {
41+
$session = Server::get(IUserSession::class);
42+
$user = $session->getUser();
43+
}
4244
$rootFolder = Server::get(IRootFolder::class);
4345
if ($user) {
4446
$userId = $user->getUID();
@@ -161,8 +163,8 @@ public function clear($prefix = '') {
161163
* Runs GC
162164
* @throws ForbiddenException
163165
*/
164-
public function gc() {
165-
$storage = $this->getStorage();
166+
public function gc(?IUser $user = null) {
167+
$storage = $this->getStorage($user);
166168
$ttl = Server::get(IConfig::class)->getSystemValueInt('cache_chunk_gc_ttl', 60 * 60 * 24);
167169
// extra hour safety, in case of stray part chunks that take longer to write,
168170
// because touch() is only called after the chunk was finished
Lines changed: 29 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,29 @@
1+
<?php
2+
3+
declare(strict_types=1);
4+
5+
/**
6+
* SPDX-FileCopyrightText: 2025 Nextcloud GmbH and Nextcloud contributors
7+
* SPDX-License-Identifier: AGPL-3.0-or-later
8+
*/
9+
namespace OC\Repair\NC34;
10+
11+
use OC\Core\BackgroundJobs\FileCacheGcJob;
12+
use OCP\BackgroundJob\IJobList;
13+
use OCP\Migration\IOutput;
14+
use OCP\Migration\IRepairStep;
15+
16+
class AddFileCacheGcBackgroundJob implements IRepairStep {
17+
public function __construct(
18+
private readonly IJobList $jobList,
19+
) {
20+
}
21+
22+
public function getName(): string {
23+
return 'Add background job to cleanup file cache';
24+
}
25+
26+
public function run(IOutput $output) {
27+
$this->jobList->add(FileCacheGcJob::class);
28+
}
29+
}

0 commit comments

Comments
 (0)