##// END OF EJS Templates
Condense raw_mimetype and mime_type traitlets into output_mimetype
Thomas Kluyver -
Show More
@@ -1,83 +1,85
1 1 import os
2 2
3 3 from tornado import web
4 4
5 5 from ..base.handlers import IPythonHandler
6 6 from IPython.nbformat.current import to_notebook_json
7 7 from IPython.nbconvert.exporters.export import exporter_map
8 8 from IPython.utils import tz
9 9
10 10
11 11 def has_resource_files(resources):
12 12 output_files_dir = resources.get('output_files_dir', "")
13 13 return bool(os.path.isdir(output_files_dir) and \
14 14 os.listdir(output_files_dir))
15 15
16 16 class NbconvertFileHandler(IPythonHandler):
17 17
18 18 SUPPORTED_METHODS = ('GET',)
19 19
20 20 @web.authenticated
21 21 def get(self, format, path='', name=None):
22 22 exporter = exporter_map[format]()
23 23
24 24 path = path.strip('/')
25 25 os_path = self.notebook_manager.get_os_path(name, path)
26 26 if not os.path.isfile(os_path):
27 27 raise web.HTTPError(404, u'Notebook does not exist: %s' % name)
28 28
29 29 info = os.stat(os_path)
30 30 self.set_header('Last-Modified', tz.utcfromtimestamp(info.st_mtime))
31 31
32 32 # Force download if requested
33 33 if self.get_argument('download', 'false').lower() == 'true':
34 34 filename = os.path.splitext(name)[0] + '.' + exporter.file_extension
35 35 self.set_header('Content-Disposition',
36 36 'attachment; filename="%s"' % filename)
37 37
38 38 # MIME type
39 if exporter.mime_type:
40 self.set_header('Content-Type', '%s; charset=utf-8' % exporter.mime_type)
39 if exporter.output_mimetype:
40 self.set_header('Content-Type',
41 '%s; charset=utf-8' % exporter.output_mimetype)
41 42
42 43 output, resources = exporter.from_filename(os_path)
43 44
44 45 # TODO: If there are resources, combine them into a zip file
45 46 assert not has_resource_files(resources)
46 47
47 48 self.finish(output)
48 49
49 50 class NbconvertPostHandler(IPythonHandler):
50 51 SUPPORTED_METHODS = ('POST',)
51 52
52 53 @web.authenticated
53 54 def post(self, format):
54 55 exporter = exporter_map[format]()
55 56
56 57 model = self.get_json_body()
57 58 nbnode = to_notebook_json(model['content'])
58 59
59 60 # MIME type
60 if exporter.mime_type:
61 self.set_header('Content-Type', '%s; charset=utf-8' % exporter.mime_type)
61 if exporter.output_mimetype:
62 self.set_header('Content-Type',
63 '%s; charset=utf-8' % exporter.output_mimetype)
62 64
63 65 output, resources = exporter.from_notebook_node(nbnode)
64 66
65 67 # TODO: If there are resources, combine them into a zip file
66 68 assert not has_resource_files(resources)
67 69
68 70 self.finish(output)
69 71
70 72 #-----------------------------------------------------------------------------
71 73 # URL to handler mappings
72 74 #-----------------------------------------------------------------------------
73 75
74 76 _format_regex = r"(?P<format>\w+)"
75 77 _path_regex = r"(?P<path>(?:/.*)*)"
76 78 _notebook_name_regex = r"(?P<name>[^/]+\.ipynb)"
77 79 _notebook_path_regex = "%s/%s" % (_path_regex, _notebook_name_regex)
78 80
79 81 default_handlers = [
80 82 (r"/nbconvert/%s%s" % (_format_regex, _notebook_path_regex),
81 83 NbconvertFileHandler),
82 84 (r"/nbconvert/%s" % _format_regex, NbconvertPostHandler),
83 85 ] No newline at end of file
@@ -1,90 +1,90
1 1 //----------------------------------------------------------------------------
2 2 // Copyright (C) 2012 The IPython Development Team
3 3 //
4 4 // Distributed under the terms of the BSD License. The full license is in
5 5 // the file COPYING, distributed as part of this software.
6 6 //----------------------------------------------------------------------------
7 7
8 8 //============================================================================
9 9 // CellToolbar Example
10 10 //============================================================================
11 11
12 12 (function(IPython) {
13 13 "use strict";
14 14
15 15 var CellToolbar = IPython.CellToolbar;
16 16 var raw_cell_preset = [];
17 17 var utils = IPython.utils;
18 18
19 19 var select_type = CellToolbar.utils.select_ui_generator([
20 20 ["None", "-"],
21 21 ["LaTeX", "text/latex"],
22 22 ["reST", "text/restructuredtext"],
23 23 ["HTML", "text/html"],
24 24 ["Markdown", "text/markdown"],
25 ["Python", "application/x-python"],
25 ["Python", "text/x-python"],
26 26 ["Custom", "dialog"],
27 27
28 28 ],
29 29 // setter
30 30 function(cell, value) {
31 31 if (value === "-") {
32 32 delete cell.metadata.raw_mimetype;
33 33 } else if (value === 'dialog'){
34 34 var dialog = $('<div/>').append(
35 35 $("<p/>")
36 36 .html("Set the MIME type of the raw cell:")
37 37 ).append(
38 38 $("<br/>")
39 39 ).append(
40 40 $('<input/>').attr('type','text').attr('size','25')
41 41 .val(cell.metadata.raw_mimetype || "-")
42 42 );
43 43 IPython.dialog.modal({
44 44 title: "Raw Cell MIME Type",
45 45 body: dialog,
46 46 buttons : {
47 47 "Cancel": {},
48 48 "OK": {
49 49 class: "btn-primary",
50 50 click: function () {
51 51 console.log(cell);
52 52 cell.metadata.raw_mimetype = $(this).find('input').val();
53 53 console.log(cell.metadata);
54 54 }
55 55 }
56 56 },
57 57 open : function (event, ui) {
58 58 var that = $(this);
59 59 // Upon ENTER, click the OK button.
60 60 that.find('input[type="text"]').keydown(function (event, ui) {
61 61 if (event.which === utils.keycodes.ENTER) {
62 62 that.find('.btn-primary').first().click();
63 63 return false;
64 64 }
65 65 });
66 66 that.find('input[type="text"]').focus().select();
67 67 }
68 68 });
69 69 } else {
70 70 cell.metadata.raw_mimetype = value;
71 71 }
72 72 },
73 73 //getter
74 74 function(cell) {
75 75 return cell.metadata.raw_mimetype || "";
76 76 },
77 77 // name
78 78 "Raw NBConvert Format",
79 79 // cell_types
80 80 ["raw"]
81 81 );
82 82
83 83 CellToolbar.register_callback('raw_cell.select', select_type);
84 84
85 85 raw_cell_preset.push('raw_cell.select');
86 86
87 87 CellToolbar.register_preset('Raw Cell Format', raw_cell_preset);
88 88 console.log('Raw Cell Format toolbar preset loaded.');
89 89
90 }(IPython)); No newline at end of file
90 }(IPython));
@@ -1,274 +1,274
1 1 """This module defines a base Exporter class. For Jinja template-based export,
2 2 see templateexporter.py.
3 3 """
4 4
5 5 #-----------------------------------------------------------------------------
6 6 # Copyright (c) 2013, the IPython Development Team.
7 7 #
8 8 # Distributed under the terms of the Modified BSD License.
9 9 #
10 10 # The full license is in the file COPYING.txt, distributed with this software.
11 11 #-----------------------------------------------------------------------------
12 12
13 13 #-----------------------------------------------------------------------------
14 14 # Imports
15 15 #-----------------------------------------------------------------------------
16 16
17 17 from __future__ import print_function, absolute_import
18 18
19 19 # Stdlib imports
20 20 import io
21 21 import os
22 22 import copy
23 23 import collections
24 24 import datetime
25 25
26 26
27 27 # IPython imports
28 28 from IPython.config.configurable import LoggingConfigurable
29 29 from IPython.config import Config
30 30 from IPython.nbformat import current as nbformat
31 31 from IPython.utils.traitlets import MetaHasTraits, Unicode, List
32 32 from IPython.utils.importstring import import_item
33 33 from IPython.utils import text, py3compat
34 34
35 35 #-----------------------------------------------------------------------------
36 36 # Class
37 37 #-----------------------------------------------------------------------------
38 38
39 39 class ResourcesDict(collections.defaultdict):
40 40 def __missing__(self, key):
41 41 return ''
42 42
43 43
44 44 class Exporter(LoggingConfigurable):
45 45 """
46 46 Class containing methods that sequentially run a list of preprocessors on a
47 47 NotebookNode object and then return the modified NotebookNode object and
48 48 accompanying resources dict.
49 49 """
50 50
51 51 file_extension = Unicode(
52 52 'txt', config=True,
53 53 help="Extension of the file that should be written to disk"
54 54 )
55 55
56 mime_type = Unicode('', config=True,
56 output_mimetype = Unicode('', config=True,
57 57 help="MIME type of the result file, for HTTP response headers."
58 58 )
59 59
60 60 #Configurability, allows the user to easily add filters and preprocessors.
61 61 preprocessors = List(config=True,
62 62 help="""List of preprocessors, by name or namespace, to enable.""")
63 63
64 64 _preprocessors = None
65 65
66 66 default_preprocessors = List(['IPython.nbconvert.preprocessors.coalesce_streams',
67 67 'IPython.nbconvert.preprocessors.SVG2PDFPreprocessor',
68 68 'IPython.nbconvert.preprocessors.ExtractOutputPreprocessor',
69 69 'IPython.nbconvert.preprocessors.CSSHTMLHeaderPreprocessor',
70 70 'IPython.nbconvert.preprocessors.RevealHelpPreprocessor',
71 71 'IPython.nbconvert.preprocessors.LatexPreprocessor',
72 72 'IPython.nbconvert.preprocessors.HighlightMagicsPreprocessor'],
73 73 config=True,
74 74 help="""List of preprocessors available by default, by name, namespace,
75 75 instance, or type.""")
76 76
77 77
78 78 def __init__(self, config=None, **kw):
79 79 """
80 80 Public constructor
81 81
82 82 Parameters
83 83 ----------
84 84 config : config
85 85 User configuration instance.
86 86 """
87 87 with_default_config = self.default_config
88 88 if config:
89 89 with_default_config.merge(config)
90 90
91 91 super(Exporter, self).__init__(config=with_default_config, **kw)
92 92
93 93 self._init_preprocessors()
94 94
95 95
96 96 @property
97 97 def default_config(self):
98 98 return Config()
99 99
100 100 @nbformat.docstring_nbformat_mod
101 101 def from_notebook_node(self, nb, resources=None, **kw):
102 102 """
103 103 Convert a notebook from a notebook node instance.
104 104
105 105 Parameters
106 106 ----------
107 107 nb : :class:`~{nbformat_mod}.nbbase.NotebookNode`
108 108 Notebook node
109 109 resources : dict
110 110 Additional resources that can be accessed read/write by
111 111 preprocessors and filters.
112 112 **kw
113 113 Ignored (?)
114 114 """
115 115 nb_copy = copy.deepcopy(nb)
116 116 resources = self._init_resources(resources)
117 117
118 118 # Preprocess
119 119 nb_copy, resources = self._preprocess(nb_copy, resources)
120 120
121 121 return nb_copy, resources
122 122
123 123
124 124 def from_filename(self, filename, resources=None, **kw):
125 125 """
126 126 Convert a notebook from a notebook file.
127 127
128 128 Parameters
129 129 ----------
130 130 filename : str
131 131 Full filename of the notebook file to open and convert.
132 132 """
133 133
134 134 # Pull the metadata from the filesystem.
135 135 if resources is None:
136 136 resources = ResourcesDict()
137 137 if not 'metadata' in resources or resources['metadata'] == '':
138 138 resources['metadata'] = ResourcesDict()
139 139 basename = os.path.basename(filename)
140 140 notebook_name = basename[:basename.rfind('.')]
141 141 resources['metadata']['name'] = notebook_name
142 142
143 143 modified_date = datetime.datetime.fromtimestamp(os.path.getmtime(filename))
144 144 resources['metadata']['modified_date'] = modified_date.strftime(text.date_format)
145 145
146 146 with io.open(filename, encoding='utf-8') as f:
147 147 return self.from_notebook_node(nbformat.read(f, 'json'), resources=resources, **kw)
148 148
149 149
150 150 def from_file(self, file_stream, resources=None, **kw):
151 151 """
152 152 Convert a notebook from a notebook file.
153 153
154 154 Parameters
155 155 ----------
156 156 file_stream : file-like object
157 157 Notebook file-like object to convert.
158 158 """
159 159 return self.from_notebook_node(nbformat.read(file_stream, 'json'), resources=resources, **kw)
160 160
161 161
162 162 def register_preprocessor(self, preprocessor, enabled=False):
163 163 """
164 164 Register a preprocessor.
165 165 Preprocessors are classes that act upon the notebook before it is
166 166 passed into the Jinja templating engine. preprocessors are also
167 167 capable of passing additional information to the Jinja
168 168 templating engine.
169 169
170 170 Parameters
171 171 ----------
172 172 preprocessor : preprocessor
173 173 """
174 174 if preprocessor is None:
175 175 raise TypeError('preprocessor')
176 176 isclass = isinstance(preprocessor, type)
177 177 constructed = not isclass
178 178
179 179 # Handle preprocessor's registration based on it's type
180 180 if constructed and isinstance(preprocessor, py3compat.string_types):
181 181 # Preprocessor is a string, import the namespace and recursively call
182 182 # this register_preprocessor method
183 183 preprocessor_cls = import_item(preprocessor)
184 184 return self.register_preprocessor(preprocessor_cls, enabled)
185 185
186 186 if constructed and hasattr(preprocessor, '__call__'):
187 187 # Preprocessor is a function, no need to construct it.
188 188 # Register and return the preprocessor.
189 189 if enabled:
190 190 preprocessor.enabled = True
191 191 self._preprocessors.append(preprocessor)
192 192 return preprocessor
193 193
194 194 elif isclass and isinstance(preprocessor, MetaHasTraits):
195 195 # Preprocessor is configurable. Make sure to pass in new default for
196 196 # the enabled flag if one was specified.
197 197 self.register_preprocessor(preprocessor(parent=self), enabled)
198 198
199 199 elif isclass:
200 200 # Preprocessor is not configurable, construct it
201 201 self.register_preprocessor(preprocessor(), enabled)
202 202
203 203 else:
204 204 # Preprocessor is an instance of something without a __call__
205 205 # attribute.
206 206 raise TypeError('preprocessor')
207 207
208 208
209 209 def _init_preprocessors(self):
210 210 """
211 211 Register all of the preprocessors needed for this exporter, disabled
212 212 unless specified explicitly.
213 213 """
214 214 if self._preprocessors is None:
215 215 self._preprocessors = []
216 216
217 217 #Load default preprocessors (not necessarly enabled by default).
218 218 if self.default_preprocessors:
219 219 for preprocessor in self.default_preprocessors:
220 220 self.register_preprocessor(preprocessor)
221 221
222 222 #Load user preprocessors. Enable by default.
223 223 if self.preprocessors:
224 224 for preprocessor in self.preprocessors:
225 225 self.register_preprocessor(preprocessor, enabled=True)
226 226
227 227
228 228 def _init_resources(self, resources):
229 229
230 230 #Make sure the resources dict is of ResourcesDict type.
231 231 if resources is None:
232 232 resources = ResourcesDict()
233 233 if not isinstance(resources, ResourcesDict):
234 234 new_resources = ResourcesDict()
235 235 new_resources.update(resources)
236 236 resources = new_resources
237 237
238 238 #Make sure the metadata extension exists in resources
239 239 if 'metadata' in resources:
240 240 if not isinstance(resources['metadata'], ResourcesDict):
241 241 resources['metadata'] = ResourcesDict(resources['metadata'])
242 242 else:
243 243 resources['metadata'] = ResourcesDict()
244 244 if not resources['metadata']['name']:
245 245 resources['metadata']['name'] = 'Notebook'
246 246
247 247 #Set the output extension
248 248 resources['output_extension'] = self.file_extension
249 249 return resources
250 250
251 251
252 252 def _preprocess(self, nb, resources):
253 253 """
254 254 Preprocess the notebook before passing it into the Jinja engine.
255 255 To preprocess the notebook is to apply all of the
256 256
257 257 Parameters
258 258 ----------
259 259 nb : notebook node
260 260 notebook that is being exported.
261 261 resources : a dict of additional resources that
262 262 can be accessed read/write by preprocessors
263 263 """
264 264
265 265 # Do a copy.deepcopy first,
266 266 # we are never safe enough with what the preprocessors could do.
267 267 nbc = copy.deepcopy(nb)
268 268 resc = copy.deepcopy(resources)
269 269
270 270 #Run each preprocessor on the notebook. Carry the output along
271 271 #to each preprocessor
272 272 for preprocessor in self._preprocessors:
273 273 nbc, resc = preprocessor(nbc, resc)
274 274 return nbc, resc
@@ -1,60 +1,60
1 1 """HTML Exporter class"""
2 2
3 3 #-----------------------------------------------------------------------------
4 4 # Copyright (c) 2013, the IPython Development Team.
5 5 #
6 6 # Distributed under the terms of the Modified BSD License.
7 7 #
8 8 # The full license is in the file COPYING.txt, distributed with this software.
9 9 #-----------------------------------------------------------------------------
10 10
11 11 #-----------------------------------------------------------------------------
12 12 # Imports
13 13 #-----------------------------------------------------------------------------
14 14
15 15 from IPython.utils.traitlets import Unicode, List
16 16
17 17 from IPython.nbconvert import preprocessors
18 18 from IPython.config import Config
19 19
20 20 from .templateexporter import TemplateExporter
21 21
22 22 #-----------------------------------------------------------------------------
23 23 # Classes
24 24 #-----------------------------------------------------------------------------
25 25
26 26 class HTMLExporter(TemplateExporter):
27 27 """
28 28 Exports a basic HTML document. This exporter assists with the export of
29 29 HTML. Inherit from it if you are writing your own HTML template and need
30 30 custom preprocessors/filters. If you don't need custom preprocessors/
31 31 filters, just change the 'template_file' config option.
32 32 """
33 33
34 34 file_extension = Unicode(
35 35 'html', config=True,
36 36 help="Extension of the file that should be written to disk"
37 37 )
38 38
39 39 mime_type = Unicode('text/html', config=True,
40 40 help="MIME type of the result file, for HTTP response headers."
41 41 )
42 42
43 43 default_template = Unicode('full', config=True, help="""Flavor of the data
44 44 format to use. I.E. 'full' or 'basic'""")
45 45
46 def _raw_mimetype_default(self):
46 def _output_mimetype_default(self):
47 47 return 'text/html'
48 48
49 49 @property
50 50 def default_config(self):
51 51 c = Config({
52 52 'CSSHTMLHeaderPreprocessor':{
53 53 'enabled':True
54 54 },
55 55 'HighlightMagicsPreprocessor': {
56 56 'enabled':True
57 57 }
58 58 })
59 59 c.merge(super(HTMLExporter,self).default_config)
60 60 return c
@@ -1,97 +1,93
1 1 """LaTeX Exporter class"""
2 2
3 3 #-----------------------------------------------------------------------------
4 4 # Copyright (c) 2013, the IPython Development Team.
5 5 #
6 6 # Distributed under the terms of the Modified BSD License.
7 7 #
8 8 # The full license is in the file COPYING.txt, distributed with this software.
9 9 #-----------------------------------------------------------------------------
10 10
11 11 #-----------------------------------------------------------------------------
12 12 # Imports
13 13 #-----------------------------------------------------------------------------
14 14
15 15 # Stdlib imports
16 16 import os
17 17
18 18 # IPython imports
19 19 from IPython.utils.traitlets import Unicode, List
20 20 from IPython.config import Config
21 21
22 22 from IPython.nbconvert import filters, preprocessors
23 23 from .templateexporter import TemplateExporter
24 24
25 25 #-----------------------------------------------------------------------------
26 26 # Classes and functions
27 27 #-----------------------------------------------------------------------------
28 28
29 29 class LatexExporter(TemplateExporter):
30 30 """
31 31 Exports to a Latex template. Inherit from this class if your template is
32 32 LaTeX based and you need custom tranformers/filters. Inherit from it if
33 33 you are writing your own HTML template and need custom tranformers/filters.
34 34 If you don't need custom tranformers/filters, just change the
35 35 'template_file' config option. Place your template in the special "/latex"
36 36 subfolder of the "../templates" folder.
37 37 """
38 38
39 39 file_extension = Unicode(
40 40 'tex', config=True,
41 41 help="Extension of the file that should be written to disk")
42 42
43 mime_type = Unicode('application/x-tex', config=True,
44 help="MIME type of the result file, for HTTP response headers."
45 )
46
47 43 default_template = Unicode('article', config=True, help="""Template of the
48 44 data format to use. I.E. 'article' or 'report'""")
49 45
50 46 #Latex constants
51 47 default_template_path = Unicode(
52 48 os.path.join("..", "templates", "latex"), config=True,
53 49 help="Path where the template files are located.")
54 50
55 51 template_skeleton_path = Unicode(
56 52 os.path.join("..", "templates", "latex", "skeleton"), config=True,
57 53 help="Path where the template skeleton files are located.")
58 54
59 55 #Special Jinja2 syntax that will not conflict when exporting latex.
60 56 jinja_comment_block_start = Unicode("((=", config=True)
61 57 jinja_comment_block_end = Unicode("=))", config=True)
62 58 jinja_variable_block_start = Unicode("(((", config=True)
63 59 jinja_variable_block_end = Unicode(")))", config=True)
64 60 jinja_logic_block_start = Unicode("((*", config=True)
65 61 jinja_logic_block_end = Unicode("*))", config=True)
66 62
67 63 #Extension that the template files use.
68 64 template_extension = Unicode(".tplx", config=True)
69 65
70 def _raw_mimetype_default(self):
66 def _output_mimetype_default(self):
71 67 return 'text/latex'
72 68
73 69
74 70 @property
75 71 def default_config(self):
76 72 c = Config({
77 73 'NbConvertBase': {
78 74 'display_data_priority' : ['latex', 'pdf', 'png', 'jpg', 'svg', 'jpeg', 'text']
79 75 },
80 76 'ExtractOutputPreprocessor': {
81 77 'enabled':True
82 78 },
83 79 'SVG2PDFPreprocessor': {
84 80 'enabled':True
85 81 },
86 82 'LatexPreprocessor': {
87 83 'enabled':True
88 84 },
89 85 'SphinxPreprocessor': {
90 86 'enabled':True
91 87 },
92 88 'HighlightMagicsPreprocessor': {
93 89 'enabled':True
94 90 }
95 91 })
96 92 c.merge(super(LatexExporter,self).default_config)
97 93 return c
@@ -1,47 +1,43
1 1 """Markdown Exporter class"""
2 2
3 3 #-----------------------------------------------------------------------------
4 4 # Copyright (c) 2013, the IPython Development Team.
5 5 #
6 6 # Distributed under the terms of the Modified BSD License.
7 7 #
8 8 # The full license is in the file COPYING.txt, distributed with this software.
9 9 #-----------------------------------------------------------------------------
10 10
11 11 #-----------------------------------------------------------------------------
12 12 # Imports
13 13 #-----------------------------------------------------------------------------
14 14
15 15 from IPython.config import Config
16 16 from IPython.utils.traitlets import Unicode
17 17
18 18 from .templateexporter import TemplateExporter
19 19
20 20 #-----------------------------------------------------------------------------
21 21 # Classes
22 22 #-----------------------------------------------------------------------------
23 23
24 24 class MarkdownExporter(TemplateExporter):
25 25 """
26 26 Exports to a markdown document (.md)
27 27 """
28 28
29 29 file_extension = Unicode(
30 30 'md', config=True,
31 31 help="Extension of the file that should be written to disk")
32 32
33 def _raw_mimetype_default(self):
33 def _output_mimetype_default(self):
34 34 return 'text/markdown'
35 35
36 36 def _raw_mimetypes_default(self):
37 return ['text/markdown', 'text/html']
38
39 mime_type = Unicode('text/x-markdown', config=True,
40 help="MIME type of the result file, for HTTP response headers."
41 )
37 return ['text/markdown', 'text/html', '']
42 38
43 39 @property
44 40 def default_config(self):
45 41 c = Config({'ExtractOutputPreprocessor':{'enabled':True}})
46 42 c.merge(super(MarkdownExporter,self).default_config)
47 43 return c
@@ -1,37 +1,33
1 1 """Python script Exporter class"""
2 2
3 3 #-----------------------------------------------------------------------------
4 4 # Copyright (c) 2013, the IPython Development Team.
5 5 #
6 6 # Distributed under the terms of the Modified BSD License.
7 7 #
8 8 # The full license is in the file COPYING.txt, distributed with this software.
9 9 #-----------------------------------------------------------------------------
10 10
11 11 #-----------------------------------------------------------------------------
12 12 # Imports
13 13 #-----------------------------------------------------------------------------
14 14
15 15 from IPython.utils.traitlets import Unicode
16 16
17 17 from .templateexporter import TemplateExporter
18 18
19 19 #-----------------------------------------------------------------------------
20 20 # Classes
21 21 #-----------------------------------------------------------------------------
22 22
23 23 class PythonExporter(TemplateExporter):
24 24 """
25 25 Exports a Python code file.
26 26 """
27 27
28 28 file_extension = Unicode(
29 29 'py', config=True,
30 30 help="Extension of the file that should be written to disk")
31 31
32 def _raw_mimetype_default(self):
33 return 'application/x-python'
34
35 mime_type = Unicode('text/x-python', config=True,
36 help="MIME type of the result file, for HTTP response headers."
37 )
32 def _output_mimetype_default(self):
33 return 'text/x-python'
@@ -1,44 +1,40
1 1 """restructuredText Exporter class"""
2 2
3 3 #-----------------------------------------------------------------------------
4 4 # Copyright (c) 2013, the IPython Development Team.
5 5 #
6 6 # Distributed under the terms of the Modified BSD License.
7 7 #
8 8 # The full license is in the file COPYING.txt, distributed with this software.
9 9 #-----------------------------------------------------------------------------
10 10
11 11 #-----------------------------------------------------------------------------
12 12 # Imports
13 13 #-----------------------------------------------------------------------------
14 14
15 15 from IPython.utils.traitlets import Unicode
16 16 from IPython.config import Config
17 17
18 18 from .templateexporter import TemplateExporter
19 19
20 20 #-----------------------------------------------------------------------------
21 21 # Classes
22 22 #-----------------------------------------------------------------------------
23 23
24 24 class RSTExporter(TemplateExporter):
25 25 """
26 26 Exports restructured text documents.
27 27 """
28 28
29 29 file_extension = Unicode(
30 30 'rst', config=True,
31 31 help="Extension of the file that should be written to disk")
32 32
33 def _raw_mimetype_default(self):
33 def _output_mimetype_default(self):
34 34 return 'text/restructuredtext'
35 35
36 mime_type = Unicode('text/x-rst', config=True,
37 help="MIME type of the result file, for HTTP response headers."
38 )
39
40 36 @property
41 37 def default_config(self):
42 38 c = Config({'ExtractOutputPreprocessor':{'enabled':True}})
43 39 c.merge(super(RSTExporter,self).default_config)
44 40 return c
@@ -1,49 +1,48
1 1 """HTML slide show Exporter class"""
2 2
3 3 #-----------------------------------------------------------------------------
4 4 # Copyright (c) 2013, the IPython Development Team.
5 5 #
6 6 # Distributed under the terms of the Modified BSD License.
7 7 #
8 8 # The full license is in the file COPYING.txt, distributed with this software.
9 9 #-----------------------------------------------------------------------------
10 10
11 11 #-----------------------------------------------------------------------------
12 12 # Imports
13 13 #-----------------------------------------------------------------------------
14 14
15 15 from IPython.utils.traitlets import Unicode
16 16
17 17 from IPython.nbconvert import preprocessors
18 18 from IPython.config import Config
19 19
20 20 from .html import HTMLExporter
21 21
22 22 #-----------------------------------------------------------------------------
23 23 # Classes
24 24 #-----------------------------------------------------------------------------
25 25
26 26 class SlidesExporter(HTMLExporter):
27 27 """Exports HTML slides with reveal.js"""
28 28
29 29 file_extension = Unicode(
30 30 'slides.html', config=True,
31 31 help="Extension of the file that should be written to disk"
32 32 )
33 33
34 mime_type = Unicode('text/html', config=True,
35 help="MIME type of the result file, for HTTP response headers."
36 )
34 def _output_mimetype_default(self):
35 return 'text/html'
37 36
38 37 default_template = Unicode('reveal', config=True, help="""Template of the
39 38 data format to use. I.E. 'reveal'""")
40 39
41 40 @property
42 41 def default_config(self):
43 42 c = Config({
44 43 'RevealHelpPreprocessor': {
45 44 'enabled': True,
46 45 },
47 46 })
48 47 c.merge(super(SlidesExporter,self).default_config)
49 48 return c
@@ -1,324 +1,324
1 1 """This module defines TemplateExporter, a highly configurable converter
2 2 that uses Jinja2 to export notebook files into different formats.
3 3 """
4 4
5 5 #-----------------------------------------------------------------------------
6 6 # Copyright (c) 2013, the IPython Development Team.
7 7 #
8 8 # Distributed under the terms of the Modified BSD License.
9 9 #
10 10 # The full license is in the file COPYING.txt, distributed with this software.
11 11 #-----------------------------------------------------------------------------
12 12
13 13 #-----------------------------------------------------------------------------
14 14 # Imports
15 15 #-----------------------------------------------------------------------------
16 16
17 17 from __future__ import print_function, absolute_import
18 18
19 19 # Stdlib imports
20 20 import os
21 21
22 22 # other libs/dependencies
23 23 from jinja2 import Environment, FileSystemLoader, ChoiceLoader, TemplateNotFound
24 24
25 25 # IPython imports
26 26 from IPython.utils.traitlets import MetaHasTraits, Unicode, List, Dict, Any
27 27 from IPython.utils.importstring import import_item
28 28 from IPython.utils import py3compat, text
29 29
30 30 from IPython.nbformat.current import docstring_nbformat_mod
31 31 from IPython.nbconvert import filters
32 32 from .exporter import Exporter
33 33
34 34 #-----------------------------------------------------------------------------
35 35 # Globals and constants
36 36 #-----------------------------------------------------------------------------
37 37
38 38 #Jinja2 extensions to load.
39 39 JINJA_EXTENSIONS = ['jinja2.ext.loopcontrols']
40 40
41 41 default_filters = {
42 42 'indent': text.indent,
43 43 'markdown2html': filters.markdown2html,
44 44 'ansi2html': filters.ansi2html,
45 45 'filter_data_type': filters.DataTypeFilter,
46 46 'get_lines': filters.get_lines,
47 47 'highlight2html': filters.Highlight2Html,
48 48 'highlight2latex': filters.Highlight2Latex,
49 49 'ipython2python': filters.ipython2python,
50 50 'posix_path': filters.posix_path,
51 51 'markdown2latex': filters.markdown2latex,
52 52 'markdown2rst': filters.markdown2rst,
53 53 'comment_lines': filters.comment_lines,
54 54 'strip_ansi': filters.strip_ansi,
55 55 'strip_dollars': filters.strip_dollars,
56 56 'strip_files_prefix': filters.strip_files_prefix,
57 57 'html2text' : filters.html2text,
58 58 'add_anchor': filters.add_anchor,
59 59 'ansi2latex': filters.ansi2latex,
60 60 'wrap_text': filters.wrap_text,
61 61 'escape_latex': filters.escape_latex,
62 62 'citation2latex': filters.citation2latex,
63 63 'path2url': filters.path2url,
64 64 'add_prompts': filters.add_prompts,
65 65 }
66 66
67 67 #-----------------------------------------------------------------------------
68 68 # Class
69 69 #-----------------------------------------------------------------------------
70 70
71 71 class TemplateExporter(Exporter):
72 72 """
73 73 Exports notebooks into other file formats. Uses Jinja 2 templating engine
74 74 to output new formats. Inherit from this class if you are creating a new
75 75 template type along with new filters/preprocessors. If the filters/
76 76 preprocessors provided by default suffice, there is no need to inherit from
77 77 this class. Instead, override the template_file and file_extension
78 78 traits via a config file.
79 79
80 80 {filters}
81 81 """
82 82
83 83 # finish the docstring
84 84 __doc__ = __doc__.format(filters = '- '+'\n - '.join(default_filters.keys()))
85 85
86 86
87 87 template_file = Unicode(u'default',
88 88 config=True,
89 89 help="Name of the template file to use")
90 90 def _template_file_changed(self, name, old, new):
91 91 if new == 'default':
92 92 self.template_file = self.default_template
93 93 else:
94 94 self.template_file = new
95 95 self.template = None
96 96 self._load_template()
97 97
98 98 default_template = Unicode(u'')
99 99 template = Any()
100 100 environment = Any()
101 101
102 102 template_path = List(['.'], config=True)
103 103 def _template_path_changed(self, name, old, new):
104 104 self._load_template()
105 105
106 106 default_template_path = Unicode(
107 107 os.path.join("..", "templates"),
108 108 help="Path where the template files are located.")
109 109
110 110 template_skeleton_path = Unicode(
111 111 os.path.join("..", "templates", "skeleton"),
112 112 help="Path where the template skeleton files are located.")
113 113
114 114 #Jinja block definitions
115 115 jinja_comment_block_start = Unicode("", config=True)
116 116 jinja_comment_block_end = Unicode("", config=True)
117 117 jinja_variable_block_start = Unicode("", config=True)
118 118 jinja_variable_block_end = Unicode("", config=True)
119 119 jinja_logic_block_start = Unicode("", config=True)
120 120 jinja_logic_block_end = Unicode("", config=True)
121 121
122 122 #Extension that the template files use.
123 123 template_extension = Unicode(".tpl", config=True)
124 124
125 125 filters = Dict(config=True,
126 126 help="""Dictionary of filters, by name and namespace, to add to the Jinja
127 127 environment.""")
128 128
129 raw_mimetype = Unicode('')
129 output_mimetype = Unicode('')
130
130 131 raw_mimetypes = List(config=True,
131 132 help="""formats of raw cells to be included in this Exporter's output."""
132 133 )
133 134 def _raw_mimetypes_default(self):
134 return [self.raw_mimetype]
135 return [self.output_mimetype, '']
135 136
136 137
137 138 def __init__(self, config=None, extra_loaders=None, **kw):
138 139 """
139 140 Public constructor
140 141
141 142 Parameters
142 143 ----------
143 144 config : config
144 145 User configuration instance.
145 146 extra_loaders : list[of Jinja Loaders]
146 147 ordered list of Jinja loader to find templates. Will be tried in order
147 148 before the default FileSystem ones.
148 149 template : str (optional, kw arg)
149 150 Template to use when exporting.
150 151 """
151 152 super(TemplateExporter, self).__init__(config=config, **kw)
152 153
153 154 #Init
154 155 self._init_template()
155 156 self._init_environment(extra_loaders=extra_loaders)
156 157 self._init_preprocessors()
157 158 self._init_filters()
158 159
159 160
160 161 def _load_template(self):
161 162 """Load the Jinja template object from the template file
162 163
163 164 This is a no-op if the template attribute is already defined,
164 165 or the Jinja environment is not setup yet.
165 166
166 167 This is triggered by various trait changes that would change the template.
167 168 """
168 169 if self.template is not None:
169 170 return
170 171 # called too early, do nothing
171 172 if self.environment is None:
172 173 return
173 174 # Try different template names during conversion. First try to load the
174 175 # template by name with extension added, then try loading the template
175 176 # as if the name is explicitly specified, then try the name as a
176 177 # 'flavor', and lastly just try to load the template by module name.
177 178 module_name = self.__module__.rsplit('.', 1)[-1]
178 179 try_names = []
179 180 if self.template_file:
180 181 try_names.extend([
181 182 self.template_file + self.template_extension,
182 183 self.template_file,
183 184 module_name + '_' + self.template_file + self.template_extension,
184 185 ])
185 186 try_names.append(module_name + self.template_extension)
186 187 for try_name in try_names:
187 188 self.log.debug("Attempting to load template %s", try_name)
188 189 try:
189 190 self.template = self.environment.get_template(try_name)
190 191 except (TemplateNotFound, IOError):
191 192 pass
192 193 except Exception as e:
193 194 self.log.warn("Unexpected exception loading template: %s", try_name, exc_info=True)
194 195 else:
195 196 self.log.info("Loaded template %s", try_name)
196 197 break
197 198
198 199 @docstring_nbformat_mod
199 200 def from_notebook_node(self, nb, resources=None, **kw):
200 201 """
201 202 Convert a notebook from a notebook node instance.
202 203
203 204 Parameters
204 205 ----------
205 206 nb : :class:`~{nbformat_mod}.nbbase.NotebookNode`
206 207 Notebook node
207 208 resources : dict
208 209 Additional resources that can be accessed read/write by
209 210 preprocessors and filters.
210 211 """
211 212 nb_copy, resources = super(TemplateExporter, self).from_notebook_node(nb, resources, **kw)
212 resources.setdefault('raw_mimetype', self.raw_mimetype)
213 213 resources.setdefault('raw_mimetypes', self.raw_mimetypes)
214 214
215 215 self._load_template()
216 216
217 217 if self.template is not None:
218 218 output = self.template.render(nb=nb_copy, resources=resources)
219 219 else:
220 220 raise IOError('template file "%s" could not be found' % self.template_file)
221 221 return output, resources
222 222
223 223
224 224 def register_filter(self, name, jinja_filter):
225 225 """
226 226 Register a filter.
227 227 A filter is a function that accepts and acts on one string.
228 228 The filters are accesible within the Jinja templating engine.
229 229
230 230 Parameters
231 231 ----------
232 232 name : str
233 233 name to give the filter in the Jinja engine
234 234 filter : filter
235 235 """
236 236 if jinja_filter is None:
237 237 raise TypeError('filter')
238 238 isclass = isinstance(jinja_filter, type)
239 239 constructed = not isclass
240 240
241 241 #Handle filter's registration based on it's type
242 242 if constructed and isinstance(jinja_filter, py3compat.string_types):
243 243 #filter is a string, import the namespace and recursively call
244 244 #this register_filter method
245 245 filter_cls = import_item(jinja_filter)
246 246 return self.register_filter(name, filter_cls)
247 247
248 248 if constructed and hasattr(jinja_filter, '__call__'):
249 249 #filter is a function, no need to construct it.
250 250 self.environment.filters[name] = jinja_filter
251 251 return jinja_filter
252 252
253 253 elif isclass and isinstance(jinja_filter, MetaHasTraits):
254 254 #filter is configurable. Make sure to pass in new default for
255 255 #the enabled flag if one was specified.
256 256 filter_instance = jinja_filter(parent=self)
257 257 self.register_filter(name, filter_instance )
258 258
259 259 elif isclass:
260 260 #filter is not configurable, construct it
261 261 filter_instance = jinja_filter()
262 262 self.register_filter(name, filter_instance)
263 263
264 264 else:
265 265 #filter is an instance of something without a __call__
266 266 #attribute.
267 267 raise TypeError('filter')
268 268
269 269
270 270 def _init_template(self):
271 271 """
272 272 Make sure a template name is specified. If one isn't specified, try to
273 273 build one from the information we know.
274 274 """
275 275 self._template_file_changed('template_file', self.template_file, self.template_file)
276 276
277 277
278 278 def _init_environment(self, extra_loaders=None):
279 279 """
280 280 Create the Jinja templating environment.
281 281 """
282 282 here = os.path.dirname(os.path.realpath(__file__))
283 283 loaders = []
284 284 if extra_loaders:
285 285 loaders.extend(extra_loaders)
286 286
287 287 paths = self.template_path
288 288 paths.extend([os.path.join(here, self.default_template_path),
289 289 os.path.join(here, self.template_skeleton_path)])
290 290 loaders.append(FileSystemLoader(paths))
291 291
292 292 self.environment = Environment(
293 293 loader= ChoiceLoader(loaders),
294 294 extensions=JINJA_EXTENSIONS
295 295 )
296 296
297 297 #Set special Jinja2 syntax that will not conflict with latex.
298 298 if self.jinja_logic_block_start:
299 299 self.environment.block_start_string = self.jinja_logic_block_start
300 300 if self.jinja_logic_block_end:
301 301 self.environment.block_end_string = self.jinja_logic_block_end
302 302 if self.jinja_variable_block_start:
303 303 self.environment.variable_start_string = self.jinja_variable_block_start
304 304 if self.jinja_variable_block_end:
305 305 self.environment.variable_end_string = self.jinja_variable_block_end
306 306 if self.jinja_comment_block_start:
307 307 self.environment.comment_start_string = self.jinja_comment_block_start
308 308 if self.jinja_comment_block_end:
309 309 self.environment.comment_end_string = self.jinja_comment_block_end
310 310
311 311
312 312 def _init_filters(self):
313 313 """
314 314 Register all of the filters required for the exporter.
315 315 """
316 316
317 317 #Add default filters to the Jinja2 environment
318 318 for key, value in default_filters.items():
319 319 self.register_filter(key, value)
320 320
321 321 #Load user filters. Overwrite existing filters if need be.
322 322 if self.filters:
323 323 for key, user_filter in self.filters.items():
324 324 self.register_filter(key, user_filter)
@@ -1,54 +1,54
1 1 """Base TestCase class for testing Exporters"""
2 2
3 3 #-----------------------------------------------------------------------------
4 4 # Copyright (c) 2013, the IPython Development Team.
5 5 #
6 6 # Distributed under the terms of the Modified BSD License.
7 7 #
8 8 # The full license is in the file COPYING.txt, distributed with this software.
9 9 #-----------------------------------------------------------------------------
10 10
11 11 #-----------------------------------------------------------------------------
12 12 # Imports
13 13 #-----------------------------------------------------------------------------
14 14
15 15 import os
16 16
17 17 from IPython.testing.decorators import onlyif_cmds_exist
18 18
19 19 from ...tests.base import TestsBase
20 20
21 21 #-----------------------------------------------------------------------------
22 22 # Class
23 23 #-----------------------------------------------------------------------------
24 24
25 25 all_raw_mimetypes = {
26 'application/x-python',
26 'text/x-python',
27 27 'text/markdown',
28 28 'text/html',
29 29 'text/restructuredtext',
30 30 'text/latex',
31 31 }
32 32
33 33 class ExportersTestsBase(TestsBase):
34 34 """Contains base test functions for exporters"""
35 35
36 36 exporter_class = None
37 37 should_include_raw = None
38 38
39 39 def _get_notebook(self, nb_name='notebook2.ipynb'):
40 40 return os.path.join(self._get_files_path(), nb_name)
41 41
42 42 @onlyif_cmds_exist('pandoc')
43 43 def test_raw_cell_inclusion(self):
44 44 """test raw cell inclusion based on raw_mimetype metadata"""
45 45 if self.should_include_raw is None:
46 46 return
47 47 exporter = self.exporter_class()
48 48 (output, resources) = exporter.from_filename(self._get_notebook('rawtest.ipynb'))
49 49 for inc in self.should_include_raw:
50 50 self.assertIn('raw %s' % inc, output, "should include %s" % inc)
51 51 self.assertIn('no raw_mimetype metadata', output)
52 52 for exc in all_raw_mimetypes.difference(self.should_include_raw):
53 53 self.assertNotIn('raw %s' % exc, output, "should exclude %s" % exc)
54 54 self.assertNotIn('never be included', output)
@@ -1,84 +1,84
1 1 {
2 2 "metadata": {
3 3 "name": ""
4 4 },
5 5 "nbformat": 3,
6 6 "nbformat_minor": 0,
7 7 "worksheets": [
8 8 {
9 9 "cells": [
10 10 {
11 11 "cell_type": "raw",
12 12 "metadata": {
13 13 "raw_mimetype": "text/html"
14 14 },
15 15 "source": [
16 16 "<b>raw html</b>"
17 17 ]
18 18 },
19 19 {
20 20 "cell_type": "raw",
21 21 "metadata": {
22 22 "raw_mimetype": "text/markdown"
23 23 },
24 24 "source": [
25 25 "* raw markdown\n",
26 26 "* bullet\n",
27 27 "* list"
28 28 ]
29 29 },
30 30 {
31 31 "cell_type": "raw",
32 32 "metadata": {
33 33 "raw_mimetype": "text/restructuredtext"
34 34 },
35 35 "source": [
36 36 "``raw rst``\n",
37 37 "\n",
38 38 ".. sourcecode:: python\n",
39 39 "\n",
40 40 " def foo(): pass\n"
41 41 ]
42 42 },
43 43 {
44 44 "cell_type": "raw",
45 45 "metadata": {
46 "raw_mimetype": "application/x-python"
46 "raw_mimetype": "text/x-python"
47 47 },
48 48 "source": [
49 49 "def bar():\n",
50 50 " \"\"\"raw python\"\"\"\n",
51 51 " pass"
52 52 ]
53 53 },
54 54 {
55 55 "cell_type": "raw",
56 56 "metadata": {
57 57 "raw_mimetype": "text/latex"
58 58 },
59 59 "source": [
60 60 "\\LaTeX\n",
61 61 "% raw latex"
62 62 ]
63 63 },
64 64 {
65 65 "cell_type": "raw",
66 66 "metadata": {},
67 67 "source": [
68 68 "# no raw_mimetype metadata, should be included by default"
69 69 ]
70 70 },
71 71 {
72 72 "cell_type": "raw",
73 73 "metadata": {
74 74 "raw_mimetype": "doesnotexist"
75 75 },
76 76 "source": [
77 77 "garbage format defined, should never be included"
78 78 ]
79 79 }
80 80 ],
81 81 "metadata": {}
82 82 }
83 83 ]
84 } No newline at end of file
84 }
@@ -1,98 +1,98
1 1 ((= Auto-generated template file, DO NOT edit directly!
2 2 To edit this file, please refer to ../../skeleton/README.md =))
3 3
4 4
5 5 ((=
6 6
7 7 DO NOT USE THIS AS A BASE,
8 8 IF YOU ARE COPY AND PASTING THIS FILE
9 9 YOU ARE PROBABLY DOING THINGS INCORRECTLY.
10 10
11 11 Null template, does nothing except defining a basic structure
12 12 To layout the different blocks of a notebook.
13 13
14 14 Subtemplates can override blocks to define their custom representation.
15 15
16 16 If one of the block you do overwrite is not a leave block, consider
17 17 calling super.
18 18
19 19 ((*- block nonLeaveBlock -*))
20 20 #add stuff at beginning
21 21 ((( super() )))
22 22 #add stuff at end
23 23 ((*- endblock nonLeaveBlock -*))
24 24
25 25 consider calling super even if it is a leave block, we might insert more blocks later.
26 26
27 27 =))
28 28 ((*- block header -*))
29 29 ((*- endblock header -*))
30 30 ((*- block body -*))
31 31 ((*- for worksheet in nb.worksheets -*))
32 32 ((*- for cell in worksheet.cells -*))
33 33 ((*- block any_cell scoped -*))
34 34 ((*- if cell.cell_type in ['code'] -*))
35 35 ((*- block codecell scoped -*))
36 36 ((*- block input_group -*))
37 37 ((*- block in_prompt -*))((*- endblock in_prompt -*))
38 38 ((*- block input -*))((*- endblock input -*))
39 39 ((*- endblock input_group -*))
40 40 ((*- if cell.outputs -*))
41 41 ((*- block output_group -*))
42 42 ((*- block output_prompt -*))((*- endblock output_prompt -*))
43 43 ((*- block outputs scoped -*))
44 44 ((*- for output in cell.outputs -*))
45 45 ((*- block output scoped -*))
46 46 ((*- if output.output_type in ['pyout'] -*))
47 47 ((*- block pyout scoped -*))((*- endblock pyout -*))
48 48 ((*- elif output.output_type in ['stream'] -*))
49 49 ((*- block stream scoped -*))
50 50 ((*- if output.stream in ['stdout'] -*))
51 51 ((*- block stream_stdout scoped -*))
52 52 ((*- endblock stream_stdout -*))
53 53 ((*- elif output.stream in ['stderr'] -*))
54 54 ((*- block stream_stderr scoped -*))
55 55 ((*- endblock stream_stderr -*))
56 56 ((*- endif -*))
57 57 ((*- endblock stream -*))
58 58 ((*- elif output.output_type in ['display_data'] -*))
59 59 ((*- block display_data scoped -*))
60 60 ((*- block data_priority scoped -*))
61 61 ((*- endblock data_priority -*))
62 62 ((*- endblock display_data -*))
63 63 ((*- elif output.output_type in ['pyerr'] -*))
64 64 ((*- block pyerr scoped -*))
65 65 ((*- for line in output.traceback -*))
66 66 ((*- block traceback_line scoped -*))((*- endblock traceback_line -*))
67 67 ((*- endfor -*))
68 68 ((*- endblock pyerr -*))
69 69 ((*- endif -*))
70 70 ((*- endblock output -*))
71 71 ((*- endfor -*))
72 72 ((*- endblock outputs -*))
73 73 ((*- endblock output_group -*))
74 74 ((*- endif -*))
75 75 ((*- endblock codecell -*))
76 76 ((*- elif cell.cell_type in ['markdown'] -*))
77 77 ((*- block markdowncell scoped-*))
78 78 ((*- endblock markdowncell -*))
79 79 ((*- elif cell.cell_type in ['heading'] -*))
80 80 ((*- block headingcell scoped-*))
81 81 ((*- endblock headingcell -*))
82 82 ((*- elif cell.cell_type in ['raw'] -*))
83 83 ((*- block rawcell scoped -*))
84 ((* if cell.metadata.get('raw_mimetype', resources.get('raw_mimetype')) == resources.get('raw_mimetype') *))
84 ((* if cell.metadata.get('raw_mimetype', '').lower() in resources.get('raw_mimetypes', ['']) *))
85 85 ((( cell.source )))
86 86 ((* endif *))
87 87 ((*- endblock rawcell -*))
88 88 ((*- else -*))
89 89 ((*- block unknowncell scoped-*))
90 90 ((*- endblock unknowncell -*))
91 91 ((*- endif -*))
92 92 ((*- endblock any_cell -*))
93 93 ((*- endfor -*))
94 94 ((*- endfor -*))
95 95 ((*- endblock body -*))
96 96
97 97 ((*- block footer -*))
98 98 ((*- endblock footer -*))
@@ -1,94 +1,94
1 1 {#
2 2
3 3 DO NOT USE THIS AS A BASE,
4 4 IF YOU ARE COPY AND PASTING THIS FILE
5 5 YOU ARE PROBABLY DOING THINGS INCORRECTLY.
6 6
7 7 Null template, does nothing except defining a basic structure
8 8 To layout the different blocks of a notebook.
9 9
10 10 Subtemplates can override blocks to define their custom representation.
11 11
12 12 If one of the block you do overwrite is not a leave block, consider
13 13 calling super.
14 14
15 15 {%- block nonLeaveBlock -%}
16 16 #add stuff at beginning
17 17 {{ super() }}
18 18 #add stuff at end
19 19 {%- endblock nonLeaveBlock -%}
20 20
21 21 consider calling super even if it is a leave block, we might insert more blocks later.
22 22
23 23 #}
24 24 {%- block header -%}
25 25 {%- endblock header -%}
26 26 {%- block body -%}
27 27 {%- for worksheet in nb.worksheets -%}
28 28 {%- for cell in worksheet.cells -%}
29 29 {%- block any_cell scoped -%}
30 30 {%- if cell.cell_type in ['code'] -%}
31 31 {%- block codecell scoped -%}
32 32 {%- block input_group -%}
33 33 {%- block in_prompt -%}{%- endblock in_prompt -%}
34 34 {%- block input -%}{%- endblock input -%}
35 35 {%- endblock input_group -%}
36 36 {%- if cell.outputs -%}
37 37 {%- block output_group -%}
38 38 {%- block output_prompt -%}{%- endblock output_prompt -%}
39 39 {%- block outputs scoped -%}
40 40 {%- for output in cell.outputs -%}
41 41 {%- block output scoped -%}
42 42 {%- if output.output_type in ['pyout'] -%}
43 43 {%- block pyout scoped -%}{%- endblock pyout -%}
44 44 {%- elif output.output_type in ['stream'] -%}
45 45 {%- block stream scoped -%}
46 46 {%- if output.stream in ['stdout'] -%}
47 47 {%- block stream_stdout scoped -%}
48 48 {%- endblock stream_stdout -%}
49 49 {%- elif output.stream in ['stderr'] -%}
50 50 {%- block stream_stderr scoped -%}
51 51 {%- endblock stream_stderr -%}
52 52 {%- endif -%}
53 53 {%- endblock stream -%}
54 54 {%- elif output.output_type in ['display_data'] -%}
55 55 {%- block display_data scoped -%}
56 56 {%- block data_priority scoped -%}
57 57 {%- endblock data_priority -%}
58 58 {%- endblock display_data -%}
59 59 {%- elif output.output_type in ['pyerr'] -%}
60 60 {%- block pyerr scoped -%}
61 61 {%- for line in output.traceback -%}
62 62 {%- block traceback_line scoped -%}{%- endblock traceback_line -%}
63 63 {%- endfor -%}
64 64 {%- endblock pyerr -%}
65 65 {%- endif -%}
66 66 {%- endblock output -%}
67 67 {%- endfor -%}
68 68 {%- endblock outputs -%}
69 69 {%- endblock output_group -%}
70 70 {%- endif -%}
71 71 {%- endblock codecell -%}
72 72 {%- elif cell.cell_type in ['markdown'] -%}
73 73 {%- block markdowncell scoped-%}
74 74 {%- endblock markdowncell -%}
75 75 {%- elif cell.cell_type in ['heading'] -%}
76 76 {%- block headingcell scoped-%}
77 77 {%- endblock headingcell -%}
78 78 {%- elif cell.cell_type in ['raw'] -%}
79 79 {%- block rawcell scoped -%}
80 {% if cell.metadata.get('raw_mimetype', resources.get('raw_mimetype', '')).lower() in resources.get('raw_mimetypes', ['']) %}
80 {% if cell.metadata.get('raw_mimetype', '').lower() in resources.get('raw_mimetypes', ['']) %}
81 81 {{ cell.source }}
82 82 {% endif %}
83 83 {%- endblock rawcell -%}
84 84 {%- else -%}
85 85 {%- block unknowncell scoped-%}
86 86 {%- endblock unknowncell -%}
87 87 {%- endif -%}
88 88 {%- endblock any_cell -%}
89 89 {%- endfor -%}
90 90 {%- endfor -%}
91 91 {%- endblock body -%}
92 92
93 93 {%- block footer -%}
94 94 {%- endblock footer -%}
General Comments 0
You need to be logged in to leave comments. Login now