[IPython-dev] updating an IPython application to work with 0.11

MinRK benjaminrk at gmail.com
Wed Jul 20 12:40:41 EDT 2011


Forwarding off-list discussion of updating an IPython application to
work with 0.11, since it could be useful to others.


---------- Forwarded message ----------
From: Hugo Gagnon <hugo.gagnon at fastmail.fm>
Date: Tue, Jul 19, 2011 at 12:24
Subject: Re: Embedding IPython 0.11 in a GUI
To: MinRK <benjaminrk at gmail.com>


That worked like a charm! There's one thing left (really) which I just
noticed: right after instantiating TerminalInteractiveShell I turned
off colouring:

IP.magic('colors NoColor')

which works fine for prompts etc. except sometimes for the header of
an object info. For example say I do "a=1" then querying "a?" may
print:

[0;31mType:             [0mint
[0;31mBase class:  [0m<type 'int'>
...

I say sometimes because at first the nocolor command works but after a
while (I would say right after the first command) it turns on again
(again, just for the info headers though). I'm not sure as to what
triggers that change. Then if I manually reset nocolor inside my GUI
it seems to remain in effect indefinitely. Bleh, I don't know if I'm
making sense at all!
--
 Hugo Gagnon



On 2011-07-19, at 2:17 PM, MinRK wrote:

> On Tue, Jul 19, 2011 at 11:10, Hugo Gagnon <hugo.gagnon at fastmail.fm> wrote:
>> Yep, this works. By the way is it possible that io.stdout and io.stderr are sometimes flushed? For example I noticed that when I use IP.complete (or maybe it is something else) they may get redirected to the terminal. I used to use
>
> No, they never get redirected to the terminal.  They are hooked up to
> sys.stdout/err when an InteractiveShell is instantiated, and any
> changes you make after that will last.  They are module-level now,
> since the Term object didn't actually do anything except contain the
> two objects, but the module itself does that just as well.
>
> It's possible there are some methods that (possibly incorrectly) hook
> themselves up directly to sys.stdout, in which case io.stdout would be
> ignored.
>
> An easier way to ensure everything goes to the right place is to
> redirect sys.stdout itself before instantiating the InteractiveShell.
> Then anything you still want to print to the terminal should use
> sys.__stdout__, or io.raw_print.
>
>>
>> self.cout = StringIO.StringIO()
>> IPython.genutils.Term.cout = self.out
>> IPython.genutils.Term.cerr = self.out
>>
>> which set them for good, but the variable Term is now gone...
>> --
>>  Hugo Gagnon
>>
>>
>>
>> On 2011-07-19, at 12:32 PM, MinRK wrote:
>>
>>> On Tue, Jul 19, 2011 at 09:17, Hugo Gagnon <hugo.gagnon at fastmail.fm> wrote:
>>>> You're right all the tools are in that interact method, and it works!
>>>>
>>>> Although FYI I had to use TerminalInteractiveShell since it has the raw_input method.
>>>>
>>>> One last thing: I redirect stdout and stderr to my own file object likewise:
>>>>
>>>> self.out = StringIO.StringIO()
>>>> IPython.utils.io.stdout = IPython.utils.io.IOStream(self.out)
>>>> IPython.utils.io.stderr = IPython.utils.io.IOStream(self.out)
>>>>
>>>> which again works fine, except for e.g. "ls", where then the output appears in the terminal running my GUI.
>>>
>>> The TerminalInteractiveShell uses os.system to launch subprocesses,
>>> which hook up directly to stdin/stdout (not sys.stdin/stdout which can
>>> change).  This is necessary to allow thing like launching subprocesses
>>> that expect input.
>>> To hook up stdout to your io.stdout, you should just need to do:
>>>
>>> IP.system = IP.system_piped
>>>
>>>>
>>>> I remember writing my own "shell_hook" in 0.10 but that hook seems to have disappeared in 0.11. Any idea?
>>>>
>>>> I am already extremely grateful for your help, and I would understand if you couldn't reply to this email,
>>>>
>>>> Cheers,
>>>> --
>>>>  Hugo Gagnon
>>>>
>>>>
>>>>
>>>> On 2011-07-19, at 3:09 AM, MinRK wrote:
>>>>
>>>>> I've been swamped with cutting the release, but I will have a look.
>>>>>
>>>>> -MinRK
>>>>>
>>>>> On Jul 18, 2011, at 17:04, "Hugo Gagnon"
>>>>> <sourcefoge.ipython at user.fastmail.fm> wrote:
>>>>>
>>>>>> Hello,
>>>>>>
>>>>>> I am sorry to personally disturb you about this issue but I haven't been
>>>>>> able to fix it myself and I really need an expert on the subject... or
>>>>>> perhaps you would like to redirect me to someone else?
>>>>>>
>>>>>> As of 0.10 I could embed an IPython shell in my GUI and everything ran
>>>>>> smoothly. What I need is actually fairly simple but unfortunately I am
>>>>>> quite at a loss in the API :(
>>>>>>
>>>>>> 1) IP = IPython.Shell.make_IPython(argv=[], user_ns=user_ns,
>>>>>> user_global_ns=user_global_ns, embedded=True,
>>>>>> shell_class=IPython.Shell.InteractiveShell)
>>>>>
>>>>> This will be:
>>>>> from IPython import InteractiveShell
>>>>>
>>>>> shell = InteractiveShell(user_ns=user_ns, user_global_ns=user_global_ns)
>>>>>
>>>>>>
>>>>>> 2) Then whenever I had a command to process I invoked:
>>>>>>
>>>>>> line = IP.raw_input(continue_prompt=iter_more)
>>>>>>
>>>>>> where raw_input was my own function returning whatever was at the prompt
>>>>>> and iter_more initially set to 0.
>>>>>>
>>>>>
>>>>> If this is your own function, then I don't know what would change. The
>>>>> raw_input method on the current InteractiveShell takes a string (the
>>>>> prompt), not a bool, though.
>>>>>
>>>>>> 3) This was followed by:
>>>>>>
>>>>>> iter_more = IP.push(line)
>>>>>> if iter_more:
>>>>>>   prompt = str(IP.outputcache.prompt2)
>>>>>> else:
>>>>>>   prompt = str(IP.outputcache.prompt1)
>>>>>> to_out = out.getvalue().strip()
>>>>>
>>>>> See the last block in TerminalInteractiveShell.interact, here:
>>>>> https://github.com/ipython/ipython/blob/master/IPython/frontend/terminal/interactiveshell.py#L258
>>>>>
>>>>> So it would be something like:
>>>>>
>>>>> prompt = IP.hooks.generate_prompt(more)
>>>>>
>>>>> IP.input_splitter.push(line)
>>>>> more = IP.input_splitter.push_accepts_more()
>>>>> if not more:
>>>>>    source_raw = IP.input_splitter.source_raw_reset()[1]
>>>>>    IP.run_cell(source_raw)
>>>>>
>>>>>
>>>>> I hope that helps.  I haven't actually worked much at all on the
>>>>> InteractiveShell, so this is mostly new to me.
>>>>>
>>>>> -MinRK
>>>>>
>>>>>>
>>>>>> where prompt is the (possibly) new prompt, out is a file-like object and
>>>>>> to_out is what I would output in my GUI.
>>>>>>
>>>>>> I would greatly appreciate if you could give me some pointers to
>>>>>> replicate the 3 steps above. I am using the EPD distro which is
>>>>>> currently on 0.11.rc1. I tried a few things myself but somehow I cannot
>>>>>> seem to find the output caching system anymore, for example.
>>>>>>
>>>>>> Kind regards,
>>>>>> --
>>>>>> Hugo Gagnon
>>>>
>>>>
>>
>>



More information about the IPython-dev mailing list