Как получить вывод из subprocess.call() в Python: решение
Быстрый ответ
Если вам необходимо выполнить захват вывода команды, рекомендую использовать функцию subprocess.run()
с указанным параметром capture_output=True
. Пример использования функции представлен ниже:
import subprocess
result = subprocess.run(['ls', '-l'], capture_output=True, text=True)
output = result.stdout # Здесь сохраняется вывод команды
error = result.stderr # Здесь сохраняются ошибки, если таковые имеются
В результате выполнения данного кода вывод команды будет сохранён в переменной output
, а возникшие ошибки – в error
.
Детальное изучение: понимание и поиск альтернатив
Выбор подходящей функции для задачи
Есть множество инструментов, подходящих для выполнения различных задач. Хотя subprocess.run()
может быть универсальным решением, для определенных задач эффективней оказывается использование subprocess.Popen()
с указанным аргументом stdout=subprocess.PIPE
. Ваш выбор должен зависеть от сложности выполняемой задачи и используемой версии Python.
import subprocess
with subprocess.Popen(['ls', '-l'], stdout=subprocess.PIPE, text=True) as proc:
output, _ = proc.communicate() # Процесс захватывает вывод
Выявление ошибок
Ошибки – это неотъемлемая часть программирования, которую невозможно игнорировать. Если вы указываете вместе stderr=subprocess.PIPE
и stdout
, то в таком случае Python будет выявлять ошибки вместе с отслеживанием вывода.
result = subprocess.run(['ls', '-la'], stdout=subprocess.PIPE, stderr=subprocess.PIPE, text=True)
print(f"Вывод: {result.stdout}")
print(f"Ошибка: {result.stderr if result.stderr else 'Ошибок нет.'}")
Обозначение команд: универсальность важнее, чем эсперанто
Разные системы предполагают разные подходы к выполнению задач, и здесь может пригодиться shlex.split()
, позволяющий корректно обрабатывать командные строки для разных платформ.
import shlex, subprocess
command = shlex.split("ls -la")
result = subprocess.run(command, stdout=subprocess.PIPE, stderr=subprocess.PIPE, text=True)
print(result.stdout)
Декодирование вывода
Иногда вывод команды напоминает закодированное послание, в то время как вашему приложению требуется работать с обычным текстом. Применение text=True
позволяет декодировать вывод в понятный строковый формат, в противном случае придется разбираться с набором байтов.
Правильный выбор инструмента
Важно внимательно смотреть при выборе подходящих инструментов! subprocess.call()
улавливает статус выполнения процесса как археолог – артефакты, тогда как subprocess.run()
и subprocess.check_output()
подробно фиксируют информацию о выводе.
Визуализация
Можно представить работу subprocess.call()
как трубу в водопроводе (🚰), где вода – это процесс.
subprocess.call(args, ...)
|
| (вывод)
V
Ведро (🪣)
Здесь ведро (🪣) собирает статус выполнения.
В отличие от ведра, текстовый вывод (🗨️) лучше собирать с помощью более впитывающего объекта:
subprocess.check_output(args, ...)
|
| (текстовый вывод 🗨️)
V
Губка (🧽)
Губка (🧽) поглощает текстовый вывод с помощью subprocess.check_output()
.
Хитрости, советы и решения, вызывающие восклицания "Ааа, вот так!"
Подготовка ко всем сценариям
Ошибки случаются, и Python предусматривает такие случаи. Для защиты от возможных проблем вы можете использовать subprocess.CalledProcessError
, что обеспечит надежную обработку исключений.
try:
output = subprocess.check_output(['false_command'], stderr=subprocess.STDOUT)
except subprocess.CalledProcessError as e:
print(f"Произошла ошибка: {e.output}")
Разъяснение недоразумений
Попытка использования StringIO
с subprocess.call()
для захвата вывода является бессмысленной и не приводит к успеху.
Быстрота и чистота
Старайтесь избегать создания лишних временных файлов при работе с выводом. Вместо этого используйте трубы (pipes) в сочетании с Popen()
и communicate()
, чтобы ваш код оставался аккуратным и работал эффективно.
Эволюция Python
Не забывайте, что subprocess.run()
доступна начиная с Python 3.5. В более ранних версиях используйте проверенный Popen()
или более лаконичный check_output()
.
Полезные материалы
- subprocess — Управление подпроцессами — Документация Python 3.12.2 — официальная документация Python по управлению подпроцессами.
- python – Сохранение вывода вызова subprocess.Popen в строке – Stack Overflow — обсуждение вопросов сохранения вывода
subprocess.Popen
в строке. - Применение модуля subprocess для работы с подпроцессами в Python – Real Python — глубокий урок по модулю subprocess.
- subprocess — Запуск внешних процессов — PyMOTW 3 — статья с примерами работы с подпроцессами в Python.
- Выполнение команд оболочки из Python — гид по выполнению команд оболочки средствами Python.
- Объяснение модуля subprocess в Python – GeeksforGeeks — разъяснение модуля subprocess на сайте GeeksforGeeks.
- Урок Python: Запуск внешних команд при помощи модуля Subprocess – YouTube — видеоурок о работе с модулем subprocess от Corey Schafer.