Subprocess module: running an interactive shell

Joe Tyson joe at routespot.com
Sun Mar 15 08:09:06 CET 2009


On 2009-03-14 20:10:29 -0400, Karthik Gurusamy <kar1107 at gmail.com> said:

> On Mar 14, 3:03 am, Roman Medina-Heigl Hernandez <ro... at rs-labs.com>
> wrote:
>> Karthik Gurusamy escribió:
>> 
>> 
>> 
>>> On Mar 13, 6:39 pm, Roman Medina-Heigl Hernandez <ro... at rs-labs.com>
>>> wrote:
>>>> Hi,
>> 
>>>> I'm experimenting with Python and I need a little help with this. What
>  I'd
>>>> like is to launch an interactive shell, having the chance to send firs
> t
>>>> several commands from python. I've written the following code:
>> 
>>>> ============
>> 
>>>> #!/usr/bin/env python
>> 
>>>> import sys, subprocess
>> 
>>>> exe = "/bin/sh"
>>>> params = "-i"
>> 
>>> -i says shell to be interactive. So looks like it is directly trying
>>> to read from the terminal.
>> 
>> Well, then the question will be: is there any way to tell python to
>> directly "map" the terminal to the subprocess?
> 
> pexpect seems to be the solution for such problems :). [other
> applications include ssh which asks for password from terminal (not
> ssh's stdin)]
> 
> http://pexpect.sourceforge.net/pexpect.html
> 
>> 
>>>> proc = subprocess.Popen([exe, params], stdin=subprocess.PIPE)
>> 
>>> proc = subprocess.Popen([exe,], stdin=subprocess.PIPE)
>> 
>>> works for me; but if there is an error 'sh' terminates.
>> 
>>> If you want to simulate interactive, explore the pexpect module.
>> 
>> I'll get it a try :)))
>> 
>>>> proc.stdin.write("id\n")
>> 
>>>> while True:
>>>>         line = sys.stdin.readline()
>>>>         if not line:
>> 
>>> note that a simple enter terminates the shell which you may not want.
>> 
>> Test my code and you'll see that this is not true :) When you hit enter
>> line will contain '\n' so it's not empty.
> 
> You are right. I thought readline() strips the trailing \n (It doesn't
> and shouldn't as it's necessary for the case a file ends without a
> newline).
> 
>> 
>>>>                 break
>>>>         proc.stdin.write(line)
>> 
>> Btw, another curiosity I have: is it possible to make a print not
>> automatically add \n (which is the normal case) neither " " (which happen
> s
>> when you add a "," to the print sentence)?  I found an alternative not
>> using print at all, eg: sys.stdout.write("KKKKK"). But it resulted strang
> e
>> to me having to do that trick :)
> 
> I am also aware of only the sys.stdout.write solution.
> 
> python3.0 has a way to do it.
> 
>>>> help(print)
> Help on built-in function print in module builtins:
> 
> print(...)
>     print(value, ..., sep=' ', end='\n', file=sys.stdout)
> 
>     Prints the values to a stream, or to sys.stdout by default.
>     Optional keyword arguments:
>     file: a file-like object (stream); defaults to the current
> sys.stdout.
>     sep:  string inserted between values, default a space.
>     end:  string appended after the last value, default a newline.
> 
>>>> print('hello', end='')
> hello>>>
> 
> Karthik
> 
>> 
>> Thank you for all your comments and comprenhension.
>> 
>> -r
>> 
>> 
>> 
>>>> sys.exit()
>> 
>>>> ============
>> 
>>>> The problem is that when I launch it, python proggy is automatically
>>>> suspended. The output I got is:
>> 
>>>> roman at rslabs:~/pruebas$ ./shell.py
>>>> roman at rslabs:~/pruebas$ uid=1000(roman) gid=1000(roman) groups=1
> 000(roman)
>>>> roman at rslabs:~/pruebas$
>> 
>>>> [2]+  Stopped                 ./shell.py
>>>> roman at rslabs:~/pruebas$
>> 
>>>> Why and how to fix it? Would you suggest a better and more elegant way
>  to
>>>> do what I want?
>> 
>>> As I see it, 'sh' is attempting to read from the keyboard and not from
>>> stdin.
>> 
>>> Karthik
>> 
>>>> Thank you.
>> 
>>>> --
>> 
>>>> Saludos,
>>>> -Roman
>> 
>>>> PGP Fingerprint:
>>>> 09BB EFCD 21ED 4E79 25FB  29E1 E47F 8A7D EAD5 6742
>>>> [Key ID: 0xEAD56742. Available at KeyServ]
>> 
>>> --
>>> http://mail.python.org/mailman/listinfo/python-list
>> 
>> --
>> 
>> Saludos,
>> -Roman
>> 
>> PGP Fingerprint:
>> 09BB EFCD 21ED 4E79 25FB  29E1 E47F 8A7D EAD5 6742
>> [Key ID: 0xEAD56742. Available at KeyServ]

There is quite a bit involved in handling this. Check out this recipe 
on activestate:
http://code.activestate.com/recipes/278731/

- Joe




More information about the Python-list mailing list