##// END OF EJS Templates
Reimplemented IPythonWidget's edit magic handling to support line numbers. Also, removed the code path for launching the file with the system default Python application, as this is too dangerous.
epatters -
Show More
@@ -1,3 +1,11 b''
1 """ A FrontendWidget that emulates the interface of the console IPython and
2 supports the additional functionality provided by the IPython kernel.
3
4 TODO: Add support for retrieving the system default editor. Requires code
5 paths for Windows (use the registry), Mac OS (use LaunchServices), and
6 Linux (use the xdg system).
7 """
8
1 9 # Standard library imports
2 10 from subprocess import Popen
3 11
@@ -153,7 +161,7 b' class IPythonWidget(FrontendWidget):'
153 161 """ Reimplemented to handle %edit and paging payloads.
154 162 """
155 163 if item['source'] == self._payload_source_edit:
156 self.edit(item['filename'], item['line_number'])
164 self._edit(item['filename'], item['line_number'])
157 165 return True
158 166 elif item['source'] == self._payload_source_page:
159 167 self._page(item['data'])
@@ -218,61 +226,34 b' class IPythonWidget(FrontendWidget):'
218 226 # 'IPythonWidget' interface
219 227 #---------------------------------------------------------------------------
220 228
221 def edit(self, filename, line=None):
222 """ Opens a Python script for editing.
223
224 Parameters:
225 -----------
226 filename : str
227 A path to a local system file.
228
229 line : int, optional
230 A line of interest in the file.
231
232 Raises:
233 -------
234 OSError
235 If the editor command cannot be executed.
236 """
237 if self._editor == 'default':
238 url = QtCore.QUrl.fromLocalFile(filename)
239 if not QtGui.QDesktopServices.openUrl(url):
240 message = 'Failed to open %s with the default application'
241 raise OSError(message % repr(filename))
242 elif self._editor is None:
243 self.custom_edit_requested.emit(filename, line)
244 else:
245 Popen(self._editor + [filename])
246
247 229 def reset_styling(self):
248 230 """ Restores the default IPythonWidget styling.
249 231 """
250 232 self.set_styling(self.default_stylesheet, syntax_style='default')
251 233 #self.set_styling(self.dark_stylesheet, syntax_style='monokai')
252 234
253 def set_editor(self, editor):
235 def set_editor(self, editor, line_editor=None):
254 236 """ Sets the editor to use with the %edit magic.
255 237
256 238 Parameters:
257 239 -----------
258 editor : str or sequence of str
259 A command suitable for use with Popen. This command will be executed
260 with a single argument--a filename--when editing is requested.
240 editor : str
241 A command for invoking a system text editor. If the string contains
242 a {filename} format specifier, it will be used. Otherwise, the
243 filename will be appended to the end the command.
261 244
262 This parameter also takes two special values:
263 'default' : Files will be edited with the system default
264 application for Python files.
245 This parameter also takes a special value:
265 246 'custom' : Emit a 'custom_edit_requested(str, int)' signal
266 247 instead of opening an editor.
248
249 line_editor : str, optional
250 The editor command to use when a specific line number is
251 requested. The string should contain two format specifiers: {line}
252 and {filename}. If this parameter is not specified, the line number
253 option to the %edit magic will be ignored.
267 254 """
268 if editor == 'default':
269 self._editor = 'default'
270 elif editor == 'custom':
271 self._editor = None
272 elif isinstance(editor, basestring):
273 self._editor = [ editor ]
274 else:
275 self._editor = list(editor)
255 self._editor = editor
256 self._editor_line = line_editor
276 257
277 258 def set_styling(self, stylesheet, syntax_style=None):
278 259 """ Sets the IPythonWidget styling.
@@ -303,6 +284,43 b' class IPythonWidget(FrontendWidget):'
303 284 # 'IPythonWidget' protected interface
304 285 #---------------------------------------------------------------------------
305 286
287 def _edit(self, filename, line=None):
288 """ Opens a Python script for editing.
289
290 Parameters:
291 -----------
292 filename : str
293 A path to a local system file.
294
295 line : int, optional
296 A line of interest in the file.
297 """
298 if self._editor == 'custom':
299 self.custom_edit_requested.emit(filename, line)
300 elif self._editor == 'default':
301 self._append_plain_text('No default editor available.\n')
302 else:
303 try:
304 filename = '"%s"' % filename
305 if line and self._editor_line:
306 command = self._editor_line.format(filename=filename,
307 line=line)
308 else:
309 try:
310 command = self._editor.format()
311 except KeyError:
312 command = self._editor.format(filename=filename)
313 else:
314 command += ' ' + filename
315 except KeyError:
316 self._append_plain_text('Invalid editor command.\n')
317 else:
318 try:
319 Popen(command, shell=True)
320 except OSError:
321 msg = 'Opening editor with command "%s" failed.\n'
322 self._append_plain_text(msg % command)
323
306 324 def _make_in_prompt(self, number):
307 325 """ Given a prompt number, returns an HTML In prompt.
308 326 """
General Comments 0
You need to be logged in to leave comments. Login now