3

I have a jupyter/ipython notebook that I am using for prototyping and tutoring.

I export it as a python script using the menu dropdown or nbconvert, i.e.

ipython nbconvert --to python notebook.ipynb

However, I would like to make notebook.py executable directly without having to hack it by hand each time, in order that I can keep updating notebook.ipynb and overwriting notebook.py with my changes. I also want to include command-line arguments in notebook.py. My boilerplate is, for example:

#!/usr/bin/env ipython
import sys
x=sys.argv[-1]

with chmod +x notebook.py of course.

One route could be to make these lines (be they python or command-line directives) ignorable in the jupyter/ipython notebook - is there a way to do this by e.g. detecting the jupyter/ipython environment?

Edit1: This is tantamount to saying:

How can I include lines in the notebook.ipynb that will be ignored in the notebook environment but parsed in notebook.py generated from it?

Edit2: This question is a partial answer, but doesn't tell me how to include the #!/usr/bin/env ipython line: How can I check if code is executed in the IPython notebook?

Edit3: Could be useful, but only if %%bash /usr/bin/env ipython would work - would it..? How do I provide inline input to an IPython (notebook) shell command?

Edit4: Another attempted answer (subtle): Since # is a comment in python, putting #!/usr/bin/env ipython in the first cell of the notebook means that it will be ignored in jupyter/ipython, but respected in the exported notebook.py. However, the #! directive is not at the top, but can easily be chopped off:

> more notebook.py 

# coding: utf-8

# In[1]:

#!/usr/bin/env ipython


# In[2]:

print 'Hello'


# In[ ]:
jtlz2
  • 7,700
  • 9
  • 64
  • 114
  • When you say directly, what method or portal are you referring to? Do you mean from the Jupyter notebook? – Landmaster Aug 10 '17 at 05:24
  • On the *nix command line, i.e. `./notebook.py` - I know how to do this, but I want to (i) export the notebook and (ii) make it executable without having to hack it by hand every time, also allowing for command-line arguments via e.g. `sys.argv` – jtlz2 Aug 10 '17 at 05:50
  • I have edited the question - does the edit make sense? – jtlz2 Aug 10 '17 at 05:52

1 Answers1

3

The answer turned out to be rather straightforward.

Part 1 - Making the exported notebook.py directly executable:

As described here, nbconvert can be customized with arbitrary templates.

So create a file hashbang.tpl containing:

#!/usr/bin/env ipython
{% extends 'python.tpl'%}

Then at the command line execute:

jupyter nbconvert --to python 'notebook.ipynb' --stdout --template=hashbang.tpl > notebook.py

Hey presto:

> more notebook.py

#!/usr/bin/env ipython

# coding: utf-8

# In[1]:

print 'Hello'
...

Part 2 - Detecting the notebook environment:

This answer from https://stackoverflow.com/a/39662359/1021819 should do it, i.e. use the following function to test for the notebook environment:

def isnotebook():
    # From https://stackoverflow.com/a/39662359/1021819
    try:
        shell = get_ipython().__class__.__name__
        if shell == 'ZMQInteractiveShell':
            return True   # Jupyter notebook or qtconsole
        elif shell == 'TerminalInteractiveShell':
            return False  # Terminal running IPython
        else:
            return False  # Other type (?)
    except NameError:
        return False      # Probably standard Python interpreter
jtlz2
  • 7,700
  • 9
  • 64
  • 114