Show More
@@ -282,9 +282,8 b' class DisplayHook(Configurable):' | |||
|
282 | 282 | """Log the output.""" |
|
283 | 283 | if self.shell.logger.log_output: |
|
284 | 284 | self.shell.logger.log_write(format_dict['text/plain'], 'output') |
|
285 | # This is a defaultdict of lists, so we can always append | |
|
286 | self.shell.history_manager.output_hist_reprs[self.prompt_count]\ | |
|
287 | .append(format_dict['text/plain']) | |
|
285 | self.shell.history_manager.output_hist_reprs[self.prompt_count] = \ | |
|
286 | format_dict['text/plain'] | |
|
288 | 287 | |
|
289 | 288 | def finish_displayhook(self): |
|
290 | 289 | """Finish up all displayhook activities.""" |
@@ -15,14 +15,11 b' from __future__ import print_function' | |||
|
15 | 15 | # Stdlib imports |
|
16 | 16 | import atexit |
|
17 | 17 | import datetime |
|
18 | import json | |
|
19 | 18 | import os |
|
20 | 19 | import re |
|
21 | 20 | import sqlite3 |
|
22 | 21 | import threading |
|
23 | 22 | |
|
24 | from collections import defaultdict | |
|
25 | ||
|
26 | 23 | # Our own packages |
|
27 | 24 | from IPython.config.configurable import Configurable |
|
28 | 25 | import IPython.utils.io |
@@ -56,11 +53,10 b' class HistoryManager(Configurable):' | |||
|
56 | 53 | return [] |
|
57 | 54 | |
|
58 | 55 | # A dict of output history, keyed with ints from the shell's |
|
59 | # execution count. If there are several outputs from one command, | |
|
60 | # only the last one is stored. | |
|
56 | # execution count. | |
|
61 | 57 | output_hist = Dict() |
|
62 | # Contains all outputs, in lists of reprs. | |
|
63 |
output_hist_reprs = |
|
|
58 | # The text/plain repr of outputs. | |
|
59 | output_hist_reprs = Dict() | |
|
64 | 60 | |
|
65 | 61 | # String holding the path to the history file |
|
66 | 62 | hist_file = Unicode(config=True) |
@@ -92,11 +88,10 b' class HistoryManager(Configurable):' | |||
|
92 | 88 | _ii = Unicode(u'') |
|
93 | 89 | _iii = Unicode(u'') |
|
94 | 90 | |
|
95 |
# A |
|
|
96 |
# the history (it's annoying to rewind the first entry and land on |
|
|
97 | # call). | |
|
98 | _exit_commands = Instance(set, args=(['Quit', 'quit', 'Exit', 'exit', | |
|
99 | '%Quit', '%quit', '%Exit', '%exit'],)) | |
|
91 | # A regex matching all forms of the exit command, so that we don't store | |
|
92 | # them in the history (it's annoying to rewind the first entry and land on | |
|
93 | # an exit call). | |
|
94 | _exit_re = re.compile(r"(exit|quit)(\s*\(.*\))?$") | |
|
100 | 95 | |
|
101 | 96 | def __init__(self, shell, config=None, **traits): |
|
102 | 97 | """Create a new history manager associated with a shell instance. |
@@ -218,9 +213,7 b' class HistoryManager(Configurable):' | |||
|
218 | 213 | cur = self.db.execute("SELECT session, line, %s FROM %s " %\ |
|
219 | 214 | (toget, sqlfrom) + sql, params) |
|
220 | 215 | if output: # Regroup into 3-tuples, and parse JSON |
|
221 | loads = lambda out: json.loads(out) if out else None | |
|
222 | return ((ses, lin, (inp, loads(out))) \ | |
|
223 | for ses, lin, inp, out in cur) | |
|
216 | return ((ses, lin, (inp, out)) for ses, lin, inp, out in cur) | |
|
224 | 217 | return cur |
|
225 | 218 | |
|
226 | 219 | |
@@ -383,7 +376,7 b' class HistoryManager(Configurable):' | |||
|
383 | 376 | source_raw = source_raw.rstrip('\n') |
|
384 | 377 | |
|
385 | 378 | # do not store exit/quit commands |
|
386 | if source_raw.strip() in self._exit_commands: | |
|
379 | if self._exit_re.match(source_raw.strip()): | |
|
387 | 380 | return |
|
388 | 381 | |
|
389 | 382 | self.input_hist_parsed.append(source) |
@@ -419,9 +412,9 b' class HistoryManager(Configurable):' | |||
|
419 | 412 | line_num : int |
|
420 | 413 | The line number from which to save outputs |
|
421 | 414 | """ |
|
422 |
if (not self.db_log_output) or not self.output_hist_reprs |
|
|
415 | if (not self.db_log_output) or (line_num not in self.output_hist_reprs): | |
|
423 | 416 | return |
|
424 |
output = |
|
|
417 | output = self.output_hist_reprs[line_num] | |
|
425 | 418 | |
|
426 | 419 | with self.db_output_cache_lock: |
|
427 | 420 | self.db_output_cache.append((line_num, output)) |
@@ -696,7 +689,7 b" def magic_history(self, parameter_s = ''):" | |||
|
696 | 689 | inline = "\n... ".join(inline.splitlines()) + "\n..." |
|
697 | 690 | print(inline, file=outfile) |
|
698 | 691 | if get_output and output: |
|
699 |
print( |
|
|
692 | print(output, file=outfile) | |
|
700 | 693 | |
|
701 | 694 | if close_at_end: |
|
702 | 695 | outfile.close() |
@@ -2150,12 +2150,9 b' class InteractiveShell(Configurable, Magic):' | |||
|
2150 | 2150 | self.showsyntaxerror() |
|
2151 | 2151 | self.execution_count += 1 |
|
2152 | 2152 | return None |
|
2153 | ||
|
2154 | interactivity = 'last' # Last node to be run interactive | |
|
2155 | if len(cell.splitlines()) == 1: | |
|
2156 | interactivity = 'all' # Single line; run fully interactive | |
|
2157 | 2153 | |
|
2158 |
self.run_ast_nodes(code_ast.body, cell_name, |
|
|
2154 | self.run_ast_nodes(code_ast.body, cell_name, | |
|
2155 | interactivity="last_expr") | |
|
2159 | 2156 | |
|
2160 | 2157 | # Execute any registered post-execution functions. |
|
2161 | 2158 | for func, status in self._post_execute.iteritems(): |
@@ -2175,7 +2172,7 b' class InteractiveShell(Configurable, Magic):' | |||
|
2175 | 2172 | # Each cell is a *single* input, regardless of how many lines it has |
|
2176 | 2173 | self.execution_count += 1 |
|
2177 | 2174 | |
|
2178 | def run_ast_nodes(self, nodelist, cell_name, interactivity='last'): | |
|
2175 | def run_ast_nodes(self, nodelist, cell_name, interactivity='last_expr'): | |
|
2179 | 2176 | """Run a sequence of AST nodes. The execution mode depends on the |
|
2180 | 2177 | interactivity parameter. |
|
2181 | 2178 | |
@@ -2187,13 +2184,21 b' class InteractiveShell(Configurable, Magic):' | |||
|
2187 | 2184 | Will be passed to the compiler as the filename of the cell. Typically |
|
2188 | 2185 | the value returned by ip.compile.cache(cell). |
|
2189 | 2186 | interactivity : str |
|
2190 |
'all', 'last' or 'none', specifying which nodes should be |
|
|
2191 |
interactively (displaying output from expressions). |
|
|
2192 | this parameter will raise a ValueError. | |
|
2187 | 'all', 'last', 'last_expr' or 'none', specifying which nodes should be | |
|
2188 | run interactively (displaying output from expressions). 'last_expr' | |
|
2189 | will run the last node interactively only if it is an expression (i.e. | |
|
2190 | expressions in loops or other blocks are not displayed. Other values | |
|
2191 | for this parameter will raise a ValueError. | |
|
2193 | 2192 | """ |
|
2194 | 2193 | if not nodelist: |
|
2195 | 2194 | return |
|
2196 | 2195 | |
|
2196 | if interactivity == 'last_expr': | |
|
2197 | if isinstance(nodelist[-1], ast.Expr): | |
|
2198 | interactivity = "last" | |
|
2199 | else: | |
|
2200 | interactivity = "none" | |
|
2201 | ||
|
2197 | 2202 | if interactivity == 'none': |
|
2198 | 2203 | to_run_exec, to_run_interactive = nodelist, [] |
|
2199 | 2204 | elif interactivity == 'last': |
@@ -33,7 +33,7 b' def test_history():' | |||
|
33 | 33 | |
|
34 | 34 | ip.history_manager.db_log_output = True |
|
35 | 35 | # Doesn't match the input, but we'll just check it's stored. |
|
36 |
ip.history_manager.output_hist_reprs[3] |
|
|
36 | ip.history_manager.output_hist_reprs[3] = "spam" | |
|
37 | 37 | ip.history_manager.store_output(3) |
|
38 | 38 | |
|
39 | 39 | nt.assert_equal(ip.history_manager.input_hist_raw, [''] + hist) |
@@ -53,7 +53,7 b' def test_history():' | |||
|
53 | 53 | # Check get_hist_tail |
|
54 | 54 | gothist = ip.history_manager.get_tail(4, output=True, |
|
55 | 55 | include_latest=True) |
|
56 |
expected = [(1, 3, (hist[-1], |
|
|
56 | expected = [(1, 3, (hist[-1], "spam")), | |
|
57 | 57 | (2, 1, (newcmds[0], None)), |
|
58 | 58 | (2, 2, (newcmds[1], None)), |
|
59 | 59 | (2, 3, (newcmds[2], None)),] |
@@ -68,7 +68,7 b' def test_history():' | |||
|
68 | 68 | gothist = ip.history_manager.search("*test*") |
|
69 | 69 | nt.assert_equal(list(gothist), [(1,2,hist[1])] ) |
|
70 | 70 | gothist = ip.history_manager.search("b*", output=True) |
|
71 |
nt.assert_equal(list(gothist), [(1,3,(hist[2], |
|
|
71 | nt.assert_equal(list(gothist), [(1,3,(hist[2],"spam"))] ) | |
|
72 | 72 | |
|
73 | 73 | # Cross testing: check that magic %save can get previous session. |
|
74 | 74 | testfilename = os.path.realpath(os.path.join(tmpdir, "test.py")) |
General Comments 0
You need to be logged in to leave comments.
Login now