[tor-commits] [stem/master] Tests required sqlite3

atagar at torproject.org atagar at torproject.org
Wed Feb 26 23:02:10 UTC 2020


commit c4072bd1705e1996eecc3236995c26e9a3fbf8bd
Author: Damian Johnson <atagar at torproject.org>
Date:   Tue Feb 18 14:45:57 2020 -0800

    Tests required sqlite3
    
    Python includes sqlite3 as a builtin, but when you compile python yourself it
    isn't included by default. Our stem.manual attempted to account for this but
    our tests didn't, and with python3 the module raises a ModuleNotFoundError
    rather than an ImportError.
    
      Traceback (most recent call last):
        File "/home/atagar/Desktop/stem/test/task.py", line 160, in _import_tests
          importlib.import_module(module.rsplit('.', 1)[0])
        File "/home/atagar/Python-3.8.1/Lib/importlib/__init__.py", line 127, in import_module
          return _bootstrap._gcd_import(name[level:], package, level)
        File "<frozen importlib._bootstrap>", line 1014, in _gcd_import
        File "<frozen importlib._bootstrap>", line 991, in _find_and_load
        File "<frozen importlib._bootstrap>", line 975, in _find_and_load_unlocked
        File "<frozen importlib._bootstrap>", line 671, in _load_unlocked
        File "<frozen importlib._bootstrap_external>", line 783, in exec_module
        File "<frozen importlib._bootstrap>", line 219, in _call_with_frames_removed
        File "/home/atagar/Desktop/stem/test/unit/manual.py", line 8, in <module>
          import sqlite3
        File "/home/atagar/Python-3.8.1/Lib/sqlite3/__init__.py", line 23, in <module>
          from sqlite3.dbapi2 import *
        File "/home/atagar/Python-3.8.1/Lib/sqlite3/dbapi2.py", line 27, in <module>
          from _sqlite3 import *
      ModuleNotFoundError: No module named '_sqlite3'
---
 stem/manual.py       |  6 +++---
 test/require.py      | 14 ++++++++++++++
 test/unit/doctest.py |  6 ++++++
 test/unit/manual.py  |  9 ++++++++-
 4 files changed, 31 insertions(+), 4 deletions(-)

diff --git a/stem/manual.py b/stem/manual.py
index 44117f93..367b6d7e 100644
--- a/stem/manual.py
+++ b/stem/manual.py
@@ -135,7 +135,7 @@ def query(query, *param):
 
   try:
     import sqlite3
-  except ImportError:
+  except (ImportError, ModuleNotFoundError):
     raise ImportError('Querying requires the sqlite3 module')
 
   # The only reason to explicitly close the sqlite connection is to ensure
@@ -386,7 +386,7 @@ class Manual(object):
 
     try:
       import sqlite3
-    except ImportError:
+    except (ImportError, ModuleNotFoundError):
       raise ImportError('Reading a sqlite cache requires the sqlite3 module')
 
     if path is None:
@@ -518,7 +518,7 @@ class Manual(object):
 
     try:
       import sqlite3
-    except ImportError:
+    except (ImportError, ModuleNotFoundError):
       raise ImportError('Saving a sqlite cache requires the sqlite3 module')
 
     tmp_path = path + '.new'
diff --git a/test/require.py b/test/require.py
index 53d66f62..8054bfad 100644
--- a/test/require.py
+++ b/test/require.py
@@ -99,6 +99,20 @@ def command(cmd):
   return needs(lambda: stem.util.system.is_available(cmd), '%s unavailable' % cmd)
 
 
+def module(module_name):
+  """
+  Skip test unless this module is available.
+  """
+
+  try:
+    import module_name
+    available = True
+  except ImportError:
+    available = False
+
+  return needs(lambda: available, '%s unavailable' % module_name)
+
+
 def version(req_version):
   """
   Skips the test unless we meet the required version.
diff --git a/test/unit/doctest.py b/test/unit/doctest.py
index 84712dc2..120940ba 100644
--- a/test/unit/doctest.py
+++ b/test/unit/doctest.py
@@ -119,6 +119,12 @@ class TestDocumentation(unittest.TestCase):
       elif path.endswith('/stem/version.py'):
         with patch('stem.version.get_system_tor_version', Mock(return_value = stem.version.Version('0.2.1.30'))):
           test_run = doctest.testfile(path, **args)
+      elif path.endswith('/stem/manual.py'):
+        try:
+          import sqlite3
+          test_run = doctest.testfile(path, **args)
+        except ImportError:
+          pass  # manual module requires sqlite3
       else:
         test_run = doctest.testfile(path, **args)
 
diff --git a/test/unit/manual.py b/test/unit/manual.py
index 006e0b3e..26cb83d8 100644
--- a/test/unit/manual.py
+++ b/test/unit/manual.py
@@ -5,7 +5,6 @@ Unit testing for the stem.manual module.
 import collections
 import io
 import os
-import sqlite3
 import tempfile
 import unittest
 import urllib.request
@@ -90,13 +89,18 @@ def _cached_manual():
 
 
 class TestManual(unittest.TestCase):
+  @test.require.module('sqlite3')
   def test_query(self):
     self.assertEqual("If set, this option overrides the default location and file name for Tor's cookie file. (See CookieAuthentication above.)", stem.manual.query('SELECT description FROM torrc WHERE name="CookieAuthFile"').fetchone()[0])
     self.assertEqual("If set, this option overrides the default location and file name for Tor's cookie file. (See CookieAuthentication above.)", stem.manual.query('SELECT description FROM torrc WHERE name=?', 'CookieAuthFile').fetchone()[0])
 
+  @test.require.module('sqlite3')
   def test_query_on_failure(self):
+    import sqlite3
+
     self.assertRaisesWith(sqlite3.OperationalError, 'near "hello": syntax error', stem.manual.query, 'hello world')
 
+  @test.require.module('sqlite3')
   def test_has_all_summaries(self):
     """
     Check that we have brief, human readable summaries for all of tor's
@@ -182,6 +186,7 @@ class TestManual(unittest.TestCase):
     self.assertEqual('Description of this new option.', option.description)
 
   @test.require.command('man')
+  @test.require.module('sqlite3')
   def test_saving_manual_as_config(self):
     """
     Check that we can save and reload manuals as a config.
@@ -198,6 +203,7 @@ class TestManual(unittest.TestCase):
       self.assertEqual(manual, loaded_manual)
 
   @test.require.command('man')
+  @test.require.module('sqlite3')
   def test_saving_manual_as_sqlite(self):
     """
     Check that we can save and reload manuals as sqlite.
@@ -213,6 +219,7 @@ class TestManual(unittest.TestCase):
       loaded_manual = stem.manual.Manual.from_cache(tmp.name)
       self.assertEqual(manual, loaded_manual)
 
+  @test.require.module('sqlite3')
   def test_cached_manual(self):
     manual = _cached_manual()
 





More information about the tor-commits mailing list