#python #cmd
Помогите разобраться с перенаправлением вывода cmd в переменную, т.к. переменной присваивается только exit_code процесса. Для наглядности есть пара примеров: Пример import sys, os command = "tasklist" result1 = os.system(command) print(result1) # на выходе получим 0 Пример 2 command = "tasklist>temp.txt" result2 = os.system(command) print(result2) # на выходе получим 0 with open('temp.txt', 'r') as f: result2 = f.read() print(result2) # выведет результат выполнения tasklist Вопрос: можно ли перенаправить вывод терминала windows не используя temp.txt файл, тобиш сразу выгружать значение в переменную.? sys.stdout пробовал. sys.stdout = open('temp.txt', 'w') #запишет 0 в файлик os.system('tasklist') #сам резульат выполнения будет выведен в интеретаторе file = open('temp.txt', 'r').read() print(file)# выведет 0
Ответы
Ответ 1
subprocess.check_output() — это самый простой способ получить вывод внешней команды: import subprocess output = subprocess.check_output(['программа', 'аргумент 1', '2']) Всё что программа выводит в стандартный вывод, сохраняется в output. Если программа завершится с ненулевым статусом возврата (как правило на ошибку указывает), то check_output() выбросит исключение (не следует неявно ошибки игнорировать). Начиная с простого случая существует множество вариаций. К примеру, чтобы получить объединённый вывод как из стандартного потока команды (stdout) так и из потока ошибок (stderr), можно передать stderr=subprocess.STDOUT параметр в check_output(). Дочерний процесс может вообще напрямую в терминал писать в обход своих stdout/stderr, в этом случае на POSIX системах можно pty создать, чтобы перехватить вывод (в таких случаях удобно pexpect модуль использовать). По умолчанию вывод возвращается в виде байт, чтобы получить текст необходимо указать кодировку символов, которая может зависеть от выбранной команды: text = subprocess.check_output(['программа', 'аргумент 1', '2'], encoding=encoding) Подробнее см. Byte при печати вывода внешней команды. Стоит упомянуть, что в отличии от старых интерфейсов, унаследованных из Си (таких как system(), popen()), функции в subprocess модуле никогда не запускают командную оболочку, если явно об этом не попросить. Что позволяет избежать shell injection и делает вызов более переносимым (если сама программа переносима).Ответ 2
Самый простой способ перенаправить вывод из системной оболочки - это подключиться к каналу команды, вот таким образом: import os command = 'dir' pipe = os.popen(command) print(pipe.read()) Здесь мы открыли канал и получили объект открытого файла из которого можно читать или писать в него в зависимости от режима (r по умолчанию) открытия, используя стандартный интерфейс работы с файлами.Ответ 3
При накоплении целой кучи батников, для записи разных стримов, пришла в голову идея, автоматизировать процесс контроля за работой этих батников. Скрипт, который будет контролировать запуск и перезапуск в случае краша, мониторинг работоспособности, добавления новых стримов и оповещать в случае изменений, либо ошибок в любом из батников. Теперь собственно для чего был задан вопрос. ffmpeg иногда ругается на прямые ссылки на стримы, поэтому предварительно их нужно обрабатывать с помощью youtube-dl. Можно конечно писать все стримы youtube-dl, а потом разбивать готовые файлы на части, но они будут недоступны для просмотра во время записи. # _*_coding: utf-8 _*_ import os, time, subprocess, re from mylib import get_current_date_time, get_file_name, send_mail from config import EXIT_CODES, STREAMS_LIST BASE_DIR = os.path.dirname(os.path.abspath(__file__)) FFMPEG_PATH = os.path.join(BASE_DIR, 'ffmpeg\\bin', 'ffmpeg.exe') YOUTDL_PATH = os.path.join(BASE_DIR, 'youtube-dl', 'youtube-dl.exe') DEST_DIR = r'D:\test_dir' if __name__ =='__main__': video_link = 'https://www.youtube.com/watch?v=GiBK0z6Zdf4' dirty_link= subprocess.check_output('{0} -f "bestvideo[height<=480]+bestaudio/best[height<=480]" -i "{1}" -g'.format(YOUTDL_PATH, video_link)) flink_compr = re.compile(r'http.*\\n') FILE_NAME = get_file_name() out_file = os.path.join(DEST_DIR, FILE_NAME) dl_link = link_pattern.findall(str(dirty_link))[0].rstrip() command = '{0} -i "{1}" -c:v copy -vsync 1 -acodec mp2 -ac 2 -ab 128k -ar 44100 "{2}.ts"'.format(FFMPEG_PATH, dl_link, out_file) os.system(command) UPD. Это кусочек тестового примера, через subprocess. Пример с os.popen, также работает. Но я решил уйти от батников, буду пытаться запустить несколько потоков. Удачи мне, вам всем огромнейшая благодарность )))
Комментариев нет:
Отправить комментарий