summaryrefslogtreecommitdiff
diff options
-rwxr-xr-xhooks/hooks.py146
-rwxr-xr-xtests/01_deploy_single.py4
-rwxr-xr-xtests/02_deploy_shard_test.py6
-rwxr-xr-xtests/03_deploy_replicaset.py6
-rwxr-xr-xtests/04_deploy_with_storage.py4
-rwxr-xr-xtests/50_relate_ceilometer_test.py2
-rw-r--r--unit_tests/test_hooks.py18
7 files changed, 89 insertions, 97 deletions
diff --git a/hooks/hooks.py b/hooks/hooks.py
index 4801dc8..c5fe7c0 100755
--- a/hooks/hooks.py
+++ b/hooks/hooks.py
@@ -46,6 +46,7 @@ from charmhelpers.core.host import (
from charmhelpers.core.hookenv import (
close_port,
config,
+ is_relation_made,
open_port,
unit_get,
relation_get,
@@ -331,6 +332,10 @@ def mongodb_conf(config_data=None):
if not config_data['web_admin_ui']:
config.append("nohttpinterface = true")
config.append("")
+ else:
+ config.append("rest = true")
+ config.append("httpinterface = true")
+ config.append("")
# noscripting
if config_data['noscripting']:
@@ -367,14 +372,23 @@ def mongodb_conf(config_data=None):
config.append("mms-interval = %s" % config_data['mms-interval'])
config.append("")
- # master/slave
- if config_data['master'] == "self":
- config.append("master = true")
+ # Set either replica-set or master, depending upon whether the
+ # the replica-set (peer) relation is established. If the user
+ # chooses to use juju scale out (e.g. juju add-unit) then the
+ # charm will use replica-set replication. The user may opt to
+ # do master/slave replication or sharding as a different form
+ # of scaleout.
+ if is_relation_made('replica-set'):
+ config.append("replSet = %s" % config_data['replicaset'])
config.append("")
else:
- config.append("slave = true")
- config.append("source = %s" % config_data['master'])
- config.append("")
+ if config_data['master'] == "self":
+ config.append("master = true")
+ config.append("")
+ else:
+ config.append("slave = true")
+ config.append("source = %s" % config_data['master'])
+ config.append("")
# arbiter
if config_data['arbiter'] != "disabled" and \
@@ -405,6 +419,27 @@ def mongodb_conf(config_data=None):
return('\n'.join(config))
+def get_current_mongo_config():
+ """Reads the current mongo configuration file and returns a dict
+ containing the key/value pairs found in the configuration file.
+
+ :returns dict: key/value pairs of the configuration file.
+ """
+ results = {}
+ with open(default_mongodb_config, 'r') as f:
+ for line in f:
+ line = line.strip()
+
+ # Skip over comments, blank lines, and any other line
+ # that appears to not contain a key = value pair.
+ if line.startswith('#') or '=' not in line:
+ continue
+
+ key, value = line.split('=', 1)
+ results[key.strip()] = value.strip()
+ return results
+
+
def mongo_client(host=None, command=None):
if host is None or command is None:
return(False)
@@ -541,22 +576,19 @@ def enable_replset(replicaset_name=None):
try:
juju_log('enable_replset: trying to get lock on: %s' %
default_mongodb_init_config)
- with FileLock(INIT_LOCKFILE):
- juju_log('enable_replset: lock acquired', level=DEBUG)
- with open(default_mongodb_init_config) as mongo_init_file:
- mongodb_init_config = mongo_init_file.read()
- if re.search(' --replSet %s ' % replicaset_name,
- mongodb_init_config, re.MULTILINE) is None:
- juju_log('enable_replset: --replset not preset,'
- ' enabling',
- level=DEBUG)
- mongodb_init_config = regex_sub([(' -- ',
- ' -- --replSet %s ' %
- replicaset_name)],
- mongodb_init_config)
- update_file(default_mongodb_init_config,
- mongodb_init_config)
- retVal = True
+
+ current_config = get_current_mongo_config()
+ config_data = config()
+
+ if 'replSet' in current_config and \
+ current_config['replSet'] == config_data['replicaset']:
+ juju_log('enable_replset: replica set is already enabled',
+ level=DEBUG)
+ else:
+ juju_log('enable_replset: enabling replicaset %s' %
+ config_data['replicaset'], level=DEBUG)
+ mongodb_config = mongodb_conf(config_data)
+ retVal = update_file(default_mongodb_config, mongodb_config)
juju_log('enable_replset will return: %s' % str(retVal), level=DEBUG)
@@ -582,64 +614,6 @@ def update_daemon_options(daemon_options=None):
return(update_file(default_mongodb_init_config, mongodb_init_config))
-def disable_replset(replicaset_name=None):
- if replicaset_name is None:
- retVal = False
- try:
- mongodb_init_config = open(default_mongodb_init_config).read()
- if re.search(' --replSet %s ' % replicaset_name,
- mongodb_init_config, re.MULTILINE) is not None:
- mongodb_init_config = regex_sub([
- (' --replSet %s ' % replicaset_name, ' ')
- ], mongodb_init_config)
- retVal = update_file(default_mongodb_init_config, mongodb_init_config)
- except Exception, e:
- juju_log(str(e))
- retVal = False
- finally:
- return(retVal)
-
-
-def enable_web_admin_ui(port=None):
- if port is None:
- juju_log("enable_web_admin_ui: port not defined.")
- return(False)
- try:
- mongodb_init_config = open(default_mongodb_init_config).read()
- if re.search(' --rest ', mongodb_init_config, re.MULTILINE) is None:
- mongodb_init_config = regex_sub([(' -- ', ' -- --rest ')],
- mongodb_init_config)
- retVal = update_file(default_mongodb_init_config, mongodb_init_config)
- except Exception, e:
- juju_log(str(e))
- retVal = False
- finally:
- if retVal:
- open_port(port)
- return(retVal)
-
-
-def disable_web_admin_ui(port=None):
- if port is None:
- juju_log("disable_web_admin_ui: port not defined.")
- return(False)
- try:
- mongodb_init_config = open(default_mongodb_init_config).read()
- if re.search(' --rest ',
- mongodb_init_config,
- re.MULTILINE) is not None:
- mongodb_init_config = regex_sub([(' --rest ', ' ')],
- mongodb_init_config)
- retVal = update_file(default_mongodb_init_config, mongodb_init_config)
- except Exception, e:
- juju_log(str(e))
- retVal = False
- finally:
- if retVal:
- close_port(port)
- return(retVal)
-
-
def enable_arbiter(master_node=None, host=None):
juju_log("enable_arbiter: master_node: %s, host: %s" %
(master_node, host))
@@ -1002,9 +976,9 @@ def config_changed():
# web_admin_ui
if config_data['web_admin_ui']:
- enable_web_admin_ui(new_web_admin_ui_port)
+ open_port(new_web_admin_ui_port)
else:
- disable_web_admin_ui(current_web_admin_ui_port)
+ close_port(current_web_admin_ui_port)
# replicaset_master
if config_data['replicaset_master'] != "auto":
@@ -1141,7 +1115,7 @@ def database_relation_joined():
relation_set(relation_id(), relation_data)
-@hooks.hook('replicaset-relation-joined')
+@hooks.hook('replica-set-relation-joined')
def replica_set_relation_joined():
juju_log("replica_set_relation_joined-start")
my_hostname = unit_get('private-address')
@@ -1194,7 +1168,7 @@ def am_i_primary():
raise TimeoutException('Unable to determine if local unit is primary')
-@hooks.hook('replicaset-relation-changed')
+@hooks.hook('replica-set-relation-changed')
def replica_set_relation_changed():
private_address = unit_get('private-address')
remote_hostname = relation_get('hostname')
@@ -1228,7 +1202,7 @@ def replica_set_relation_changed():
juju_log('replica_set_relation_changed-finish')
-@hooks.hook('replicaset-relation-departed')
+@hooks.hook('replica-set-relation-departed')
def replica_set_relation_departed():
juju_log('replica_set_relation_departed-start')
@@ -1259,7 +1233,7 @@ def replica_set_relation_departed():
juju_log('replica_set_relation_departed-finish')
-@hooks.hook('replicaset-relation-broken')
+@hooks.hook('replica-set-relation-broken')
def replica_set_relation_broken():
juju_log('replica_set_relation_broken-start')
diff --git a/tests/01_deploy_single.py b/tests/01_deploy_single.py
index 885ee26..fd2cabc 100755
--- a/tests/01_deploy_single.py
+++ b/tests/01_deploy_single.py
@@ -5,7 +5,7 @@ from pymongo import MongoClient
seconds = 900
-d = amulet.Deployment(series='trusty')
+d = amulet.Deployment(series='xenial')
d.add('mongodb', charm='mongodb')
d.expose('mongodb')
@@ -36,7 +36,7 @@ def validate_world_connectivity():
amulet.raise_status(amulet.FAIL, msg="Failed to insert test data")
# Can we delete from a shard using the Mongos hub?
result = db.amulet.remove(insert_id)
- if result['err'] is not None:
+ if 'err' in result and result['err'] is not None:
amulet.raise_status(amulet.FAIL, msg="Failed to remove test data")
diff --git a/tests/02_deploy_shard_test.py b/tests/02_deploy_shard_test.py
index 2ff0750..5ff0250 100755
--- a/tests/02_deploy_shard_test.py
+++ b/tests/02_deploy_shard_test.py
@@ -16,7 +16,7 @@ seconds = 1400
#########################################################
# 3shard cluster configuration
#########################################################
-d = amulet.Deployment(series='trusty')
+d = amulet.Deployment(series='xenial')
d.add('configsvr', charm='mongodb', units=scale)
d.add('mongos', charm='mongodb', units=scale)
@@ -92,7 +92,7 @@ def validate_status_interface():
def validate_running_services():
for service in sentry_dict:
output = sentry_dict[service].run('service mongodb status')
- service_active = str(output).find('mongodb start/running')
+ service_active = str(output).find('active (running)')
if service_active == -1:
message = "Failed to find running MongoDB on host {}".format(
service)
@@ -115,7 +115,7 @@ def validate_world_connectivity():
amulet.raise_status(amulet.FAIL, msg="Failed to insert test data")
# Can we delete from a shard using the Mongos hub?
result = db.amulet.remove(insert_id)
- if result['err'] is not None:
+ if 'err' in result and result['err'] is not None:
amulet.raise_status(amulet.FAIL, msg="Failed to remove test data")
diff --git a/tests/03_deploy_replicaset.py b/tests/03_deploy_replicaset.py
index 02d25f5..7be3141 100755
--- a/tests/03_deploy_replicaset.py
+++ b/tests/03_deploy_replicaset.py
@@ -23,7 +23,7 @@ wait_for_replicaset = 600
#########################################################
# 3shard cluster configuration
#########################################################
-d = amulet.Deployment(series='trusty')
+d = amulet.Deployment(series='xenial')
d.add('mongodb', charm='mongodb', units=scale)
d.expose('mongodb')
@@ -63,7 +63,7 @@ def validate_status_interface():
def validate_running_services():
for service in sentry_dict:
output = sentry_dict[service].run('service mongodb status')
- service_active = str(output).find('mongodb start/running')
+ service_active = str(output).find('active (running)')
if service_active == -1:
message = "Failed to find running MongoDB on host {}".format(
service)
@@ -158,7 +158,7 @@ def validate_world_connectivity():
amulet.raise_status(amulet.FAIL, msg="Failed to insert test data")
# Can we delete from a shard using the Mongos hub?
result = db.amulet.remove(insert_id)
- if result['err'] is not None:
+ if 'err' in result and result['err'] is not None:
amulet.raise_status(amulet.FAIL, msg="Failed to remove test data")
diff --git a/tests/04_deploy_with_storage.py b/tests/04_deploy_with_storage.py
index 46aef57..347b7ef 100755
--- a/tests/04_deploy_with_storage.py
+++ b/tests/04_deploy_with_storage.py
@@ -20,9 +20,9 @@ wait_for_relation = 60*5
#########################################################
# 3shard cluster configuration
#########################################################
-d = amulet.Deployment(series='trusty')
+d = amulet.Deployment(series='xenial')
-d.add('mongodb', units=scale, series='trusty',
+d.add('mongodb', units=scale, series='xenial',
constraints={'root-disk': '20480M'})
d.add('storage', charm='cs:~chris-gondolin/trusty/storage-5', series='trusty')
d.configure('storage', {'provider': 'local'})
diff --git a/tests/50_relate_ceilometer_test.py b/tests/50_relate_ceilometer_test.py
index ef45166..52571d8 100755
--- a/tests/50_relate_ceilometer_test.py
+++ b/tests/50_relate_ceilometer_test.py
@@ -7,7 +7,7 @@ class TestDeploy(object):
def __init__(self, time=2500):
# Attempt to load the deployment topology from a bundle.
- self.deploy = amulet.Deployment(series="trusty")
+ self.deploy = amulet.Deployment(series="xenial")
# If something errored out, attempt to continue by
# manually specifying a standalone deployment
diff --git a/unit_tests/test_hooks.py b/unit_tests/test_hooks.py
index 4573b2c..85331f7 100644
--- a/unit_tests/test_hooks.py
+++ b/unit_tests/test_hooks.py
@@ -3,6 +3,7 @@ from mock import patch, call
import hooks
from test_utils import CharmTestCase
+from test_utils import mock_open
from pymongo.errors import OperationFailure
from subprocess import CalledProcessError
@@ -339,3 +340,20 @@ class MongoHooksTest(CharmTestCase):
call1 = call('juju-local:27017', 'juju-remote:27017')
mock_leave_replset.assert_has_calls([call1])
+
+ def test_get_current_mongo_config(self):
+ test_config = u"""
+ # Comment
+ key = value
+ one=two
+
+ three =four
+ """
+ expected = {
+ 'key': 'value',
+ 'one': 'two',
+ 'three': 'four'
+ }
+ with mock_open('/etc/mongodb.conf', test_config):
+ results = hooks.get_current_mongo_config()
+ self.assertEqual(results, expected)