0

I would like be able to reroute the stdin of my program to a StringIO() object so that I can simulate user response to an input statement.

newstdin = StringIO()
sys.stdin = newstdin
newstdin.write("hey")
newstdin.seek(0)

response = input()
print(response)

My code works when a response is already in the StringIO() object however if there isn't anything, it immediately raises a EOF error instead of waiting for a response like it would if set to the normal sys.stdin. How can I do this so that the input() statement waits for a response to be written to the StringIO() object (this will be done in a separate thread). Thanks!

TheFluffDragon9
  • 514
  • 5
  • 11
  • Instead of messing with fds, can't you extract the `response = input()` part and instead do `response = your_fixture()`? I.e. factoring away `input()` when you're testing (if that's what you're doing). – chelmertz Apr 29 '20 at 21:27
  • Sorry, should probably have mentioned this in the question; I am currently working on a IDE and want to be able to run code and have the output inserted into a Tkinter textbox. I have the code set up to insert the stdout of what is being run, but I also want to allow users to put input() statements into their code and type the input into a Tkinter Entry widget. – TheFluffDragon9 Apr 30 '20 at 08:12

1 Answers1

0

If anyone is interested, the way I have decided to do it is with this:

accinput = input

def input(prompt=None):
    if prompt:
        print(prompt)
    while True:
        try:
            return accinput()
        except EOFError:
            pass

You can store the real functionality of input in accinput the redefine input to continuously retry to read input from the stdin stringIO() until it doesn't meet an EOFError.

TheFluffDragon9
  • 514
  • 5
  • 11