Upgrade the charm to py3 runtime
Change-Id: I98f4e6664080407a045ca5e76db59d46ffa9c38a
This commit is contained in:
parent
9f33b8135e
commit
fc81200315
@ -1,4 +1,4 @@
|
|||||||
#!/usr/bin/python
|
#!/usr/bin/python3
|
||||||
#
|
#
|
||||||
# Copyright 2016 Canonical Ltd
|
# Copyright 2016 Canonical Ltd
|
||||||
#
|
#
|
||||||
@ -19,6 +19,17 @@ import os
|
|||||||
import sys
|
import sys
|
||||||
import yaml
|
import yaml
|
||||||
|
|
||||||
|
_path = os.path.dirname(os.path.realpath(__file__))
|
||||||
|
_root = os.path.abspath(os.path.join(_path, '..'))
|
||||||
|
|
||||||
|
|
||||||
|
def _add_path(path):
|
||||||
|
if path not in sys.path:
|
||||||
|
sys.path.insert(1, path)
|
||||||
|
|
||||||
|
|
||||||
|
_add_path(_root)
|
||||||
|
|
||||||
from charmhelpers.core.host import service_pause, service_resume
|
from charmhelpers.core.host import service_pause, service_resume
|
||||||
from charmhelpers.core.hookenv import action_fail
|
from charmhelpers.core.hookenv import action_fail
|
||||||
from charmhelpers.core.unitdata import HookData, kv
|
from charmhelpers.core.unitdata import HookData, kv
|
||||||
@ -101,7 +112,7 @@ def main(argv):
|
|||||||
try:
|
try:
|
||||||
action = ACTIONS[action_name]
|
action = ACTIONS[action_name]
|
||||||
except KeyError:
|
except KeyError:
|
||||||
return "Action %s undefined" % action_name
|
return "Action {} undefined".format(action_name)
|
||||||
else:
|
else:
|
||||||
try:
|
try:
|
||||||
action(args)
|
action(args)
|
||||||
|
@ -1 +0,0 @@
|
|||||||
../charmhelpers/
|
|
@ -1,4 +1,4 @@
|
|||||||
#!/usr/bin/python
|
#!/usr/bin/python3
|
||||||
#
|
#
|
||||||
# Copyright 2016 Canonical Ltd
|
# Copyright 2016 Canonical Ltd
|
||||||
#
|
#
|
||||||
@ -14,15 +14,26 @@
|
|||||||
# See the License for the specific language governing permissions and
|
# See the License for the specific language governing permissions and
|
||||||
# limitations under the License.
|
# limitations under the License.
|
||||||
|
|
||||||
|
import os
|
||||||
import sys
|
import sys
|
||||||
|
|
||||||
sys.path.append('hooks/')
|
_path = os.path.dirname(os.path.realpath(__file__))
|
||||||
|
_root = os.path.abspath(os.path.join(_path, '..'))
|
||||||
|
|
||||||
|
|
||||||
|
def _add_path(path):
|
||||||
|
if path not in sys.path:
|
||||||
|
sys.path.insert(1, path)
|
||||||
|
|
||||||
|
|
||||||
|
_add_path(_root)
|
||||||
|
|
||||||
|
|
||||||
from charmhelpers.contrib.openstack.utils import (
|
from charmhelpers.contrib.openstack.utils import (
|
||||||
do_action_openstack_upgrade,
|
do_action_openstack_upgrade,
|
||||||
)
|
)
|
||||||
|
|
||||||
from swift_storage_hooks import (
|
from hooks.swift_storage_hooks import (
|
||||||
config_changed,
|
config_changed,
|
||||||
CONFIGS,
|
CONFIGS,
|
||||||
)
|
)
|
||||||
|
@ -1,4 +1,4 @@
|
|||||||
#!/usr/bin/env python
|
#!/usr/bin/env python3
|
||||||
|
|
||||||
# Copyright (C) 2014, 2017 Canonical
|
# Copyright (C) 2014, 2017 Canonical
|
||||||
# All Rights Reserved
|
# All Rights Reserved
|
||||||
@ -6,7 +6,7 @@
|
|||||||
|
|
||||||
import sys
|
import sys
|
||||||
import json
|
import json
|
||||||
import urllib2
|
import urllib
|
||||||
import argparse
|
import argparse
|
||||||
import hashlib
|
import hashlib
|
||||||
import datetime
|
import datetime
|
||||||
@ -20,10 +20,11 @@ STATUS_UNKNOWN = 3
|
|||||||
def generate_md5(filename):
|
def generate_md5(filename):
|
||||||
with open(filename, 'rb') as f:
|
with open(filename, 'rb') as f:
|
||||||
md5 = hashlib.md5()
|
md5 = hashlib.md5()
|
||||||
|
while True:
|
||||||
buffer = f.read(2 ** 20)
|
buffer = f.read(2 ** 20)
|
||||||
while buffer:
|
if not buffer:
|
||||||
|
break
|
||||||
md5.update(buffer)
|
md5.update(buffer)
|
||||||
buffer = f.read(2 ** 20)
|
|
||||||
return md5.hexdigest()
|
return md5.hexdigest()
|
||||||
|
|
||||||
|
|
||||||
@ -34,9 +35,9 @@ def check_md5(base_url):
|
|||||||
"/etc/swift/container.ring.gz"]
|
"/etc/swift/container.ring.gz"]
|
||||||
results = []
|
results = []
|
||||||
try:
|
try:
|
||||||
data = urllib2.urlopen(url).read()
|
data = urllib.request.urlopen(url).read()
|
||||||
ringmd5_info = json.loads(data)
|
ringmd5_info = json.loads(data)
|
||||||
except urllib2.URLError:
|
except urllib.error.URLError:
|
||||||
return [(STATUS_UNKNOWN, "Can't open url: {}".format(url))]
|
return [(STATUS_UNKNOWN, "Can't open url: {}".format(url))]
|
||||||
except ValueError:
|
except ValueError:
|
||||||
return [(STATUS_UNKNOWN, "Can't parse status data")]
|
return [(STATUS_UNKNOWN, "Can't parse status data")]
|
||||||
@ -96,9 +97,9 @@ def check_replication(base_url, limits):
|
|||||||
for repl in types:
|
for repl in types:
|
||||||
url = base_url + "replication/" + repl
|
url = base_url + "replication/" + repl
|
||||||
try:
|
try:
|
||||||
data = urllib2.urlopen(url).read()
|
data = urllib.request.urlopen(url).read()
|
||||||
repl_info = json.loads(data)
|
repl_info = json.loads(data)
|
||||||
except urllib2.URLError:
|
except urllib.error.URLError:
|
||||||
results.append((STATUS_UNKNOWN, "Can't open url: {}".format(url)))
|
results.append((STATUS_UNKNOWN, "Can't open url: {}".format(url)))
|
||||||
continue
|
continue
|
||||||
except ValueError:
|
except ValueError:
|
||||||
|
@ -1 +0,0 @@
|
|||||||
../charmhelpers/
|
|
@ -11,7 +11,7 @@ check_and_install() {
|
|||||||
fi
|
fi
|
||||||
}
|
}
|
||||||
|
|
||||||
PYTHON="python"
|
PYTHON="python3"
|
||||||
|
|
||||||
for dep in ${DEPS[@]}; do
|
for dep in ${DEPS[@]}; do
|
||||||
check_and_install ${PYTHON} ${dep}
|
check_and_install ${PYTHON} ${dep}
|
||||||
|
@ -1,4 +1,4 @@
|
|||||||
#!/usr/bin/python
|
#!/usr/bin/python3
|
||||||
#
|
#
|
||||||
# Copyright 2016 Canonical Ltd
|
# Copyright 2016 Canonical Ltd
|
||||||
#
|
#
|
||||||
@ -24,6 +24,19 @@ import socket
|
|||||||
import subprocess
|
import subprocess
|
||||||
import tempfile
|
import tempfile
|
||||||
|
|
||||||
|
|
||||||
|
_path = os.path.dirname(os.path.realpath(__file__))
|
||||||
|
_root = os.path.abspath(os.path.join(_path, '..'))
|
||||||
|
|
||||||
|
|
||||||
|
def _add_path(path):
|
||||||
|
if path not in sys.path:
|
||||||
|
sys.path.insert(1, path)
|
||||||
|
|
||||||
|
|
||||||
|
_add_path(_root)
|
||||||
|
|
||||||
|
|
||||||
from lib.swift_storage_utils import (
|
from lib.swift_storage_utils import (
|
||||||
PACKAGES,
|
PACKAGES,
|
||||||
RESTART_MAP,
|
RESTART_MAP,
|
||||||
|
@ -10,13 +10,13 @@ from subprocess import check_call, call, CalledProcessError, check_output
|
|||||||
|
|
||||||
# Stuff copied from cinder py charm, needs to go somewhere
|
# Stuff copied from cinder py charm, needs to go somewhere
|
||||||
# common.
|
# common.
|
||||||
from misc_utils import (
|
from lib.misc_utils import (
|
||||||
ensure_block_device,
|
ensure_block_device,
|
||||||
clean_storage,
|
clean_storage,
|
||||||
is_paused
|
is_paused
|
||||||
)
|
)
|
||||||
|
|
||||||
from swift_storage_context import (
|
from lib.swift_storage_context import (
|
||||||
SwiftStorageContext,
|
SwiftStorageContext,
|
||||||
SwiftStorageServerContext,
|
SwiftStorageServerContext,
|
||||||
RsyncContext,
|
RsyncContext,
|
||||||
@ -222,7 +222,7 @@ def _is_storage_ready(partition):
|
|||||||
def get_mount_point(device):
|
def get_mount_point(device):
|
||||||
mnt_point = None
|
mnt_point = None
|
||||||
try:
|
try:
|
||||||
out = check_output(['findmnt', device])
|
out = check_output(['findmnt', device]).decode('ascii')
|
||||||
mnt_points = []
|
mnt_points = []
|
||||||
for line in out.split('\n'):
|
for line in out.split('\n'):
|
||||||
if line and not line.startswith('TARGET'):
|
if line and not line.startswith('TARGET'):
|
||||||
@ -286,7 +286,8 @@ def determine_block_devices():
|
|||||||
storage_ids = storage_list('block-devices')
|
storage_ids = storage_list('block-devices')
|
||||||
bdevs.extend((storage_get('location', s) for s in storage_ids))
|
bdevs.extend((storage_get('location', s) for s in storage_ids))
|
||||||
|
|
||||||
bdevs = list(set(bdevs))
|
# only sorted so the tests pass; doesn't affect functionality
|
||||||
|
bdevs = sorted(set(bdevs))
|
||||||
# attempt to ensure block devices, but filter out missing devs
|
# attempt to ensure block devices, but filter out missing devs
|
||||||
_none = ['None', 'none']
|
_none = ['None', 'none']
|
||||||
valid_bdevs = \
|
valid_bdevs = \
|
||||||
@ -340,7 +341,7 @@ def is_device_in_ring(dev, skip_rel_check=False, ignore_deactivated=True):
|
|||||||
"devstore)" % (dev), level=INFO)
|
"devstore)" % (dev), level=INFO)
|
||||||
return True
|
return True
|
||||||
|
|
||||||
for key, val in devstore.iteritems():
|
for key, val in devstore.items():
|
||||||
if key != masterkey and val.get('blkid') == blk_uuid:
|
if key != masterkey and val.get('blkid') == blk_uuid:
|
||||||
log("Device '%s' appears to be in use by Swift (found in "
|
log("Device '%s' appears to be in use by Swift (found in "
|
||||||
"local devstore) but has a different "
|
"local devstore) but has a different "
|
||||||
@ -354,7 +355,7 @@ def is_device_in_ring(dev, skip_rel_check=False, ignore_deactivated=True):
|
|||||||
if ignore_deactivated:
|
if ignore_deactivated:
|
||||||
deactivated = [k == masterkey and v.get('blkid') == blk_uuid and
|
deactivated = [k == masterkey and v.get('blkid') == blk_uuid and
|
||||||
v.get('status') != 'active'
|
v.get('status') != 'active'
|
||||||
for k, v in devstore.iteritems()]
|
for k, v in devstore.items()]
|
||||||
|
|
||||||
if skip_rel_check:
|
if skip_rel_check:
|
||||||
log("Device '%s' does not appear to be in use by swift (searched "
|
log("Device '%s' does not appear to be in use by swift (searched "
|
||||||
@ -387,7 +388,9 @@ def get_device_blkid(dev):
|
|||||||
:returns: UUID of device if found else None
|
:returns: UUID of device if found else None
|
||||||
"""
|
"""
|
||||||
try:
|
try:
|
||||||
blk_uuid = subprocess.check_output(['blkid', '-s', 'UUID', dev])
|
blk_uuid = (subprocess
|
||||||
|
.check_output(['blkid', '-s', 'UUID', dev])
|
||||||
|
.decode('ascii'))
|
||||||
except CalledProcessError:
|
except CalledProcessError:
|
||||||
# If the device has not be used or formatted yet we expect this to
|
# If the device has not be used or formatted yet we expect this to
|
||||||
# fail.
|
# fail.
|
||||||
@ -420,7 +423,7 @@ def remember_devices(devs):
|
|||||||
log("Device '%s' already in devstore (status:%s)" %
|
log("Device '%s' already in devstore (status:%s)" %
|
||||||
(dev, devstore[key].get('status')), level=DEBUG)
|
(dev, devstore[key].get('status')), level=DEBUG)
|
||||||
else:
|
else:
|
||||||
existing = [(k, v) for k, v in devstore.iteritems()
|
existing = [(k, v) for k, v in devstore.items()
|
||||||
if v.get('blkid') == blk_uuid and
|
if v.get('blkid') == blk_uuid and
|
||||||
re.match("^(.+)@(.+)$", k).group(1) == dev]
|
re.match("^(.+)@(.+)$", k).group(1) == dev]
|
||||||
if existing:
|
if existing:
|
||||||
@ -435,7 +438,7 @@ def remember_devices(devs):
|
|||||||
devstore[key] = {'blkid': blk_uuid, 'status': 'active'}
|
devstore[key] = {'blkid': blk_uuid, 'status': 'active'}
|
||||||
|
|
||||||
if devstore:
|
if devstore:
|
||||||
kvstore.set(key='devices', value=json.dumps(devstore))
|
kvstore.set(key='devices', value=json.dumps(devstore, sort_keys=True))
|
||||||
|
|
||||||
kvstore.flush()
|
kvstore.flush()
|
||||||
kvstore.close()
|
kvstore.close()
|
||||||
|
8
tox.ini
8
tox.ini
@ -2,8 +2,9 @@
|
|||||||
# This file is managed centrally by release-tools and should not be modified
|
# This file is managed centrally by release-tools and should not be modified
|
||||||
# within individual charm repos.
|
# within individual charm repos.
|
||||||
[tox]
|
[tox]
|
||||||
envlist = pep8,py27
|
envlist = pep8,py27,py35,py36
|
||||||
skipsdist = True
|
skipsdist = True
|
||||||
|
skip_missing_interpreters = True
|
||||||
|
|
||||||
[testenv]
|
[testenv]
|
||||||
setenv = VIRTUAL_ENV={envdir}
|
setenv = VIRTUAL_ENV={envdir}
|
||||||
@ -18,8 +19,7 @@ passenv = HOME TERM AMULET_* CS_API_*
|
|||||||
|
|
||||||
[testenv:py27]
|
[testenv:py27]
|
||||||
basepython = python2.7
|
basepython = python2.7
|
||||||
deps = -r{toxinidir}/requirements.txt
|
commands = /bin/true
|
||||||
-r{toxinidir}/test-requirements.txt
|
|
||||||
|
|
||||||
[testenv:py35]
|
[testenv:py35]
|
||||||
basepython = python3.5
|
basepython = python3.5
|
||||||
@ -32,7 +32,7 @@ deps = -r{toxinidir}/requirements.txt
|
|||||||
-r{toxinidir}/test-requirements.txt
|
-r{toxinidir}/test-requirements.txt
|
||||||
|
|
||||||
[testenv:pep8]
|
[testenv:pep8]
|
||||||
basepython = python2.7
|
basepython = python3
|
||||||
deps = -r{toxinidir}/requirements.txt
|
deps = -r{toxinidir}/requirements.txt
|
||||||
-r{toxinidir}/test-requirements.txt
|
-r{toxinidir}/test-requirements.txt
|
||||||
commands = flake8 {posargs} hooks unit_tests tests actions lib
|
commands = flake8 {posargs} hooks unit_tests tests actions lib
|
||||||
|
@ -11,3 +11,20 @@
|
|||||||
# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
||||||
# See the License for the specific language governing permissions and
|
# See the License for the specific language governing permissions and
|
||||||
# limitations under the License.
|
# limitations under the License.
|
||||||
|
|
||||||
|
import os
|
||||||
|
import sys
|
||||||
|
|
||||||
|
_path = os.path.dirname(os.path.realpath(__file__))
|
||||||
|
_actions = os.path.abspath(os.path.join(_path, '../actions'))
|
||||||
|
_hooks = os.path.abspath(os.path.join(_path, '../hooks'))
|
||||||
|
_lib = os.path.abspath(os.path.join(_path, '../lib'))
|
||||||
|
|
||||||
|
|
||||||
|
def _add_path(path):
|
||||||
|
if path not in sys.path:
|
||||||
|
sys.path.insert(1, path)
|
||||||
|
|
||||||
|
_add_path(_actions)
|
||||||
|
_add_path(_hooks)
|
||||||
|
_add_path(_lib)
|
||||||
|
@ -21,7 +21,7 @@ import unittest
|
|||||||
import mock
|
import mock
|
||||||
import yaml
|
import yaml
|
||||||
|
|
||||||
from test_utils import CharmTestCase
|
from unit_tests.test_utils import CharmTestCase
|
||||||
|
|
||||||
from mock import patch, MagicMock
|
from mock import patch, MagicMock
|
||||||
|
|
||||||
@ -30,12 +30,12 @@ from mock import patch, MagicMock
|
|||||||
sys.modules['apt'] = MagicMock()
|
sys.modules['apt'] = MagicMock()
|
||||||
sys.modules['apt_pkg'] = MagicMock()
|
sys.modules['apt_pkg'] = MagicMock()
|
||||||
|
|
||||||
with patch('actions.hooks.charmhelpers.contrib.hardening.harden.harden') as \
|
with patch('charmhelpers.contrib.hardening.harden.harden') as \
|
||||||
mock_dec:
|
mock_dec:
|
||||||
mock_dec.side_effect = (lambda *dargs, **dkwargs: lambda f:
|
mock_dec.side_effect = (lambda *dargs, **dkwargs: lambda f:
|
||||||
lambda *args, **kwargs: f(*args, **kwargs))
|
lambda *args, **kwargs: f(*args, **kwargs))
|
||||||
with patch('actions.hooks.lib.misc_utils.is_paused') as is_paused:
|
with patch('lib.misc_utils.is_paused') as is_paused:
|
||||||
with patch('actions.hooks.lib.swift_storage_utils.register_configs'):
|
with patch('lib.swift_storage_utils.register_configs'):
|
||||||
import actions.actions
|
import actions.actions
|
||||||
|
|
||||||
|
|
||||||
@ -196,7 +196,8 @@ class GetActionParserTestCase(unittest.TestCase):
|
|||||||
"""ArgumentParser is seeded from actions.yaml."""
|
"""ArgumentParser is seeded from actions.yaml."""
|
||||||
actions_yaml = tempfile.NamedTemporaryFile(
|
actions_yaml = tempfile.NamedTemporaryFile(
|
||||||
prefix="GetActionParserTestCase", suffix="yaml")
|
prefix="GetActionParserTestCase", suffix="yaml")
|
||||||
actions_yaml.write(yaml.dump({"foo": {"description": "Foo is bar"}}))
|
actions_yaml.write(
|
||||||
|
yaml.dump({"foo": {"description": "Foo is bar"}}).encode('utf-8'))
|
||||||
actions_yaml.seek(0)
|
actions_yaml.seek(0)
|
||||||
parser = actions.actions.get_action_parser(actions_yaml.name, "foo",
|
parser = actions.actions.get_action_parser(actions_yaml.name, "foo",
|
||||||
get_services=lambda: [])
|
get_services=lambda: [])
|
||||||
|
@ -31,9 +31,7 @@ with patch('charmhelpers.contrib.hardening.harden.harden') as mock_dec:
|
|||||||
with patch('lib.swift_storage_utils.register_configs'):
|
with patch('lib.swift_storage_utils.register_configs'):
|
||||||
import actions.openstack_upgrade as openstack_upgrade
|
import actions.openstack_upgrade as openstack_upgrade
|
||||||
|
|
||||||
from test_utils import (
|
from unit_tests.test_utils import CharmTestCase
|
||||||
CharmTestCase
|
|
||||||
)
|
|
||||||
|
|
||||||
TO_PATCH = [
|
TO_PATCH = [
|
||||||
'config_changed',
|
'config_changed',
|
||||||
@ -47,10 +45,9 @@ class TestSwiftStorageUpgradeActions(CharmTestCase):
|
|||||||
super(TestSwiftStorageUpgradeActions, self).setUp(openstack_upgrade,
|
super(TestSwiftStorageUpgradeActions, self).setUp(openstack_upgrade,
|
||||||
TO_PATCH)
|
TO_PATCH)
|
||||||
|
|
||||||
@patch('actions.charmhelpers.contrib.openstack.utils.config')
|
@patch('charmhelpers.contrib.openstack.utils.config')
|
||||||
@patch('actions.charmhelpers.contrib.openstack.utils.action_set')
|
@patch('charmhelpers.contrib.openstack.utils.action_set')
|
||||||
@patch('actions.charmhelpers.contrib.openstack.utils.'
|
@patch('charmhelpers.contrib.openstack.utils.openstack_upgrade_available')
|
||||||
'openstack_upgrade_available')
|
|
||||||
def test_openstack_upgrade_true(self, upgrade_avail,
|
def test_openstack_upgrade_true(self, upgrade_avail,
|
||||||
action_set, config):
|
action_set, config):
|
||||||
upgrade_avail.return_value = True
|
upgrade_avail.return_value = True
|
||||||
@ -61,10 +58,9 @@ class TestSwiftStorageUpgradeActions(CharmTestCase):
|
|||||||
self.assertTrue(self.do_openstack_upgrade.called)
|
self.assertTrue(self.do_openstack_upgrade.called)
|
||||||
self.assertTrue(self.config_changed.called)
|
self.assertTrue(self.config_changed.called)
|
||||||
|
|
||||||
@patch('actions.charmhelpers.contrib.openstack.utils.config')
|
@patch('charmhelpers.contrib.openstack.utils.config')
|
||||||
@patch('actions.charmhelpers.contrib.openstack.utils.action_set')
|
@patch('charmhelpers.contrib.openstack.utils.action_set')
|
||||||
@patch('actions.charmhelpers.contrib.openstack.utils.'
|
@patch('charmhelpers.contrib.openstack.utils.openstack_upgrade_available')
|
||||||
'openstack_upgrade_available')
|
|
||||||
def test_openstack_upgrade_false(self, upgrade_avail,
|
def test_openstack_upgrade_false(self, upgrade_avail,
|
||||||
action_set, config):
|
action_set, config):
|
||||||
upgrade_avail.return_value = True
|
upgrade_avail.return_value = True
|
||||||
|
@ -15,7 +15,7 @@
|
|||||||
import datetime
|
import datetime
|
||||||
import sys
|
import sys
|
||||||
import unittest
|
import unittest
|
||||||
import urllib2
|
import urllib
|
||||||
|
|
||||||
from mock import (
|
from mock import (
|
||||||
patch,
|
patch,
|
||||||
@ -63,7 +63,7 @@ class CheckSwiftStorageTestCase(unittest.TestCase):
|
|||||||
"""
|
"""
|
||||||
Ensure md5 checksum is generated from a file content
|
Ensure md5 checksum is generated from a file content
|
||||||
"""
|
"""
|
||||||
with patch("__builtin__.open", mock_open(read_data='data')) as \
|
with patch("builtins.open", mock_open(read_data=b'data')) as \
|
||||||
mock_file:
|
mock_file:
|
||||||
result = generate_md5('path/to/file')
|
result = generate_md5('path/to/file')
|
||||||
mock_file.assert_called_with('path/to/file', 'rb')
|
mock_file.assert_called_with('path/to/file', 'rb')
|
||||||
@ -71,24 +71,26 @@ class CheckSwiftStorageTestCase(unittest.TestCase):
|
|||||||
self.assertEqual(result,
|
self.assertEqual(result,
|
||||||
'8d777f385d3dfec8815d20f7496026dc')
|
'8d777f385d3dfec8815d20f7496026dc')
|
||||||
|
|
||||||
@patch('urllib2.urlopen')
|
@patch('urllib.request.urlopen')
|
||||||
def test_check_md5_unknown_urlerror(self, mock_urlopen):
|
def test_check_md5_unknown_urlerror(self, mock_urlopen):
|
||||||
"""
|
"""
|
||||||
Force urllib2.URLError to test try-except
|
Force urllib.request.URLError to test try-except
|
||||||
"""
|
"""
|
||||||
base_url = 'http://localhost:6000/recon/'
|
base_url = 'http://localhost:6000/recon/'
|
||||||
url = '{}ringmd5'.format(base_url)
|
url = '{}ringmd5'.format(base_url)
|
||||||
error = 'connection refused'
|
error = 'connection refused'
|
||||||
mock_urlopen.side_effect = urllib2.URLError(Mock(return_value=error))
|
mock_urlopen.side_effect = (urllib
|
||||||
|
.error
|
||||||
|
.URLError(Mock(return_value=error)))
|
||||||
result = check_md5(base_url)
|
result = check_md5(base_url)
|
||||||
self.assertEqual(result,
|
self.assertEqual(result,
|
||||||
[(STATUS_UNKNOWN,
|
[(STATUS_UNKNOWN,
|
||||||
"Can't open url: {}".format(url))])
|
"Can't open url: {}".format(url))])
|
||||||
|
|
||||||
@patch('urllib2.urlopen')
|
@patch('urllib.request.urlopen')
|
||||||
def test_check_md5_unknown_valueerror1(self, mock_urlopen):
|
def test_check_md5_unknown_valueerror1(self, mock_urlopen):
|
||||||
"""
|
"""
|
||||||
Force ValueError on urllib2 to test try-except
|
Force ValueError on urllib.error.URLError to test try-except
|
||||||
"""
|
"""
|
||||||
base_url = 'asdfasdf'
|
base_url = 'asdfasdf'
|
||||||
url = '{}ringmd5'.format(base_url)
|
url = '{}ringmd5'.format(base_url)
|
||||||
@ -99,7 +101,7 @@ class CheckSwiftStorageTestCase(unittest.TestCase):
|
|||||||
[(STATUS_UNKNOWN,
|
[(STATUS_UNKNOWN,
|
||||||
"Can't parse status data")])
|
"Can't parse status data")])
|
||||||
|
|
||||||
@patch('urllib2.urlopen')
|
@patch('urllib.request.urlopen')
|
||||||
def test_check_md5_unknown_valueerror2(self, mock_urlopen):
|
def test_check_md5_unknown_valueerror2(self, mock_urlopen):
|
||||||
"""
|
"""
|
||||||
Force ValueError on json to test try-catch
|
Force ValueError on json to test try-catch
|
||||||
@ -125,7 +127,7 @@ class CheckSwiftStorageTestCase(unittest.TestCase):
|
|||||||
'"0ea1ec9585ef644ce2b5c5b1dced4128"}'
|
'"0ea1ec9585ef644ce2b5c5b1dced4128"}'
|
||||||
pmock_jdata = PropertyMock(return_value=jdata)
|
pmock_jdata = PropertyMock(return_value=jdata)
|
||||||
mock_generate_md5.side_effect = IOError()
|
mock_generate_md5.side_effect = IOError()
|
||||||
with patch('urllib2.urlopen') as mock_urlopen:
|
with patch('urllib.request.urlopen') as mock_urlopen:
|
||||||
mock_urlopen.return_value = MagicMock(read=pmock_jdata)
|
mock_urlopen.return_value = MagicMock(read=pmock_jdata)
|
||||||
result = check_md5('.')
|
result = check_md5('.')
|
||||||
mock_urlopen.assert_called_with('.ringmd5')
|
mock_urlopen.assert_called_with('.ringmd5')
|
||||||
@ -148,7 +150,7 @@ class CheckSwiftStorageTestCase(unittest.TestCase):
|
|||||||
'"0ea1ec9585ef644ce2b5c5b1dced4128"}'
|
'"0ea1ec9585ef644ce2b5c5b1dced4128"}'
|
||||||
pmock_jdata = PropertyMock(return_value=jdata)
|
pmock_jdata = PropertyMock(return_value=jdata)
|
||||||
mock_generate_md5.return_value = 'xxxx'
|
mock_generate_md5.return_value = 'xxxx'
|
||||||
with patch('urllib2.urlopen') as mock_urlopen:
|
with patch('urllib.request.urlopen') as mock_urlopen:
|
||||||
mock_urlopen.return_value = MagicMock(read=pmock_jdata)
|
mock_urlopen.return_value = MagicMock(read=pmock_jdata)
|
||||||
result = check_md5('.')
|
result = check_md5('.')
|
||||||
mock_urlopen.assert_called_with('.ringmd5')
|
mock_urlopen.assert_called_with('.ringmd5')
|
||||||
@ -171,22 +173,24 @@ class CheckSwiftStorageTestCase(unittest.TestCase):
|
|||||||
'"6b4f3a0ef3731f18291ecd053ce0d9b6"}'
|
'"6b4f3a0ef3731f18291ecd053ce0d9b6"}'
|
||||||
pmock_jdata = PropertyMock(return_value=jdata)
|
pmock_jdata = PropertyMock(return_value=jdata)
|
||||||
mock_generate_md5.return_value = '6b4f3a0ef3731f18291ecd053ce0d9b6'
|
mock_generate_md5.return_value = '6b4f3a0ef3731f18291ecd053ce0d9b6'
|
||||||
with patch('urllib2.urlopen') as mock_urlopen:
|
with patch('urllib.request.urlopen') as mock_urlopen:
|
||||||
mock_urlopen.return_value = MagicMock(read=pmock_jdata)
|
mock_urlopen.return_value = MagicMock(read=pmock_jdata)
|
||||||
result = check_md5('.')
|
result = check_md5('.')
|
||||||
mock_urlopen.assert_called_with('.ringmd5')
|
mock_urlopen.assert_called_with('.ringmd5')
|
||||||
self.assertEqual(result,
|
self.assertEqual(result,
|
||||||
[(STATUS_OK, 'OK')])
|
[(STATUS_OK, 'OK')])
|
||||||
|
|
||||||
@patch('urllib2.urlopen')
|
@patch('urllib.request.urlopen')
|
||||||
def test_check_replication_unknown_urlerror(self, mock_urlopen):
|
def test_check_replication_unknown_urlerror(self, mock_urlopen):
|
||||||
"""
|
"""
|
||||||
Force urllib2.URLError to test try-catch
|
Force urllib.error.URLError to test try-catch
|
||||||
"""
|
"""
|
||||||
base_url = 'http://localhost:6000/recon/'
|
base_url = 'http://localhost:6000/recon/'
|
||||||
url = '{}replication/{}'
|
url = '{}replication/{}'
|
||||||
error = 'connection refused'
|
error = 'connection refused'
|
||||||
mock_urlopen.side_effect = urllib2.URLError(Mock(return_value=error))
|
mock_urlopen.side_effect = (urllib
|
||||||
|
.error
|
||||||
|
.URLError(Mock(return_value=error)))
|
||||||
result = check_replication(base_url, 60)
|
result = check_replication(base_url, 60)
|
||||||
expected_result = [(STATUS_UNKNOWN,
|
expected_result = [(STATUS_UNKNOWN,
|
||||||
"Can't open url: "
|
"Can't open url: "
|
||||||
@ -194,10 +198,10 @@ class CheckSwiftStorageTestCase(unittest.TestCase):
|
|||||||
for name in ('account', 'object', 'container')]
|
for name in ('account', 'object', 'container')]
|
||||||
self.assertEqual(result, expected_result)
|
self.assertEqual(result, expected_result)
|
||||||
|
|
||||||
@patch('urllib2.urlopen')
|
@patch('urllib.request.urlopen')
|
||||||
def test_check_replication_unknown_valueerror1(self, mock_urlopen):
|
def test_check_replication_unknown_valueerror1(self, mock_urlopen):
|
||||||
"""
|
"""
|
||||||
Force ValueError on urllib2 to test try-catch
|
Force ValueError on urllib.error to test try-catch
|
||||||
"""
|
"""
|
||||||
base_url = '.'
|
base_url = '.'
|
||||||
mock_urlopen.side_effect = ValueError(Mock(return_value=''))
|
mock_urlopen.side_effect = ValueError(Mock(return_value=''))
|
||||||
@ -206,7 +210,7 @@ class CheckSwiftStorageTestCase(unittest.TestCase):
|
|||||||
3*[(STATUS_UNKNOWN,
|
3*[(STATUS_UNKNOWN,
|
||||||
"Can't parse status data")])
|
"Can't parse status data")])
|
||||||
|
|
||||||
@patch('urllib2.urlopen')
|
@patch('urllib.request.urlopen')
|
||||||
def test_check_replication_unknown_valueerror2(self, mock_urlopen):
|
def test_check_replication_unknown_valueerror2(self, mock_urlopen):
|
||||||
"""
|
"""
|
||||||
Force ValueError on json to test try-catch
|
Force ValueError on json to test try-catch
|
||||||
@ -233,7 +237,7 @@ class CheckSwiftStorageTestCase(unittest.TestCase):
|
|||||||
'"empty": 0}, "replication_time": 0.0076580047607421875}'
|
'"empty": 0}, "replication_time": 0.0076580047607421875}'
|
||||||
pmock_jdata = PropertyMock(return_value=jdata)
|
pmock_jdata = PropertyMock(return_value=jdata)
|
||||||
mock_timestamp.return_value = (None, 0)
|
mock_timestamp.return_value = (None, 0)
|
||||||
with patch('urllib2.urlopen') as mock_urlopen:
|
with patch('urllib.request.urlopen') as mock_urlopen:
|
||||||
mock_urlopen.return_value = MagicMock(read=pmock_jdata)
|
mock_urlopen.return_value = MagicMock(read=pmock_jdata)
|
||||||
result = check_replication(base_url, [4, 10, 4, 10])
|
result = check_replication(base_url, [4, 10, 4, 10])
|
||||||
self.assertEqual(result,
|
self.assertEqual(result,
|
||||||
@ -256,7 +260,7 @@ class CheckSwiftStorageTestCase(unittest.TestCase):
|
|||||||
'"empty": 0}, "replication_time": 0.0076580047607421875}'
|
'"empty": 0}, "replication_time": 0.0076580047607421875}'
|
||||||
pmock_jdata = PropertyMock(return_value=jdata)
|
pmock_jdata = PropertyMock(return_value=jdata)
|
||||||
mock_timestamp.return_value = (MagicMock(days=0, seconds=12), 0)
|
mock_timestamp.return_value = (MagicMock(days=0, seconds=12), 0)
|
||||||
with patch('urllib2.urlopen') as mock_urlopen:
|
with patch('urllib.request.urlopen') as mock_urlopen:
|
||||||
mock_urlopen.return_value = MagicMock(read=pmock_jdata)
|
mock_urlopen.return_value = MagicMock(read=pmock_jdata)
|
||||||
result = check_replication(base_url, [4, 10, 4, 10])
|
result = check_replication(base_url, [4, 10, 4, 10])
|
||||||
self.assertEqual(result,
|
self.assertEqual(result,
|
||||||
@ -279,7 +283,7 @@ class CheckSwiftStorageTestCase(unittest.TestCase):
|
|||||||
'"empty": 0}, "replication_time": 0.0076580047607421875}'
|
'"empty": 0}, "replication_time": 0.0076580047607421875}'
|
||||||
pmock_jdata = PropertyMock(return_value=jdata)
|
pmock_jdata = PropertyMock(return_value=jdata)
|
||||||
mock_timestamp.return_value = (MagicMock(days=0, seconds=0), 12)
|
mock_timestamp.return_value = (MagicMock(days=0, seconds=0), 12)
|
||||||
with patch('urllib2.urlopen') as mock_urlopen:
|
with patch('urllib.request.urlopen') as mock_urlopen:
|
||||||
mock_urlopen.return_value = MagicMock(read=pmock_jdata)
|
mock_urlopen.return_value = MagicMock(read=pmock_jdata)
|
||||||
result = check_replication(base_url, [4, 10, 4, 10])
|
result = check_replication(base_url, [4, 10, 4, 10])
|
||||||
self.assertEqual(result,
|
self.assertEqual(result,
|
||||||
@ -299,7 +303,7 @@ class CheckSwiftStorageTestCase(unittest.TestCase):
|
|||||||
'"empty": 0}, "replication_time": 0.0076580047607421875}'
|
'"empty": 0}, "replication_time": 0.0076580047607421875}'
|
||||||
pmock_jdata = PropertyMock(return_value=jdata)
|
pmock_jdata = PropertyMock(return_value=jdata)
|
||||||
mock_timestamp.return_value = (MagicMock(days=0, seconds=0), -1)
|
mock_timestamp.return_value = (MagicMock(days=0, seconds=0), -1)
|
||||||
with patch('urllib2.urlopen') as mock_urlopen:
|
with patch('urllib.request.urlopen') as mock_urlopen:
|
||||||
mock_urlopen.return_value = MagicMock(read=pmock_jdata)
|
mock_urlopen.return_value = MagicMock(read=pmock_jdata)
|
||||||
result = check_replication(base_url, [4, 10, 4, 10])
|
result = check_replication(base_url, [4, 10, 4, 10])
|
||||||
self.assertEqual(result,
|
self.assertEqual(result,
|
||||||
@ -321,7 +325,7 @@ class CheckSwiftStorageTestCase(unittest.TestCase):
|
|||||||
'"empty": 0}, "replication_time": 0.0076580047607421875}'
|
'"empty": 0}, "replication_time": 0.0076580047607421875}'
|
||||||
pmock_jdata = PropertyMock(return_value=jdata)
|
pmock_jdata = PropertyMock(return_value=jdata)
|
||||||
mock_timestamp.return_value = (MagicMock(days=0, seconds=5), 0)
|
mock_timestamp.return_value = (MagicMock(days=0, seconds=5), 0)
|
||||||
with patch('urllib2.urlopen') as mock_urlopen:
|
with patch('urllib.request.urlopen') as mock_urlopen:
|
||||||
mock_urlopen.return_value = MagicMock(read=pmock_jdata)
|
mock_urlopen.return_value = MagicMock(read=pmock_jdata)
|
||||||
result = check_replication(base_url, [4, 10, 4, 10])
|
result = check_replication(base_url, [4, 10, 4, 10])
|
||||||
self.assertEqual(result,
|
self.assertEqual(result,
|
||||||
@ -344,7 +348,7 @@ class CheckSwiftStorageTestCase(unittest.TestCase):
|
|||||||
'"empty": 0}, "replication_time": 0.0076580047607421875}'
|
'"empty": 0}, "replication_time": 0.0076580047607421875}'
|
||||||
pmock_jdata = PropertyMock(return_value=jdata)
|
pmock_jdata = PropertyMock(return_value=jdata)
|
||||||
mock_timestamp.return_value = (MagicMock(days=2, seconds=5), 0)
|
mock_timestamp.return_value = (MagicMock(days=2, seconds=5), 0)
|
||||||
with patch('urllib2.urlopen') as mock_urlopen:
|
with patch('urllib.request.urlopen') as mock_urlopen:
|
||||||
mock_urlopen.return_value = MagicMock(read=pmock_jdata)
|
mock_urlopen.return_value = MagicMock(read=pmock_jdata)
|
||||||
result = check_replication(base_url, [4, 10, 4, 10])
|
result = check_replication(base_url, [4, 10, 4, 10])
|
||||||
self.assertEqual(result,
|
self.assertEqual(result,
|
||||||
@ -367,7 +371,8 @@ class CheckSwiftStorageTestCase(unittest.TestCase):
|
|||||||
'"empty": 0}, "replication_time": 0.0076580047607421875}'
|
'"empty": 0}, "replication_time": 0.0076580047607421875}'
|
||||||
pmock_jdata = PropertyMock(return_value=jdata)
|
pmock_jdata = PropertyMock(return_value=jdata)
|
||||||
mock_timestamp.return_value = (MagicMock(days=0, seconds=0), 5)
|
mock_timestamp.return_value = (MagicMock(days=0, seconds=0), 5)
|
||||||
with patch('urllib2.urlopen') as mock_urlopen:
|
# with patch('urllib2.urlopen') as mock_urlopen:
|
||||||
|
with patch('urllib.request.urlopen') as mock_urlopen:
|
||||||
mock_urlopen.return_value = MagicMock(read=pmock_jdata)
|
mock_urlopen.return_value = MagicMock(read=pmock_jdata)
|
||||||
result = check_replication(base_url, [4, 10, 4, 10])
|
result = check_replication(base_url, [4, 10, 4, 10])
|
||||||
self.assertEqual(result,
|
self.assertEqual(result,
|
||||||
@ -388,7 +393,7 @@ class CheckSwiftStorageTestCase(unittest.TestCase):
|
|||||||
'"empty": 0}, "replication_time": 0.0076580047607421875}'
|
'"empty": 0}, "replication_time": 0.0076580047607421875}'
|
||||||
pmock_jdata = PropertyMock(return_value=jdata)
|
pmock_jdata = PropertyMock(return_value=jdata)
|
||||||
mock_timestamp.return_value = (MagicMock(days=0, seconds=0), 0)
|
mock_timestamp.return_value = (MagicMock(days=0, seconds=0), 0)
|
||||||
with patch('urllib2.urlopen') as mock_urlopen:
|
with patch('urllib.request.urlopen') as mock_urlopen:
|
||||||
mock_urlopen.return_value = MagicMock(read=pmock_jdata)
|
mock_urlopen.return_value = MagicMock(read=pmock_jdata)
|
||||||
result = check_replication(base_url, [4, 10, 4, 10])
|
result = check_replication(base_url, [4, 10, 4, 10])
|
||||||
self.assertEqual(result, [(STATUS_OK, 'OK')])
|
self.assertEqual(result, [(STATUS_OK, 'OK')])
|
||||||
|
@ -13,7 +13,8 @@
|
|||||||
# limitations under the License.
|
# limitations under the License.
|
||||||
|
|
||||||
from mock import MagicMock
|
from mock import MagicMock
|
||||||
from test_utils import CharmTestCase, patch_open
|
|
||||||
|
from unit_tests.test_utils import CharmTestCase, patch_open
|
||||||
|
|
||||||
import lib.swift_storage_context as swift_context
|
import lib.swift_storage_context as swift_context
|
||||||
|
|
||||||
|
@ -13,18 +13,18 @@
|
|||||||
# limitations under the License.
|
# limitations under the License.
|
||||||
|
|
||||||
from mock import patch
|
from mock import patch
|
||||||
import os
|
|
||||||
import json
|
import json
|
||||||
import uuid
|
import os
|
||||||
import tempfile
|
import tempfile
|
||||||
|
import uuid
|
||||||
|
|
||||||
from test_utils import CharmTestCase, TestKV, patch_open
|
from unit_tests.test_utils import CharmTestCase, TestKV, patch_open
|
||||||
|
|
||||||
with patch('hooks.charmhelpers.contrib.hardening.harden.harden') as mock_dec:
|
with patch('charmhelpers.contrib.hardening.harden.harden') as mock_dec:
|
||||||
mock_dec.side_effect = (lambda *dargs, **dkwargs: lambda f:
|
mock_dec.side_effect = (lambda *dargs, **dkwargs: lambda f:
|
||||||
lambda *args, **kwargs: f(*args, **kwargs))
|
lambda *args, **kwargs: f(*args, **kwargs))
|
||||||
with patch('hooks.lib.misc_utils.is_paused') as is_paused:
|
with patch('lib.misc_utils.is_paused') as is_paused:
|
||||||
with patch('hooks.lib.swift_storage_utils.register_configs') as _:
|
with patch('lib.swift_storage_utils.register_configs') as _:
|
||||||
import hooks.swift_storage_hooks as hooks
|
import hooks.swift_storage_hooks as hooks
|
||||||
|
|
||||||
from lib.swift_storage_utils import PACKAGES
|
from lib.swift_storage_utils import PACKAGES
|
||||||
@ -69,7 +69,7 @@ TO_PATCH = [
|
|||||||
]
|
]
|
||||||
|
|
||||||
|
|
||||||
UFW_DUMMY_RULES = """
|
UFW_DUMMY_RULES = b"""
|
||||||
# Don't delete these required lines, otherwise there will be errors
|
# Don't delete these required lines, otherwise there will be errors
|
||||||
*filter
|
*filter
|
||||||
:ufw-before-input - [0:0]
|
:ufw-before-input - [0:0]
|
||||||
@ -88,8 +88,7 @@ UFW_DUMMY_RULES = """
|
|||||||
class SwiftStorageRelationsTests(CharmTestCase):
|
class SwiftStorageRelationsTests(CharmTestCase):
|
||||||
|
|
||||||
def setUp(self):
|
def setUp(self):
|
||||||
super(SwiftStorageRelationsTests, self).setUp(hooks,
|
super(SwiftStorageRelationsTests, self).setUp(hooks, TO_PATCH)
|
||||||
TO_PATCH)
|
|
||||||
self.config.side_effect = self.test_config.get
|
self.config.side_effect = self.test_config.get
|
||||||
self.relation_get.side_effect = self.test_relation.get
|
self.relation_get.side_effect = self.test_relation.get
|
||||||
self.get_relation_ip.return_value = '10.10.10.2'
|
self.get_relation_ip.return_value = '10.10.10.2'
|
||||||
@ -178,14 +177,14 @@ class SwiftStorageRelationsTests(CharmTestCase):
|
|||||||
self.assertTrue(self.update_nrpe_config.called)
|
self.assertTrue(self.update_nrpe_config.called)
|
||||||
self.assertTrue(mock_ensure_devs_tracked.called)
|
self.assertTrue(mock_ensure_devs_tracked.called)
|
||||||
|
|
||||||
@patch('hooks.lib.swift_storage_utils.get_device_blkid',
|
@patch('lib.swift_storage_utils.get_device_blkid',
|
||||||
lambda dev: str(uuid.uuid4()))
|
lambda dev: str(uuid.uuid4()))
|
||||||
@patch.object(hooks.os, 'environ')
|
@patch.object(hooks.os, 'environ')
|
||||||
@patch('hooks.lib.swift_storage_utils.os.path.isdir', lambda *args: True)
|
@patch('lib.swift_storage_utils.os.path.isdir', lambda *args: True)
|
||||||
@patch.object(hooks, 'relation_set')
|
@patch.object(hooks, 'relation_set')
|
||||||
@patch('hooks.lib.swift_storage_utils.local_unit')
|
@patch('lib.swift_storage_utils.local_unit')
|
||||||
@patch('hooks.lib.swift_storage_utils.relation_ids', lambda *args: [])
|
@patch('lib.swift_storage_utils.relation_ids', lambda *args: [])
|
||||||
@patch('hooks.lib.swift_storage_utils.KVStore')
|
@patch('lib.swift_storage_utils.KVStore')
|
||||||
@patch.object(uuid, 'uuid4', lambda: 'a-test-uuid')
|
@patch.object(uuid, 'uuid4', lambda: 'a-test-uuid')
|
||||||
def _test_storage_joined_single_device(self, mock_kvstore, mock_local_unit,
|
def _test_storage_joined_single_device(self, mock_kvstore, mock_local_unit,
|
||||||
mock_rel_set, mock_environ,
|
mock_rel_set, mock_environ,
|
||||||
@ -199,6 +198,9 @@ class SwiftStorageRelationsTests(CharmTestCase):
|
|||||||
kvstore.get.return_value = None
|
kvstore.get.return_value = None
|
||||||
self.test_kv.set('prepared-devices', ['/dev/vdb'])
|
self.test_kv.set('prepared-devices', ['/dev/vdb'])
|
||||||
|
|
||||||
|
# py3 is very picky, and log is only patched in
|
||||||
|
# hooks.swift_storage_hooks
|
||||||
|
with patch('lib.swift_storage_utils.log'):
|
||||||
hooks.swift_storage_relation_joined()
|
hooks.swift_storage_relation_joined()
|
||||||
|
|
||||||
self.get_relation_ip.assert_called_once_with('swift-storage')
|
self.get_relation_ip.assert_called_once_with('swift-storage')
|
||||||
@ -230,8 +232,8 @@ class SwiftStorageRelationsTests(CharmTestCase):
|
|||||||
devices = {"vdb@%s" % (test_uuid):
|
devices = {"vdb@%s" % (test_uuid):
|
||||||
{"status": "active",
|
{"status": "active",
|
||||||
"blkid": 'a-test-uuid'}}
|
"blkid": 'a-test-uuid'}}
|
||||||
kvstore.set.assert_called_with(key='devices',
|
kvstore.set.assert_called_with(
|
||||||
value=json.dumps(devices))
|
key='devices', value=json.dumps(devices, sort_keys=True))
|
||||||
|
|
||||||
def test_storage_joined_single_device_juju_1(self):
|
def test_storage_joined_single_device_juju_1(self):
|
||||||
'''Ensure use of JUJU_ENV_UUID for Juju < 2'''
|
'''Ensure use of JUJU_ENV_UUID for Juju < 2'''
|
||||||
@ -241,13 +243,13 @@ class SwiftStorageRelationsTests(CharmTestCase):
|
|||||||
'''Ensure use of JUJU_MODEL_UUID for Juju >= 2'''
|
'''Ensure use of JUJU_MODEL_UUID for Juju >= 2'''
|
||||||
self._test_storage_joined_single_device(env_key='JUJU_MODEL_UUID')
|
self._test_storage_joined_single_device(env_key='JUJU_MODEL_UUID')
|
||||||
|
|
||||||
@patch('hooks.lib.swift_storage_utils.get_device_blkid',
|
@patch('lib.swift_storage_utils.get_device_blkid',
|
||||||
lambda dev: '%s-blkid-uuid' % os.path.basename(dev))
|
lambda dev: '%s-blkid-uuid' % os.path.basename(dev))
|
||||||
@patch.object(hooks.os, 'environ')
|
@patch.object(hooks.os, 'environ')
|
||||||
@patch('hooks.lib.swift_storage_utils.os.path.isdir', lambda *args: True)
|
@patch('lib.swift_storage_utils.os.path.isdir', lambda *args: True)
|
||||||
@patch('hooks.lib.swift_storage_utils.local_unit')
|
@patch('lib.swift_storage_utils.local_unit')
|
||||||
@patch('hooks.lib.swift_storage_utils.relation_ids', lambda *args: [])
|
@patch('lib.swift_storage_utils.relation_ids', lambda *args: [])
|
||||||
@patch('hooks.lib.swift_storage_utils.KVStore')
|
@patch('lib.swift_storage_utils.KVStore')
|
||||||
@patch.object(uuid, 'uuid4', lambda: 'a-test-uuid')
|
@patch.object(uuid, 'uuid4', lambda: 'a-test-uuid')
|
||||||
def test_storage_joined_multi_device(self, mock_kvstore, mock_local_unit,
|
def test_storage_joined_multi_device(self, mock_kvstore, mock_local_unit,
|
||||||
mock_environ):
|
mock_environ):
|
||||||
@ -272,6 +274,9 @@ class SwiftStorageRelationsTests(CharmTestCase):
|
|||||||
|
|
||||||
kvstore.get.side_effect = fake_kv_get
|
kvstore.get.side_effect = fake_kv_get
|
||||||
|
|
||||||
|
# py3 is very picky, and log is only patched in
|
||||||
|
# hooks.swift_storage_hooks
|
||||||
|
with patch('lib.swift_storage_utils.log'):
|
||||||
hooks.swift_storage_relation_joined()
|
hooks.swift_storage_relation_joined()
|
||||||
devices = {"vdb@%s" % (test_uuid): {"status": "active",
|
devices = {"vdb@%s" % (test_uuid): {"status": "active",
|
||||||
"blkid": 'vdb-blkid-uuid'},
|
"blkid": 'vdb-blkid-uuid'},
|
||||||
@ -280,17 +285,17 @@ class SwiftStorageRelationsTests(CharmTestCase):
|
|||||||
"vdc@%s" % (test_uuid): {"status": "active",
|
"vdc@%s" % (test_uuid): {"status": "active",
|
||||||
"blkid": 'vdc-blkid-uuid'}}
|
"blkid": 'vdc-blkid-uuid'}}
|
||||||
kvstore.set.assert_called_with(
|
kvstore.set.assert_called_with(
|
||||||
key='devices', value=json.dumps(devices)
|
key='devices', value=json.dumps(devices, sort_keys=True)
|
||||||
)
|
)
|
||||||
self.get_relation_ip.assert_called_once_with('swift-storage')
|
self.get_relation_ip.assert_called_once_with('swift-storage')
|
||||||
|
|
||||||
@patch('hooks.lib.swift_storage_utils.get_device_blkid',
|
@patch('lib.swift_storage_utils.get_device_blkid',
|
||||||
lambda dev: '%s-blkid-uuid' % os.path.basename(dev))
|
lambda dev: '%s-blkid-uuid' % os.path.basename(dev))
|
||||||
@patch.object(hooks.os, 'environ')
|
@patch.object(hooks.os, 'environ')
|
||||||
@patch('hooks.lib.swift_storage_utils.os.path.isdir', lambda *args: True)
|
@patch('lib.swift_storage_utils.os.path.isdir', lambda *args: True)
|
||||||
@patch('hooks.lib.swift_storage_utils.local_unit')
|
@patch('lib.swift_storage_utils.local_unit')
|
||||||
@patch('hooks.lib.swift_storage_utils.relation_ids', lambda *args: [])
|
@patch('lib.swift_storage_utils.relation_ids', lambda *args: [])
|
||||||
@patch('hooks.lib.swift_storage_utils.KVStore')
|
@patch('lib.swift_storage_utils.KVStore')
|
||||||
def test_storage_joined_dev_exists_unknown_juju_env_uuid(self,
|
def test_storage_joined_dev_exists_unknown_juju_env_uuid(self,
|
||||||
mock_kvstore,
|
mock_kvstore,
|
||||||
mock_local_unit,
|
mock_local_unit,
|
||||||
@ -317,7 +322,11 @@ class SwiftStorageRelationsTests(CharmTestCase):
|
|||||||
|
|
||||||
kvstore.get.side_effect = fake_kv_get
|
kvstore.get.side_effect = fake_kv_get
|
||||||
|
|
||||||
|
# py3 is very picky, and log is only patched in
|
||||||
|
# hooks.swift_storage_hooks
|
||||||
|
with patch('lib.swift_storage_utils.log'):
|
||||||
hooks.swift_storage_relation_joined()
|
hooks.swift_storage_relation_joined()
|
||||||
|
|
||||||
devices = {"vdb@%s" % (test_uuid): {"status": "active",
|
devices = {"vdb@%s" % (test_uuid): {"status": "active",
|
||||||
"blkid": 'vdb-blkid-uuid'},
|
"blkid": 'vdb-blkid-uuid'},
|
||||||
"vdd@%s" % (test_uuid): {"status": "active",
|
"vdd@%s" % (test_uuid): {"status": "active",
|
||||||
@ -325,7 +334,7 @@ class SwiftStorageRelationsTests(CharmTestCase):
|
|||||||
"vdc@%s" % (test_uuid): {"status": "active",
|
"vdc@%s" % (test_uuid): {"status": "active",
|
||||||
"blkid": 'vdc-blkid-uuid'}}
|
"blkid": 'vdc-blkid-uuid'}}
|
||||||
kvstore.set.assert_called_with(
|
kvstore.set.assert_called_with(
|
||||||
key='devices', value=json.dumps(devices)
|
key='devices', value=json.dumps(devices, sort_keys=True)
|
||||||
)
|
)
|
||||||
self.get_relation_ip.assert_called_once_with('swift-storage')
|
self.get_relation_ip.assert_called_once_with('swift-storage')
|
||||||
|
|
||||||
@ -345,8 +354,8 @@ class SwiftStorageRelationsTests(CharmTestCase):
|
|||||||
'http://swift-proxy.com/rings/'
|
'http://swift-proxy.com/rings/'
|
||||||
)
|
)
|
||||||
|
|
||||||
@patch('sys.argv')
|
@patch('sys.argv', new=['dodah'])
|
||||||
def test_main_hook_missing(self, _argv):
|
def test_main_hook_missing(self):
|
||||||
hooks.main()
|
hooks.main()
|
||||||
self.assertTrue(self.log.called)
|
self.assertTrue(self.log.called)
|
||||||
|
|
||||||
|
@ -12,12 +12,12 @@
|
|||||||
# See the License for the specific language governing permissions and
|
# See the License for the specific language governing permissions and
|
||||||
# limitations under the License.
|
# limitations under the License.
|
||||||
|
|
||||||
|
from collections import namedtuple
|
||||||
|
from mock import call, patch, MagicMock
|
||||||
import shutil
|
import shutil
|
||||||
import tempfile
|
import tempfile
|
||||||
from collections import namedtuple
|
|
||||||
|
|
||||||
from mock import call, patch, MagicMock
|
from unit_tests.test_utils import CharmTestCase, TestKV, patch_open
|
||||||
from test_utils import CharmTestCase, TestKV, patch_open
|
|
||||||
|
|
||||||
import lib.swift_storage_utils as swift_utils
|
import lib.swift_storage_utils as swift_utils
|
||||||
|
|
||||||
@ -175,7 +175,7 @@ class SwiftStorageUtilsTests(CharmTestCase):
|
|||||||
self.test_config.set('block-device', bdevs)
|
self.test_config.set('block-device', bdevs)
|
||||||
result = swift_utils.determine_block_devices()
|
result = swift_utils.determine_block_devices()
|
||||||
ex = ['/dev/vdb', '/dev/vdc', '/tmp/swift.img']
|
ex = ['/dev/vdb', '/dev/vdc', '/tmp/swift.img']
|
||||||
ex = list(set(ex))
|
ex = sorted(set(ex))
|
||||||
self.assertEqual(ex, result)
|
self.assertEqual(ex, result)
|
||||||
|
|
||||||
@patch.object(swift_utils, 'ensure_block_device')
|
@patch.object(swift_utils, 'ensure_block_device')
|
||||||
@ -185,7 +185,7 @@ class SwiftStorageUtilsTests(CharmTestCase):
|
|||||||
self.test_config.set('block-device', bdevs)
|
self.test_config.set('block-device', bdevs)
|
||||||
result = swift_utils.determine_block_devices()
|
result = swift_utils.determine_block_devices()
|
||||||
ex = ['/dev/vdb', '/dev/vdc', '/tmp/swift.img']
|
ex = ['/dev/vdb', '/dev/vdc', '/tmp/swift.img']
|
||||||
ex = list(set(ex))
|
ex = sorted(set(ex))
|
||||||
self.assertEqual(ex, result)
|
self.assertEqual(ex, result)
|
||||||
|
|
||||||
@patch.object(swift_utils, 'ensure_block_device')
|
@patch.object(swift_utils, 'ensure_block_device')
|
||||||
@ -206,14 +206,16 @@ class SwiftStorageUtilsTests(CharmTestCase):
|
|||||||
def _findmnt(cmd):
|
def _findmnt(cmd):
|
||||||
dev = cmd[1].split('/')[-1]
|
dev = cmd[1].split('/')[-1]
|
||||||
mnt_point = '/srv/node/' + dev
|
mnt_point = '/srv/node/' + dev
|
||||||
return FINDMNT_FOUND_TEMPLATE.format(mnt_point, dev)
|
return (FINDMNT_FOUND_TEMPLATE
|
||||||
|
.format(mnt_point, dev).encode('ascii'))
|
||||||
_check_output.side_effect = _findmnt
|
_check_output.side_effect = _findmnt
|
||||||
_ensure.side_effect = self._fake_ensure
|
_ensure.side_effect = self._fake_ensure
|
||||||
self.test_config.set('block-device', 'guess')
|
self.test_config.set('block-device', 'guess')
|
||||||
_find.return_value = ['/dev/vdb', '/dev/sdb']
|
_find.return_value = ['/dev/vdb', '/dev/sdb']
|
||||||
result = swift_utils.determine_block_devices()
|
result = swift_utils.determine_block_devices()
|
||||||
self.assertTrue(_find.called)
|
self.assertTrue(_find.called)
|
||||||
self.assertEqual(result, ['/dev/vdb', '/dev/sdb'])
|
# always returns sorted results
|
||||||
|
self.assertEqual(result, ['/dev/sdb', '/dev/vdb'])
|
||||||
|
|
||||||
@patch.object(swift_utils, 'check_output')
|
@patch.object(swift_utils, 'check_output')
|
||||||
@patch.object(swift_utils, 'find_block_devices')
|
@patch.object(swift_utils, 'find_block_devices')
|
||||||
@ -225,7 +227,8 @@ class SwiftStorageUtilsTests(CharmTestCase):
|
|||||||
def _findmnt(cmd):
|
def _findmnt(cmd):
|
||||||
dev = cmd[1].split('/')[-1]
|
dev = cmd[1].split('/')[-1]
|
||||||
mnt_point = '/'
|
mnt_point = '/'
|
||||||
return FINDMNT_FOUND_TEMPLATE.format(mnt_point, dev)
|
return (FINDMNT_FOUND_TEMPLATE
|
||||||
|
.format(mnt_point, dev).encode('ascii'))
|
||||||
_check_output.side_effect = _findmnt
|
_check_output.side_effect = _findmnt
|
||||||
_ensure.side_effect = self._fake_ensure
|
_ensure.side_effect = self._fake_ensure
|
||||||
self.test_config.set('block-device', 'guess')
|
self.test_config.set('block-device', 'guess')
|
||||||
@ -569,7 +572,7 @@ class SwiftStorageUtilsTests(CharmTestCase):
|
|||||||
def test_get_device_blkid(self, mock_check_output):
|
def test_get_device_blkid(self, mock_check_output):
|
||||||
dev = '/dev/vdb'
|
dev = '/dev/vdb'
|
||||||
cmd = ['blkid', '-s', 'UUID', dev]
|
cmd = ['blkid', '-s', 'UUID', dev]
|
||||||
ret = '/dev/vdb: UUID="808bc298-0609-4619-aaef-ed7a5ab0ebb7" \n'
|
ret = b'/dev/vdb: UUID="808bc298-0609-4619-aaef-ed7a5ab0ebb7" \n'
|
||||||
mock_check_output.return_value = ret
|
mock_check_output.return_value = ret
|
||||||
uuid = swift_utils.get_device_blkid(dev)
|
uuid = swift_utils.get_device_blkid(dev)
|
||||||
self.assertEqual(uuid, "808bc298-0609-4619-aaef-ed7a5ab0ebb7")
|
self.assertEqual(uuid, "808bc298-0609-4619-aaef-ed7a5ab0ebb7")
|
||||||
|
@ -12,9 +12,10 @@
|
|||||||
# See the License for the specific language governing permissions and
|
# See the License for the specific language governing permissions and
|
||||||
# limitations under the License.
|
# limitations under the License.
|
||||||
|
|
||||||
|
import io
|
||||||
import logging
|
import logging
|
||||||
import unittest
|
|
||||||
import os
|
import os
|
||||||
|
import unittest
|
||||||
import yaml
|
import yaml
|
||||||
|
|
||||||
from contextlib import contextmanager
|
from contextlib import contextmanager
|
||||||
@ -37,7 +38,7 @@ def load_config():
|
|||||||
|
|
||||||
if not config:
|
if not config:
|
||||||
logging.error('Could not find config.yaml in any parent directory '
|
logging.error('Could not find config.yaml in any parent directory '
|
||||||
'of %s. ' % file)
|
'of %s. ' % __file__)
|
||||||
raise Exception
|
raise Exception
|
||||||
|
|
||||||
return yaml.safe_load(open(config).read())['options']
|
return yaml.safe_load(open(config).read())['options']
|
||||||
@ -50,7 +51,7 @@ def get_default_config():
|
|||||||
'''
|
'''
|
||||||
default_config = {}
|
default_config = {}
|
||||||
config = load_config()
|
config = load_config()
|
||||||
for k, v in config.iteritems():
|
for k, v in config.items():
|
||||||
if 'default' in v:
|
if 'default' in v:
|
||||||
default_config[k] = v['default']
|
default_config[k] = v['default']
|
||||||
else:
|
else:
|
||||||
@ -141,12 +142,12 @@ def patch_open():
|
|||||||
|
|
||||||
Yields the mock for "open" and "file", respectively.'''
|
Yields the mock for "open" and "file", respectively.'''
|
||||||
mock_open = MagicMock(spec=open)
|
mock_open = MagicMock(spec=open)
|
||||||
mock_file = MagicMock(spec=file)
|
mock_file = MagicMock(spec=io.FileIO)
|
||||||
|
|
||||||
@contextmanager
|
@contextmanager
|
||||||
def stub_open(*args, **kwargs):
|
def stub_open(*args, **kwargs):
|
||||||
mock_open(*args, **kwargs)
|
mock_open(*args, **kwargs)
|
||||||
yield mock_file
|
yield mock_file
|
||||||
|
|
||||||
with patch('__builtin__.open', stub_open):
|
with patch('builtins.open', stub_open):
|
||||||
yield mock_open, mock_file
|
yield mock_open, mock_file
|
||||||
|
Loading…
x
Reference in New Issue
Block a user