Use resource methods for metadata get/set
The current approach of using the Metadata descriptor class has some issues including: * Unintended database queries on accessing a metadata attribute * get/modify/set patterns since the attribute isn't backed by a real dict * lack of control over whether to fetch metadata locally or from the db This change creates Resource methods metadata_get and metadata_set to use for reading and modifying resource data. This is a refactoring change only so there should be no change in behaviour. This change will help in the future with Related-Bug: #1306743 Change-Id: I7cd87a071ac410a388d787f132c9aee194030714
This commit is contained in:
parent
464d25927b
commit
96791aaa10
|
@ -118,7 +118,7 @@ def format_stack_resource(resource, detail=True):
|
|||
api.RES_UPDATED_TIME: timeutils.isotime(last_updated_time),
|
||||
api.RES_NAME: resource.name,
|
||||
api.RES_PHYSICAL_ID: resource.resource_id or '',
|
||||
api.RES_METADATA: resource.metadata,
|
||||
api.RES_METADATA: resource.metadata_get(),
|
||||
api.RES_ACTION: resource.action,
|
||||
api.RES_STATUS: resource.status,
|
||||
api.RES_STATUS_DATA: resource.status_reason,
|
||||
|
@ -134,7 +134,6 @@ def format_stack_resource(resource, detail=True):
|
|||
|
||||
if detail:
|
||||
res[api.RES_DESCRIPTION] = resource.parsed_template('Description', '')
|
||||
res[api.RES_METADATA] = resource.metadata
|
||||
|
||||
return res
|
||||
|
||||
|
|
|
@ -530,7 +530,7 @@ class ResourceFacade(function.Function):
|
|||
attr = function.resolve(self.args)
|
||||
|
||||
if attr == self.METADATA:
|
||||
return self.stack.parent_resource.metadata
|
||||
return self.stack.parent_resource.metadata_get()
|
||||
elif attr == self.UPDATE_POLICY:
|
||||
up = self.stack.parent_resource.t.get('UpdatePolicy', {})
|
||||
return function.resolve(up)
|
||||
|
|
|
@ -65,30 +65,6 @@ class UpdateReplace(Exception):
|
|||
super(Exception, self).__init__(msg)
|
||||
|
||||
|
||||
class Metadata(object):
|
||||
'''
|
||||
A descriptor for accessing the metadata of a resource while ensuring the
|
||||
most up-to-date data is always obtained from the database.
|
||||
'''
|
||||
|
||||
def __get__(self, resource, resource_class):
|
||||
'''Return the metadata for the owning resource.'''
|
||||
if resource is None:
|
||||
return None
|
||||
if resource.id is None:
|
||||
return resource.parsed_template('Metadata')
|
||||
rs = db_api.resource_get(resource.stack.context, resource.id)
|
||||
rs.refresh(attrs=['rsrc_metadata'])
|
||||
return rs.rsrc_metadata
|
||||
|
||||
def __set__(self, resource, metadata):
|
||||
'''Update the metadata for the owning resource.'''
|
||||
if resource.id is None:
|
||||
raise exception.ResourceNotAvailable(resource_name=resource.name)
|
||||
rs = db_api.resource_get(resource.stack.context, resource.id)
|
||||
rs.update_and_save({'rsrc_metadata': metadata})
|
||||
|
||||
|
||||
class Resource(object):
|
||||
ACTIONS = (INIT, CREATE, DELETE, UPDATE, ROLLBACK, SUSPEND, RESUME, ADOPT
|
||||
) = ('INIT', 'CREATE', 'DELETE', 'UPDATE', 'ROLLBACK',
|
||||
|
@ -100,8 +76,6 @@ class Resource(object):
|
|||
# If True, this resource must be created before it can be referenced.
|
||||
strict_dependency = True
|
||||
|
||||
_metadata = Metadata()
|
||||
|
||||
# Resource implementation set this to the subset of template keys
|
||||
# which are supported for handle_update, used by update_template_diff
|
||||
update_allowed_keys = ()
|
||||
|
@ -207,13 +181,18 @@ class Resource(object):
|
|||
return result
|
||||
return not result
|
||||
|
||||
@property
|
||||
def metadata(self):
|
||||
return self._metadata
|
||||
def metadata_get(self):
|
||||
if self.id is None:
|
||||
return self.parsed_template('Metadata')
|
||||
rs = db_api.resource_get(self.stack.context, self.id)
|
||||
rs.refresh(attrs=['rsrc_metadata'])
|
||||
return rs.rsrc_metadata
|
||||
|
||||
@metadata.setter
|
||||
def metadata(self, metadata):
|
||||
self._metadata = metadata
|
||||
def metadata_set(self, metadata):
|
||||
if self.id is None:
|
||||
raise exception.ResourceNotAvailable(resource_name=self.name)
|
||||
rs = db_api.resource_get(self.stack.context, self.id)
|
||||
rs.update_and_save({'rsrc_metadata': metadata})
|
||||
|
||||
def type(self):
|
||||
return self.t['Type']
|
||||
|
@ -465,7 +444,7 @@ class Resource(object):
|
|||
'type': self.type(),
|
||||
'action': self.action,
|
||||
'status': self.status,
|
||||
'metadata': self.metadata,
|
||||
'metadata': self.metadata_get(),
|
||||
'resource_data': self.data()
|
||||
}
|
||||
|
||||
|
@ -493,7 +472,7 @@ class Resource(object):
|
|||
self.data_set(key, value)
|
||||
|
||||
# save the resource metadata
|
||||
self.metadata = metadata
|
||||
self.metadata_set(metadata)
|
||||
|
||||
def _get_resource_info(self, resource_data):
|
||||
if not resource_data:
|
||||
|
@ -743,7 +722,7 @@ class Resource(object):
|
|||
|
||||
def _store(self):
|
||||
'''Create the resource in the database.'''
|
||||
metadata = self.metadata
|
||||
metadata = self.metadata_get()
|
||||
try:
|
||||
rs = {'action': self.action,
|
||||
'status': self.status,
|
||||
|
|
|
@ -58,7 +58,7 @@ class CooldownMixin(object):
|
|||
# If not specified, it will be None, same as cooldown == 0
|
||||
cooldown = 0
|
||||
|
||||
metadata = self.metadata
|
||||
metadata = self.metadata_get()
|
||||
if metadata and cooldown != 0:
|
||||
last_adjust = metadata.keys()[0]
|
||||
if not timeutils.is_older_than(last_adjust, cooldown):
|
||||
|
@ -71,7 +71,7 @@ class CooldownMixin(object):
|
|||
# we could maintain event history here, but since we only need
|
||||
# the latest event for cooldown, just store that for now
|
||||
metadata = {timeutils.strtime(): reason}
|
||||
self.metadata = metadata
|
||||
self.metadata_set(metadata)
|
||||
|
||||
|
||||
class InstanceGroup(stack_resource.StackResource):
|
||||
|
|
|
@ -545,7 +545,7 @@ class Instance(resource.Resource):
|
|||
|
||||
def handle_update(self, json_snippet, tmpl_diff, prop_diff):
|
||||
if 'Metadata' in tmpl_diff:
|
||||
self.metadata = tmpl_diff['Metadata']
|
||||
self.metadata_set(tmpl_diff['Metadata'])
|
||||
checkers = []
|
||||
server = None
|
||||
if self.TAGS in prop_diff:
|
||||
|
@ -643,7 +643,7 @@ class Instance(resource.Resource):
|
|||
Refresh the metadata if new_metadata is None
|
||||
'''
|
||||
if new_metadata is None:
|
||||
self.metadata = self.parsed_template('Metadata')
|
||||
self.metadata_set(self.parsed_template('Metadata'))
|
||||
|
||||
def validate(self):
|
||||
'''
|
||||
|
|
|
@ -474,11 +474,11 @@ class LoadBalancer(stack_resource.StackResource):
|
|||
templ = self.get_parsed_template()
|
||||
cfg = self._haproxy_config(templ, prop_diff[self.INSTANCES])
|
||||
|
||||
md = self.nested()['LB_instance'].metadata
|
||||
md = self.nested()['LB_instance'].metadata_get()
|
||||
files = md['AWS::CloudFormation::Init']['config']['files']
|
||||
files['/etc/haproxy/haproxy.cfg']['content'] = cfg
|
||||
|
||||
self.nested()['LB_instance'].metadata = md
|
||||
self.nested()['LB_instance'].metadata_set(md)
|
||||
|
||||
def handle_delete(self):
|
||||
return self.delete_nested()
|
||||
|
|
|
@ -350,7 +350,7 @@ class Pool(neutron.NeutronResource):
|
|||
vip_arguments['pool_id'] = pool['id']
|
||||
vip = client.create_vip({'vip': vip_arguments})['vip']
|
||||
|
||||
self.metadata = {'vip': vip['id']}
|
||||
self.metadata_set({'vip': vip['id']})
|
||||
|
||||
def _show_resource(self):
|
||||
return self.neutron().show_pool(self.resource_id)['pool']
|
||||
|
@ -361,7 +361,7 @@ class Pool(neutron.NeutronResource):
|
|||
return False
|
||||
elif attributes['status'] == 'ACTIVE':
|
||||
vip_attributes = self.neutron().show_vip(
|
||||
self.metadata['vip'])['vip']
|
||||
self.metadata_get()['vip'])['vip']
|
||||
if vip_attributes['status'] == 'PENDING_CREATE':
|
||||
return False
|
||||
elif vip_attributes['status'] == 'ACTIVE':
|
||||
|
@ -395,7 +395,7 @@ class Pool(neutron.NeutronResource):
|
|||
|
||||
def _resolve_attribute(self, name):
|
||||
if name == 'vip':
|
||||
return self.neutron().show_vip(self.metadata['vip'])['vip']
|
||||
return self.neutron().show_vip(self.metadata_get()['vip'])['vip']
|
||||
return super(Pool, self)._resolve_attribute(name)
|
||||
|
||||
def _confirm_vip_delete(self):
|
||||
|
@ -403,16 +403,16 @@ class Pool(neutron.NeutronResource):
|
|||
while True:
|
||||
try:
|
||||
yield
|
||||
client.show_vip(self.metadata['vip'])
|
||||
client.show_vip(self.metadata_get()['vip'])
|
||||
except NeutronClientException as ex:
|
||||
self._handle_not_found_exception(ex)
|
||||
break
|
||||
|
||||
def handle_delete(self):
|
||||
checkers = []
|
||||
if self.metadata:
|
||||
if self.metadata_get():
|
||||
try:
|
||||
self.neutron().delete_vip(self.metadata['vip'])
|
||||
self.neutron().delete_vip(self.metadata_get()['vip'])
|
||||
except NeutronClientException as ex:
|
||||
self._handle_not_found_exception(ex)
|
||||
else:
|
||||
|
|
|
@ -236,7 +236,7 @@ echo -e '%s\tALL=(ALL)\tNOPASSWD: ALL' >> /etc/sudoers
|
|||
attachments.append((read_cloudinit_file('loguserdata.py'),
|
||||
'loguserdata.py', 'x-shellscript'))
|
||||
|
||||
metadata = resource.metadata
|
||||
metadata = resource.metadata_get()
|
||||
if metadata:
|
||||
attachments.append((json.dumps(metadata),
|
||||
'cfn-init-data', 'x-cfninitdata'))
|
||||
|
|
|
@ -427,17 +427,15 @@ class Server(stack_user.StackUser):
|
|||
else:
|
||||
self.data_set('password', password, True)
|
||||
|
||||
@property
|
||||
def metadata(self):
|
||||
def metadata_get(self):
|
||||
if self.user_data_software_config():
|
||||
return self._build_deployments_metadata()
|
||||
else:
|
||||
return self._metadata
|
||||
return super(Server, self).metadata_get()
|
||||
|
||||
@metadata.setter
|
||||
def metadata(self, metadata):
|
||||
def metadata_set(self, metadata):
|
||||
if not self.user_data_software_config():
|
||||
self._metadata = metadata
|
||||
super(Server, self).metadata_set(metadata)
|
||||
|
||||
def user_data_raw(self):
|
||||
return self.properties.get(self.USER_DATA_FORMAT) == self.RAW
|
||||
|
@ -713,7 +711,7 @@ class Server(stack_user.StackUser):
|
|||
|
||||
def handle_update(self, json_snippet, tmpl_diff, prop_diff):
|
||||
if 'Metadata' in tmpl_diff:
|
||||
self.metadata = tmpl_diff['Metadata']
|
||||
self.metadata_set(tmpl_diff['Metadata'])
|
||||
|
||||
checkers = []
|
||||
server = None
|
||||
|
@ -846,7 +844,7 @@ class Server(stack_user.StackUser):
|
|||
Refresh the metadata if new_metadata is None
|
||||
'''
|
||||
if new_metadata is None:
|
||||
self.metadata = self.parsed_template('Metadata')
|
||||
self.metadata_set(self.parsed_template('Metadata'))
|
||||
|
||||
def validate(self):
|
||||
'''
|
||||
|
|
|
@ -72,17 +72,15 @@ class WaitConditionHandle(signal_responder.SignalResponder):
|
|||
return
|
||||
|
||||
if self._metadata_format_ok(new_metadata):
|
||||
rsrc_metadata = self.metadata
|
||||
rsrc_metadata = self.metadata_get()
|
||||
if new_metadata['UniqueId'] in rsrc_metadata:
|
||||
logger.warning(_("Overwriting Metadata item for UniqueId %s!")
|
||||
% new_metadata['UniqueId'])
|
||||
safe_metadata = {}
|
||||
for k in ('Data', 'Reason', 'Status'):
|
||||
safe_metadata[k] = new_metadata[k]
|
||||
# Note we can't update self.metadata directly, as it
|
||||
# is a Metadata descriptor object which only supports get/set
|
||||
rsrc_metadata.update({new_metadata['UniqueId']: safe_metadata})
|
||||
self.metadata = rsrc_metadata
|
||||
self.metadata_set(rsrc_metadata)
|
||||
else:
|
||||
logger.error(_("Metadata failed validation for %s") % self.name)
|
||||
raise ValueError(_("Metadata format invalid"))
|
||||
|
@ -91,14 +89,14 @@ class WaitConditionHandle(signal_responder.SignalResponder):
|
|||
'''
|
||||
Return a list of the Status values for the handle signals
|
||||
'''
|
||||
return [v['Status'] for v in self.metadata.values()]
|
||||
return [v['Status'] for v in self.metadata_get().values()]
|
||||
|
||||
def get_status_reason(self, status):
|
||||
'''
|
||||
Return a list of reasons associated with a particular status
|
||||
'''
|
||||
return [v['Reason']
|
||||
for v in self.metadata.values()
|
||||
for v in self.metadata_get().values()
|
||||
if v['Status'] == status]
|
||||
|
||||
|
||||
|
@ -269,14 +267,14 @@ class WaitCondition(resource.Resource):
|
|||
return
|
||||
|
||||
handle = self.stack[self.resource_id]
|
||||
handle.metadata = {}
|
||||
handle.metadata_set({})
|
||||
|
||||
def _resolve_attribute(self, key):
|
||||
res = {}
|
||||
handle_res_name = self._get_handle_resource_name()
|
||||
handle = self.stack[handle_res_name]
|
||||
if key == 'Data':
|
||||
meta = handle.metadata
|
||||
meta = handle.metadata_get()
|
||||
# Note, can't use a dict generator on python 2.6, hence:
|
||||
res = dict([(k, meta[k]['Data']) for k in meta])
|
||||
logger.debug(_('%(name)s.GetAtt(%(key)s) == %(res)s') %
|
||||
|
|
|
@ -1024,7 +1024,7 @@ class EngineService(service.Service):
|
|||
if res.name != resource_name and res.id is not None:
|
||||
res.metadata_update()
|
||||
|
||||
return resource.metadata
|
||||
return resource.metadata_get()
|
||||
|
||||
@request_context
|
||||
def create_watch_data(self, cnxt, watch_name, stats_data):
|
||||
|
|
|
@ -25,7 +25,6 @@ from heat.common import template_format
|
|||
from heat.engine.notification import autoscaling as notification
|
||||
from heat.engine import parser
|
||||
from heat.engine import resource
|
||||
from heat.engine.resource import Metadata
|
||||
from heat.engine.resources import autoscaling as asc
|
||||
from heat.engine.resources import image
|
||||
from heat.engine.resources import instance
|
||||
|
@ -244,12 +243,12 @@ class AutoScalingTest(HeatTestCase):
|
|||
|
||||
# Then set a stub to ensure the metadata update is as
|
||||
# expected based on the timestamp and data
|
||||
self.m.StubOutWithMock(Metadata, '__set__')
|
||||
self.m.StubOutWithMock(resource.Resource, 'metadata_set')
|
||||
expected = {timeutils.strtime(now): data}
|
||||
# Note for ScalingPolicy, we expect to get a metadata
|
||||
# update for the policy and autoscaling group, so pass nmeta=2
|
||||
for x in range(nmeta):
|
||||
Metadata.__set__(mox.IgnoreArg(), expected).AndReturn(None)
|
||||
resource.Resource.metadata_set(expected).AndReturn(None)
|
||||
|
||||
def test_scaling_delete_empty(self):
|
||||
t = template_format.parse(as_template)
|
||||
|
@ -1031,7 +1030,7 @@ class AutoScalingTest(HeatTestCase):
|
|||
# Now move time on 10 seconds - Cooldown in template is 60
|
||||
# so this should not update the policy metadata, and the
|
||||
# scaling group instances should be unchanged
|
||||
# Note we have to stub Metadata.__get__ since up_policy isn't
|
||||
# Note we have to stub Resource.metadata_get since up_policy isn't
|
||||
# stored in the DB (because the stack hasn't really been created)
|
||||
previous_meta = {timeutils.strtime(now):
|
||||
'PercentChangeInCapacity : -50'}
|
||||
|
@ -1043,9 +1042,8 @@ class AutoScalingTest(HeatTestCase):
|
|||
self.m.StubOutWithMock(timeutils, 'utcnow')
|
||||
timeutils.utcnow().MultipleTimes().AndReturn(now)
|
||||
|
||||
self.m.StubOutWithMock(Metadata, '__get__')
|
||||
Metadata.__get__(mox.IgnoreArg(), rsrc, mox.IgnoreArg()
|
||||
).AndReturn(previous_meta)
|
||||
self.m.StubOutWithMock(resource.Resource, 'metadata_get')
|
||||
rsrc.metadata_get().AndReturn(previous_meta)
|
||||
|
||||
self.m.ReplayAll()
|
||||
|
||||
|
@ -1091,13 +1089,12 @@ class AutoScalingTest(HeatTestCase):
|
|||
|
||||
now = now + datetime.timedelta(seconds=61)
|
||||
|
||||
self.m.StubOutWithMock(Metadata, '__get__')
|
||||
Metadata.__get__(mox.IgnoreArg(), rsrc, mox.IgnoreArg()
|
||||
).AndReturn(previous_meta)
|
||||
self.m.StubOutWithMock(resource.Resource, 'metadata_get')
|
||||
rsrc.metadata_get().AndReturn(previous_meta)
|
||||
|
||||
#stub for the metadata accesses while creating the two instances
|
||||
Metadata.__get__(mox.IgnoreArg(), mox.IgnoreArg(), mox.IgnoreArg())
|
||||
Metadata.__get__(mox.IgnoreArg(), mox.IgnoreArg(), mox.IgnoreArg())
|
||||
resource.Resource.metadata_get()
|
||||
resource.Resource.metadata_get()
|
||||
|
||||
# raise by 200%, should work
|
||||
self._stub_lb_reload(3, unset=False)
|
||||
|
@ -1141,13 +1138,12 @@ class AutoScalingTest(HeatTestCase):
|
|||
self.m.VerifyAll()
|
||||
self.m.UnsetStubs()
|
||||
|
||||
self.m.StubOutWithMock(Metadata, '__get__')
|
||||
Metadata.__get__(mox.IgnoreArg(), rsrc, mox.IgnoreArg()
|
||||
).AndReturn(previous_meta)
|
||||
self.m.StubOutWithMock(resource.Resource, 'metadata_get')
|
||||
rsrc.metadata_get().AndReturn(previous_meta)
|
||||
|
||||
#stub for the metadata accesses while creating the two instances
|
||||
Metadata.__get__(mox.IgnoreArg(), mox.IgnoreArg(), mox.IgnoreArg())
|
||||
Metadata.__get__(mox.IgnoreArg(), mox.IgnoreArg(), mox.IgnoreArg())
|
||||
resource.Resource.metadata_get()
|
||||
resource.Resource.metadata_get()
|
||||
# raise by 200%, should work
|
||||
|
||||
self._stub_lb_reload(3, unset=False)
|
||||
|
@ -1266,7 +1262,7 @@ class AutoScalingTest(HeatTestCase):
|
|||
self.m.ReplayAll()
|
||||
|
||||
expected_meta = {'IPs': u'127.0.0.1,127.0.0.1'}
|
||||
self.assertEqual(expected_meta, stack['MyCustomLB'].metadata)
|
||||
self.assertEqual(expected_meta, stack['MyCustomLB'].metadata_get())
|
||||
|
||||
rsrc.delete()
|
||||
self.m.VerifyAll()
|
||||
|
@ -1337,7 +1333,7 @@ class AutoScalingTest(HeatTestCase):
|
|||
# Now move time on 10 seconds - Cooldown in template is 60
|
||||
# so this should not update the policy metadata, and the
|
||||
# scaling group instances should be unchanged
|
||||
# Note we have to stub Metadata.__get__ since up_policy isn't
|
||||
# Note we have to stub Resource.metadata_get since up_policy isn't
|
||||
# stored in the DB (because the stack hasn't really been created)
|
||||
previous_meta = {timeutils.strtime(now): 'ChangeInCapacity : 1'}
|
||||
|
||||
|
@ -1348,9 +1344,8 @@ class AutoScalingTest(HeatTestCase):
|
|||
self.m.StubOutWithMock(timeutils, 'utcnow')
|
||||
timeutils.utcnow().MultipleTimes().AndReturn(now)
|
||||
|
||||
self.m.StubOutWithMock(Metadata, '__get__')
|
||||
Metadata.__get__(mox.IgnoreArg(), up_policy, mox.IgnoreArg()
|
||||
).AndReturn(previous_meta)
|
||||
self.m.StubOutWithMock(resource.Resource, 'metadata_get')
|
||||
up_policy.metadata_get().AndReturn(previous_meta)
|
||||
|
||||
self.m.ReplayAll()
|
||||
up_policy.signal()
|
||||
|
@ -1394,14 +1389,12 @@ class AutoScalingTest(HeatTestCase):
|
|||
self.m.VerifyAll()
|
||||
self.m.UnsetStubs()
|
||||
|
||||
self.m.StubOutWithMock(Metadata, '__get__')
|
||||
Metadata.__get__(mox.IgnoreArg(), up_policy, mox.IgnoreArg()
|
||||
).AndReturn(previous_meta)
|
||||
Metadata.__get__(mox.IgnoreArg(), rsrc, mox.IgnoreArg()
|
||||
).AndReturn(previous_meta)
|
||||
self.m.StubOutWithMock(resource.Resource, 'metadata_get')
|
||||
up_policy.metadata_get().AndReturn(previous_meta)
|
||||
rsrc.metadata_get().AndReturn(previous_meta)
|
||||
|
||||
#stub for the metadata accesses while creating the additional instance
|
||||
Metadata.__get__(mox.IgnoreArg(), mox.IgnoreArg(), mox.IgnoreArg())
|
||||
resource.Resource.metadata_get()
|
||||
|
||||
now = now + datetime.timedelta(seconds=61)
|
||||
self._stub_lb_reload(3, unset=False)
|
||||
|
@ -1453,14 +1446,12 @@ class AutoScalingTest(HeatTestCase):
|
|||
self.m.VerifyAll()
|
||||
self.m.UnsetStubs()
|
||||
|
||||
self.m.StubOutWithMock(Metadata, '__get__')
|
||||
Metadata.__get__(mox.IgnoreArg(), up_policy, mox.IgnoreArg()
|
||||
).AndReturn(previous_meta)
|
||||
Metadata.__get__(mox.IgnoreArg(), rsrc, mox.IgnoreArg()
|
||||
).AndReturn(previous_meta)
|
||||
self.m.StubOutWithMock(resource.Resource, 'metadata_get')
|
||||
up_policy.metadata_get().AndReturn(previous_meta)
|
||||
rsrc.metadata_get().AndReturn(previous_meta)
|
||||
|
||||
#stub for the metadata accesses while creating the additional instance
|
||||
Metadata.__get__(mox.IgnoreArg(), mox.IgnoreArg(), mox.IgnoreArg())
|
||||
resource.Resource.metadata_get()
|
||||
|
||||
self._stub_lb_reload(3, unset=False)
|
||||
self._stub_meta_expected(now, 'ChangeInCapacity : 1', 2)
|
||||
|
@ -1513,14 +1504,12 @@ class AutoScalingTest(HeatTestCase):
|
|||
self.m.VerifyAll()
|
||||
self.m.UnsetStubs()
|
||||
|
||||
self.m.StubOutWithMock(Metadata, '__get__')
|
||||
Metadata.__get__(mox.IgnoreArg(), up_policy, mox.IgnoreArg()
|
||||
).AndReturn(previous_meta)
|
||||
Metadata.__get__(mox.IgnoreArg(), rsrc, mox.IgnoreArg()
|
||||
).AndReturn(previous_meta)
|
||||
self.m.StubOutWithMock(resource.Resource, 'metadata_get')
|
||||
up_policy.metadata_get().AndReturn(previous_meta)
|
||||
rsrc.metadata_get().AndReturn(previous_meta)
|
||||
|
||||
#stub for the metadata accesses while creating the additional instance
|
||||
Metadata.__get__(mox.IgnoreArg(), mox.IgnoreArg(), mox.IgnoreArg())
|
||||
resource.Resource.metadata_get()
|
||||
|
||||
self._stub_lb_reload(3, unset=False)
|
||||
self._stub_meta_expected(now, 'ChangeInCapacity : 1', 2)
|
||||
|
@ -1578,16 +1567,13 @@ class AutoScalingTest(HeatTestCase):
|
|||
self.m.VerifyAll()
|
||||
self.m.UnsetStubs()
|
||||
|
||||
self.m.StubOutWithMock(Metadata, '__get__')
|
||||
|
||||
Metadata.__get__(mox.IgnoreArg(), up_policy, mox.IgnoreArg()
|
||||
).AndReturn(previous_meta)
|
||||
Metadata.__get__(mox.IgnoreArg(), rsrc, mox.IgnoreArg()
|
||||
).AndReturn(previous_meta)
|
||||
self.m.StubOutWithMock(resource.Resource, 'metadata_get')
|
||||
up_policy.metadata_get().AndReturn(previous_meta)
|
||||
rsrc.metadata_get().AndReturn(previous_meta)
|
||||
|
||||
#stub for the metadata accesses while creating the two instances
|
||||
Metadata.__get__(mox.IgnoreArg(), mox.IgnoreArg(), mox.IgnoreArg())
|
||||
Metadata.__get__(mox.IgnoreArg(), mox.IgnoreArg(), mox.IgnoreArg())
|
||||
resource.Resource.metadata_get()
|
||||
resource.Resource.metadata_get()
|
||||
|
||||
now = now + datetime.timedelta(seconds=61)
|
||||
|
||||
|
|
|
@ -2221,7 +2221,7 @@ class StackServiceTest(HeatTestCase):
|
|||
@stack_context('service_metadata_test_stack')
|
||||
def test_metadata(self):
|
||||
test_metadata = {'foo': 'bar', 'baz': 'quux', 'blarg': 'wibble'}
|
||||
pre_update_meta = self.stack['WebServer'].metadata
|
||||
pre_update_meta = self.stack['WebServer'].metadata_get()
|
||||
|
||||
self.m.StubOutWithMock(service.EngineService, '_get_stack')
|
||||
s = db_api.stack_get(self.ctx, self.stack.id)
|
||||
|
|
|
@ -368,7 +368,7 @@ class ScalingPolicyTest(HeatTestCase):
|
|||
|
||||
past = timeutils.strtime(timeutils.utcnow() -
|
||||
datetime.timedelta(seconds=65))
|
||||
policy.metadata = {past: 'ChangeInCapacity : 1'}
|
||||
policy.metadata_set({past: 'ChangeInCapacity : 1'})
|
||||
|
||||
policy.signal()
|
||||
self.assertEqual(3, len(group.get_instance_names()))
|
||||
|
|
|
@ -71,6 +71,16 @@ resources:
|
|||
''')
|
||||
|
||||
|
||||
class DummyClass(object):
|
||||
metadata = None
|
||||
|
||||
def metadata_get(self):
|
||||
return self.metadata
|
||||
|
||||
def metadata_set(self, metadata):
|
||||
self.metadata = metadata
|
||||
|
||||
|
||||
class HOTemplateTest(HeatTestCase):
|
||||
"""Test processing of HOT templates."""
|
||||
|
||||
|
@ -545,10 +555,8 @@ class HOTemplateTest(HeatTestCase):
|
|||
deletion_policy_snippet = {'resource_facade': 'deletion_policy'}
|
||||
update_policy_snippet = {'resource_facade': 'update_policy'}
|
||||
|
||||
class DummyClass(object):
|
||||
pass
|
||||
parent_resource = DummyClass()
|
||||
parent_resource.metadata = {"foo": "bar"}
|
||||
parent_resource.metadata_set({"foo": "bar"})
|
||||
parent_resource.t = {'DeletionPolicy': 'Retain',
|
||||
'UpdatePolicy': {"blarg": "wibble"}}
|
||||
parent_resource.stack = parser.Stack(utils.dummy_context(),
|
||||
|
@ -567,10 +575,8 @@ class HOTemplateTest(HeatTestCase):
|
|||
def test_resource_facade_function(self):
|
||||
deletion_policy_snippet = {'resource_facade': 'deletion_policy'}
|
||||
|
||||
class DummyClass(object):
|
||||
pass
|
||||
parent_resource = DummyClass()
|
||||
parent_resource.metadata = {"foo": "bar"}
|
||||
parent_resource.metadata_set({"foo": "bar"})
|
||||
parent_resource.stack = parser.Stack(utils.dummy_context(),
|
||||
'toplevel_stack',
|
||||
parser.Template({}))
|
||||
|
@ -599,10 +605,8 @@ class HOTemplateTest(HeatTestCase):
|
|||
def test_resource_facade_missing_deletion_policy(self):
|
||||
snippet = {'resource_facade': 'deletion_policy'}
|
||||
|
||||
class DummyClass(object):
|
||||
pass
|
||||
parent_resource = DummyClass()
|
||||
parent_resource.metadata = {"foo": "bar"}
|
||||
parent_resource.metadata_set({"foo": "bar"})
|
||||
parent_resource.t = {}
|
||||
parent_resource.stack = parser.Stack(utils.dummy_context(),
|
||||
'toplevel_stack',
|
||||
|
@ -733,7 +737,8 @@ class StackTest(test_parser.StackTest):
|
|||
(parser.Stack.UPDATE, parser.Stack.COMPLETE))
|
||||
self.assertEqual(self.stack['AResource'].properties['Foo'], 'xyz')
|
||||
|
||||
self.assertEqual(self.stack['AResource'].metadata['Bar'], stack_id)
|
||||
self.assertEqual(
|
||||
self.stack['AResource'].metadata_get()['Bar'], stack_id)
|
||||
|
||||
def test_load_param_id(self):
|
||||
tmpl = parser.Template(hot_tpl_empty)
|
||||
|
|
|
@ -340,7 +340,7 @@ class InstancesTest(HeatTestCase):
|
|||
update_template = copy.deepcopy(instance.t)
|
||||
update_template['Metadata'] = {'test': 123}
|
||||
scheduler.TaskRunner(instance.update, update_template)()
|
||||
self.assertEqual({'test': 123}, instance.metadata)
|
||||
self.assertEqual({'test': 123}, instance.metadata_get())
|
||||
|
||||
def test_instance_update_instance_type(self):
|
||||
"""
|
||||
|
|
|
@ -21,7 +21,7 @@ from oslo.config import cfg
|
|||
from heat.common import exception
|
||||
from heat.common import template_format
|
||||
from heat.engine import clients
|
||||
from heat.engine.resource import Metadata
|
||||
from heat.engine import resource
|
||||
from heat.engine.resources import instance
|
||||
from heat.engine.resources import loadbalancer as lb
|
||||
from heat.engine.resources import wait_condition as wc
|
||||
|
@ -106,7 +106,7 @@ class LoadBalancerTest(HeatTestCase):
|
|||
self.fc = fakes.FakeClient()
|
||||
self.m.StubOutWithMock(clients.OpenStackClients, 'nova')
|
||||
self.m.StubOutWithMock(self.fc.servers, 'create')
|
||||
self.m.StubOutWithMock(Metadata, '__set__')
|
||||
self.m.StubOutWithMock(resource.Resource, 'metadata_set')
|
||||
self.fkc = test_fakes.FakeKeystoneClient(
|
||||
username='test_stack.CfnLBUser')
|
||||
|
||||
|
@ -141,8 +141,7 @@ class LoadBalancerTest(HeatTestCase):
|
|||
security_groups=None, availability_zone=None).AndReturn(
|
||||
self.fc.servers.list()[1])
|
||||
if stub_meta:
|
||||
Metadata.__set__(mox.IgnoreArg(),
|
||||
mox.IgnoreArg()).AndReturn(None)
|
||||
resource.Resource.metadata_set(mox.IgnoreArg()).AndReturn(None)
|
||||
|
||||
self.m.StubOutWithMock(wc.WaitConditionHandle, 'get_status')
|
||||
wc.WaitConditionHandle.get_status().AndReturn(['SUCCESS'])
|
||||
|
|
|
@ -179,14 +179,16 @@ class MetadataRefreshTest(HeatTestCase):
|
|||
|
||||
s1 = self.stack['S1']
|
||||
s2 = self.stack['S2']
|
||||
files = s1.metadata['AWS::CloudFormation::Init']['config']['files']
|
||||
files = s1.metadata_get()[
|
||||
'AWS::CloudFormation::Init']['config']['files']
|
||||
cont = files['/tmp/random_file']['content']
|
||||
self.assertEqual((s2.CREATE, s2.COMPLETE), s2.state)
|
||||
self.assertEqual('s2-ip=1.2.3.5', cont)
|
||||
|
||||
s1.metadata_update()
|
||||
s2.metadata_update()
|
||||
files = s1.metadata['AWS::CloudFormation::Init']['config']['files']
|
||||
files = s1.metadata_get()[
|
||||
'AWS::CloudFormation::Init']['config']['files']
|
||||
cont = files['/tmp/random_file']['content']
|
||||
self.assertEqual('s2-ip=10.0.0.5', cont)
|
||||
|
||||
|
@ -259,7 +261,7 @@ class WaitCondMetadataUpdateTest(HeatTestCase):
|
|||
|
||||
def check_empty(sleep_time):
|
||||
self.assertEqual('{}', watch.FnGetAtt('Data'))
|
||||
self.assertIsNone(inst.metadata['test'])
|
||||
self.assertIsNone(inst.metadata_get()['test'])
|
||||
|
||||
def update_metadata(id, data, reason):
|
||||
self.man.metadata_update(utils.dummy_context(),
|
||||
|
@ -283,12 +285,12 @@ class WaitCondMetadataUpdateTest(HeatTestCase):
|
|||
self.stack.state)
|
||||
|
||||
self.assertEqual('{"123": "foo"}', watch.FnGetAtt('Data'))
|
||||
self.assertEqual('{"123": "foo"}', inst.metadata['test'])
|
||||
self.assertEqual('{"123": "foo"}', inst.metadata_get()['test'])
|
||||
|
||||
update_metadata('456', 'blarg', 'wibble')
|
||||
self.assertEqual('{"123": "foo", "456": "blarg"}',
|
||||
watch.FnGetAtt('Data'))
|
||||
self.assertEqual('{"123": "foo", "456": "blarg"}',
|
||||
inst.metadata['test'])
|
||||
inst.metadata_get()['test'])
|
||||
|
||||
self.m.VerifyAll()
|
||||
|
|
|
@ -121,7 +121,7 @@ Resources:
|
|||
self.assertIsNone(rsrc.validate())
|
||||
self.assertEqual((rsrc.CREATE, rsrc.COMPLETE), rsrc.state)
|
||||
self.assertEqual(ref_id, rsrc.FnGetRefId())
|
||||
self.assertEqual(metadata, dict(rsrc.metadata))
|
||||
self.assertEqual(metadata, dict(rsrc.metadata_get()))
|
||||
|
||||
def test_security_group(self):
|
||||
|
||||
|
|
|
@ -167,7 +167,7 @@ class NovaUtilsUserdataTests(HeatTestCase):
|
|||
def test_build_userdata(self):
|
||||
"""Tests the build_userdata function."""
|
||||
resource = self.m.CreateMockAnything()
|
||||
resource.metadata = {}
|
||||
resource.metadata_get().AndReturn({})
|
||||
self.m.StubOutWithMock(nova_utils.cfg, 'CONF')
|
||||
cnf = nova_utils.cfg.CONF
|
||||
cnf.heat_metadata_server_url = 'http://server.test:123'
|
||||
|
@ -189,7 +189,7 @@ class NovaUtilsUserdataTests(HeatTestCase):
|
|||
def test_build_userdata_without_instance_user(self):
|
||||
"""Don't add a custom instance user when not requested."""
|
||||
resource = self.m.CreateMockAnything()
|
||||
resource.metadata = {}
|
||||
resource.metadata_get().AndReturn({})
|
||||
self.m.StubOutWithMock(nova_utils.cfg, 'CONF')
|
||||
cnf = nova_utils.cfg.CONF
|
||||
cnf.instance_user = 'config_instance_user'
|
||||
|
@ -205,7 +205,7 @@ class NovaUtilsUserdataTests(HeatTestCase):
|
|||
def test_build_userdata_with_instance_user(self):
|
||||
"""Add the custom instance user when requested."""
|
||||
resource = self.m.CreateMockAnything()
|
||||
resource.metadata = {}
|
||||
resource.metadata_get().AndReturn(None)
|
||||
self.m.StubOutWithMock(nova_utils.cfg, 'CONF')
|
||||
cnf = nova_utils.cfg.CONF
|
||||
cnf.instance_user = 'config_instance_user'
|
||||
|
|
|
@ -145,6 +145,16 @@ resource_template = template_format.parse('''{
|
|||
}''')
|
||||
|
||||
|
||||
class DummyClass(object):
|
||||
metadata = None
|
||||
|
||||
def metadata_get(self):
|
||||
return self.metadata
|
||||
|
||||
def metadata_set(self, metadata):
|
||||
self.metadata = metadata
|
||||
|
||||
|
||||
class TemplateTest(HeatTestCase):
|
||||
|
||||
def setUp(self):
|
||||
|
@ -529,10 +539,8 @@ Mappings:
|
|||
deletion_policy_snippet = {'Fn::ResourceFacade': 'DeletionPolicy'}
|
||||
update_policy_snippet = {'Fn::ResourceFacade': 'UpdatePolicy'}
|
||||
|
||||
class DummyClass(object):
|
||||
pass
|
||||
parent_resource = DummyClass()
|
||||
parent_resource.metadata = {"foo": "bar"}
|
||||
parent_resource.metadata_set({"foo": "bar"})
|
||||
parent_resource.t = {'DeletionPolicy': 'Retain',
|
||||
'UpdatePolicy': {"blarg": "wibble"}}
|
||||
parent_resource.stack = parser.Stack(self.ctx, 'toplevel_stack',
|
||||
|
@ -550,10 +558,8 @@ Mappings:
|
|||
def test_resource_facade_function(self):
|
||||
deletion_policy_snippet = {'Fn::ResourceFacade': 'DeletionPolicy'}
|
||||
|
||||
class DummyClass(object):
|
||||
pass
|
||||
parent_resource = DummyClass()
|
||||
parent_resource.metadata = {"foo": "bar"}
|
||||
parent_resource.metadata_set({"foo": "bar"})
|
||||
parent_resource.stack = parser.Stack(self.ctx, 'toplevel_stack',
|
||||
parser.Template({}))
|
||||
parent_snippet = {'DeletionPolicy': {'Fn::Join': ['eta',
|
||||
|
@ -580,10 +586,8 @@ Mappings:
|
|||
def test_resource_facade_missing_deletion_policy(self):
|
||||
snippet = {'Fn::ResourceFacade': 'DeletionPolicy'}
|
||||
|
||||
class DummyClass(object):
|
||||
pass
|
||||
parent_resource = DummyClass()
|
||||
parent_resource.metadata = {"foo": "bar"}
|
||||
parent_resource.metadata_set({"foo": "bar"})
|
||||
parent_resource.t = {}
|
||||
parent_resource.stack = parser.Stack(self.ctx, 'toplevel_stack',
|
||||
parser.Template({}))
|
||||
|
@ -1107,7 +1111,8 @@ class StackTest(HeatTestCase):
|
|||
self.stack.state)
|
||||
self.assertEqual('xyz', self.stack['AResource'].properties['Foo'])
|
||||
|
||||
self.assertEqual(stack_arn, self.stack['AResource'].metadata['Bar'])
|
||||
self.assertEqual(
|
||||
stack_arn, self.stack['AResource'].metadata_get()['Bar'])
|
||||
|
||||
def test_load_param_id(self):
|
||||
self.stack = parser.Stack(self.ctx, 'param_load_arn_test',
|
||||
|
|
|
@ -288,7 +288,7 @@ class ResourceTest(HeatTestCase):
|
|||
def test_metadata_default(self):
|
||||
tmpl = {'Type': 'Foo'}
|
||||
res = generic_rsrc.GenericResource('test_resource', tmpl, self.stack)
|
||||
self.assertEqual({}, res.metadata)
|
||||
self.assertEqual({}, res.metadata_get())
|
||||
|
||||
def test_equals_different_stacks(self):
|
||||
tmpl1 = {'Type': 'Foo'}
|
||||
|
@ -767,7 +767,7 @@ class ResourceAdoptTest(HeatTestCase):
|
|||
}
|
||||
adopt = scheduler.TaskRunner(res.adopt, res_data)
|
||||
adopt()
|
||||
self.assertEqual({}, res.metadata)
|
||||
self.assertEqual({}, res.metadata_get())
|
||||
self.assertEqual((res.ADOPT, res.COMPLETE), res.state)
|
||||
|
||||
def test_adopt_with_resource_data_and_metadata(self):
|
||||
|
@ -795,7 +795,7 @@ class ResourceAdoptTest(HeatTestCase):
|
|||
adopt()
|
||||
self.assertEqual("test-value",
|
||||
db_api.resource_data_get(res, "test-key"))
|
||||
self.assertEqual({"os_distro": "test-distro"}, res.metadata)
|
||||
self.assertEqual({"os_distro": "test-distro"}, res.metadata_get())
|
||||
self.assertEqual((res.ADOPT, res.COMPLETE), res.state)
|
||||
|
||||
def test_adopt_resource_missing(self):
|
||||
|
@ -1300,12 +1300,12 @@ class MetadataTest(HeatTestCase):
|
|||
self.addCleanup(self.stack.delete)
|
||||
|
||||
def test_read_initial(self):
|
||||
self.assertEqual({'Test': 'Initial metadata'}, self.res.metadata)
|
||||
self.assertEqual({'Test': 'Initial metadata'}, self.res.metadata_get())
|
||||
|
||||
def test_write(self):
|
||||
test_data = {'Test': 'Newly-written data'}
|
||||
self.res.metadata = test_data
|
||||
self.assertEqual(test_data, self.res.metadata)
|
||||
self.res.metadata_set(test_data)
|
||||
self.assertEqual(test_data, self.res.metadata_get())
|
||||
|
||||
|
||||
class ReducePhysicalResourceNameTest(HeatTestCase):
|
||||
|
|
|
@ -162,7 +162,7 @@ Resources:
|
|||
self.assertIsNone(rsrc.validate())
|
||||
self.assertEqual((rsrc.CREATE, rsrc.COMPLETE), rsrc.state)
|
||||
self.assertEqual(ref_id, rsrc.FnGetRefId())
|
||||
self.assertEqual(metadata, dict(rsrc.metadata))
|
||||
self.assertEqual(metadata, dict(rsrc.metadata_get()))
|
||||
|
||||
def test_security_group_nova(self):
|
||||
#create script
|
||||
|
|
|
@ -553,7 +553,7 @@ class ServersTest(HeatTestCase):
|
|||
}
|
||||
},
|
||||
'deployments': {'foo': 'bar'}
|
||||
}, server.metadata)
|
||||
}, server.metadata_get())
|
||||
|
||||
created_server = servers.Server('WebServer',
|
||||
t['Resources']['WebServer'], stack)
|
||||
|
@ -623,7 +623,7 @@ class ServersTest(HeatTestCase):
|
|||
}
|
||||
},
|
||||
'deployments': {'foo': 'bar'}
|
||||
}, server.metadata)
|
||||
}, server.metadata_get())
|
||||
|
||||
created_server = servers.Server('WebServer',
|
||||
t['Resources']['WebServer'], stack)
|
||||
|
@ -641,7 +641,7 @@ class ServersTest(HeatTestCase):
|
|||
t['Resources']['WebServer'], stack)
|
||||
self.m.StubOutWithMock(server, 'keystone')
|
||||
self.m.ReplayAll()
|
||||
deployments = server.metadata['deployments']
|
||||
deployments = server.metadata_get()['deployments']
|
||||
self.assertEqual([], deployments)
|
||||
self.m.VerifyAll()
|
||||
|
||||
|
@ -947,11 +947,11 @@ class ServersTest(HeatTestCase):
|
|||
update_template = copy.deepcopy(server.t)
|
||||
update_template['Metadata'] = {'test': 123}
|
||||
scheduler.TaskRunner(server.update, update_template)()
|
||||
self.assertEqual({'test': 123}, server.metadata)
|
||||
self.assertEqual({'test': 123}, server.metadata_get())
|
||||
|
||||
server.t['Metadata'] = {'test': 456}
|
||||
server.metadata_update()
|
||||
self.assertEqual({'test': 456}, server.metadata)
|
||||
self.assertEqual({'test': 456}, server.metadata_get())
|
||||
|
||||
def test_server_update_nova_metadata(self):
|
||||
return_server = self.fc.servers.list()[1]
|
||||
|
|
|
@ -293,4 +293,4 @@ class swiftTest(HeatTestCase):
|
|||
scheduler.TaskRunner(rsrc.delete)()
|
||||
self.m.VerifyAll()
|
||||
|
||||
self.assertEqual({}, rsrc.metadata)
|
||||
self.assertEqual({}, rsrc.metadata_get())
|
||||
|
|
|
@ -455,7 +455,7 @@ class WaitConditionHandleTest(HeatTestCase):
|
|||
handle_metadata = {u'123': {u'Data': u'foo',
|
||||
u'Reason': u'bar',
|
||||
u'Status': u'SUCCESS'}}
|
||||
self.assertEqual(handle_metadata, rsrc.metadata)
|
||||
self.assertEqual(handle_metadata, rsrc.metadata_get())
|
||||
self.m.VerifyAll()
|
||||
|
||||
def test_metadata_update_invalid(self):
|
||||
|
|
Loading…
Reference in New Issue