From 547bc88a701633f4c908b818e280b8111bb07581 Mon Sep 17 00:00:00 2001 From: James Page Date: Tue, 12 Apr 2016 15:12:03 +0100 Subject: [PATCH] Use network space binding for shared-db relation To ensure that the charm presents the right IP address for accessing the MySQL database over the shared-db relation, ensure that any network space binding provided by the user is preferred over the default of 'private-address'. If network spaces is not supported (juju < 2.0), fallback to using 'private-address'. Change-Id: If91dd8e9a4f47c5455095532ed27433eaf0d47d4 --- README.md | 5 ++++- hooks/nova_cc_hooks.py | 10 +++++++++- unit_tests/test_nova_cc_hooks.py | 14 ++++++++++++++ 3 files changed, 27 insertions(+), 2 deletions(-) diff --git a/README.md b/README.md index 01e89d1b..b3c4cd25 100644 --- a/README.md +++ b/README.md @@ -108,9 +108,11 @@ This charm supports the use of Juju Network Spaces, allowing the charm to be bou API endpoints can be bound to distinct network spaces supporting the network separation of public, internal and admin endpoints. +Access to the underlying MySQL instance can also be bound to a specific space using the shared-db relation. + To use this feature, use the --bind option when deploying the charm: - juju deploy nova-cloud-controller --bind "public=public-space internal=internal-space admin=admin-space" + juju deploy nova-cloud-controller --bind "public=public-space internal=internal-space admin=admin-space shared-db=internal-space" alternatively these can also be provided as part of a juju native bundle configuration: @@ -121,6 +123,7 @@ alternatively these can also be provided as part of a juju native bundle configu public: public-space admin: admin-space internal: internal-space + shared-db: internal-space NOTE: Spaces must be configured in the underlying provider prior to attempting to use them. diff --git a/hooks/nova_cc_hooks.py b/hooks/nova_cc_hooks.py index 7c818edc..7cda1617 100755 --- a/hooks/nova_cc_hooks.py +++ b/hooks/nova_cc_hooks.py @@ -28,6 +28,7 @@ from charmhelpers.core.hookenv import ( open_port, unit_get, status_set, + network_get_primary_address, ) from charmhelpers.core.host import ( @@ -317,7 +318,14 @@ def db_joined(relation_id=None): relation_prefix='novaapi') else: - host = unit_get('private-address') + host = None + try: + # NOTE: try to use network spaces + host = network_get_primary_address('shared-db') + except NotImplementedError: + # NOTE: fallback to private-address + host = unit_get('private-address') + relation_set(nova_database=config('database'), nova_username=config('database-user'), nova_hostname=host, diff --git a/unit_tests/test_nova_cc_hooks.py b/unit_tests/test_nova_cc_hooks.py index fb97c2a2..b6ed8c6d 100644 --- a/unit_tests/test_nova_cc_hooks.py +++ b/unit_tests/test_nova_cc_hooks.py @@ -74,6 +74,7 @@ TO_PATCH = [ 'git_install', 'git_install_requested', 'status_set', + 'network_get_primary_address', ] @@ -100,6 +101,7 @@ class NovaCCHooksTests(CharmTestCase): self.config.side_effect = self.test_config.get self.relation_get.side_effect = self.test_relation.get self.charm_dir.return_value = '/var/lib/juju/charms/nova/charm' + self.network_get_primary_address.side_effect = NotImplementedError def tearDown(self): try: @@ -364,6 +366,18 @@ class NovaCCHooksTests(CharmTestCase): relation_id=None) self.unit_get.assert_called_with('private-address') + def test_db_joined_spaces(self): + self.network_get_primary_address.side_effect = None + self.network_get_primary_address.return_value = '192.168.20.1' + self.unit_get.return_value = 'nova.foohost.com' + self.is_relation_made.return_value = False + hooks.db_joined() + self.relation_set.assert_called_with(nova_database='nova', + nova_username='nova', + nova_hostname='192.168.20.1', + relation_id=None) + self.assertFalse(self.unit_get.called) + def test_db_joined_mitaka(self): self.unit_get.return_value = 'nova.foohost.com' self.os_release.return_value = 'mitaka'