Skip to content
Snippets Groups Projects
scheduler.php 8.14 KiB
Newer Older
  • Learn to ignore specific revisions
  • use Configuration\models\ConfigurationModel;
    
    use Document\models\DocumentModel;
    use Email\controllers\EmailController;
    
    use History\controllers\HistoryController;
    
    use Notification\models\NotificationsScheduleModel;
    use Notification\models\NotificationStackModel;
    use SrcCore\controllers\LanguageController;
    use SrcCore\models\DatabasePDO;
    
    use SrcCore\models\ValidatorModel;
    
    use User\models\UserModel;
    
    require './vendor/autoload.php';
    
    $configPath = $argv[1];
    
    DatabasePDO::reset();
    new DatabasePDO(['configPath' => $configPath]);
    
    
    $configuration = ConfigurationModel::getByIdentifier(['identifier' => 'customization']);
    $configuration = $configuration[0];
    
    $configuration['value'] = json_decode($configuration['value'], true);
    
    $applicationUrl = $configuration['value']['applicationUrl'];
    
    $GLOBALS['id'] = 0;
    $GLOBALS['webhook'] = 'SCHEDULER';
    
    
    if (empty($applicationUrl)) {
    
        HistoryController::add([
            'code'       => 'KO',
            'objectType' => 'configurations',
            'objectId'   => $configuration['id'],
            'type'       => 'ERROR',
    
            'message'    => "{scheduler} :  {noApplicationUrlDefined}"
    
        echo "Cannot run scheduler : no applicationUrl defined\n";
        exit(1);
    }
    
    $restUser = UserModel::get(['select' => ['id'], 'where' => ['"isRest" = ?'], 'data' => ['true']]);
    if (empty($restUser[0])) {
        HistoryController::add([
            'code'       => 'KO',
            'objectType' => 'configurations',
            'objectId'   => $configuration['id'],
            'type'       => 'ERROR',
    
            'message'    => "{scheduler} : {noRestUserFound}"
    
        echo "Cannot run scheduler :  no rest user found\n";
    
        exit(1);
    }
    $restUser = $restUser[0];
    $GLOBALS['id'] = $restUser['id'];
    
    
    $schedules = NotificationsScheduleModel::get();
    
    $currentDate = new DateTime();
    
    foreach ($schedules as $schedule) {
        if ($schedule['status'] != 'READY') {
            continue;
        }
    
        $currentMonth = $currentDate->format('n');
        $schedule['months'] = json_decode($schedule['months']);
        if (!in_array($currentMonth, $schedule['months']) && $schedule['months'][0] != '*') {
            continue;
        }
    
        $currentDayOfMonth = $currentDate->format('j');
        $schedule['days_of_month'] = json_decode($schedule['days_of_month']);
        if (!in_array($currentDayOfMonth, $schedule['days_of_month']) && $schedule['days_of_month'][0] != '*') {
            continue;
        }
    
        $currentDayOfWeek = $currentDate->format('N');
        $schedule['days_of_week'] = json_decode($schedule['days_of_week']);
        if (!in_array($currentDayOfWeek, $schedule['days_of_week']) && $schedule['days_of_week'][0] != '*') {
            continue;
        }
    
        $lastExecution = new DateTime($schedule['last_execution']);
        if (!empty($schedule['last_execution'])) {
            $difference = $currentDate->diff($lastExecution);
            if (empty($schedule['frequency']) && $lastExecution->format('Y-m-d') == $currentDate->format('Y-m-d')) {
                continue;
            } elseif (!empty($schedule['frequency']) && $schedule['frequency_mode'] == 'minutes' && $difference->i < $schedule['frequency']) {
                continue;
    
            } elseif(!empty($schedule['frequency']) && $schedule['frequency_mode'] == 'hours' && $difference->h < $schedule['frequency']) {
    
                continue;
            }
        }
    
        $startTime = new DateTime($schedule['start_time']);
        $endTime = new DateTime($schedule['end_time']);
    
        if ($currentDate < $startTime) {
            continue;
    
        } elseif (!empty($schedule['frequency']) && $endTime < $currentDate) {
    
            continue;
        }
    
        // RUN TASK
        NotificationsScheduleModel::update([
            'set'   => ['status' => 'RUNNING'],
            'where' => ['id = ?'],
            'data'  => [$schedule['id']]
        ]);
    
        $notificationStack = NotificationStackModel::get([
            'select' => ['*'],
            'where'  => ['type = ?'],
            'data'   => [$schedule['type']]
        ]);
    
    
        if (!empty($notificationStack)) {
    
            sendNotifications([
                'type'            => $schedule['type'],
                'stack'           => $notificationStack,
                'restUser'        => $restUser,
                'applicationUrl'  => $applicationUrl,
                'configurationId' => $configuration['id']
    
        }
    
        NotificationsScheduleModel::update([
            'set'   => ['status' => 'READY', 'last_execution' => 'CURRENT_TIMESTAMP'],
            'where' => ['id = ?'],
            'data'  => [$schedule['id']]
        ]);
    }
    
    
    function sendNotifications(array $args)
    
        ValidatorModel::notEmpty($args, ['stack', 'restUser', 'type', 'applicationUrl']);
        ValidatorModel::arrayType($args, ['stack', 'restUser']);
        ValidatorModel::stringType($args, ['type', 'applicationUrl']);
    
    
        $notificationStack = $args['stack'];
        $restUser = $args['restUser'];
    
    
        if ($args['type'] == 'next_user') {
            $subjectKey = 'notificationDocumentsAddedSubject';
            $bodyKey = 'notificationDocumentsAddedBody';
        } elseif ($args['type'] == 'typist_END') {
            $subjectKey = 'notificationEndOfWorkflowsSubject';
            $bodyKey = 'notificationEndOfWorkflowsBody';
        } elseif ($args['type'] == 'typist_INT') {
            $subjectKey = 'notificationInterruptsSubject';
            $bodyKey = 'notificationInterruptsBody';
        } elseif ($args['type'] == 'typist_REF') {
            $subjectKey = 'notificationRefusedWorkflowsSubject';
    
            $bodyKey = 'notificationRefusedWorkflowsBody';
    
        $recipients = array_unique(array_column($notificationStack, 'recipient_id'));
    
    
        foreach ($recipients as $recipientId) {
            $recipientNotifications = array_filter($notificationStack, function ($notification) use ($recipientId) {
                return $notification['recipient_id'] == $recipientId;
            });
    
    
            $recipient = UserModel::getById(['id' => $recipientId, 'select' => ['email', 'preferences']]);
    
            $recipient['preferences'] = json_decode($recipient['preferences'], true);
            $lang = LanguageController::get(['lang' => $recipient['preferences']['lang']]);
    
    
            $recipientNotificationIds = [];
    
            foreach ($recipientNotifications as $recipientNotification) {
    
                $url  = $args['applicationUrl'] . 'dist/#/documents/' . $recipientNotification['main_document_id'];
    
                $document = DocumentModel::getById(['id' => $recipientNotification['main_document_id'], 'select' => ['title']]);
    
                $row = str_replace('{{object}}', $document['title'], $lang['notificationTemplateRow']);
                $row = str_replace('{{link}}', $url, $row);
                $rows .= $row . "\n";
    
                $recipientNotificationIds[] = $recipientNotification['id'];
    
            }
    
            $emailBody .= str_replace('{{rows}}', $rows, $lang['notificationTemplateTable']);
    
    
            $isSent = EmailController::createEmail([
    
                'userId' => $restUser['id'],
                'data'   => [
                    'sender'     => 'Notification',
                    'recipients' => [$recipient['email']],
    
                    'subject'    => $lang[$subjectKey],
    
                    'body'       => $emailBody . $lang['notificationFooter'],
    
                    'isHtml'     => true,
                    'status'     => 'EXPRESS'
    
    
            if (!empty($isSent['errors'])) {
                HistoryController::add([
                    'code'       => 'KO',
                    'objectType' => 'configurations',
                    'objectId'   => $args['configurationId'],
                    'type'       => 'ERROR',
    
                    'message'    => "{scheduler} : {sendingSummaryError} : " . $isSent['errors']
    
                $notificationSent = array_merge($notificationSent, $recipientNotificationIds);
    
        HistoryController::add([
    
            'objectType' => 'configurations',
            'objectId'   => $args['configurationId'],
    
            'type'       => 'ACTION',
            'message'    => "{scheduler} : $nbEmailSent {summariesSent} {notification_{$args['type']}}"
    
        // Delete only the sent notifications in the stack
    
        NotificationStackModel::delete([
            'where' => ['id in (?)'],
    
            'data'  => [$notificationSent]