Как запустить python script как pm2 для nodejs

Я использовал pm2 для моего Node.js script, и мне это нравится.
Теперь у меня есть python script, который собирает потоковые данные на EC2. Иногда script срабатывает, и я хотел бы, чтобы диспетчер процессов перезапустил себя, как pm2.

Есть ли что-то такое же, как pm2 для python? Я искал вокруг и ничего не мог найти.

Здесь моя ошибка

  File "/usr/local/lib/python2.7/dist-packages/tweepy/streaming.py", line 430, in filter
    self._start(async)
  File "/usr/local/lib/python2.7/dist-packages/tweepy/streaming.py", line 346, in _start
    self._run()
  File "/usr/local/lib/python2.7/dist-packages/tweepy/streaming.py", line 286, in _run
    raise exception
AttributeError: 'NoneType' object has no attribute 'strip'
/usr/local/lib/python2.7/dist-packages/requests/packages/urllib3/util/ssl_.py:90:

Это простой сбор данных script

class StdOutListener(StreamListener):

    def on_data(self, data):
        mydata = json.loads(data)
        db.raw_tweets.insert_one(mydata)
        return True

    def on_error(self, status):
        mydata = json.loads(status)
        db.error_tweets.insert_one(mydata)


if __name__ == '__main__':

    #This handles Twitter authetification and the connection to Twitter Streaming API
    l = StdOutListener()
    auth = OAuthHandler(consumer_key, consumer_secret)
    auth.set_access_token(access_token, access_token_secret)
    stream = Stream(auth, l)

    #This line filter Twitter Streams to capture data by the keywords: 'python', 'javascript', 'ruby'
    stream.filter(follow=[''])

Я бы хотел, чтобы он просто перезапустил себя, если что-то случится.

Ответ 1

UPD: см. ответы ниже для более эффективных решений.

-

Для этого есть несколько решений. Во-первых, вы можете использовать http://supervisord.org/, который является достойной универсальной системой управления процессом, которая включает в себя множество функций из коробки, таких как autorestart, счетчик перезапуска, протоколирование, гибкая настройка и многое другое.

Кроме того, вы можете просто превратить свою логику реализации в функцию, запустить ее в блоке try except, уловить все исключения и при возникновении исключения запустить функцию снова, а не выйти из script. В вашем случае такая функция может включать создание функции прослушивания, аутентификации и потока.

Ответ 2

Фактически вы можете запускать скрипты python из pm2:

pm2 start echo.py

Если script заканчивается суффиксом .py, он будет использовать интерпретатор python по умолчанию. Если ваше имя файла не заканчивается на .py, вы можете сделать:

pm2 start echo --interpreter=python

Я обнаружил, что вы должны быть немного осторожны, какой питон вы используете, особенно если вы используете виртуальный питон с другой версией на "python" по умолчанию на вашем компьютере.

Ответ 3

PM2 достаточно, он будет запускать интерпретатор с помощью суффикса:

{
  ".sh": "bash",
  ".py": "python",
  ".rb": "ruby",
  ".coffee" : "coffee",
  ".php": "php",
  ".pl" : "perl",
  ".js" : "node"
}

Ответ 4

Я создал файл экосистемы ecosystem.config.json

{
    "apps": [{
        "name": "app_name",
        "script": "/the/app/path/my_app.py",
        "args": ["-c", "my_config.prod.json"],
        "instances": "1",
        "wait_ready": true,
        "autorestart": false,
        "max_restarts": 5,
        "interpreter" : "/path/to/venv/bin/python",
    }]
}

Запустите службу pm2:

$ pm2 start ecosystem.config.json
$ pm2 -v
3.2.8

Ответ 5

PM2 с пипенв

Для тех, кто пытается запустить программу на Python из/с pipenv, попробуйте pm2.config.json (или ecosystem.json.config, как в официальной документации PM2), например:

Важными частями являются "interpreter": "pipenv" и "interpreter_args": "run python3".

pm2.config.json

{
    "apps": [{
        "name": "BackupService",
        "script": "/home/service-backup/service/server.py",
        "args": [""],
        "wait_ready": true,
        "autorestart": false,
        "max_restarts": 5,
        "interpreter" : "pipenv",
        "interpreter_args": "run python3"
    }]
}

Затем pm2 start pm2.config.json. Я всегда pm2 delete BackupService (или как вы его называете в "имя"), прежде чем начинать снова, потому что даже с --update-env он не использует обновленный pm2.config.json. Не знаю почему.

Также обратите внимание, что "interpreter_args" "node_args", по-видимому, был изменен на "node_args", согласно последним документам PM2. Я использую pm2 --version 3.0.0, и старый способ все еще работает.

PM2 с многопроцессорной обработкой Python

Если вы хотите запустить программу на Python, использующую многопроцессорную библиотеку Pythons, решение состоит в том, чтобы принудительно запустить ее в режиме форка. Похоже, что PM2, если не указано иное, автоматически пытается запустить его в cluster режиме.

Однако я подозреваю, что нам нужно полностью оставить многопроцессорную часть Python. Я не могу представить, чтобы PM2 мог управлять несколькими процессами, порождаемыми многопроцессорной обработкой Python - что он пытается при работе в режиме cluster. Кроме того, при использовании опции "interpreter" (например, для pipenv) будет работать только fork_mode, в соответствии с документами PM2.

Поэтому добавьте "exec_mode": "fork" в ваш pm2.config.json чтобы он запустился.

Если вы не используете файл pm2.config.json, передача -i 0 до pm2 start должна pm2 start режим форка. (-i обозначает случаи)

Ответ 6

В моем случае я использую scrapyd в своем проекте. Исходная команда:

scrapyd --pidfile /var/log/scrapyd/twistd.pid -l /var/log/scrapyd/logs/scrapyd.log

а версия pm2:

pm2 start scrapyd --interpreter python --watch --name=scrapyd -- --pidfile "/var/log/scrapyd/twistd.pid" -l "/var/log/scrapyd/logs/scrapyd.log"

надеюсь, что этот пример поможет