web/scripts/update-project-statuses

93 lines
2.7 KiB
PHP
Executable file

#!/usr/bin/php
<?
require_once('/standardebooks.org/web/lib/Core.php');
use function Safe\file_get_contents;
use Safe\DateTimeImmutable;
/**
* Iterate over all `Project`s that are in progress or stalled and get their latest GitHub commit.
*
* If the last activity was more than 30 days old, mark the `Project` as stalled and send a reminder email.
*
* 60 days after the reminder email, the `Project` is marked as abandoned if there has not been any activity since.
*
* If a `Project` stalls and is re-activated, the process will repeat except no further reminder emails will be sent.
*/
/** @var array<Project> $projects */
$projects = array_merge(
Project::GetAllByStatus(Enums\ProjectStatusType::InProgress),
Project::GetAllByStatus(Enums\ProjectStatusType::Stalled)
);
$apiKey = trim(file_get_contents('/standardebooks.org/config/secrets/se-vcs-bot@api.github.com'));
$oldestStalledTimestamp = new DateTimeImmutable('60 days ago');
$oldestAbandonedTimestamp = new DateTimeImmutable('60 days ago');
foreach($projects as $project){
try{
$project->FetchLastDiscussionTimestamp();
}
catch(Exceptions\AppException $ex){
Log::WriteErrorLogEntry($ex->getMessage());
}
try{
$project->FetchLatestCommitTimestamp($apiKey);
}
catch(Exceptions\AppException $ex){
Log::WriteErrorLogEntry($ex->getMessage());
}
if($project->IsStatusAutomaticallyUpdated){
if(
$project->Status == Enums\ProjectStatusType::InProgress
&&
$project->LastActivityTimestamp < $oldestStalledTimestamp
){
// An active `Project` has stalled.
$project->Status = Enums\ProjectStatusType::Stalled;
// Send an email to the producer.
$project->SendReminder(Enums\ProjectReminderType::Stalled);
}
elseif(
$project->Status == Enums\ProjectStatusType::Stalled
&&
$project->LastActivityTimestamp >= $oldestStalledTimestamp
){
// Revive previously-stalled `Project`s.
$project->Status = Enums\ProjectStatusType::InProgress;
}
elseif(
$project->Status == Enums\ProjectStatusType::Stalled
&&
$project->LastActivityTimestamp < $oldestStalledTimestamp
&&
$project->GetReminder(Enums\ProjectReminderType::Stalled)?->Created < $oldestAbandonedTimestamp
){
// A stalled `Project` is now abandoned.
$project->Status = Enums\ProjectStatusType::Abandoned;
// Set the corresponding `EbookPlaceholder` to not be "in progress" any more.
if($project->Ebook->EbookPlaceholder !== null){
try{
$project->Ebook->EbookPlaceholder->IsInProgress = false;
$project->Ebook->EbookPlaceholder->Save();
}
catch(Exceptions\InvalidEbookPlaceholderException){
// Pass.
}
}
// Send a notification to the producer.
$project->SendReminder(Enums\ProjectReminderType::Abandoned);
}
}
$project->Save();
sleep(5);
}