subprocess — Управление дочерними процессами
Исходный код: Lib/subprocess.py
Модуль subprocess позволяет запускать новые процессы, подключаться к их каналам ввода/вывода/ошибок и получать их коды возврата. Этот модуль призван заменить несколько более старых модулей и функций:
os.system os.spawn*
Информация о том, как модуль subprocess может быть использован для замены этих модулей и функций, приведена в следующих разделах.
См. также
PEP 324 — PEP, предлагающий модуль subprocess
Использование модуля subprocess
Рекомендуемый подход к вызову дочерних процессов — использование функции run() для всех случаев, которые она поддерживает. Для более сложных случаев можно напрямую использовать базовый интерфейс Popen.
Функция run() была добавлена в Python 3.5; если вам нужна обратная совместимость со старыми версиями, см. раздел Старый высокоуровневый API.
-
subprocess.run(args, *, stdin=None, input=None, stdout=None, stderr=None, capture_output=False, shell=False, cwd=None, timeout=None, check=False, encoding=None, errors=None, text=None, env=None, universal_newlines=None, **other_popen_kwargs) -
Запускает команду, описанную в args. Ждет завершения команды и возвращает объект
CompletedProcess.Приведённые выше аргументы — лишь наиболее распространённые, описанные ниже в разделе Часто используемые аргументы (отсюда и использование ключевых только обозначений в сокращенной сигнатуре). Полная сигнатура функции в основном такая же, как у конструктора
Popen— большинство аргументов этой функции передаются в этот интерфейс. (timeout, input, check и capture_output не передаются).Если capture_output имеет значение True, stdout и stderr будут захвачены. При использовании внутренний объект
Popenавтоматически создаётся сstdout=PIPEиstderr=PIPE. Аргументы stdout и stderr не могут быть переданы одновременно с capture_output. Если вы хотите захватить и объединить оба потока в один, используйтеstdout=PIPEиstderr=STDOUTвместо capture_output.Аргумент timeout передаётся в
Popen.communicate(). Если таймаут истекает, дочерний процесс будет убит и дождаться его завершения. ИсключениеTimeoutExpiredбудет повторно поднято после завершения дочернего процесса.Аргумент input передаётся в
Popen.communicate()и, таким образом, в стандартный ввод дочернего процесса. Если используется, он должен быть последовательностью байтов или строкой, если указаны encoding или errors, или text имеет значение True. При использовании внутренний объектPopenавтоматически создаётся сstdin=PIPE, и аргумент stdin также не может быть использован.Если check имеет значение True, и процесс завершается с ненулевым кодом возврата, будет поднято исключение
CalledProcessError. Атрибуты этого исключения содержат аргументы, код возврата и stdout и stderr, если они были захвачены.Если заданы encoding или errors, или text имеет значение True, файлы для stdin, stdout и stderr открываются в текстовом режиме с использованием указанного encoding и errors или по умолчанию
io.TextIOWrapper. Аргумент universal_newlines эквивалентен text и предоставляется для обратной совместимости. По умолчанию файлы открываются в двоичном режиме.Если env не
None, он должен быть отображением, определяющим переменные среды для нового процесса; они используются вместо поведения по умолчанию, которое наследует среду текущего процесса. Он передается непосредственно вPopen.Примеры:
>>> subprocess.run(["ls", "-l"]) # doesn't capture output CompletedProcess(args=['ls', '-l'], returncode=0) >>> subprocess.run("exit 1", shell=True, check=True) Traceback (most recent call last): ... subprocess.CalledProcessError: Command 'exit 1' returned non-zero exit status 1 >>> subprocess.run(["ls", "-l", "/dev/null"], capture_output=True) CompletedProcess(args=['ls', '-l', '/dev/null'], returncode=0, stdout=b'crw-rw-rw- 1 root root 1, 3 Jan 23 16:23 /dev/null\n', stderr=b'')Добавлена в версии 3.5.
Изменено в версии 3.6: Добавлены параметры encoding и errors
Изменено в версии 3.7: Добавлен параметр text, как более понятный псевдоним universal_newlines. Добавлен параметр capture_output.
-
class subprocess.CompletedProcess -
Значение, возвращаемое функцией
run(), представляющее собой процесс, который завершился.-
args -
Аргументы, используемые для запуска процесса. Это может быть список или строка.
-
returncode -
Код завершения дочернего процесса. Обычно код завершения 0 указывает, что процесс завершился успешно.
Отрицательное значение
-Nуказывает, что дочерний процесс был завершен сигналомN(только POSIX).
-
stdout -
Захваченный stdout дочернего процесса. Последовательность байтов или строка, если функция
run()была вызвана с кодировкой, ошибками или text=True.Noneесли stdout не был захвачен.Если вы запустили процесс с
stderr=subprocess.STDOUT, stdout и stderr будут объединены в этом атрибуте, иstderrбудетNone.
-
stderr -
Захваченный stderr дочернего процесса. Последовательность байтов или строка, если функция
run()была вызвана с кодировкой, ошибками или text=True.Noneесли stderr не был захвачен.
-
check_returncode() -
Если
returncodeимеет ненулевое значение, поднимается исключениеCalledProcessError.
Добавлена в версии 3.5.
-
-
subprocess.DEVNULL -
Специальное значение, которое может использоваться в качестве аргумента stdin, stdout или stderr к
Popenи указывает, что будет использован специальный файлos.devnull.Добавлена в версии 3.3.
-
subprocess.PIPE -
Специальное значение, которое может использоваться в качестве аргумента stdin, stdout или stderr к
Popenи указывает, что должен быть открыт канал к стандартному потоку. Наиболее полезно сPopen.communicate().
-
subprocess.STDOUT -
Специальное значение, которое может использоваться в качестве аргумента stderr к
Popenи указывает, что стандартная ошибка должна быть отправлена в тот же обработчик, что и стандартный вывод.
-
exception subprocess.SubprocessError -
Базовый класс для всех других исключений из этого модуля.
Добавлена в версии 3.3.
-
exception subprocess.TimeoutExpired -
Подкласс
SubprocessError, поднимаемый при истечении таймаута во время ожидания дочернего процесса.-
cmd -
Команда, которая использовалась для запуска дочернего процесса.
-
timeout -
Таймаут в секундах.
-
output -
Вывод дочернего процесса, если он был перехвачен функцией
run()илиcheck_output(). В противном случае,None.
-
stdout -
Псевдоним для output, для симметрии с
stderr.
-
stderr -
Вывод stderr дочернего процесса, если он был перехвачен функцией
run(). В противном случае,None.
Добавлена в версии 3.3.
Изменено в версии 3.5: Добавлены атрибуты stdout и stderr
-
-
exception subprocess.CalledProcessError -
Подкласс
SubprocessError, поднимаемый, когда процесс, запущенный с помощьюcheck_call()илиcheck_output(), возвращает ненулевой код выхода.-
returncode -
Код выхода дочернего процесса. Если процесс завершился из-за сигнала, это будет отрицательное число сигнала.
-
cmd -
Команда, которая использовалась для запуска дочернего процесса.
-
output -
Вывод дочернего процесса, если он был перехвачен функцией
run()илиcheck_output(). В противном случае,None.
-
stdout -
Псевдоним для output, для симметрии с
stderr.
-
stderr -
Вывод stderr дочернего процесса, если он был перехвачен функцией
run(). В противном случае,None.
Изменено в версии 3.5: Добавлены атрибуты stdout и stderr
-
Часто используемые аргументы
Для поддержки широкого спектра вариантов использования конструктор Popen (и функции-удобства) принимает большое количество необязательных аргументов. Для большинства типичных вариантов использования многие из этих аргументов можно безопасно оставить по умолчанию. Аргументы, которые чаще всего необходимы:
args обязателен для всех вызовов и должен быть строкой или последовательностью аргументов программы. Предоставление последовательности аргументов обычно предпочтительнее, так как это позволяет модулю позаботиться об обработке необходимой экранировки и кавычек аргументов (например, для разрешения пробелов в именах файлов). Если передается единственная строка, либо shell должен быть True (см. ниже), либо строка должна просто называть программу для выполнения без указания каких-либо аргументов.
stdin, stdout и stderr соответственно задают стандартный ввод, стандартный вывод и стандартную ошибку выполняемой программы. Допустимые значения: PIPE, DEVNULL, существующий дескриптор файла (положительное целое число), существующий объект файла и None. PIPE указывает на то, что должен быть создан новый канал для дочернего процесса. DEVNULL указывает, что будет использован специальный файл os.devnull. При значениях по умолчанию для None, перенаправление не произойдёт; дескрипторы файлов дочернего процесса будут унаследованы от родительского.
В дополнение к этому, stderr может быть STDOUT, что указывает на то, что данные stderr дочернего процесса должны быть перехвачены в тот же дескриптор файла, что и stdout.
Если указаны encoding или errors, или text (также известный как universal_newlines) имеет значение True, объекты файлов stdin, stdout и stderr будут открыты в текстовом режиме с использованием encoding и errors, указанных в вызове или значений по умолчанию для io.TextIOWrapper.
Для stdin символы конца строки '\n' во входных данных будут преобразованы в разделитель строк по умолчанию os.linesep. Для stdout и stderr все символы конца строки в выводе будут преобразованы в '\n'. Для получения дополнительной информации см. документацию класса io.TextIOWrapper, когда аргумент newline его конструктору имеет значение None.
Если режим текстовый не используется, stdin, stdout и stderr будут открыты как бинарные потоки. Преобразование кодировки или символов конца строки не выполняется.
Добавлена в версии 3.6: Добавлены параметры encoding и errors.
Добавлена в версии 3.7: Добавлен параметр text как псевдоним для universal_newlines.
Примечание
Атрибут newlines объектов файлов Popen.stdin, Popen.stdout и Popen.stderr не обновляется методом Popen.communicate().
Если shell имеет значение True, указанная команда будет выполнена через оболочку. Это может быть полезно, если вы используете Python в основном для расширенного управления потоком по сравнению с большинством системных оболочек и по-прежнему хотите получить удобный доступ к другим функциям оболочки, таким как оболочные конвейеры, подстановочные знаки имён файлов, расширение переменных среды и расширение ~ до домашнего каталога пользователя. Однако обратите внимание, что сам Python предлагает реализации многих функций, похожих на оболочку (в частности, glob, fnmatch, os.walk(), os.path.expandvars(), os.path.expanduser() и shutil).
Изменено в версии 3.3: Когда universal_newlines имеет значение True, класс использует кодировку locale.getpreferredencoding(False) вместо locale.getpreferredencoding(). Дополнительная информация об этом изменении содержится в классе io.TextIOWrapper.
Примечание
Перед использованием shell=True прочтите раздел Рекомендации по безопасности.
Эти параметры, а также все остальные, описаны более подробно в документации к конструктору Popen.
Конструктор Popen
В этом модуле создание и управление дочерними процессами обрабатывается классом Popen. Он предлагает большую гибкость, позволяющую разработчикам обрабатывать менее распространенные случаи, не охваченные функциями-удобствами.
-
class subprocess.Popen(args, bufsize=-1, executable=None, stdin=None, stdout=None, stderr=None, preexec_fn=None, close_fds=True, shell=False, cwd=None, env=None, universal_newlines=None, startupinfo=None, creationflags=0, restore_signals=True, start_new_session=False, pass_fds=(), *, encoding=None, errors=None, text=None)
-
Выполнить дочернюю программу в новом процессе. В POSIX класс использует поведение, подобное
os.execvp(), для выполнения дочерней программы. В Windows класс использует функцию WindowsCreateProcess(). Аргументы дляPopenследующие.args должен быть последовательностью аргументов программы или строкой. По умолчанию, программа для выполнения — это первый элемент в args, если args является последовательностью. Если args является строкой, интерпретация зависит от платформы и описана ниже. Обратите внимание на аргументы shell и executable для дополнительных отличий от поведения по умолчанию. Если не указано иное, рекомендуется передавать args в виде последовательности.
Пример передачи некоторых аргументов внешней программе как последовательности:
Popen(["/usr/bin/git", "commit", "-m", "Fixes a bug."])
В POSIX, если args — строка, эта строка интерпретируется как имя или путь к выполняемой программе. Однако это можно сделать только если не передавать аргументы программе.
Примечание
Возможно, не очевидно, как разбить командную строку оболочки на последовательность аргументов, особенно в сложных случаях.
shlex.split()демонстрирует, как определить правильную токенизацию для args:>>> import shlex, subprocess >>> command_line = input() /bin/vikings -input eggs.txt -output "spam spam.txt" -cmd "echo '$MONEY'" >>> args = shlex.split(command_line) >>> print(args) ['/bin/vikings', '-input', 'eggs.txt', '-output', 'spam spam.txt', '-cmd', "echo '$MONEY'"] >>> p = subprocess.Popen(args) # Success!
Обратите внимание, что опции (например, -input) и аргументы (например, eggs.txt), разделённые пробелами в оболочке, попадают в отдельные элементы списка, а аргументы, которые требуют кавычек или экранирования обратной косой чертой при использовании в оболочке (например, имена файлов, содержащие пробелы, или команда echo, показанная выше), являются отдельными элементами списка.
В Windows, если args — последовательность, она будет преобразована в строку способом, описанным в Преобразование последовательности аргументов в строку в Windows. Это происходит потому, что базовая функция
CreateProcess()работает со строками.Аргумент shell (по умолчанию
False) указывает, использовать ли оболочку в качестве программы для выполнения. Если shellTrue, рекомендуется передавать args в виде строки, а не последовательности.В POSIX с
shell=True, оболочка по умолчанию/bin/sh. Если args — строка, строка определяет команду для выполнения через оболочку. Это означает, что строка должна быть отформатирована точно так же, как она вводилась бы в командной строке оболочки. Это включает, например, кавычки или экранирование обратной косой чертой имён файлов с пробелами. Если args — последовательность, первый элемент указывает строку команды, а все дополнительные элементы будут обрабатываться как дополнительные аргументы для самой оболочки. То есть,Popenвыполняет эквивалент:Popen(['/bin/sh', '-c', args[0], args[1], ...])
В Windows с
shell=True, переменная средыCOMSPECопределяет оболочку по умолчанию. Единственный случай, когда необходимо указатьshell=Trueв Windows, — это когда команда, которую вы хотите выполнить, встроена в оболочку (например, dir или copy). Вам не нужно указыватьshell=Trueдля запуска пакетного файла или консольной исполняемой программы.Примечание
Перед использованием
shell=Trueпрочтите раздел «Учёт мер безопасности».bufsize будет передано соответствующим аргументом функции
open()при создании объектов файлов канала stdin/stdout/stderr:-
0означает небуферизованный (чтение и запись — один системный вызов и могут вернуть короткий результат) -
1означает буферизованный по строкам (применяется только еслиuniversal_newlines=True, т.е. в текстовом режиме) - любое другое положительное значение означает использование буфера примерно такого размера
- отрицательное значение bufsize (по умолчанию) означает использование системного значения io.DEFAULT_BUFFER_SIZE.
Изменено в версии 3.3.1: bufsize теперь по умолчанию имеет значение -1, чтобы включить буферизацию по умолчанию, соответствуя ожидаемому поведению большинства кода. В версиях до Python 3.2.4 и 3.3.1 он неправильно по умолчанию имел значение
0, что было небуферизованным и допускало короткие чтения. Это было непреднамеренно и не соответствовало поведению Python 2, как того ожидал большинство кода.Аргумент executable указывает заменяемую программу для выполнения. Он очень редко необходим. Когда
shell=False, executable заменяет программу для выполнения, указанную в args. Тем не менее, исходные args по-прежнему передаются программе. Большинство программ обрабатывают программу, указанную в args, как имя команды, которое может отличаться от фактически выполняемой программы. В POSIX имя args становится отображаемым именем исполняемого файла в таких утилитах, как ps. Еслиshell=True, в POSIX аргумент executable указывает заменяющую оболочку для значения по умолчанию/bin/sh.stdin, stdout и stderr указывают соответственно стандартный вход, стандартный вывод и стандартную ошибку выполняемой программы. Допустимые значения —
PIPE,DEVNULL, существующий дескриптор файла (положительное целое число), существующий объект файла иNone.PIPEозначает, что должен быть создан новый канал связи с дочерним процессом.DEVNULLозначает, что будет использован специальный файлos.devnull. При значениях по умолчанию дляNone, перенаправления не произойдёт; дескрипторы файлов дочернего процесса унаследуются от родительского. Кроме того, stderr может бытьSTDOUT, что означает, что данные stderr приложения должны быть сохранены в том же файловом дескрипторе, что и stdout.Если preexec_fn установлено в вызываемый объект, этот объект будет вызван в дочернем процессе непосредственно перед выполнением дочернего процесса. (Только POSIX)
Предупреждение
Параметр preexec_fn небезопасен для использования при наличии потоков в вашем приложении. Дочерний процесс может заблокироваться до вызова exec. Если вам необходимо его использовать, сделайте его простым! Минимизируйте количество вызовов библиотек.
Примечание
Если вам нужно изменить среду для дочернего процесса, используйте параметр env вместо его изменения в preexec_fn. Параметр start_new_session может заменить ранее часто используемое применение preexec_fn для вызова os.setsid() в дочернем процессе.
Если close_fds имеет значение true, все дескрипторы файлов, кроме
0,1и2, будут закрыты перед выполнением дочернего процесса. В противном случае, когда close_fds имеет значение false, дескрипторы файлов подчиняются своему признаку наследуемости, как описано в Наследование дескрипторов файлов.В Windows, если close_fds имеет значение true, никакие дескрипторы не будут унаследованы дочерним процессом, если явно не переданы в элемент
handle_listобъектаSTARTUPINFO.lpAttributeList, или с помощью стандартного перенаправления дескрипторов.Изменено в версии 3.2: Значение по умолчанию для close_fds было изменено с
Falseна указанное выше.Изменено в версии 3.7: В Windows значение по умолчанию для close_fds было изменено с
FalseнаTrueпри перенаправлении стандартных каналов. Теперь можно установить close_fds вTrueпри перенаправлении стандартных каналов.pass_fds — необязательная последовательность дескрипторов файлов, которые необходимо оставить открытыми между родительским и дочерним процессом. Передача pass_fds принудительно устанавливает close_fds в
True. (Только POSIX)Добавлена в версии 3.2: Параметр pass_fds был добавлен.
Если cwd не
None, функция изменяет рабочую директорию на cwd перед выполнением дочернего процесса. cwd может бытьstrи объектом, подобным пути. В частности, функция ищет executable (или первый элемент в args) относительно cwd, если путь к исполняемому файлу является относительным.Изменено в версии 3.6: Параметр cwd принимает объект, подобный пути.
Если restore_signals имеет значение true (по умолчанию), все сигналы, которые Python установил в SIG_IGN, восстанавливаются до SIG_DFL в дочернем процессе перед выполнением exec. В настоящее время это включает сигналы SIGPIPE, SIGXFZ и SIGXFSZ. (Только POSIX)
Изменено в версии 3.2: Добавлен параметр restore_signals.
Если start_new_session имеет значение true, вызов системной функции setsid() будет выполнен в дочернем процессе до выполнения подпроцесса. (Только POSIX)
Изменено в версии 3.2: Добавлен параметр start_new_session.
-
Если env не
None, то это должно быть отображение, определяющее переменные среды для нового процесса; они используются вместо стандартного поведения наследования среды текущего процесса.Примечание
Если указано, env должен предоставлять все переменные, необходимые для выполнения программы. В Windows, для запуска побочного сборника, указанное env обязательно должно включать допустимое значение
SystemRoot.Если указаны encoding или errors, или text равно true, объекты файлов stdin, stdout и stderr открываются в текстовом режиме с указанным кодированием и errors, как описано выше в Часто используемые аргументы. Аргумент universal_newlines эквивалентен text и предоставляется для обратной совместимости. По умолчанию объекты файлов открываются в двоичном режиме.
Новое в версии 3.6: Были добавлены encoding и errors.
Новое в версии 3.7: text был добавлен как более читабельный псевдоним для universal_newlines.
Если задано, startupinfo будет объектом
STARTUPINFO, который передаётся в базовую функциюCreateProcess. creationflags, если заданы, могут быть одним или несколькими из следующих флагов:CREATE_NEW_CONSOLECREATE_NEW_PROCESS_GROUPABOVE_NORMAL_PRIORITY_CLASSBELOW_NORMAL_PRIORITY_CLASSHIGH_PRIORITY_CLASSIDLE_PRIORITY_CLASSNORMAL_PRIORITY_CLASSREALTIME_PRIORITY_CLASSCREATE_NO_WINDOWDETACHED_PROCESSCREATE_DEFAULT_ERROR_MODECREATE_BREAKAWAY_FROM_JOB
Объекты Popen поддерживаются в качестве менеджеров контекста с помощью инструкции
with: при выходе стандартные дескрипторы файлов закрываются, и процесс дожидается завершения.with Popen(["ifconfig"], stdout=PIPE) as proc: log.write(proc.stdout.read())Изменено в версии 3.2: Добавлена поддержка менеджеров контекста.
Изменено в версии 3.6: Деструктор Popen теперь генерирует предупреждение
ResourceWarning, если дочерний процесс всё ещё работает.
Исключения
Исключения, поднятые в дочернем процессе, до того, как новая программа начнёт выполняться, будут повторно подняты в родительском.
Самое распространённое поднимаемое исключение — OSError. Это происходит, например, при попытке выполнить несуществующий файл. Приложения должны быть готовы к исключениям OSError.
Исключение ValueError будет поднято, если Popen вызывается с недопустимыми аргументами.
check_call() и check_output() будут поднимать CalledProcessError, если вызванный процесс возвращает код возврата, отличный от нуля.
Все функции и методы, принимающие параметр timeout, такие как call() и Popen.communicate(), будут поднимать TimeoutExpired, если таймаут истечёт до завершения процесса.
Все исключения, определённые в этом модуле, наследуются от SubprocessError.
Новое в версии 3.3: Базовый класс SubprocessError был добавлен.
Рекомендации по безопасности
В отличие от некоторых других функций popen, эта реализация никогда не будет неявно вызывать системную оболочку. Это означает, что все символы, включая метасимволы оболочки, могут безопасно передаваться в дочерние процессы. Если оболочка вызывается явно, через shell=True, приложение несёт ответственность за обеспечение правильной цитирования всех пробелов и метасимволов, чтобы избежать уязвимостей ввода оболочки.
При использовании shell=True, функция shlex.quote() может использоваться для правильного экранирования пробелов и метасимволов оболочки в строках, которые будут использоваться для построения команд оболочки.
Объекты Popen
Экземпляры класса Popen имеют следующие методы:
-
Popen.poll() -
Проверить, завершился ли дочерний процесс. Установить и вернуть атрибут
returncode. В противном случае возвращаетNone.
-
Popen.wait(timeout=None) -
Дождаться завершения дочернего процесса. Установить и вернуть атрибут
returncode.Если процесс не завершится через timeout секунд, вызовите исключение
TimeoutExpired. Безопасно перехватить это исключение и повторить ожидание.Примечание
Это приведёт к тупиковой ситуации при использовании
stdout=PIPEилиstderr=PIPEи дочерний процесс генерирует достаточно вывода в канал, чтобы заблокировать его, ожидая, пока буфер канала ОС примет больше данных. ИспользуйтеPopen.communicate()при использовании каналов, чтобы избежать этого.Примечание
Функция реализована с помощью цикла busy-wait (неблокирующий вызов и короткие паузы). Используйте модуль
asyncioдля асинхронного ожидания: см.asyncio.create_subprocess_exec.Изменено в версии 3.3: Добавлен timeout.
-
Popen.communicate(input=None, timeout=None) -
Взаимодействие с процессом: отправка данных в stdin. Чтение данных из stdout и stderr до тех пор, пока не будет достигнут конец файла. Дожидается завершения процесса. Необязательный аргумент input должен содержать данные, которые будут отправлены дочернему процессу, или
None, если данные не должны отправляться в дочерний процесс. Если потоки открыты в текстовом режиме, input должен быть строкой. В противном случае он должен быть байтами.communicate()возвращает кортеж(stdout_data, stderr_data). Данные будут строками, если потоки открыты в текстовом режиме; в противном случае это байты.Обратите внимание, что если вы хотите отправить данные в stdin процесса, вам нужно создать объект Popen с
stdin=PIPE. Аналогично, чтобы получить что-либо, кромеNoneв кортеже результатов, вам нужно указатьstdout=PIPEи/илиstderr=PIPE.Если процесс не завершится через timeout секунд, будет поднято исключение
TimeoutExpired. Перехват этого исключения и повторная попытка связи не потеряет никакого вывода.Дочерний процесс не убивается, если таймаут истекает, поэтому для правильной очистки хорошо работающее приложение должно убить дочерний процесс и завершить общение:
proc = subprocess.Popen(...) try: outs, errs = proc.communicate(timeout=15) except TimeoutExpired: proc.kill() outs, errs = proc.communicate()Примечание
Считанные данные буферизуются в памяти, поэтому не используйте этот метод, если размер данных большой или неограниченный.
Изменено в версии 3.3: Добавлен timeout.
-
Popen.send_signal(signal) -
Отправляет сигнал signal дочернему процессу.
Примечание
В Windows SIGTERM является псевдонимом для
terminate(). CTRL_C_EVENT и CTRL_BREAK_EVENT могут быть отправлены процессам, запущенным с параметром creationflags, включающимCREATE_NEW_PROCESS_GROUP.
-
Popen.terminate() -
Останавливает дочерний процесс. В POSIX-системах метод отправляет SIGTERM дочернему процессу. В Windows вызывается функция Win32 API
TerminateProcess()для остановки дочернего процесса.
-
Popen.kill() -
Уничтожает дочерний процесс. В POSIX-системах функция отправляет SIGKILL дочернему процессу. В Windows
kill()является псевдонимом дляterminate().
Доступны также следующие атрибуты:
-
Popen.args -
Аргумент args, как он был передан в
Popen– последовательность аргументов программы или строка.Введено в версии 3.3.
-
Popen.stdin -
Если аргумент stdin был
PIPE, этот атрибут является объектом потока для записи, возвращенным функциейopen(). Если были указаны аргументы encoding или errors или аргумент universal_newlines былTrue, поток является текстовым, в противном случае – байтовым. Если аргумент stdin не былPIPE, этот атрибут равенNone.
-
Popen.stdout -
Если аргумент stdout был
PIPE, этот атрибут является объектом потока для чтения, возвращенным функциейopen(). Чтение из потока предоставляет вывод дочернего процесса. Если были указаны аргументы encoding или errors или аргумент universal_newlines былTrue, поток является текстовым, в противном случае – байтовым. Если аргумент stdout не былPIPE, этот атрибут равенNone.
-
Popen.stderr -
Если аргумент stderr был
PIPE, этот атрибут является объектом потока для чтения, возвращенным функциейopen(). Чтение из потока предоставляет вывод об ошибках дочернего процесса. Если были указаны аргументы encoding или errors или аргумент universal_newlines былTrue, поток является текстовым, в противном случае – байтовым. Если аргумент stderr не былPIPE, этот атрибут равенNone.
Предупреждение
Используйте communicate() вместо .stdin.write, .stdout.read или .stderr.read для предотвращения тупиков из-за заполнения буферов каналов ОС и блокировки дочернего процесса.
-
Popen.pid -
Идентификатор процесса дочернего процесса.
Обратите внимание, что если вы установили аргумент shell в
True, это идентификатор процесса запущенной оболочки.
-
Popen.returncode -
Код возврата дочернего процесса, заданный методами
poll()иwait()(и косвенно методомcommunicate()). ЗначениеNoneуказывает, что процесс еще не завершился.Отрицательное значение
-Nуказывает, что дочерний процесс был завершен сигналомN(только POSIX).
Справочные функции для Windows Popen
Класс STARTUPINFO и следующие константы доступны только в Windows.
-
class subprocess.STARTUPINFO(*, dwFlags=0, hStdInput=None, hStdOutput=None, hStdError=None, wShowWindow=0, lpAttributeList=None) -
Частичная поддержка структуры Windows STARTUPINFO используется для создания
Popen. Следующие атрибуты могут быть установлены, передавая их как ключевые аргументы.Изменено в версии 3.7: Добавлена поддержка ключевых аргументов.
-
dwFlags -
Поле битов, определяющее, используются ли определенные атрибуты
STARTUPINFOпри создании окна процесса.si = subprocess.STARTUPINFO() si.dwFlags = subprocess.STARTF_USESTDHANDLES | subprocess.STARTF_USESHOWWINDOW
-
hStdInput -
Если
dwFlagsуказываетSTARTF_USESTDHANDLES, этот атрибут является дескриптором стандартного входного потока процесса. ЕслиSTARTF_USESTDHANDLESне указан, по умолчанию для стандартного ввода используется буфер клавиатуры.
-
hStdOutput -
Если
dwFlagsуказываетSTARTF_USESTDHANDLES, этот атрибут является дескриптором стандартного выходного потока процесса. В противном случае этот атрибут игнорируется, и по умолчанию для стандартного вывода используется буфер окна консоли.
-
hStdError -
Если
dwFlagsуказываетSTARTF_USESTDHANDLES, этот атрибут является дескриптором стандартного потока ошибок процесса. В противном случае этот атрибут игнорируется, и по умолчанию для стандартного вывода ошибок используется буфер окна консоли.
-
wShowWindow -
Если
dwFlagsуказываетSTARTF_USESHOWWINDOW, этот атрибут может принимать любое значение, которое может быть указано в параметреnCmdShowдля функции ShowWindow, за исключениемSW_SHOWDEFAULT. В противном случае этот атрибут игнорируется.SW_HIDEпредоставляется для этого атрибута. Он используется, когдаPopenвызывается сshell=True.
-
lpAttributeList -
Словарь дополнительных атрибутов для создания процесса, как указано в
STARTUPINFOEX, см. UpdateProcThreadAttribute.Поддерживаемые атрибуты:
- handle_list
-
Последовательность дескрипторов, которые будут унаследованы. close_fds должно быть true, если список не пуст.
Дескрипторы должны быть временно сделаны наследуемыми с помощью
os.set_handle_inheritable()при передаче в конструкторPopen, в противном случае будет поднята ошибкаOSErrorс ошибкой WindowsERROR_INVALID_PARAMETER(87).Предупреждение
В многопоточном процессе будьте осторожны, чтобы не утечь дескрипторы, помеченные как наследуемые, при сочетании этой функции с одновременными вызовами других функций создания процессов, которые наследуют все дескрипторы, такие как
os.system(). Это также относится к перенаправлению стандартных дескрипторов, которое временно создает наследуемые дескрипторы.
Введено в версии 3.7.
-
Константы Windows
Модуль subprocess экспонирует следующие константы.
-
subprocess.STD_INPUT_HANDLE -
Устройство стандартного ввода. Изначально, это буфер ввода консоли,
CONIN$.
-
subprocess.STD_OUTPUT_HANDLE -
Устройство стандартного вывода. Изначально, это буфер активного экрана консоли,
CONOUT$.
-
subprocess.STD_ERROR_HANDLE -
Устройство стандартной ошибки. Изначально, это буфер активного экрана консоли,
CONOUT$.
-
subprocess.SW_HIDE -
Скрывает окно. Будет активировано другое окно.
-
subprocess.STARTF_USESTDHANDLES -
Указывает, что атрибуты
STARTUPINFO.hStdInput,STARTUPINFO.hStdOutputиSTARTUPINFO.hStdErrorсодержат дополнительную информацию.
-
subprocess.STARTF_USESHOWWINDOW -
Указывает, что атрибут
STARTUPINFO.wShowWindowсодержит дополнительную информацию.
-
subprocess.CREATE_NEW_CONSOLE -
Новый процесс имеет новую консоль вместо наследования консоли родительского процесса (по умолчанию).
-
subprocess.CREATE_NEW_PROCESS_GROUP -
Параметр
Popenдля указания на создание новой группы процессов. Этот флаг необходим для использованияos.kill()на дочернем процессе.Этот флаг игнорируется, если указан
CREATE_NEW_CONSOLE.
-
subprocess.ABOVE_NORMAL_PRIORITY_CLASS -
Параметр
Popenдля указания того, что новый процесс будет иметь приоритет выше среднего.Добавлено в версии 3.7.
-
subprocess.BELOW_NORMAL_PRIORITY_CLASS -
Параметр
Popenдля указания того, что новый процесс будет иметь приоритет ниже среднего.Добавлено в версии 3.7.
-
subprocess.HIGH_PRIORITY_CLASS -
Параметр
Popenдля указания того, что новый процесс будет иметь высокий приоритет.Добавлено в версии 3.7.
-
subprocess.IDLE_PRIORITY_CLASS -
Параметр
Popenдля указания того, что новый процесс будет иметь приоритет низкой активности (самый низкий).Добавлено в версии 3.7.
-
subprocess.NORMAL_PRIORITY_CLASS -
Параметр
Popenдля указания того, что новый процесс будет иметь нормальный приоритет. (по умолчанию)Добавлено в версии 3.7.
-
subprocess.REALTIME_PRIORITY_CLASS -
Параметр
Popenдля указания того, что новый процесс будет иметь приоритет реального времени. Практически никогда не следует использовать REALTIME_PRIORITY_CLASS, так как это прерывает системные потоки, которые управляют вводом с мыши, вводом с клавиатуры и кэшированием фоновых дисков. Этот класс может быть уместен для приложений, которые «разговаривают» напрямую с аппаратным обеспечением или выполняют кратковременные задачи, которые должны иметь ограниченные прерывания.Добавлено в версии 3.7.
-
subprocess.CREATE_NO_WINDOW -
Параметр
Popenдля указания того, что новый процесс не будет создавать окно.Добавлено в версии 3.7.
-
subprocess.DETACHED_PROCESS -
Параметр
Popenдля указания того, что новый процесс не будет наследоваться от консоли родительского процесса. Это значение не может использоваться с CREATE_NEW_CONSOLE.Добавлено в версии 3.7.
-
subprocess.CREATE_DEFAULT_ERROR_MODE -
Параметр
Popenдля указания того, что новый процесс не наследует режим ошибок вызывающего процесса. Вместо этого новый процесс получает режим ошибок по умолчанию. Эта функция особенно полезна для многопоточных оболочечных приложений, выполняемых с отключенными жесткими ошибками.Добавлено в версии 3.7.
-
subprocess.CREATE_BREAKAWAY_FROM_JOB -
Параметр
Popenдля указания того, что новый процесс не связан с задачей.Добавлено в версии 3.7.
API более высокого уровня (старая версия)
До Python 3.5 эти три функции составляли API более высокого уровня для subprocess. Теперь в многих случаях можно использовать run(), но много существующего кода использует эти функции.
-
subprocess.call(args, *, stdin=None, stdout=None, stderr=None, shell=False, cwd=None, timeout=None, **other_popen_kwargs) -
Выполняет команду, описанную в args. Ждет завершения команды, затем возвращает атрибут
returncode.Код, которому необходимо захватить stdout или stderr, должен использовать
run()вместо этого:run(…).returncode
Для подавления stdout или stderr, укажите значение
DEVNULL.Указанные выше аргументы — лишь некоторые из общих. Полная сигнатура функции такая же, как у конструктора
Popen— эта функция передает все предоставленные аргументы, кроме timeout, непосредственно в этот интерфейс.Примечание
Не используйте
stdout=PIPEилиstderr=PIPEс этой функцией. Дочерний процесс заблокируется, если он сгенерирует достаточно вывода в канал, чтобы заполнить буфер канала ОС, так как каналы не считываются.Изменено в версии 3.3: Добавлен timeout.
-
subprocess.check_call(args, *, stdin=None, stdout=None, stderr=None, shell=False, cwd=None, timeout=None, **other_popen_kwargs) -
Выполняет команду с аргументами. Ждет завершения команды. Если код возврата был равен нулю, то возвращается, иначе генерируется
CalledProcessError. ОбъектCalledProcessErrorбудет содержать код возврата в атрибутеreturncode.Код, которому необходимо захватить stdout или stderr, должен использовать
run()вместо этого:run(…, check=True)
Для подавления stdout или stderr, укажите значение
DEVNULL.Указанные выше аргументы — лишь некоторые из общих. Полная сигнатура функции такая же, как у конструктора
Popen— эта функция передает все предоставленные аргументы, кроме timeout, непосредственно в этот интерфейс.Примечание
Не используйте
stdout=PIPEилиstderr=PIPEс этой функцией. Дочерний процесс заблокируется, если он сгенерирует достаточно вывода в канал, чтобы заполнить буфер канала ОС, так как каналы не считываются.Изменено в версии 3.3: Добавлен timeout.
-
subprocess.check_output(args, *, stdin=None, stderr=None, shell=False, cwd=None, encoding=None, errors=None, universal_newlines=None, timeout=None, text=None, **other_popen_kwargs) -
Выполнение команды с аргументами и возврат её вывода.
Если код возврата не равен нулю, генерируется исключение
CalledProcessError. ОбъектCalledProcessErrorбудет содержать код возврата в атрибутеreturncodeи любой вывод в атрибутеoutput.Это эквивалентно:
run(..., check=True, stdout=PIPE).stdout
Приведённые выше аргументы являются лишь общими примерами. Полная сигнатура функции в основном совпадает с сигнатурой
run()— большинство аргументов передаются напрямую в этот интерфейс. Однако явное указаниеinput=Noneдля наследования стандартного файла ввода родительского процесса не поддерживается.По умолчанию, эта функция возвращает данные в виде закодированных байтов. Фактическая кодировка данных вывода может зависеть от вызываемой команды, поэтому декодирование в текст часто необходимо выполнять на уровне приложения.
Это поведение можно переопределить, задав text, encoding, errors или universal_newlines в
Trueв соответствии с описанием в Часто используемые аргументы иrun().Для захвата стандартной ошибки в результате используйте
stderr=subprocess.STDOUT:>>> subprocess.check_output( ... "ls non_existent_file; exit 0", ... stderr=subprocess.STDOUT, ... shell=True) 'ls: non_existent_file: No such file or directory\n'
Введено в версии 3.1.
Изменено в версии 3.3: Добавлен параметр timeout.
Изменено в версии 3.4: Добавлена поддержка ключевого аргумента input.
Изменено в версии 3.6: Добавлены encoding и errors. Для подробностей см.
run().Введено в версии 3.7: Добавлен text в качестве более удобочитаемого псевдонима для universal_newlines.
Замена устаревших функций модулем subprocess
В данном разделе «a становится b» означает, что b можно использовать как замену для a.
Примечание
Все функции «a» в этом разделе беззвучно терпят неудачу (в той или иной степени), если исполняемая программа не может быть найдена; замещающие функции «b» вместо этого генерируют OSError.
Кроме того, заменители, использующие check_output(), завершатся с CalledProcessError, если запрошенная операция возвращает ненулевой код. Вывод всё равно доступен в качестве атрибута output сгенерированного исключения.
В следующих примерах предполагается, что соответствующие функции уже импортированы из модуля subprocess.
Замена оболочки /bin/sh обратными кавычками
output=`mycmd myarg`
становится:
output = check_output(["mycmd", "myarg"])
Замена конвейера оболочки
output=`dmesg | grep hda`
становится:
p1 = Popen(["dmesg"], stdout=PIPE) p2 = Popen(["grep", "hda"], stdin=p1.stdout, stdout=PIPE) p1.stdout.close() # Allow p1 to receive a SIGPIPE if p2 exits. output = p2.communicate()[0]
Вызов p1.stdout.close() после запуска p2 важен для того, чтобы p1 получил SIGPIPE, если p2 завершится до завершения p1.
В качестве альтернативы, для надёжного ввода, собственная поддержка конвейера оболочки по-прежнему может использоваться напрямую:
output=`dmesg | grep hda`
становится:
output=check_output("dmesg | grep hda", shell=True)
Замена os.system()
sts = os.system("mycmd" + " myarg")
# becomes
sts = call("mycmd" + " myarg", shell=True)
Примечания:
- Вызов программы через оболочку обычно не требуется.
Более реалистичный пример выглядит так:
try:
retcode = call("mycmd" + " myarg", shell=True)
if retcode < 0:
print("Child was terminated by signal", -retcode, file=sys.stderr)
else:
print("Child returned", retcode, file=sys.stderr)
except OSError as e:
print("Execution failed:", e, file=sys.stderr)
Замена семейства os.spawn
Пример P_NOWAIT:
pid = os.spawnlp(os.P_NOWAIT, "/bin/mycmd", "mycmd", "myarg") ==> pid = Popen(["/bin/mycmd", "myarg"]).pid
Пример P_WAIT:
retcode = os.spawnlp(os.P_WAIT, "/bin/mycmd", "mycmd", "myarg") ==> retcode = call(["/bin/mycmd", "myarg"])
Пример с вектором:
os.spawnvp(os.P_NOWAIT, path, args) ==> Popen([path] + args[1:])
Пример с переменными окружения:
os.spawnlpe(os.P_NOWAIT, "/bin/mycmd", "mycmd", "myarg", env)
==>
Popen(["/bin/mycmd", "myarg"], env={"PATH": "/usr/bin"})
Замена os.popen(), os.popen2(), os.popen3()
(child_stdin, child_stdout) = os.popen2(cmd, mode, bufsize)
==>
p = Popen(cmd, shell=True, bufsize=bufsize,
stdin=PIPE, stdout=PIPE, close_fds=True)
(child_stdin, child_stdout) = (p.stdin, p.stdout)
(child_stdin,
child_stdout,
child_stderr) = os.popen3(cmd, mode, bufsize)
==>
p = Popen(cmd, shell=True, bufsize=bufsize,
stdin=PIPE, stdout=PIPE, stderr=PIPE, close_fds=True)
(child_stdin,
child_stdout,
child_stderr) = (p.stdin, p.stdout, p.stderr)
(child_stdin, child_stdout_and_stderr) = os.popen4(cmd, mode, bufsize)
==>
p = Popen(cmd, shell=True, bufsize=bufsize,
stdin=PIPE, stdout=PIPE, stderr=STDOUT, close_fds=True)
(child_stdin, child_stdout_and_stderr) = (p.stdin, p.stdout)
Обработка кода возврата преобразуется следующим образом:
pipe = os.popen(cmd, 'w')
...
rc = pipe.close()
if rc is not None and rc >> 8:
print("There were some errors")
==>
process = Popen(cmd, stdin=PIPE)
...
process.stdin.close()
if process.wait() != 0:
print("There were some errors")
Замена функций из модуля popen2
Примечание
Если аргумент cmd функций popen2 является строкой, команда выполняется через /bin/sh. Если это список, команда выполняется напрямую.
(child_stdout, child_stdin) = popen2.popen2("somestring", bufsize, mode)
==>
p = Popen("somestring", shell=True, bufsize=bufsize,
stdin=PIPE, stdout=PIPE, close_fds=True)
(child_stdout, child_stdin) = (p.stdout, p.stdin)
(child_stdout, child_stdin) = popen2.popen2(["mycmd", "myarg"], bufsize, mode)
==>
p = Popen(["mycmd", "myarg"], bufsize=bufsize,
stdin=PIPE, stdout=PIPE, close_fds=True)
(child_stdout, child_stdin) = (p.stdout, p.stdin)
popen2.Popen3 и popen2.Popen4 работают в основном как subprocess.Popen, за исключением:
-
Popenгенерирует исключение при неудачном выполнении. - Аргумент capturestderr заменён на аргумент stderr.
-
stdin=PIPEиstdout=PIPEдолжны быть указаны. - popen2 по умолчанию закрывает все дескрипторы файлов, но для обеспечения этого поведения на всех платформах и в прошлых версиях Python необходимо явно указать
close_fds=TrueсPopen.
Устаревшие функции вызова оболочки
В данном модуле также представлены следующие устаревшие функции из модуля 2.x commands. Эти операции неявно вызывают системную оболочку, и никакие гарантии, описанные выше относительно безопасности и согласованности обработки исключений, для этих функций недействительны.
-
subprocess.getstatusoutput(cmd) -
Возвращает
(exitcode, output)выполнения cmd в оболочке.Выполняет строку cmd в оболочке с
Popen.check_output()и возвращает кортеж из 2 элементов(exitcode, output). Используется кодировка по умолчанию; см. примечания к Часто используемые аргументы для получения дополнительной информации.Конец строки удаляется из вывода. Код выхода команды может быть интерпретирован как код возврата подпроцесса. Пример:
>>> subprocess.getstatusoutput('ls /bin/ls') (0, '/bin/ls') >>> subprocess.getstatusoutput('cat /bin/junk') (1, 'cat: /bin/junk: No such file or directory') >>> subprocess.getstatusoutput('/bin/junk') (127, 'sh: /bin/junk: not found') >>> subprocess.getstatusoutput('/bin/kill $$') (-15, '')Доступность: POSIX & Windows.
Изменено в версии 3.3.4: Добавлена поддержка Windows.
Теперь функция возвращает (exitcode, output) вместо (status, output), как было в Python 3.3.3 и ранее. exitcode имеет то же значение, что и
returncode.
-
subprocess.getoutput(cmd) -
Возвращает вывод (stdout и stderr) выполнения cmd в оболочке.
Как
getstatusoutput(), но код выхода игнорируется, и возвращаемое значение — это строка, содержащая вывод команды. Пример:>>> subprocess.getoutput('ls /bin/ls') '/bin/ls'Доступность: POSIX & Windows.
Изменено в версии 3.3.4: Добавлена поддержка Windows
Примечания
Преобразование последовательности аргументов в строку в Windows
В Windows последовательность args преобразуется в строку, которую можно разобрать по следующим правилам (они соответствуют правилам, используемым MS C runtime):
- Аргументы разделяются пробелами, которые могут быть пробелами или табуляциями.
- Строка, заключённая в двойные кавычки, интерпретируется как один аргумент независимо от содержащихся в ней пробелов. В строке в кавычках могут быть вложены другие строки в кавычках.
- Двойная кавычка, предшествующая обратной косой чертой, интерпретируется как двойная кавычка в прямом виде.
- Обратные косые черты интерпретируются буквально, за исключением случаев, когда они непосредственно предшествуют двойной кавычке.
- Если обратные косые черты непосредственно предшествуют двойной кавычке, каждая пара обратных косых черт интерпретируется как обратная косая черта в прямом виде. Если количество обратных косых черт нечётное, последняя обратная косая черта экранирует следующую двойную кавычку, как описано в правиле 3.
См. также
-
shlex -
Модуль, предоставляющий функции для разбора и экранирования командных строк.
© 2001–2020 Python Software Foundation
Licensed under the PSF License.
https://docs.python.org/3.7/library/subprocess.html