Текст терминала становится невидимым после завершения подпроцесса

После завершения подпроцесса ffmpeg, терминал становится испорченным - введенные символы невидимы! Вход по-прежнему работает в том, что команды могут быть выполнены, но ввод клавиатуры не отражается на терминале.

Выдача команды оболочки reset возвращает все в норму (или !reset изнутри ipython), поэтому обходной путь, который вызывает проблема, вызывает os.system('reset') внутри script.

Другие вещи, которые я пробовал: import curses; curses.initscr() до появления подпроцесса и curses.endwin() после завершения, что несколько сработало, но сломало другие вещи. Другая, возможно, связанная с этим проблема заключается в том, что после нереста дочернего процесса интерактивный терминал становится лаггированным и иногда не может отображать типизированные символы.

Код для запуска процесса выглядит следующим образом:

with open('/tmp/stdout.log', 'w') as o:
    with open('/tmp/stderr.log', 'w') as e:
        proc = subprocess.Popen([args], stdout=o, stderr=e)

И позже, чтобы остановить его:

proc.terminate()
proc.communicate()

Что здесь может быть не так?

Ответы

Ответ 1

Измените script так, чтобы proc.terminate() не использовался. Вы можете приостановить подпроцесс ffmpeg более вежливо с помощью

  proc.send_signal(signal.SIGINT)
  proc.wait()

Это позволяет ffmpeg возможность записывать любые escape-последовательности, необходимые для восстановления терминала.


edit: обнаружено позже - еще один совет, чтобы сделать ffmpeg лучше с Popen, чтобы предоставить ему subprocess.PIPE или open(os.devnull) в дескрипторе stdin. В противном случае, похоже, он пытается получить вход от родительского stdin, который может вызвать странное поведение терминала. Выполняющий ffmpeg процесс прослушивает '?' и "q" на stdin.

Ответ 2

Вы связываетесь с подпроцессом? в этом случае я бы использовал pexpect, который делает этот тип настройки очень простым, возможно, вам нужно дождаться завершения команды? то есть.

 p = subprocess.Popen(argv, stdout=o, stderr=e)
 p.wait()
 if p.returncode != 0:
      print("problems")

что я использую на dvd2h264 script, я написал некоторое время назад, у меня никогда не было никаких проблем, но я не перенаправляю stdin/stderr в tmpfiles..

Ответ 3

os.system('stty sane') работал у меня. Это reset настройки, делающие эхо невидимым.