(Laravel 5) Отслеживайте и при необходимости отменяйте задание УЖЕ ЗАПУСК в очереди - PullRequest
0 голосов
/ 03 июля 2019

Мне нужно добиться возможности отслеживать и иметь возможность отменять задание УЖЕ ЗАПУСК в очереди.

Существует множество ответов об удалении заданий QUEUED, но не об уже запущенных.

Это ситуация: у меня есть «задание», состоящее из сотен строк в базе данных, которые нужно запрашивать один-на-один у веб-службы.

Каждая строка должна бытьподнял, запросил у веб-службы, сохранил ответ и обновил его статус.

Я уже работал с командой (запуск из консоли / вывод на консоль), но теперь мне нужно реализовать очереди, чтобыПозволяет накапливать больше заданий от большего количества пользователей.

До сих пор я видел Horizon (который не работает в Windows из-за отсутствия библиотек управления процессами).Тем не менее, в некоторых демонстрационных версиях отсутствует (я считаю) пара вещей, которые мне нужны:

  • Динамически настраиваемое время ожидания (вся работа может занять более 12 часов, в зависимости от количества обрабатываемых строкна выбранной работе)
  • Возможность ОТМЕНИТЬ УЖЕ ЗАПУСК.

Я также рассмотрел вариант создания КАЖДОГО ЗАПРОСА как нового задания вместо того, чтобы рассматривать «задание» как целую коллекцию строк (это могло бы преодолеть время ожидания), но это дало бы мнеHorizon - список «ожидающих заданий» сотен тысяч записей на одно задание, и это может убить браузер (я знаю, что Redis может справиться с этим без всякого зуда).Кроме того, я думаю, что невозможно отменить «все задания, принадлежащие тегу X».

Я думал о переходе по маршруту API, запускаю работу и отсоединяю ее от приложения, но я вижучто это требует разветвления процессов.

Для возможности отмены я бы реализовал базу данных с помощью job_id, а когда пользователь нажимает API для отмены задания, я отмечал бы его как «остановленный».В каждом цикле я проверял бы его состояние, и если он обнаружил, что он «остановлен», то убивал себя.

Если я пропустил какой-либо аспект, просто кричите, и я добавлю его или уточню об этом.

Поэтому я прошу совета здесь, так как я новичок в Laravel: как я могу этого достичь?

Ответы [ 2 ]

0 голосов
/ 16 июля 2019

Итак, я наконец-то нашел это (немного неуклюжее) решение:

В контроллере:

 public function cancelJob()
    {
        $jobs = DB::table('jobs')->get();

        # I could use a specific ID and user owner filter, etc.
        foreach ($jobs as $job) {
            DB::table('jobs')->delete($job->id);
        }

        # This is a file that... well, it's self explaining
        touch(base_path(config('afip_client.files.halt_process_signal')));

        return "Job cancelled - It will stop soon";
    }

В рабочем классе (внутри model::chunk() функция)

                # CHECK FOR HALT SIGNAL AND [OPTIONALLY] STOP THE PROCESS
                if ($this->service->shouldHaltProcess()) {

                    # build stats, do some cleanup, log, etc...

                    $this->halted = true;
                    $this->service->stopProcess();

                    # This FALSE is what it makes the chunk() method to stop looping
                    return false;
                }

В классе обслуживания:

    /**
     * Checks the existence of the 'Halt Process Signal' file
     *
     * @return bool
     */
    public function shouldHaltProcess() :bool
    {
        return file_exists($this->config['files.halt_process_signal']);
    }


    /**
     * Stop the batch process
     *
     * @return void
     */
    public function stopProcess() :void
    {
        logger()->info("=== HALT PROCESS SIGNAL FOUND - STOPPING THE PROCESS ===");
        $this->deleteHaltProcessSignalFile();

        return ;
    }

Это выглядит не совсем элегантно, но работает. Я просмотрел всю сеть, и многие выбирают Horizon или другие инструменты, которые не подходят для моего случая. Если у кого-то есть лучший способ добиться этого, он может поделиться.

0 голосов
/ 03 июля 2019

У очереди Laravel есть 3 важных конфигурации:

1. retry_after
2. timeout
3. tries

Подробнее: https://laravel.com/docs/5.8/queues

Динамически настраиваемое время ожидания (вся работа может занять более 12 часов, в зависимости отколичество строк для обработки в выбранном задании)

Я думаю, что вы можете настроить время ожидания + retry_after примерно через 24 часа.

Возможность ОТМЕНИТЬ УЖЕ ЗАПУСК ЗАДАЧИ.

  • Удалить задание в таблице заданий
  • Удалить процесс по идентификатору процесса на вашем сервере

Надеюсь, это поможет вам :)

...