Субпроцесс Python с каналами и большими файлами - PullRequest
7 голосов
/ 01 марта 2010

Я пытаюсь использовать python + ffmpeg + oggenc для преобразования любого аудиофайла в ogg. Программа работает, почти. Но для больших файлов (я думаю> 6 МБ) процесс ffmpeg начинает спать в pipe_wait. Я не знаю, какую трубу он ждет.

Если я уничтожу процесс ffmpeg, процесс oggenc продолжится, и я получу в результате ogg-файл с ~ 2: 40 всего звука.

#!/usr/bin/env python
# -*- coding: utf-8 -*-

from subprocess import Popen, PIPE
from sys import argv

ffmpeg = Popen([
    "ffmpeg",
    "-i", argv[1],
    "-vcodec", "null",
    "-acodec", "pcm_s16le",
    "-ac", "2",
    "-ab", "44100",
    "-f", "wav",
    "-"
],stdout = PIPE,stderr = PIPE)

oggenc = Popen([
    "oggenc",
    "-", "--raw",
    "-q", "4",
    "-o", argv[2]
],stdin = ffmpeg.stdout,stderr = PIPE)

oggenc.communicate()
ffmpeg.communicate()

EDIT:

Я мог бы добавить, что это прекрасно работает:

#!/bin/bash

ffmpeg -i "$1" -vcodec null -acodec pcm_s16le -ac 2 -ab 44100 -f wav - | oggenc - --raw -q 4 -o "$2"

Ответы [ 2 ]

5 голосов
/ 02 марта 2010

Что именно вы делаете с stderr каналами двух каналов?

Кодеры / декодеры обычно выдают много выводов stderr, как обновления состояния;этот вывод передается в ваш процесс, и буферы заполнятся.Возможно, вам следует добавить несколько фиктивных вызовов ffmpeg.stderr.read() перед (бесполезными, я думаю) .communicate вызовами или, что еще лучше, полностью отбросить аргументы stderr=PIPE.

ОБНОВЛЕНИЕ

Для>/dev/null эквивалент, выполните следующие действия:

nulfp = open(os.devnull, "w")
…
… = subprocess.Popen(…, stderr=nulfp.fileno())

Очевидно, что вы можете повторно использовать тот же nulfp для всех stderr с, которые хотите игнорировать.

0 голосов
/ 01 марта 2010

Сложно увидеть, кому нужно пройти по каналу, то есть я имею в виду, что вы должны использовать отладчик, подобный NetBeans, чтобы помочь собрать больше подсказок. Трубы могут быть не лучшим подходом, возможно, использование временного файла упростит вещи.

Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...