summaryrefslogtreecommitdiff
path: root/alembic/testing
diff options
context:
space:
mode:
authorMike Bayer <mike_mp@zzzcomputing.com>2014-09-14 15:49:04 -0400
committerMike Bayer <mike_mp@zzzcomputing.com>2014-09-14 15:51:19 -0400
commitadc081312ea9228d22618ea68b80a798a2d43e77 (patch)
tree0e4c453118982b254f488166ecad268d21bd8919 /alembic/testing
parent58149cf4d097f09afc5e7f5033db4b2b37dabc4d (diff)
downloadalembic-adc081312ea9228d22618ea68b80a798a2d43e77.tar.gz
- coverage was not working (and needs to be fixed in SQLAlchemy too),
go back to using a "bootstrap" system where we load in pytestplugin/ noseplugin via file importing, plugin/ is not used as a package. - identify the pytest_sessionstart hook as the best place to do plugin_base.post_begin() and actually begin importing main modules; this is where coverage has actually started. - we're now targeting 1.0.0 as this has to be ported to SQLAlchemy. - start using .coveragerc
Diffstat (limited to 'alembic/testing')
-rw-r--r--alembic/testing/config.py2
-rw-r--r--alembic/testing/engines.py2
-rw-r--r--alembic/testing/env.py6
-rw-r--r--alembic/testing/exclusions.py2
-rw-r--r--alembic/testing/mock.py4
-rw-r--r--alembic/testing/plugin/__init__.py2
-rw-r--r--alembic/testing/plugin/bootstrap.py44
-rw-r--r--alembic/testing/plugin/noseplugin.py26
-rw-r--r--alembic/testing/plugin/plugin_base.py14
-rw-r--r--alembic/testing/plugin/pytestplugin.py26
-rw-r--r--alembic/testing/provision.py (renamed from alembic/testing/plugin/provision.py)4
-rw-r--r--alembic/testing/runner.py4
12 files changed, 95 insertions, 41 deletions
diff --git a/alembic/testing/config.py b/alembic/testing/config.py
index 98006f2..474fde4 100644
--- a/alembic/testing/config.py
+++ b/alembic/testing/config.py
@@ -5,7 +5,7 @@
# This module is part of SQLAlchemy and is released under
# the MIT License: http://www.opensource.org/licenses/mit-license.php
"""NOTE: copied/adapted from SQLAlchemy master for backwards compatibility;
- this should be removable when Alembic targets SQLAlchemy 0.9.4.
+ this should be removable when Alembic targets SQLAlchemy 1.0.0
"""
import collections
diff --git a/alembic/testing/engines.py b/alembic/testing/engines.py
index 22d04f2..35aa8b5 100644
--- a/alembic/testing/engines.py
+++ b/alembic/testing/engines.py
@@ -5,7 +5,7 @@
# This module is part of SQLAlchemy and is released under
# the MIT License: http://www.opensource.org/licenses/mit-license.php
"""NOTE: copied/adapted from SQLAlchemy master for backwards compatibility;
- this should be removable when Alembic targets SQLAlchemy 0.9.4.
+ this should be removable when Alembic targets SQLAlchemy 1.0.0.
"""
from __future__ import absolute_import
diff --git a/alembic/testing/env.py b/alembic/testing/env.py
index bf04378..6c449a5 100644
--- a/alembic/testing/env.py
+++ b/alembic/testing/env.py
@@ -8,12 +8,12 @@ from alembic.compat import u
from alembic.script import Script, ScriptDirectory
from alembic import util
from . import engines
-from alembic.testing.plugin import plugin_base
+from . import provision
def _get_staging_directory():
- if plugin_base.FOLLOWER_IDENT:
- return "scratch_%s" % plugin_base.FOLLOWER_IDENT
+ if provision.FOLLOWER_IDENT:
+ return "scratch_%s" % provision.FOLLOWER_IDENT
else:
return 'scratch'
diff --git a/alembic/testing/exclusions.py b/alembic/testing/exclusions.py
index 1b572e5..a64fe35 100644
--- a/alembic/testing/exclusions.py
+++ b/alembic/testing/exclusions.py
@@ -5,7 +5,7 @@
# This module is part of SQLAlchemy and is released under
# the MIT License: http://www.opensource.org/licenses/mit-license.php
"""NOTE: copied/adapted from SQLAlchemy master for backwards compatibility;
- this should be removable when Alembic targets SQLAlchemy 0.9.4.
+ this should be removable when Alembic targets SQLAlchemy 1.0.0
"""
diff --git a/alembic/testing/mock.py b/alembic/testing/mock.py
index 8d0c051..cdfcb88 100644
--- a/alembic/testing/mock.py
+++ b/alembic/testing/mock.py
@@ -8,7 +8,7 @@
"""Import stub for mock library.
NOTE: copied/adapted from SQLAlchemy master for backwards compatibility;
- this should be removable when Alembic targets SQLAlchemy 0.9.4.
+ this should be removable when Alembic targets SQLAlchemy 1.0.0
"""
from __future__ import absolute_import
@@ -18,7 +18,7 @@ if py33:
from unittest.mock import MagicMock, Mock, call, patch
else:
try:
- from mock import MagicMock, Mock, call, patch
+ from mock import MagicMock, Mock, call, patch # noqa
except ImportError:
raise ImportError(
"SQLAlchemy's test suite requires the "
diff --git a/alembic/testing/plugin/__init__.py b/alembic/testing/plugin/__init__.py
index 3e00e40..98616f4 100644
--- a/alembic/testing/plugin/__init__.py
+++ b/alembic/testing/plugin/__init__.py
@@ -1,3 +1,3 @@
"""NOTE: copied/adapted from SQLAlchemy master for backwards compatibility;
- this should be removable when Alembic targets SQLAlchemy 0.9.4.
+ this should be removable when Alembic targets SQLAlchemy 1.0.0
"""
diff --git a/alembic/testing/plugin/bootstrap.py b/alembic/testing/plugin/bootstrap.py
new file mode 100644
index 0000000..1560b03
--- /dev/null
+++ b/alembic/testing/plugin/bootstrap.py
@@ -0,0 +1,44 @@
+"""
+Bootstrapper for nose/pytest plugins.
+
+The entire rationale for this system is to get the modules in plugin/
+imported without importing all of the supporting library, so that we can
+set up things for testing before coverage starts.
+
+The rationale for all of plugin/ being *in* the supporting library in the
+first place is so that the testing and plugin suite is available to other
+libraries, mainly external SQLAlchemy and Alembic dialects, to make use
+of the same test environment and standard suites available to
+SQLAlchemy/Alembic themselves without the need to ship/install a separate
+package outside of SQLAlchemy.
+
+NOTE: copied/adapted from SQLAlchemy master for backwards compatibility;
+this should be removable when Alembic targets SQLAlchemy 1.0.0.
+
+"""
+
+import os
+import sys
+
+bootstrap_file = locals()['bootstrap_file']
+to_bootstrap = locals()['to_bootstrap']
+
+
+def load_file_as_module(name):
+ path = os.path.join(os.path.dirname(bootstrap_file), "%s.py" % name)
+ if sys.version_info >= (3, 3):
+ from importlib import machinery
+ mod = machinery.SourceFileLoader(name, path).load_module()
+ else:
+ import imp
+ mod = imp.load_source(name, path)
+ return mod
+
+if to_bootstrap == "pytest":
+ sys.modules["alembic_plugin_base"] = load_file_as_module("plugin_base")
+ sys.modules["alembic_pytestplugin"] = load_file_as_module("pytestplugin")
+elif to_bootstrap == "nose":
+ sys.modules["alembic_plugin_base"] = load_file_as_module("plugin_base")
+ sys.modules["alembic_noseplugin"] = load_file_as_module("noseplugin")
+else:
+ raise Exception("unknown bootstrap: %s" % to_bootstrap) # noqa
diff --git a/alembic/testing/plugin/noseplugin.py b/alembic/testing/plugin/noseplugin.py
index ec3eebe..3235d4f 100644
--- a/alembic/testing/plugin/noseplugin.py
+++ b/alembic/testing/plugin/noseplugin.py
@@ -5,15 +5,22 @@
# This module is part of SQLAlchemy and is released under
# the MIT License: http://www.opensource.org/licenses/mit-license.php
-"""NOTE: copied/adapted from SQLAlchemy master for backwards compatibility;
- this should be removable when Alembic targets SQLAlchemy 0.9.4.
"""
+Enhance nose with extra options and behaviors for running SQLAlchemy tests.
-"""Enhance nose with extra options and behaviors for running SQLAlchemy tests.
+NOTE: copied/adapted from SQLAlchemy master for backwards compatibility;
+this should be removable when Alembic targets SQLAlchemy 1.0.0.
"""
+try:
+ # installed by bootstrap.py
+ import alembic_plugin_base as plugin_base
+except ImportError:
+ # assume we're a package, use traditional import
+ from . import plugin_base
+
import os
import sys
@@ -21,16 +28,6 @@ from nose.plugins import Plugin
fixtures = None
py3k = sys.version_info >= (3, 0)
-# no package imports yet! this prevents us from tripping coverage
-# too soon.
-path = os.path.join(os.path.dirname(__file__), "plugin_base.py")
-if sys.version_info >= (3, 3):
- from importlib import machinery
- plugin_base = machinery.SourceFileLoader(
- "plugin_base", path).load_module()
-else:
- import imp
- plugin_base = imp.load_source("plugin_base", path)
class NoseSQLAlchemy(Plugin):
@@ -60,10 +57,10 @@ class NoseSQLAlchemy(Plugin):
plugin_base.set_coverage_flag(options.enable_plugin_coverage)
+ def begin(self):
global fixtures
from alembic.testing import fixtures # noqa
- def begin(self):
plugin_base.post_begin()
def describeTest(self, test):
@@ -77,7 +74,6 @@ class NoseSQLAlchemy(Plugin):
cls = fn.__self__.cls
else:
cls = fn.im_class
- print "METH:", fn, "CLS:", cls
return plugin_base.want_method(cls, fn)
def wantClass(self, cls):
diff --git a/alembic/testing/plugin/plugin_base.py b/alembic/testing/plugin/plugin_base.py
index c4d1f83..c4c600d 100644
--- a/alembic/testing/plugin/plugin_base.py
+++ b/alembic/testing/plugin/plugin_base.py
@@ -11,7 +11,7 @@ so that we can continue to support nose and also begin adding new
functionality via py.test.
NOTE: copied/adapted from SQLAlchemy master for backwards compatibility;
- this should be removable when Alembic targets SQLAlchemy 0.9.4.
+this should be removable when Alembic targets SQLAlchemy 1.0.0
"""
@@ -34,11 +34,10 @@ if py3k:
else:
import ConfigParser as configparser
-FOLLOWER_IDENT = None
-
# late imports
fixtures = None
engines = None
+provision = None
exclusions = None
warnings = None
assertions = None
@@ -111,8 +110,8 @@ def configure_follower(follower_ident):
database creation.
"""
- global FOLLOWER_IDENT
- FOLLOWER_IDENT = follower_ident
+ from alembic.testing import provision
+ provision.FOLLOWER_IDENT = follower_ident
def memoize_important_follower_config(dict_):
@@ -164,6 +163,7 @@ def set_coverage_flag(value):
def post_begin():
"""things to set up later, once we know coverage is running."""
+
# Lazy setup of other options (post coverage)
for fn in post_configure:
fn(options, file_config)
@@ -245,7 +245,7 @@ def _monkeypatch_cdecimal(options, file_config):
@post
def _engine_uri(options, file_config):
from alembic.testing import config
- from alembic.testing.plugin import provision
+ from alembic.testing import provision
if options.dburi:
db_urls = list(options.dburi)
@@ -268,7 +268,7 @@ def _engine_uri(options, file_config):
for db_url in db_urls:
cfg = provision.setup_config(
- db_url, db_opts, options, file_config, FOLLOWER_IDENT)
+ db_url, db_opts, options, file_config, provision.FOLLOWER_IDENT)
if not config._current:
cfg.set_as_current(cfg)
diff --git a/alembic/testing/plugin/pytestplugin.py b/alembic/testing/plugin/pytestplugin.py
index 26f188f..78194a3 100644
--- a/alembic/testing/plugin/pytestplugin.py
+++ b/alembic/testing/plugin/pytestplugin.py
@@ -1,10 +1,21 @@
"""NOTE: copied/adapted from SQLAlchemy master for backwards compatibility;
- this should be removable when Alembic targets SQLAlchemy 0.9.4.
+ this should be removable when Alembic targets SQLAlchemy 1.0.0.
"""
+
+try:
+ # installed by bootstrap.py
+ import alembic_plugin_base as plugin_base
+except ImportError:
+ # assume we're a package, use traditional import
+ from . import plugin_base
+
+import sys
+
+py3k = sys.version_info >= (3, 0)
+
import pytest
import argparse
import inspect
-from . import plugin_base
import collections
import itertools
@@ -42,9 +53,11 @@ def pytest_configure(config):
plugin_base.pre_begin(config.option)
- plugin_base.set_coverage_flag(bool(getattr(config.option,
- "cov_source", False)))
+ coverage = bool(getattr(config.option, "cov_source", False))
+ plugin_base.set_coverage_flag(coverage)
+
+def pytest_sessionstart(session):
plugin_base.post_begin()
if has_xdist:
@@ -57,11 +70,11 @@ if has_xdist:
plugin_base.memoize_important_follower_config(node.slaveinput)
node.slaveinput["follower_ident"] = "test_%s" % next(_follower_count)
- from . import provision
+ from alembic.testing import provision
provision.create_follower_db(node.slaveinput["follower_ident"])
def pytest_testnodedown(node, error):
- from . import provision
+ from alembic.testing import provision
provision.drop_follower_db(node.slaveinput["follower_ident"])
@@ -121,6 +134,7 @@ def pytest_pycollect_makeitem(collector, name, obj):
_current_class = None
+
def pytest_runtest_setup(item):
# here we seem to get called only based on what we collected
# in pytest_collection_modifyitems. So to do class-based stuff
diff --git a/alembic/testing/plugin/provision.py b/alembic/testing/provision.py
index d0edbef..801d36b 100644
--- a/alembic/testing/plugin/provision.py
+++ b/alembic/testing/provision.py
@@ -1,5 +1,5 @@
"""NOTE: copied/adapted from SQLAlchemy master for backwards compatibility;
- this should be removable when Alembic targets SQLAlchemy 0.9.4.
+ this should be removable when Alembic targets SQLAlchemy 1.0.0
"""
from sqlalchemy.engine import url as sa_url
from sqlalchemy import text
@@ -7,6 +7,8 @@ from alembic import compat
from alembic.testing import config, engines
from alembic.testing.compat import get_url_backend_name
+FOLLOWER_IDENT = None
+
class register(object):
def __init__(self):
diff --git a/alembic/testing/runner.py b/alembic/testing/runner.py
index 2810b88..2ad9387 100644
--- a/alembic/testing/runner.py
+++ b/alembic/testing/runner.py
@@ -29,9 +29,7 @@ plugin in a special (somewhat hacky) way so that coverage against
SQLAlchemy itself is possible.
"""
-
-from alembic.testing.plugin.noseplugin import NoseSQLAlchemy
-
+from .plugin.noseplugin import NoseSQLAlchemy
import nose