Using resolving properties for update

For definition reference in template we should use built-in functions.
So template after parsing with resolve_static_data will contain
references on these functions instead resolve values.
If we want get some information about previous state of stack during
update, we should use self.properties instead of self.t['Properties'].
Also default=[] was added to avoid error when we try to do set([]).

Closes-bug: #1292495
Change-Id: I0cc44a0a541913cca665caec1a7f3a2a1a6cebc9
This commit is contained in:
Sergey Kraynev 2014-03-14 09:33:12 -04:00
parent 976801ecdd
commit 61b804a861
2 changed files with 125 additions and 2 deletions

View File

@ -276,6 +276,7 @@ class Pool(neutron.NeutronResource):
MONITORS: properties.Schema(
properties.Schema.LIST,
_('List of health monitors associated with the pool.'),
default=[],
update_allowed=True
),
}
@ -319,7 +320,7 @@ class Pool(neutron.NeutronResource):
self.properties,
self.physical_resource_name())
vip_properties = properties.pop(self.VIP)
monitors = properties.pop(self.MONITORS, [])
monitors = properties.pop(self.MONITORS)
client = self.neutron()
pool = client.create_pool({'pool': properties})['pool']
self.resource_id_set(pool['id'])
@ -383,7 +384,7 @@ class Pool(neutron.NeutronResource):
client = self.neutron()
monitors = set(prop_diff.pop(self.MONITORS, []))
if monitors:
old_monitors = set(self.t['Properties'][self.MONITORS])
old_monitors = set(self.properties[self.MONITORS])
for monitor in old_monitors - monitors:
client.disassociate_health_monitor(self.resource_id,
monitor)

View File

@ -152,6 +152,50 @@ pool_with_session_persistence_template = '''
'''
pool_with_health_monitors_template = '''
{
"AWSTemplateFormatVersion" : "2010-09-09",
"Description" : "Template to test load balancer resources",
"Parameters" : {},
"Resources" : {
"monitor1": {
"Type": "OS::Neutron::HealthMonitor",
"Properties": {
"type": "HTTP",
"delay": 3,
"max_retries": 5,
"timeout": 10
}
},
"monitor2": {
"Type": "OS::Neutron::HealthMonitor",
"Properties": {
"type": "HTTP",
"delay": 3,
"max_retries": 5,
"timeout": 10
}
},
"pool": {
"Type": "OS::Neutron::Pool",
"Properties": {
"protocol": "HTTP",
"subnet_id": "sub123",
"lb_method": "ROUND_ROBIN",
"vip": {
"protocol_port": 80
},
"monitors": [
{"Ref": "monitor1"},
{"Ref": "monitor2"}
]
}
}
}
}
'''
@skipIf(neutronclient is None, 'neutronclient unavailable')
class HealthMonitorTest(HeatTestCase):
@ -921,3 +965,81 @@ class LoadBalancerTest(HeatTestCase):
scheduler.TaskRunner(rsrc.delete)()
self.assertEqual((rsrc.DELETE, rsrc.COMPLETE), rsrc.state)
self.m.VerifyAll()
@skipIf(neutronclient is None, 'neutronclient unavailable')
class PoolUpdateHealthMonitorsTest(HeatTestCase):
def setUp(self):
super(PoolUpdateHealthMonitorsTest, self).setUp()
self.m.StubOutWithMock(neutronclient.Client, 'create_pool')
self.m.StubOutWithMock(neutronclient.Client, 'delete_pool')
self.m.StubOutWithMock(neutronclient.Client, 'show_pool')
self.m.StubOutWithMock(neutronclient.Client, 'update_pool')
self.m.StubOutWithMock(neutronclient.Client,
'associate_health_monitor')
self.m.StubOutWithMock(neutronclient.Client,
'disassociate_health_monitor')
self.m.StubOutWithMock(neutronclient.Client, 'create_health_monitor')
self.m.StubOutWithMock(neutronclient.Client, 'delete_health_monitor')
self.m.StubOutWithMock(neutronclient.Client, 'show_health_monitor')
self.m.StubOutWithMock(neutronclient.Client, 'update_health_monitor')
self.m.StubOutWithMock(neutronclient.Client, 'create_vip')
self.m.StubOutWithMock(neutronclient.Client, 'delete_vip')
self.m.StubOutWithMock(neutronclient.Client, 'show_vip')
self.m.StubOutWithMock(clients.OpenStackClients, 'keystone')
utils.setup_dummy_db()
@utils.stack_delete_after
def test_update_pool_with_references_to_health_monitors(self):
clients.OpenStackClients.keystone().MultipleTimes().AndReturn(
fakes.FakeKeystoneClient())
neutronclient.Client.create_health_monitor({
'health_monitor': {
'delay': 3, 'max_retries': 5, 'type': u'HTTP',
'timeout': 10, 'admin_state_up': True}}
).AndReturn({'health_monitor': {'id': '5555'}})
neutronclient.Client.create_health_monitor({
'health_monitor': {
'delay': 3, 'max_retries': 5, 'type': u'HTTP',
'timeout': 10, 'admin_state_up': True}}
).AndReturn({'health_monitor': {'id': '6666'}})
neutronclient.Client.create_pool({
'pool': {
'subnet_id': 'sub123', 'protocol': u'HTTP',
'name': utils.PhysName('test_stack', 'pool'),
'lb_method': 'ROUND_ROBIN', 'admin_state_up': True}}
).AndReturn({'pool': {'id': '5678'}})
neutronclient.Client.associate_health_monitor(
'5678', {'health_monitor': {'id': '5555'}}).InAnyOrder()
neutronclient.Client.associate_health_monitor(
'5678', {'health_monitor': {'id': '6666'}}).InAnyOrder()
neutronclient.Client.create_vip({
'vip': {
'protocol': u'HTTP', 'name': 'pool.vip',
'admin_state_up': True, 'subnet_id': u'sub123',
'pool_id': '5678', 'protocol_port': 80}}
).AndReturn({'vip': {'id': 'xyz'}})
neutronclient.Client.show_pool('5678').AndReturn(
{'pool': {'status': 'ACTIVE'}})
neutronclient.Client.show_vip('xyz').AndReturn(
{'vip': {'status': 'ACTIVE'}})
neutronclient.Client.disassociate_health_monitor(
'5678', mox.IsA(unicode))
self.m.ReplayAll()
snippet = template_format.parse(pool_with_health_monitors_template)
self.stack = utils.parse_stack(snippet)
self.stack.create()
self.assertEqual((self.stack.CREATE, self.stack.COMPLETE),
self.stack.state)
snippet['Resources']['pool']['Properties']['monitors'] = [
{u'Ref': u'monitor1'}]
updated_stack = utils.parse_stack(snippet)
self.stack.update(updated_stack)
self.assertEqual((self.stack.UPDATE, self.stack.COMPLETE),
self.stack.state)
self.m.VerifyAll()