Reputation: 31
How to build a custom IPython magic command that:
Similar cases
%matplotlib
,
%pdb
,
%doctest_mode
Example
In [1]: %myMagic 1
Out[1]: myMagic is: ON
In [2]: x = 1
Out[2]: 'Hello World'
In [3]: x
Out[3]: 'Hello World'
...: 1
In [4]: %myMagic 0
Out[4]: myMagic is: OFF
In [5]: y=x+1
...: y
Out[5]: 2
Upvotes: 3
Views: 375
Reputation: 1832
I'm currently working on a Jupyter nbextension where I want to wrap a code cell's entire contents in a specific context manager before the kernel executes it, where code cells are wrapped or not based upon various user-configurable logic.
As far as I've been able to determine, it's not possible to do what you want using magics, because magics aren't able to hook into the execution machinery of the IPython kernel itself. As best I know, all of those magics you mention work by changing settings within some specific module or class, which then control the global behavior of that module/class in the rest of the notebook.
What I've had to do is approach this from the nbextension side, where I fetch the cell code in the frontend Javascript, inject my context manager, indent the block, and then submit the edited code for execution by the kernel. For reference, my WIP as of this writing is here; a barebones implementation is:
define([
'notebook/js/codecell'
], function (codecell) {
"use strict";
var CodeCell = codecell.CodeCell
return {
load_ipython_extension: function () {
/* Store the original .execute() before overriding,
* for use in the overridden method
*/
var orig_execute = CodeCell.prototype.execute;
// Override .execute()
CodeCell.prototype.execute = function (stop_on_error) {
var orig_text = this.get_text();
var new_text = orig_text;
/* == Make whatever modifications to new_text == */
/* Rewrite the cell text, make the .execute() call,
* and restore the original cell text
*/
this.set_text(new_text);
orig_execute.call(this, stop_on_error);
this.set_text(orig_text);
};
}
};
});
Upvotes: 1