3

So - the good folks in the ROOT community made the following magic:

# This is for intercepting the output of ROOT
# In a cell, put %%rootprint so that the output that would normally be
# sent directly to the stdout will instead be displayed in the cell.
# It must be the first element in the cell.
import tempfile
import ROOT
from IPython.core.magic import (Magics, magics_class, cell_magic)

@magics_class
class RootMagics(Magics):
    """Magics related to Root.

    %%rootprint  - Capture Root stdout output and show in result cell
    """

    def __init__(self, shell):
        super(RootMagics, self).__init__(shell)

    @cell_magic
    def rootprint(self, line, cell):
        """Capture Root stdout output and print in ipython notebook."""

        with tempfile.NamedTemporaryFile() as tmpFile:

            ROOT.gSystem.RedirectOutput(tmpFile.name, "w")
            # ns = {}
            # exec cell in self.shell.user_ns, ns
            exec cell in self.shell.user_ns
            ROOT.gROOT.ProcessLine("gSystem->RedirectOutput(0);")
            print tmpFile.read()

# Register
ip = get_ipython()
ip.register_magics(RootMagics)

This works great if I do ye olde import rootprint in a cell in my IPython notebook - no complaints and it all works as expected. But, now I want to import this and do some stuff in a python file in ~/.ipython/profile/startup - python files in that directory apparently get run first thing when IPython starts, allowing access to whatever you defined therein. If I just do something simple (that does not import rootprint), everything works exactly as expected - I can make a function in the startup script and use it later at will. But when I try to import rootprint in the startup script and then start IPython (just IPython, not the notebook for now), it flips out with the complaint:

---------------------------------------------------------------------------
NameError                                 Traceback (most recent call last)
/usr/lib/python2.6/site-packages/ipython-1.1.0-py2.6.egg/IPython/utils/py3compat.pyc in execfile(fname, *where)
    202             else:
    203                 filename = fname
--> 204             __builtin__.execfile(filename, *where)

/home/wjmills/.ipython/profile_nbserver/startup/dummy.py in <module>()
      2 import ROOT
      3 from ROOT import gROOT, TCanvas, TF1, TFile, TTree, gRandom, TH1F
----> 4 import numpy, rootprint
      5 
      6 def foo():

/home/wjmills/.ipython/profile_nbserver/startup/rootprint.py in <module>()
     31 
     32 # Register
---> 33 ip = get_ipython()
     34 ip.register_magics(RootMagics)

NameError: name 'get_ipython' is not defined

What happens to get_ipython in the context of a python script run on startup from profile/startup? Again, this all works perfectly if I do it interactively from an IPython notebook, so it seems to be something extra-special about the startup procedure. Thanks in advance!

2 Answers 2

5

This is an incomplete suggestion -- but if get_ipython isn't in the namespace yet, you can try importing it directly:

from IPython import get_ipython
ipython_shell = get_ipython()

Also, ipython has different behavior when importing .py files vs .ipy files. You might try saving rootprint as an .ipy file.

I am not sure i would classify that as a solution if it works, but it may point you in the right direction.

Sign up to request clarification or add additional context in comments.

Comments

0

I think the preferred way to register your magics is

def load_ipython_extension(ip):
    """Load the extension in IPython."""
    ip.register_magics(RootMagics)

Comments

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service and acknowledge you have read our privacy policy.

Start asking to get answers

Find the answer to your question by asking.

Ask question

Explore related questions

See similar questions with these tags.