1
# Copyright 2012 Canonical Ltd. This software is licensed under the
2
# GNU Affero General Public License version 3 (see the file LICENSE).
4
"""Tests for the config_master_dhcp command."""
6
from __future__ import (
15
from optparse import OptionValueError
17
from django.conf import settings
18
from django.core.management import call_command
19
from maasserver import dhcp
20
from maasserver.enum import NODEGROUPINTERFACE_MANAGEMENT
21
from maasserver.management.commands.config_master_dhcp import name_option
22
from maasserver.models import NodeGroup
23
from maasserver.testing.factory import factory
24
from maasserver.testing.testcase import TestCase
25
from testtools.matchers import MatchesStructure
28
def make_master_constants():
29
"""Return the standard, unchanging config for the master nodegroup."""
35
def make_dhcp_settings():
36
"""Return an arbitrary dict of DHCP settings."""
37
network = factory.getRandomNetwork()
39
'ip': factory.getRandomIPInNetwork(network),
40
'interface': factory.make_name('interface'),
41
'subnet_mask': str(network.netmask),
42
'broadcast_ip': str(network.broadcast),
43
'router_ip': factory.getRandomIPInNetwork(network),
44
'ip_range_low': factory.getRandomIPInNetwork(network),
45
'ip_range_high': factory.getRandomIPInNetwork(network),
49
def make_cleared_dhcp_settings():
50
"""Return dict of cleared DHCP settings."""
51
return dict.fromkeys(make_dhcp_settings())
54
class TestConfigMasterDHCP(TestCase):
57
super(TestConfigMasterDHCP, self).setUp()
58
# Make sure any attempts to write a dhcp config do nothing.
59
self.patch(dhcp, 'configure_dhcp')
60
self.patch(settings, 'DHCP_CONNECT', True)
62
def test_configures_dhcp_for_master_nodegroup(self):
63
settings = make_dhcp_settings()
64
call_command('config_master_dhcp', **settings)
65
master = NodeGroup.objects.get(name='master')
66
interface = master.get_managed_interface()
69
MatchesStructure.byEquality(**make_master_constants()))
71
interface, MatchesStructure.byEquality(
72
management=NODEGROUPINTERFACE_MANAGEMENT.DHCP, **settings))
74
def test_configures_dhcp_for_master_nodegroup_existing_master(self):
75
management = NODEGROUPINTERFACE_MANAGEMENT.DHCP_AND_DNS
76
master = factory.make_node_group(uuid='master', management=management)
77
settings = make_dhcp_settings()
78
call_command('config_master_dhcp', **settings)
79
master = NodeGroup.objects.ensure_master()
80
interface = master.get_managed_interface()
82
interface, MatchesStructure.byEquality(
83
management=interface.management, **settings))
85
def test_clears_dhcp_settings(self):
86
master = NodeGroup.objects.ensure_master()
87
for attribute, value in make_dhcp_settings().items():
88
setattr(master, attribute, value)
90
call_command('config_master_dhcp', clear=True)
93
MatchesStructure.byEquality(**make_master_constants()))
94
self.assertIsNone(master.get_managed_interface())
96
def test_does_not_accept_partial_dhcp_settings(self):
97
settings = make_dhcp_settings()
98
del settings['subnet_mask']
101
call_command, 'config_master_dhcp', **settings)
103
def test_ignores_nonsense_settings_when_clear_is_passed(self):
104
settings = make_dhcp_settings()
105
call_command('config_master_dhcp', **settings)
106
settings['subnet_mask'] = '@%$^&'
107
settings['broadcast_ip'] = ''
108
call_command('config_master_dhcp', clear=True, **settings)
109
master = NodeGroup.objects.get(name='master')
110
self.assertIsNone(master.get_managed_interface())
112
def test_clear_conflicts_with_ensure(self):
115
call_command, 'config_master_dhcp', clear=True, ensure=True)
117
def test_ensure_creates_master_nodegroup_without_dhcp_settings(self):
118
call_command('config_master_dhcp', ensure=True)
120
NodeGroup.objects.get(name='master').get_managed_interface())
122
def test_ensure_leaves_cleared_settings_cleared(self):
123
call_command('config_master_dhcp', clear=True)
124
call_command('config_master_dhcp', ensure=True)
125
master = NodeGroup.objects.get(name='master')
126
self.assertIsNone(master.get_managed_interface())
128
def test_ensure_leaves_dhcp_settings_intact(self):
129
settings = make_dhcp_settings()
130
call_command('config_master_dhcp', **settings)
131
call_command('config_master_dhcp', ensure=True)
133
NodeGroup.objects.get(name='master').get_managed_interface(),
134
MatchesStructure.byEquality(**settings))
136
def test_name_option_turns_dhcp_setting_name_into_option(self):
137
self.assertEqual('--subnet-mask', name_option('subnet_mask'))
139
def test_configures_dhcp(self):
140
NodeGroup.objects.ensure_master()
141
self.patch(dhcp, 'configure_dhcp')
142
settings = make_dhcp_settings()
143
call_command('config_master_dhcp', **settings)
144
self.assertEqual(1, dhcp.configure_dhcp.call_count)