{ "cells": [ { "cell_type": "markdown", "metadata": {}, "source": [ "# Notebook Splitter\n", "\n", "A simple routine for splitting Jupyter notebooks.\n", "\n", "\n", "Simply add one or more code or markdown cells containing just the line:\n", "\n", "`# --SPLIT HERE--`\n", "\n", "and run the code cells below.\n", "\n", "The script will split your `long_notebook.ipynb` at the defined split points, creating new notebooks `long_notebook_PART1.ipynb`, `long_notebook_PART2.ipynb`, etc...\n", "\n", "Note that we could start to elaborate this script, for example by providing an option to clean the new notebook parts by removing the code output cells, resetting the code cell execution numbers, etc etc." ] }, { "cell_type": "code", "execution_count": 114, "metadata": {}, "outputs": [], "source": [ "#Enter the file name for the file you want to split\n", "fn = 'Notebook Splitter.ipynb'\n", "\n", "#Prevent the overwriting of files that already exist\n", "overwrite = False" ] }, { "cell_type": "code", "execution_count": 115, "metadata": {}, "outputs": [], "source": [ "# --SPLIT HERE--" ] }, { "cell_type": "code", "execution_count": 116, "metadata": {}, "outputs": [], "source": [ "#The nbformat package provides an API for working with notebook documents\n", "#https://nbformat.readthedocs.io/en/latest/api.html\n", "import nbformat\n", "nb = nbformat.read(fn, as_version=4)\n", "\n", "#Make a copy of the notebook, just in case...\n", "nb2 = nb.copy()\n", "\n", "if overwrite:\n", " print('If notebook parts pre-exist, they will be overwritten...\\nSet: overwrite=False to guard against this.')" ] }, { "cell_type": "markdown", "metadata": {}, "source": [ "# --SPLIT HERE--" ] }, { "cell_type": "code", "execution_count": 119, "metadata": {}, "outputs": [ { "name": "stdout", "output_type": "stream", "text": [ "Writing Notebook Splitter_PART 0.ipynb...\n", "Writing Notebook Splitter_PART 1.ipynb...\n", "Writing Notebook Splitter_PART 2.ipynb...\n" ] } ], "source": [ "#We are going to see if we can split the notebook into separate parts\n", "parts=[]\n", "\n", "#Each part will contain the cells for the part\n", "#The rest of the notebook structure, (notebook metadata etc) will be copied from the original notebook\n", "partcells = []\n", "\n", "#Iterate through all the cells\n", "for cell in nb2['cells']:\n", " #Check for a splitline marker - go defensive!\n", " splitline = cell['source'].upper().strip().replace(' ','') == '#--SPLITHERE--'\n", " #If we're not at a split line,\n", " if not splitline:\n", " #Append the cell to the cell list for this part\n", " partcells.append(cell)\n", " else:\n", " #Otherwise, save the cells to the part...\n", " parts.append(partcells)\n", " #...and create a new part cells list\n", " partcells=[]\n", "\n", "#Commit the final set of cells to the final part\n", "parts.append(partcells)\n", "\n", "#This is a precautionary step...\n", "# Try not to clobber files we may have created previously\n", "import os\n", "import warnings\n", "\n", "#We can provide more warning notices...\n", "caution = False\n", "\n", "for ix, cells in enumerate(parts):\n", " part_fn = fn.replace('.ipynb','_PART {}.ipynb'.format(ix))\n", " if os.path.isfile(part_fn) and not overwrite:\n", " raise Exception('File {} already exists. Set: overwrite=True. Exiting...'.format(part_fn))\n", " elif caution:\n", " warnings.warn(\"You were warned... The following file will be overwritten: {}\".format(part_fn))\n", "\n", "#If you want to go really defensive, put the next bit of code into it's own cell so you can react\n", "# the file overwriting warning...\n", " \n", "#For each part, write out a separate notebook containing just the cells in that part.\n", "for ix, cells in enumerate(parts):\n", " part_fn = fn.replace('.ipynb','_PART {}.ipynb'.format(ix)) \n", " nb_out=nb.copy()\n", " nb_out['cells']=cells\n", " print('Writing {}...'.format(part_fn))\n", " nbformat.write(nb_out, part_fn)" ] } ], "metadata": { "kernelspec": { "display_name": "Python 3", "language": "python", "name": "python3" }, "language_info": { "codemirror_mode": { "name": "ipython", "version": 3 }, "file_extension": ".py", "mimetype": "text/x-python", "name": "python", "nbconvert_exporter": "python", "pygments_lexer": "ipython3", "version": "3.5.2" } }, "nbformat": 4, "nbformat_minor": 2 }