From c04a107e322ecf16b59b85090f3c432040b52c14 Mon Sep 17 00:00:00 2001 From: Chris Dent Date: Mon, 4 Mar 2019 20:00:55 +0000 Subject: [PATCH] Make the PlacementFixture usable without intercept There are cases where it is necessary to use the PlacementFixture without it running a wsgi-intercept, for example when you'd like to run an indepdendent wsgi-intercept, as in the nova tests that exercise the report client. In the bug listed as partial below those report client tests were using a nova conf global to initialize the wsgi intercept. They just happened to be working because that CONF has the required configuration settings. When placement's conf diverged [1] things broke. A nova change which depends on this one will resolve the bug. Note that as a part of this change, the code which deletes 'sync_on_startup' (the new conf option) before configuring the database, is adapted to be more flexible. There really is only one conf setting that is required to start the placement database, connection, and we'd like to make it possible for people to set just that when doing tests or experiments and not have to worry about extraneous optional things. Some parameter descriptions are added to the PlacementFixture __init__. We should add more robust testing to all three of PlacementFixture, fixtures.Database, and PlacementDirect, but at the moment we are trying to fix a gate blocking bug. Partial-Bug: #1818560 [1] Ie43a69be8b75250d9deca6a911eda7b722ef8648 Change-Id: I8c36f35dbe85b0c0db1a5b6b5389b160b68ca488 --- placement/db_api.py | 4 ++- .../tests/functional/fixtures/placement.py | 30 ++++++++++++++----- 2 files changed, 26 insertions(+), 8 deletions(-) diff --git a/placement/db_api.py b/placement/db_api.py index eb5fce403..f7baff97a 100644 --- a/placement/db_api.py +++ b/placement/db_api.py @@ -23,7 +23,9 @@ placement_context_manager = enginefacade.transaction_context() def _get_db_conf(conf_group): conf_dict = dict(conf_group.items()) # Remove the 'sync_on_startup' conf setting, enginefacade does not use it. - del conf_dict['sync_on_startup'] + # Use pop since it might not be present in testing situations and we + # don't want to care here. + conf_dict.pop('sync_on_startup', None) return conf_dict diff --git a/placement/tests/functional/fixtures/placement.py b/placement/tests/functional/fixtures/placement.py index 6e910f9b0..ca008e074 100644 --- a/placement/tests/functional/fixtures/placement.py +++ b/placement/tests/functional/fixtures/placement.py @@ -30,6 +30,9 @@ class PlacementFixture(fixtures.Fixture): Runs a local WSGI server bound on a free port and having the Placement application with NoAuth middleware. + Optionally, the caller can choose to not use a wsgi-intercept and use + this fixture to set up configuration and (optionally) the database. + It's possible to ask for a specific token when running the fixtures so all calls would be passing this token. @@ -38,9 +41,21 @@ class PlacementFixture(fixtures.Fixture): Used by other services, including nova, for functional tests. """ - def __init__(self, token='admin', conf_fixture=None, db=True): + def __init__(self, token='admin', conf_fixture=None, db=True, + use_intercept=True): + """Create a Placement Fixture. + + :param token: The value to be used when passing an auth token + header in HTTP requests. + :param conf_fixture: An oslo_conf.fixture.Config. If provided, config + will be based from it. + :param db: Whether to start the Database fixture. + :param use_intercept: If true, install a wsgi-intercept of the + placement WSGI app. + """ self.token = token self.db = db + self.use_intercept = use_intercept self.conf_fixture = conf_fixture def setUp(self): @@ -60,9 +75,10 @@ class PlacementFixture(fixtures.Fixture): self.useFixture(policy_fixture.PolicyFixture(self.conf_fixture)) - loader = deploy.loadapp(self.conf_fixture.conf) - app = lambda: loader - self.endpoint = 'http://%s/placement' % uuidutils.generate_uuid() - intercept = interceptor.RequestsInterceptor(app, url=self.endpoint) - intercept.install_intercept() - self.addCleanup(intercept.uninstall_intercept) + if self.use_intercept: + loader = deploy.loadapp(self.conf_fixture.conf) + app = lambda: loader + self.endpoint = 'http://%s/placement' % uuidutils.generate_uuid() + intercept = interceptor.RequestsInterceptor(app, url=self.endpoint) + intercept.install_intercept() + self.addCleanup(intercept.uninstall_intercept)