~lazypower/charms/trusty/keystone/fix_proof

« back to all changes in this revision

Viewing changes to unit_tests/test_utils.py

  • Committer: Ante Karamatic
  • Date: 2014-02-25 11:34:13 UTC
  • Revision ID: ivoks@ubuntu.com-20140225113413-tlm02x1ibc6xb10d
Rewrite charm to get it more in line with other OpenStack charms.

Added support for contexts and templating. Makes use of charm-helpers
instead of relaying on its own tools (probably could use some additional work).

HA is currently non-functional. ETA for fixing: less than 2 days.

Show diffs side-by-side

added added

removed removed

Lines of Context:
 
1
import logging
 
2
import unittest
 
3
import os
 
4
import yaml
 
5
 
 
6
from contextlib import contextmanager
 
7
from mock import patch, MagicMock
 
8
 
 
9
 
 
10
def load_config():
 
11
    '''
 
12
    Walk backwords from __file__ looking for config.yaml, load and return the
 
13
    'options' section'
 
14
    '''
 
15
    config = None
 
16
    f = __file__
 
17
    while config is None:
 
18
        d = os.path.dirname(f)
 
19
        if os.path.isfile(os.path.join(d, 'config.yaml')):
 
20
            config = os.path.join(d, 'config.yaml')
 
21
            break
 
22
        f = d
 
23
 
 
24
    if not config:
 
25
        logging.error('Could not find config.yaml in any parent directory '
 
26
                      'of %s. ' % file)
 
27
        raise Exception
 
28
 
 
29
    return yaml.safe_load(open(config).read())['options']
 
30
 
 
31
 
 
32
def get_default_config():
 
33
    '''
 
34
    Load default charm config from config.yaml return as a dict.
 
35
    If no default is set in config.yaml, its value is None.
 
36
    '''
 
37
    default_config = {}
 
38
    config = load_config()
 
39
    for k, v in config.iteritems():
 
40
        if 'default' in v:
 
41
            default_config[k] = v['default']
 
42
        else:
 
43
            default_config[k] = None
 
44
    return default_config
 
45
 
 
46
 
 
47
class CharmTestCase(unittest.TestCase):
 
48
 
 
49
    def setUp(self, obj, patches):
 
50
        super(CharmTestCase, self).setUp()
 
51
        self.patches = patches
 
52
        self.obj = obj
 
53
        self.test_config = TestConfig()
 
54
        self.test_relation = TestRelation()
 
55
        self.patch_all()
 
56
 
 
57
    def patch(self, method):
 
58
        _m = patch.object(self.obj, method)
 
59
        mock = _m.start()
 
60
        self.addCleanup(_m.stop)
 
61
        return mock
 
62
 
 
63
    def patch_all(self):
 
64
        for method in self.patches:
 
65
            setattr(self, method, self.patch(method))
 
66
 
 
67
 
 
68
class TestConfig(object):
 
69
 
 
70
    def __init__(self):
 
71
        self.config = get_default_config()
 
72
 
 
73
    def get(self, attr=None):
 
74
        if not attr:
 
75
            return self.get_all()
 
76
        try:
 
77
            return self.config[attr]
 
78
        except KeyError:
 
79
            return None
 
80
 
 
81
    def get_all(self):
 
82
        return self.config
 
83
 
 
84
    def set(self, attr, value):
 
85
            if attr not in self.config:
 
86
                raise KeyError
 
87
            self.config[attr] = value
 
88
 
 
89
 
 
90
class TestRelation(object):
 
91
 
 
92
    def __init__(self, relation_data={}):
 
93
        self.relation_data = relation_data
 
94
 
 
95
    def set(self, relation_data):
 
96
        self.relation_data = relation_data
 
97
 
 
98
    def get(self, attr=None, unit=None, rid=None):
 
99
        if attr is None:
 
100
            return self.relation_data
 
101
        elif attr in self.relation_data:
 
102
            return self.relation_data[attr]
 
103
        return None
 
104
 
 
105
 
 
106
@contextmanager
 
107
def patch_open():
 
108
    '''Patch open() to allow mocking both open() itself and the file that is
 
109
    yielded.
 
110
 
 
111
    Yields the mock for "open" and "file", respectively.'''
 
112
    mock_open = MagicMock(spec=open)
 
113
    mock_file = MagicMock(spec=file)
 
114
 
 
115
    @contextmanager
 
116
    def stub_open(*args, **kwargs):
 
117
        mock_open(*args, **kwargs)
 
118
        yield mock_file
 
119
 
 
120
    with patch('__builtin__.open', stub_open):
 
121
        yield mock_open, mock_file