diff --git a/app/config/collections/projects.php b/app/config/collections/projects.php index dae0337dc9..86346d2672 100644 --- a/app/config/collections/projects.php +++ b/app/config/collections/projects.php @@ -2098,6 +2098,13 @@ return [ 'lengths' => [], 'orders' => [], ], + [ + '$id' => ID::custom('_key_resourceType'), + 'type' => Database::INDEX_KEY, + 'attributes' => ['resourceType'], + 'lengths' => [], + 'orders' => [Database::ORDER_ASC], + ], ], ], diff --git a/app/controllers/general.php b/app/controllers/general.php index 685ab14aea..4222d18ff1 100644 --- a/app/controllers/general.php +++ b/app/controllers/general.php @@ -807,6 +807,7 @@ function router(App $utopia, Database $dbForPlatform, callable $getProjectDB, Sw if ($executionsRetentionCount > 0) { $queueForDeletes ->setProject($project) + ->setResourceType($type) ->setResource($resource->getSequence()) ->setType(DELETE_TYPE_EXECUTIONS_LIMIT) ->trigger(); diff --git a/src/Appwrite/Platform/Modules/Functions/Http/Executions/Create.php b/src/Appwrite/Platform/Modules/Functions/Http/Executions/Create.php index 5e8b6d9e02..8c4b68edb6 100644 --- a/src/Appwrite/Platform/Modules/Functions/Http/Executions/Create.php +++ b/src/Appwrite/Platform/Modules/Functions/Http/Executions/Create.php @@ -63,7 +63,6 @@ class Create extends Base ->label('scope', 'execution.write') ->label('resourceType', RESOURCE_TYPE_FUNCTIONS) ->label('event', 'functions.[functionId].executions.[executionId].create') - ->label('resourceType', RESOURCE_TYPE_FUNCTIONS) ->label('sdk', new Method( namespace: 'functions', group: 'executions', @@ -523,6 +522,7 @@ class Create extends Base $queueForDeletes ->setProject($project) ->setResource($function->getSequence()) + ->setResourceType(RESOURCE_TYPE_FUNCTIONS) ->setType(DELETE_TYPE_EXECUTIONS_LIMIT) ->trigger(); } diff --git a/src/Appwrite/Platform/Workers/Deletes.php b/src/Appwrite/Platform/Workers/Deletes.php index 0bbd7b7e66..3c66eef277 100644 --- a/src/Appwrite/Platform/Workers/Deletes.php +++ b/src/Appwrite/Platform/Workers/Deletes.php @@ -150,12 +150,14 @@ class Deletes extends Action break; case DELETE_TYPE_EXECUTIONS_LIMIT: $resourceInternalId = $payload['resource'] ?? null; + $resourceType = $payload['resourceType'] ?? null; if ($resourceInternalId) { $this->deleteExecutionsByLimit( $project, $getProjectDB, $executionsRetentionCount, - $resourceInternalId + $resourceInternalId, + $resourceType ); } break; @@ -214,16 +216,15 @@ class Deletes extends Action * @param Database $dbForPlatform * @param callable $getProjectDB * @param string $datetime - * @param Document|null $document * @return void * @throws Conflict * @throws Restricted * @throws Structure - * @throws DatabaseException + * @throws DatabaseException|Exception */ private function deleteSchedules(Database $dbForPlatform, callable $getProjectDB, string $datetime): void { - // Temporarly accepting both 'fra' and 'default' + // Temporarily accepting both 'fra' and 'default' // When all migrated, only use _APP_REGION with 'default' as default value $regions = [System::getEnv('_APP_REGION', 'default')]; if (!in_array('default', $regions)) { @@ -737,6 +738,7 @@ class Deletes extends Action * @param callable $getProjectDB * @param int|null $executionsRetentionCount * @param string|null $resourceInternalId + * @param string|null $resourceType * @return void * @throws DatabaseException */ @@ -744,7 +746,8 @@ class Deletes extends Action Document $project, callable $getProjectDB, ?int $executionsRetentionCount = 0, - ?string $resourceInternalId = null + ?string $resourceInternalId = null, + ?string $resourceType = null ): void { if ($executionsRetentionCount <= 0) { return; @@ -754,11 +757,12 @@ class Deletes extends Action $dbForProject = $getProjectDB($project); /* delete log for a given $resourceInternalId */ - $deleteExecDocuments = function (Database $dbForProject, string $resourceInternalId) use ($executionsRetentionCount) { + $delete = function (Database $dbForProject, string $resourceInternalId, string $resourceType) use ($executionsRetentionCount) { // get the execution at position `N+1` $execution = $dbForProject->findOne('executions', [ Query::select(['$createdAt']), Query::equal('resourceInternalId', [$resourceInternalId]), + Query::equal('resourceType', [$resourceType]), Query::orderDesc('$createdAt'), Query::offset($executionsRetentionCount), ]); @@ -770,6 +774,7 @@ class Deletes extends Action $this->deleteByGroup('executions', [ Query::select([...$this->selects, '$createdAt']), Query::equal('resourceInternalId', [$resourceInternalId]), + Query::equal('resourceType', [$resourceType]), Query::lessThan('$createdAt', $cutoffTime), Query::orderDesc('$createdAt'), Query::orderDesc(), @@ -779,23 +784,23 @@ class Deletes extends Action if (!empty($resourceInternalId)) { // fast path, no need to list anything! - $deleteExecDocuments($dbForProject, $resourceInternalId); + $delete($dbForProject, $resourceInternalId, $resourceType); } else { - $processResource = function (string $type) use ($dbForProject, $deleteExecDocuments) { + $processResource = function (string $type) use ($dbForProject, $delete, $resourceType) { $this->listByGroup( collection: $type, queries: [Query::select(['$id'])], database: $dbForProject, - callback: function (Document $resource) use ($dbForProject, $deleteExecDocuments) { - $deleteExecDocuments($dbForProject, $resource->getSequence()); + callback: function (Document $resource) use ($dbForProject, $delete, $type) { + $delete($dbForProject, $resource->getSequence(), $type); } ); }; /* perform processing in parallel */ batch([ - fn () => $processResource('sites'), - fn () => $processResource('functions'), + fn () => $processResource(RESOURCE_TYPE_SITES), + fn () => $processResource(RESOURCE_TYPE_FUNCTIONS), ]); } }