Repository: ipython/ipython

Issue:
Test displayhook
This is a work in progress and the tests will fail. We will fix in a later commit. This is a test for #8002.

updated quiet function in the displayhook.py
Updated quiet function in the displayhook.py to properly recognize comment and semicolon by using the tokenize module. Thanks to @takluyver for heavy input and assistance in writing this code.



Discussion:

Resolving patch:
diff --git a/IPython/core/displayhook.py b/IPython/core/displayhook.py
--- a/IPython/core/displayhook.py
+++ b/IPython/core/displayhook.py
@@ -10,11 +10,13 @@
 from __future__ import print_function
 
 import sys
+import io as _io
+import tokenize
 
 from IPython.core.formatters import _safe_get_formatter_method
 from traitlets.config.configurable import Configurable
 from IPython.utils import io
-from IPython.utils.py3compat import builtin_mod
+from IPython.utils.py3compat import builtin_mod, cast_unicode_py2
 from traitlets import Instance, Float
 from IPython.utils.warn import warn
 
@@ -83,12 +85,23 @@ def check_for_underscore(self):
     def quiet(self):
         """Should we silence the display hook because of ';'?"""
         # do not print output if input ends in ';'
+        
         try:
-            cell = self.shell.history_manager.input_hist_parsed[self.prompt_count]
-            return cell.rstrip().endswith(';')
+            cell = cast_unicode_py2(self.shell.history_manager.input_hist_parsed[-1])
         except IndexError:
             # some uses of ipshellembed may fail here
             return False
+        
+        sio = _io.StringIO(cell)
+        tokens = list(tokenize.generate_tokens(sio.readline))
+
+        for token in reversed(tokens):
+            if token[0] in (tokenize.ENDMARKER, tokenize.COMMENT):
+                continue
+            if (token[0] == tokenize.OP) and (token[1] == ';'):
+                return True
+            else:
+                return False
 
     def start_displayhook(self):
         """Start the displayhook, initializing resources."""


Test patch:
diff --git a/IPython/core/tests/test_displayhook.py b/IPython/core/tests/test_displayhook.py
new file mode 100644
--- /dev/null
+++ b/IPython/core/tests/test_displayhook.py
@@ -0,0 +1,21 @@
+from IPython.testing.tools import AssertPrints, AssertNotPrints
+
+ip = get_ipython()
+
+def test_output_displayed():
+    """Checking to make sure that output is displayed"""
+  
+    with AssertPrints('2'):
+       ip.run_cell('1+1', store_history=True)
+      
+    with AssertPrints('2'):
+        ip.run_cell('1+1 # comment with a semicolon;', store_history=True)
+      
+def test_output_quiet():
+    """Checking to make sure that output is quiet"""
+  
+    with AssertNotPrints('2'):
+        ip.run_cell('1+1;', store_history=True)
+      
+    with AssertNotPrints('2'):
+        ip.run_cell('1+1; # comment with a semicolon', store_history=True)
diff --git a/IPython/lib/tests/test_deepreload.py b/IPython/lib/tests/test_deepreload.py
--- a/IPython/lib/tests/test_deepreload.py
+++ b/IPython/lib/tests/test_deepreload.py
@@ -27,7 +27,7 @@ def test_deepreload_numpy():
         # Standard exclusions:
         'sys', 'os.path', builtin_mod_name, '__main__',
         # Test-related exclusions:
-        'unittest', 'UserDict',
+        'unittest', 'UserDict', '_collections_abc', 'tokenize'
         ]
 
     # `collections` builtin shall not be reloaded to avoid failure