Выполнение длинной задачи на удаленном сервере с помощью python-rq

Я написал код, выполнение которого занимает много времени (2-3 дня), и я хочу отправить его на сервер, который будет выполняться там. Код богат классами и функциями, взаимодействующими друг с другом, но в конце концов выполнение всего кода выполняется с помощью одной функции (test2), которая заставит его работать. Я обнаружил, что решением для меня может быть очередь задач, и, поскольку мне не нужно выполнять несколько задач одновременно, я обнаружил, что RQ может удовлетворить мои потребности.

#action_test.py

import action2

def test1():
    fl = action2.FollowersList()
    mech = action2.Mechanics()
    manager = action2.Manager()
    manager.launch(mech,fl)
    for i in range(0,10):
        manager.iterate(mech,fl)

def test2():
    messageList = []
    fl = action2.FollowersList()
    mech = action2.Mechanics()
    manager = action2.Manager()
    manager.launch(mech,fl)
    for i in range(0,2000):
        message = manager.iterate(mech,fl)
        messageList.append(message)
    return messageList

Я настроил Reddis на удаленном сервере. Запустите его в режиме демона. Затем я написал простой модуль, который должен просто поставить мою функцию test2 в очередь.

#app.py

from rq import Connection, Queue
from redis import Redis
from action_test import test2

def main():
    # Tell RQ what Redis connection to use
    redis_conn = Redis()
    q = Queue(connection=redis_conn)  # no args implies the default queue

    # Delay calculation of the multiplication
    job = q.enqueue(test2, timeout = 259200)
    print job.result   # => None

if __name__ == '__main__':
    main()

Затем я столкнулся с проблемой: на веб-странице документации по python-rq ( http://python-rq.org/docs/workers/) описанный способ запуска работника - выполнить

$ rqworker

из скорлупы Но этот рабочий запускается не как демон, и поэтому, когда я подключаюсь к этому удаленному серверу, где мое приложение настроено по ssh, если мое ssh-соединение прерывается, рабочий тоже отключается, и это не совсем то поведение, которое мне бы хотелось иметь. Поддержание соединения ssh в течение 2-3 дней во время выполнения моего кода отрицает всю логику, кроме использования python-rq в моем случае. Есть ли способы обойти эту проблему? Возможно, рабочий python-rq должен быть запущен не из оболочки, которую нужно демонизировать?

3 ответа

Решение

Вы можете запустить работника в фоновом режиме (&) и отправить вывод в текстовый файл (nohup):

nohup rqworker &

По умолчанию это запишет вывод в файл nohup.out в том же каталоге (или $HOME/nohup.out если это не разрешено). Теперь вы можете закрыть соединение ssh.

При настройках по умолчанию rq будет много писать в этом файле, но --quiet помогает:

nohup rqworker --quiet &

Смотрите man nohup и как начать работу в фоновом режиме.

Насколько я могу сказать, вам не нужно python-rq совсем. Очередь сообщений обычно используется для связи в распределенной системе, что является слишком сложным для человека, который просто хочет запустить долго выполняющийся скрипт на удаленном сервере. Вы могли бы пропустить rqworker и запустите ваш скрипт напрямую. добавлять if __name__=='__main__': test2() на ваш action_test.py скрипт, тогда вы можете запустить скрипт из командной строки:

python test_action.py

Как вы указали, когда вы закрываете сеанс SSH, ваш скрипт также уничтожается. Это происходит из-за магии Unix/Linux, называемой "сигналы": система отправляет сигнал "зависания" на вашу работу, также известный как SIGHUP, Мартин упомянул nohup уже и это работоспособный ответ (например, nohup python test_action.py) но это немного сложно для новичка, который просто хочет запустить длинный скрипт.

Более простым решением для вас является использование screen, Screen создает виртуальный терминал, который позволяет вам отключиться от оболочки и подключиться позже. Если у вас установлен экран, просто запустите screen и он создаст новый виртуальный терминал для вас. Теперь запустите вашу программу как обычно: python test_action.py, Как только это начнется, нажмите Ctrl+A, а затем D, чтобы отключиться. Теперь вы можете отключить сеанс SSH, но работа будет продолжаться в виртуальном терминале, как будто ничего не произошло. Позже вы можете вернуться по SSH на сервер и набрать screen -r возобновить использование этого терминала.

Более подробная информация здесь: https://unix.stackexchange.com/questions/24658/nohup-vs-screen

Вы можете использовать пакет http://supervisord.org/ для этого. Это помогает настроить процесс deamon для запуска задачи в фоновом режиме. И это также довольно легко настроить.

Другие вопросы по тегам