Несколько подпроцессов с тайм-аутами

Я использую рецепт, который полагается на SIGALRM для установки прерывания тревоги – использование подпроцесса модуля с тайм-аутом

Проблема в том, что у меня есть более одного скрипта Python с использованием процесса signal.ALARM для установки тайм-аутов, и вызывается только самый последний сигнал тревоги. Каков хороший способ улучшить это множество функций Python, устанавливающих тайм-ауты?

One Solution collect form web for “Несколько подпроцессов с тайм-аутами”

За исключением простых, быстрых хаков, избегайте SIGALRM. Это очень старый, ограниченный механизм, не подходящий ни к чему более сложному: вы можете установить только один сигнал тревоги и прерывать любой системный вызов в то время, а не только тот, который вы собираетесь прервать.

Гораздо чище использовать тайм-аут, чтобы убить процесс, например:

import subprocess, signal, os, threading, errno from contextlib import contextmanager class TimeoutThread(object): def __init__(self, seconds): self.seconds = seconds self.cond = threading.Condition() self.cancelled = False self.thread = threading.Thread(target=self._wait) def run(self): """Begin the timeout.""" self.thread.start() def _wait(self): with self.cond: self.cond.wait(self.seconds) if not self.cancelled: self.timed_out() def cancel(self): """Cancel the timeout, if it hasn't yet occured.""" with self.cond: self.cancelled = True self.cond.notify() self.thread.join() def timed_out(self): """The timeout has expired.""" raise NotImplementedError class KillProcessThread(TimeoutThread): def __init__(self, seconds, pid): super(KillProcessThread, self).__init__(seconds) self.pid = pid def timed_out(self): try: os.kill(self.pid, signal.SIGKILL) except OSError as e: # If the process is already gone, ignore the error. if e.errno not in (errno.EPERM, errno. ESRCH): raise e @contextmanager def processTimeout(seconds, pid): timeout = KillProcessThread(seconds, pid) timeout.run() try: yield finally: timeout.cancel() def example(): proc = subprocess.Popen(["sleep", "5"], stdin=subprocess.PIPE, stdout=subprocess.PIPE) with processTimeout(1, proc.pid): print proc.communicate() resultcode = proc.wait() if resultcode < 0: print "error: %i" % resultcode if __name__ == '__main__': example() 

В зависимости от того, что вы выбрали, вы можете использовать более светлый сигнал, чем SIGKILL, чтобы очистить процесс тайм-аута после себя.

  • CTRL + C не прерывает вызов в общую библиотеку с помощью CTYPES в Python
  • Приостановка процесса?
  • Python 2 не обрабатывает сигналы, если TCPServer работает в другом потоке
  • Сохранение работы после SIGINT
  • Пользовательский сигнал не обрабатывается внутренним API Scrapy
  • Как сигнализировать слоты в графическом интерфейсе из другого процесса?
  • Получить имена сигналов из чисел в Python
  • Как остановить python от распространения сигналов на подпроцессы?
  •  
    Interesting Posts for Van-Lav

    Как преобразовать частично альфа-прозрачное изображение, чтобы иметь один (непрозрачный) цвет в PIL?

    Расширенное поперечное сечение с мультииндексами в пандах

    Выясните, присутствует ли элемент в многомерном массиве в python

    Как создать учетную запись суперпользователя в Django 1.9.6

    Selenium (Python) – SELECT

    Существует ли разница в скорости между WSGI и FCGI?

    Кросс-платформенный графический интерфейс Python, подходящий для функциональности панели задач (Win) и menubar (mac)?

    Планирование кадров данных Pandas

    Могу ли я показывать строки на экране ncurses без функции getch ()?

    Разбор файла Python: сборка дерева из текстового файла

    ValueError в matplotlib при использовании горизонтального интервала \: LaTeX

    Как удалить определенные строки из списка

    Как добавить пользовательское разрешение для модели пользователя в django?

    Установить маску для matplotlib tricontourf

    Как остановить приложение qt от замораживания основной программы?

    Python - лучший язык программирования в мире.