Передайте стандартный ввод подпроцесса в стандартный родительский процесс для пользовательской отладки Python - PullRequest
0 голосов
/ 29 ноября 2018

Я пытаюсь написать функцию python, которая позволит мне легко отлаживать произвольный код в подпроцессе

Идея состоит в том, чтобы завершить один вызов функции

def subProcessDebug(functionToDebug)

и когда это вызывается, открывается новое окно терминала, которое будет передавать любые команды, переданные ему, в стандартный поток родительского процесса, а любые выходные данные родительского процесса - в стандартный вывод подпроцесса.Поскольку я разрешаю запуск произвольного кода, я не могу использовать функцию связи или аналогичные функции подпроцесса.Он должен быть напрямую передан в stdin и обработан как обычный ввод родительским процессом

Для этого нужны два моих файла:

Сервер отладки

import pdb
import subprocess
import sys


def subProcessDebug(functionToDebug):
    server = DebugServer()
    server.run(functionToDebug)

class DebugServer:
    def run(self, functionToDebug):
        p = subprocess.Popen(args=["gnome-terminal", "--command=python DebugClient.py"], stdout=subprocess.PIPE, stdin=subprocess.PIPE)

        savedIn = sys.stdin
        savedOut = sys.stdout

        sys.stdin = p.stdin
        sys.stdout = p.stdout

        # Debug the function
        pdb.set_trace()
        functionToDebug()

        # Reset to old stdin/stdout    
        sys.stdin = savedIn
        sys.stdout = savedOut

и DebugClient

class DebugClient:
    def run(self):
        while True:
            command = input(">>>")



client = DebugClient()
client.run()

и пример, вызывающий это, будет

    from DebugServer import subProcessDebug
    import time

    def exampleDebugFunction():
        import time
        counter = 0
        while True:
            counter += 1
            time.sleep(1)


    subProcessDebug(exampleDebugFunction)

Это все работает нормально, пока не произойдет вызов чтения или записи в любом месте после изменения stdin или stdout родительского процесса, который является своего роданеобходимо при использовании pdb

Точная обратная трассировка

  File "<home_path>/SubProcessDebug/DebugServer.py", line 22, in run
    functionToDebug()
  File "/usr/lib/python3.6/bdb.py", line 51, in trace_dispatch
    return self.dispatch_line(frame)
  File "/usr/lib/python3.6/bdb.py", line 69, in dispatch_line
    self.user_line(frame)
  File "/usr/lib/python3.6/pdb.py", line 261, in user_line
    self.interaction(frame, None)
  File "/usr/lib/python3.6/pdb.py", line 351, in interaction
    self.print_stack_entry(self.stack[self.curindex])
  File "/usr/lib/python3.6/pdb.py", line 1453, in print_stack_entry
    self.format_stack_entry(frame_lineno, prompt_prefix))
  File "/usr/lib/python3.6/pdb.py", line 453, in message
    print(msg, file=self.stdout)
 io.UnsupportedOperation: write
...