"version" section should be required in template
"HeatTemplateFormatVersion" as default while a template missing version section now in heat. But then the server can't parse the template in right way, not translate hot format to cfn. Some errors raised such as: Error : At least one Resources member must be defined. but "resources" section has one resource. Error: The Parameter (image_id) was not defined in template. but "image_id" was defined in "parameter" section. So if we cannot determine the template version, we should raise an exception. This patch will check whether version section is in template, if not we should raise exception. Change-Id: Idc2ba2b9ae099d4509dfd81914aa9bb8bd3bfefb Closes-Bug: #1267735
This commit is contained in:
parent
f4337bc58c
commit
ae5647f8d5
@ -28,7 +28,7 @@ from ..plugin import docker_container # noqa
|
|||||||
|
|
||||||
template = '''
|
template = '''
|
||||||
{
|
{
|
||||||
"AWSTemplateFormatVersion" : "2010-09-09",
|
"AWSTemplateFormatVersion": "2010-09-09",
|
||||||
"Description": "Test template",
|
"Description": "Test template",
|
||||||
"Parameters": {},
|
"Parameters": {},
|
||||||
"Resources": {
|
"Resources": {
|
||||||
|
@ -169,6 +169,7 @@ class FakeAutoScale(object):
|
|||||||
class ScalingGroupTest(HeatTestCase):
|
class ScalingGroupTest(HeatTestCase):
|
||||||
|
|
||||||
group_template = template_format.parse('''
|
group_template = template_format.parse('''
|
||||||
|
HeatTemplateFormatVersion: "2012-12-12"
|
||||||
Description: "Rackspace Auto Scale"
|
Description: "Rackspace Auto Scale"
|
||||||
Parameters: {}
|
Parameters: {}
|
||||||
Resources:
|
Resources:
|
||||||
@ -330,6 +331,7 @@ class ScalingGroupTest(HeatTestCase):
|
|||||||
|
|
||||||
class PolicyTest(HeatTestCase):
|
class PolicyTest(HeatTestCase):
|
||||||
policy_template = template_format.parse('''
|
policy_template = template_format.parse('''
|
||||||
|
HeatTemplateFormatVersion: "2012-12-12"
|
||||||
Description: "Rackspace Auto Scale"
|
Description: "Rackspace Auto Scale"
|
||||||
Parameters: {}
|
Parameters: {}
|
||||||
Resources:
|
Resources:
|
||||||
@ -472,6 +474,7 @@ class PolicyTest(HeatTestCase):
|
|||||||
|
|
||||||
class WebHookTest(HeatTestCase):
|
class WebHookTest(HeatTestCase):
|
||||||
webhook_template = template_format.parse('''
|
webhook_template = template_format.parse('''
|
||||||
|
HeatTemplateFormatVersion: "2012-12-12"
|
||||||
Description: "Rackspace Auto Scale"
|
Description: "Rackspace Auto Scale"
|
||||||
Parameters: {}
|
Parameters: {}
|
||||||
Resources:
|
Resources:
|
||||||
|
@ -69,28 +69,14 @@ def parse(tmpl_str):
|
|||||||
else:
|
else:
|
||||||
if tpl is None:
|
if tpl is None:
|
||||||
tpl = {}
|
tpl = {}
|
||||||
if u'heat_template_version' not in tpl:
|
# Looking for supported version keys in the loaded template
|
||||||
default_for_missing(tpl, u'HeatTemplateFormatVersion',
|
if not ('HeatTemplateFormatVersion' in tpl
|
||||||
HEAT_VERSIONS)
|
or 'heat_template_version' in tpl
|
||||||
|
or 'AWSTemplateFormatVersion' in tpl):
|
||||||
|
raise ValueError(_("Template format version not found."))
|
||||||
return tpl
|
return tpl
|
||||||
|
|
||||||
|
|
||||||
def default_for_missing(tpl, version_param, versions):
|
|
||||||
'''
|
|
||||||
Checks a parsed template for missing version and sections.
|
|
||||||
|
|
||||||
This is currently only applied to YAML templates.
|
|
||||||
'''
|
|
||||||
# if version is missing, implicitly use the lastest one
|
|
||||||
if version_param not in tpl:
|
|
||||||
tpl[version_param] = versions[-1]
|
|
||||||
|
|
||||||
# create empty placeholders for any of the main dict sections
|
|
||||||
for param in (u'Parameters', u'Mappings', u'Resources', u'Outputs'):
|
|
||||||
if param not in tpl:
|
|
||||||
tpl[param] = {}
|
|
||||||
|
|
||||||
|
|
||||||
def convert_json_to_yaml(json_str):
|
def convert_json_to_yaml(json_str):
|
||||||
'''Convert a string containing the AWS JSON template format
|
'''Convert a string containing the AWS JSON template format
|
||||||
to an equivalent string containing the Heat YAML format.
|
to an equivalent string containing the Heat YAML format.
|
||||||
|
@ -3,10 +3,6 @@
|
|||||||
|
|
||||||
"Description" : "Template to test Neutron resources",
|
"Description" : "Template to test Neutron resources",
|
||||||
|
|
||||||
"Parameters" : {
|
|
||||||
|
|
||||||
},
|
|
||||||
|
|
||||||
"Resources" : {
|
"Resources" : {
|
||||||
"network": {
|
"network": {
|
||||||
"Type": "OS::Neutron::Net",
|
"Type": "OS::Neutron::Net",
|
||||||
|
@ -30,6 +30,7 @@ from heat.tests.common import HeatTestCase
|
|||||||
from heat.tests import utils
|
from heat.tests import utils
|
||||||
|
|
||||||
policy_path = os.path.dirname(os.path.realpath(__file__)) + "/policy/"
|
policy_path = os.path.dirname(os.path.realpath(__file__)) + "/policy/"
|
||||||
|
template = {u'AWSTemplateFormatVersion': u'2010-09-09', u'Foo': u'bar'}
|
||||||
|
|
||||||
|
|
||||||
class CfnStackControllerTest(HeatTestCase):
|
class CfnStackControllerTest(HeatTestCase):
|
||||||
@ -464,7 +465,6 @@ class CfnStackControllerTest(HeatTestCase):
|
|||||||
def test_create(self):
|
def test_create(self):
|
||||||
# Format a dummy request
|
# Format a dummy request
|
||||||
stack_name = "wordpress"
|
stack_name = "wordpress"
|
||||||
template = {u'Foo': u'bar'}
|
|
||||||
json_template = json.dumps(template)
|
json_template = json.dumps(template)
|
||||||
params = {'Action': 'CreateStack', 'StackName': stack_name,
|
params = {'Action': 'CreateStack', 'StackName': stack_name,
|
||||||
'TemplateBody': '%s' % json_template,
|
'TemplateBody': '%s' % json_template,
|
||||||
@ -511,7 +511,6 @@ class CfnStackControllerTest(HeatTestCase):
|
|||||||
def test_create_rollback(self):
|
def test_create_rollback(self):
|
||||||
# Format a dummy request
|
# Format a dummy request
|
||||||
stack_name = "wordpress"
|
stack_name = "wordpress"
|
||||||
template = {u'Foo': u'bar'}
|
|
||||||
json_template = json.dumps(template)
|
json_template = json.dumps(template)
|
||||||
params = {'Action': 'CreateStack', 'StackName': stack_name,
|
params = {'Action': 'CreateStack', 'StackName': stack_name,
|
||||||
'TemplateBody': '%s' % json_template,
|
'TemplateBody': '%s' % json_template,
|
||||||
@ -558,7 +557,6 @@ class CfnStackControllerTest(HeatTestCase):
|
|||||||
def test_create_onfailure_true(self):
|
def test_create_onfailure_true(self):
|
||||||
# Format a dummy request
|
# Format a dummy request
|
||||||
stack_name = "wordpress"
|
stack_name = "wordpress"
|
||||||
template = {u'Foo': u'bar'}
|
|
||||||
json_template = json.dumps(template)
|
json_template = json.dumps(template)
|
||||||
params = {'Action': 'CreateStack', 'StackName': stack_name,
|
params = {'Action': 'CreateStack', 'StackName': stack_name,
|
||||||
'TemplateBody': '%s' % json_template,
|
'TemplateBody': '%s' % json_template,
|
||||||
@ -605,7 +603,6 @@ class CfnStackControllerTest(HeatTestCase):
|
|||||||
def test_create_onfailure_false_delete(self):
|
def test_create_onfailure_false_delete(self):
|
||||||
# Format a dummy request
|
# Format a dummy request
|
||||||
stack_name = "wordpress"
|
stack_name = "wordpress"
|
||||||
template = {u'Foo': u'bar'}
|
|
||||||
json_template = json.dumps(template)
|
json_template = json.dumps(template)
|
||||||
params = {'Action': 'CreateStack', 'StackName': stack_name,
|
params = {'Action': 'CreateStack', 'StackName': stack_name,
|
||||||
'TemplateBody': '%s' % json_template,
|
'TemplateBody': '%s' % json_template,
|
||||||
@ -652,7 +649,6 @@ class CfnStackControllerTest(HeatTestCase):
|
|||||||
def test_create_onfailure_false_rollback(self):
|
def test_create_onfailure_false_rollback(self):
|
||||||
# Format a dummy request
|
# Format a dummy request
|
||||||
stack_name = "wordpress"
|
stack_name = "wordpress"
|
||||||
template = {u'Foo': u'bar'}
|
|
||||||
json_template = json.dumps(template)
|
json_template = json.dumps(template)
|
||||||
params = {'Action': 'CreateStack', 'StackName': stack_name,
|
params = {'Action': 'CreateStack', 'StackName': stack_name,
|
||||||
'TemplateBody': '%s' % json_template,
|
'TemplateBody': '%s' % json_template,
|
||||||
@ -699,7 +695,6 @@ class CfnStackControllerTest(HeatTestCase):
|
|||||||
def test_create_onfailure_err(self):
|
def test_create_onfailure_err(self):
|
||||||
# Format a dummy request
|
# Format a dummy request
|
||||||
stack_name = "wordpress"
|
stack_name = "wordpress"
|
||||||
template = {u'Foo': u'bar'}
|
|
||||||
json_template = json.dumps(template)
|
json_template = json.dumps(template)
|
||||||
params = {'Action': 'CreateStack', 'StackName': stack_name,
|
params = {'Action': 'CreateStack', 'StackName': stack_name,
|
||||||
'TemplateBody': '%s' % json_template,
|
'TemplateBody': '%s' % json_template,
|
||||||
@ -739,7 +734,6 @@ class CfnStackControllerTest(HeatTestCase):
|
|||||||
def test_create_err_rpcerr(self):
|
def test_create_err_rpcerr(self):
|
||||||
# Format a dummy request
|
# Format a dummy request
|
||||||
stack_name = "wordpress"
|
stack_name = "wordpress"
|
||||||
template = {u'Foo': u'bar'}
|
|
||||||
json_template = json.dumps(template)
|
json_template = json.dumps(template)
|
||||||
params = {'Action': 'CreateStack', 'StackName': stack_name,
|
params = {'Action': 'CreateStack', 'StackName': stack_name,
|
||||||
'TemplateBody': '%s' % json_template,
|
'TemplateBody': '%s' % json_template,
|
||||||
@ -809,7 +803,6 @@ class CfnStackControllerTest(HeatTestCase):
|
|||||||
def test_create_err_exists(self):
|
def test_create_err_exists(self):
|
||||||
# Format a dummy request
|
# Format a dummy request
|
||||||
stack_name = "wordpress"
|
stack_name = "wordpress"
|
||||||
template = {u'Foo': u'bar'}
|
|
||||||
json_template = json.dumps(template)
|
json_template = json.dumps(template)
|
||||||
params = {'Action': 'CreateStack', 'StackName': stack_name,
|
params = {'Action': 'CreateStack', 'StackName': stack_name,
|
||||||
'TemplateBody': '%s' % json_template,
|
'TemplateBody': '%s' % json_template,
|
||||||
@ -845,7 +838,6 @@ class CfnStackControllerTest(HeatTestCase):
|
|||||||
def test_create_err_engine(self):
|
def test_create_err_engine(self):
|
||||||
# Format a dummy request
|
# Format a dummy request
|
||||||
stack_name = "wordpress"
|
stack_name = "wordpress"
|
||||||
template = {u'Foo': u'bar'}
|
|
||||||
json_template = json.dumps(template)
|
json_template = json.dumps(template)
|
||||||
params = {'Action': 'CreateStack', 'StackName': stack_name,
|
params = {'Action': 'CreateStack', 'StackName': stack_name,
|
||||||
'TemplateBody': '%s' % json_template,
|
'TemplateBody': '%s' % json_template,
|
||||||
@ -881,7 +873,6 @@ class CfnStackControllerTest(HeatTestCase):
|
|||||||
def test_update(self):
|
def test_update(self):
|
||||||
# Format a dummy request
|
# Format a dummy request
|
||||||
stack_name = "wordpress"
|
stack_name = "wordpress"
|
||||||
template = {u'Foo': u'bar'}
|
|
||||||
json_template = json.dumps(template)
|
json_template = json.dumps(template)
|
||||||
params = {'Action': 'UpdateStack', 'StackName': stack_name,
|
params = {'Action': 'UpdateStack', 'StackName': stack_name,
|
||||||
'TemplateBody': '%s' % json_template,
|
'TemplateBody': '%s' % json_template,
|
||||||
@ -929,7 +920,6 @@ class CfnStackControllerTest(HeatTestCase):
|
|||||||
|
|
||||||
def test_update_bad_name(self):
|
def test_update_bad_name(self):
|
||||||
stack_name = "wibble"
|
stack_name = "wibble"
|
||||||
template = {u'Foo': u'bar'}
|
|
||||||
json_template = json.dumps(template)
|
json_template = json.dumps(template)
|
||||||
params = {'Action': 'UpdateStack', 'StackName': stack_name,
|
params = {'Action': 'UpdateStack', 'StackName': stack_name,
|
||||||
'TemplateBody': '%s' % json_template,
|
'TemplateBody': '%s' % json_template,
|
||||||
@ -961,7 +951,6 @@ class CfnStackControllerTest(HeatTestCase):
|
|||||||
# Format a dummy request
|
# Format a dummy request
|
||||||
stack_name = "wordpress"
|
stack_name = "wordpress"
|
||||||
identity = dict(identifier.HeatIdentifier('t', stack_name, '6'))
|
identity = dict(identifier.HeatIdentifier('t', stack_name, '6'))
|
||||||
template = {u'Foo': u'bar'}
|
|
||||||
params = {'Action': 'GetTemplate', 'StackName': stack_name}
|
params = {'Action': 'GetTemplate', 'StackName': stack_name}
|
||||||
dummy_req = self._dummy_GET_request(params)
|
dummy_req = self._dummy_GET_request(params)
|
||||||
self._stub_enforce(dummy_req, 'GetTemplate')
|
self._stub_enforce(dummy_req, 'GetTemplate')
|
||||||
@ -1092,12 +1081,10 @@ class CfnStackControllerTest(HeatTestCase):
|
|||||||
def test_bad_resources_in_template(self):
|
def test_bad_resources_in_template(self):
|
||||||
# Format a dummy request
|
# Format a dummy request
|
||||||
json_template = {
|
json_template = {
|
||||||
'template': {
|
'AWSTemplateFormatVersion': '2010-09-09',
|
||||||
'AWSTemplateFormatVersion': '2010-09-09',
|
'Resources': {
|
||||||
'Resources': {
|
'Type': 'AWS: : EC2: : Instance',
|
||||||
'Type': 'AWS: : EC2: : Instance',
|
},
|
||||||
},
|
|
||||||
}
|
|
||||||
}
|
}
|
||||||
params = {'Action': 'ValidateTemplate',
|
params = {'Action': 'ValidateTemplate',
|
||||||
'TemplateBody': '%s' % json.dumps(json_template)}
|
'TemplateBody': '%s' % json.dumps(json_template)}
|
||||||
|
@ -64,8 +64,12 @@ def to_remote_error(error):
|
|||||||
class InstantiationDataTest(HeatTestCase):
|
class InstantiationDataTest(HeatTestCase):
|
||||||
|
|
||||||
def test_format_parse(self):
|
def test_format_parse(self):
|
||||||
data = {"key1": ["val1[0]", "val1[1]"], "key2": "val2"}
|
data = {"AWSTemplateFormatVersion": "2010-09-09",
|
||||||
json_repr = '{ "key1": [ "val1[0]", "val1[1]" ], "key2": "val2" }'
|
"key1": ["val1[0]", "val1[1]"],
|
||||||
|
"key2": "val2"}
|
||||||
|
json_repr = '{"AWSTemplateFormatVersion" : "2010-09-09",' \
|
||||||
|
'"key1": [ "val1[0]", "val1[1]" ], ' \
|
||||||
|
'"key2": "val2" }'
|
||||||
parsed = stacks.InstantiationData.format_parse(json_repr, 'foo')
|
parsed = stacks.InstantiationData.format_parse(json_repr, 'foo')
|
||||||
self.assertEqual(parsed, data)
|
self.assertEqual(parsed, data)
|
||||||
|
|
||||||
@ -77,6 +81,7 @@ class InstantiationDataTest(HeatTestCase):
|
|||||||
def test_format_parse_invalid_message(self):
|
def test_format_parse_invalid_message(self):
|
||||||
# make sure the parser error gets through to the caller.
|
# make sure the parser error gets through to the caller.
|
||||||
bad_temp = '''
|
bad_temp = '''
|
||||||
|
heat_template_version: '2012-12-12'
|
||||||
parameters:
|
parameters:
|
||||||
KeyName:
|
KeyName:
|
||||||
type: string
|
type: string
|
||||||
@ -86,7 +91,7 @@ parameters:
|
|||||||
parse_ex = self.assertRaises(webob.exc.HTTPBadRequest,
|
parse_ex = self.assertRaises(webob.exc.HTTPBadRequest,
|
||||||
stacks.InstantiationData.format_parse,
|
stacks.InstantiationData.format_parse,
|
||||||
bad_temp, 'foo')
|
bad_temp, 'foo')
|
||||||
self.assertIn('line 3, column 3', str(parse_ex))
|
self.assertIn('line 4, column 3', str(parse_ex))
|
||||||
|
|
||||||
def test_stack_name(self):
|
def test_stack_name(self):
|
||||||
body = {'stack_name': 'wibble'}
|
body = {'stack_name': 'wibble'}
|
||||||
@ -105,20 +110,18 @@ parameters:
|
|||||||
self.assertEqual(data.template(), template)
|
self.assertEqual(data.template(), template)
|
||||||
|
|
||||||
def test_template_string_json(self):
|
def test_template_string_json(self):
|
||||||
template = '{"foo": "bar", "blarg": "wibble"}'
|
template = '{"heat_template_version": "2012-12-12",' \
|
||||||
|
'"foo": "bar", "blarg": "wibble"}'
|
||||||
body = {'template': template}
|
body = {'template': template}
|
||||||
data = stacks.InstantiationData(body)
|
data = stacks.InstantiationData(body)
|
||||||
self.assertEqual(data.template(), json.loads(template))
|
self.assertEqual(data.template(), json.loads(template))
|
||||||
|
|
||||||
def test_template_string_yaml(self):
|
def test_template_string_yaml(self):
|
||||||
template = '''foo: bar
|
template = '''HeatTemplateFormatVersion: 2012-12-12
|
||||||
|
foo: bar
|
||||||
blarg: wibble
|
blarg: wibble
|
||||||
'''
|
'''
|
||||||
parsed = {u'HeatTemplateFormatVersion': u'2012-12-12',
|
parsed = {u'HeatTemplateFormatVersion': u'2012-12-12',
|
||||||
u'Mappings': {},
|
|
||||||
u'Outputs': {},
|
|
||||||
u'Parameters': {},
|
|
||||||
u'Resources': {},
|
|
||||||
u'blarg': u'wibble',
|
u'blarg': u'wibble',
|
||||||
u'foo': u'bar'}
|
u'foo': u'bar'}
|
||||||
|
|
||||||
@ -127,7 +130,9 @@ blarg: wibble
|
|||||||
self.assertEqual(data.template(), parsed)
|
self.assertEqual(data.template(), parsed)
|
||||||
|
|
||||||
def test_template_url(self):
|
def test_template_url(self):
|
||||||
template = {'foo': 'bar', 'blarg': 'wibble'}
|
template = {'heat_template_version': '2013-05-23',
|
||||||
|
'foo': 'bar',
|
||||||
|
'blarg': 'wibble'}
|
||||||
url = 'http://example.com/template'
|
url = 'http://example.com/template'
|
||||||
body = {'template_url': url}
|
body = {'template_url': url}
|
||||||
data = stacks.InstantiationData(body)
|
data = stacks.InstantiationData(body)
|
||||||
|
@ -320,7 +320,7 @@ Outputs:
|
|||||||
|
|
||||||
def test_nested_stack_three_deep(self):
|
def test_nested_stack_three_deep(self):
|
||||||
root_template = '''
|
root_template = '''
|
||||||
HeatTemplateFormat: 2012-12-12
|
HeatTemplateFormatVersion: 2012-12-12
|
||||||
Resources:
|
Resources:
|
||||||
Nested:
|
Nested:
|
||||||
Type: AWS::CloudFormation::Stack
|
Type: AWS::CloudFormation::Stack
|
||||||
@ -328,7 +328,7 @@ Resources:
|
|||||||
TemplateURL: 'https://server.test/depth1.template'
|
TemplateURL: 'https://server.test/depth1.template'
|
||||||
'''
|
'''
|
||||||
depth1_template = '''
|
depth1_template = '''
|
||||||
HeatTemplateFormat: 2012-12-12
|
HeatTemplateFormatVersion: 2012-12-12
|
||||||
Resources:
|
Resources:
|
||||||
Nested:
|
Nested:
|
||||||
Type: AWS::CloudFormation::Stack
|
Type: AWS::CloudFormation::Stack
|
||||||
@ -336,7 +336,7 @@ Resources:
|
|||||||
TemplateURL: 'https://server.test/depth2.template'
|
TemplateURL: 'https://server.test/depth2.template'
|
||||||
'''
|
'''
|
||||||
depth2_template = '''
|
depth2_template = '''
|
||||||
HeatTemplateFormat: 2012-12-12
|
HeatTemplateFormatVersion: 2012-12-12
|
||||||
Resources:
|
Resources:
|
||||||
Nested:
|
Nested:
|
||||||
Type: AWS::CloudFormation::Stack
|
Type: AWS::CloudFormation::Stack
|
||||||
@ -360,7 +360,7 @@ Resources:
|
|||||||
|
|
||||||
def test_nested_stack_four_deep(self):
|
def test_nested_stack_four_deep(self):
|
||||||
root_template = '''
|
root_template = '''
|
||||||
HeatTemplateFormat: 2012-12-12
|
HeatTemplateFormatVersion: 2012-12-12
|
||||||
Resources:
|
Resources:
|
||||||
Nested:
|
Nested:
|
||||||
Type: AWS::CloudFormation::Stack
|
Type: AWS::CloudFormation::Stack
|
||||||
@ -368,7 +368,7 @@ Resources:
|
|||||||
TemplateURL: 'https://server.test/depth1.template'
|
TemplateURL: 'https://server.test/depth1.template'
|
||||||
'''
|
'''
|
||||||
depth1_template = '''
|
depth1_template = '''
|
||||||
HeatTemplateFormat: 2012-12-12
|
HeatTemplateFormatVersion: 2012-12-12
|
||||||
Resources:
|
Resources:
|
||||||
Nested:
|
Nested:
|
||||||
Type: AWS::CloudFormation::Stack
|
Type: AWS::CloudFormation::Stack
|
||||||
@ -376,7 +376,7 @@ Resources:
|
|||||||
TemplateURL: 'https://server.test/depth2.template'
|
TemplateURL: 'https://server.test/depth2.template'
|
||||||
'''
|
'''
|
||||||
depth2_template = '''
|
depth2_template = '''
|
||||||
HeatTemplateFormat: 2012-12-12
|
HeatTemplateFormatVersion: 2012-12-12
|
||||||
Resources:
|
Resources:
|
||||||
Nested:
|
Nested:
|
||||||
Type: AWS::CloudFormation::Stack
|
Type: AWS::CloudFormation::Stack
|
||||||
@ -384,7 +384,7 @@ Resources:
|
|||||||
TemplateURL: 'https://server.test/depth3.template'
|
TemplateURL: 'https://server.test/depth3.template'
|
||||||
'''
|
'''
|
||||||
depth3_template = '''
|
depth3_template = '''
|
||||||
HeatTemplateFormat: 2012-12-12
|
HeatTemplateFormatVersion: 2012-12-12
|
||||||
Resources:
|
Resources:
|
||||||
Nested:
|
Nested:
|
||||||
Type: AWS::CloudFormation::Stack
|
Type: AWS::CloudFormation::Stack
|
||||||
@ -415,7 +415,7 @@ Resources:
|
|||||||
|
|
||||||
def test_nested_stack_four_wide(self):
|
def test_nested_stack_four_wide(self):
|
||||||
root_template = '''
|
root_template = '''
|
||||||
HeatTemplateFormat: 2012-12-12
|
HeatTemplateFormatVersion: 2012-12-12
|
||||||
Resources:
|
Resources:
|
||||||
Nested:
|
Nested:
|
||||||
Type: AWS::CloudFormation::Stack
|
Type: AWS::CloudFormation::Stack
|
||||||
@ -460,7 +460,7 @@ Resources:
|
|||||||
|
|
||||||
def test_nested_stack_infinite_recursion(self):
|
def test_nested_stack_infinite_recursion(self):
|
||||||
template = '''
|
template = '''
|
||||||
HeatTemplateFormat: 2012-12-12
|
HeatTemplateFormatVersion: 2012-12-12
|
||||||
Resources:
|
Resources:
|
||||||
Nested:
|
Nested:
|
||||||
Type: AWS::CloudFormation::Stack
|
Type: AWS::CloudFormation::Stack
|
||||||
|
@ -104,6 +104,7 @@ class ParserTest(HeatTestCase):
|
|||||||
|
|
||||||
|
|
||||||
mapping_template = template_format.parse('''{
|
mapping_template = template_format.parse('''{
|
||||||
|
"AWSTemplateFormatVersion" : "2010-09-09",
|
||||||
"Mappings" : {
|
"Mappings" : {
|
||||||
"ValidMapping" : {
|
"ValidMapping" : {
|
||||||
"TestKey" : { "TestValue" : "wibble" }
|
"TestKey" : { "TestValue" : "wibble" }
|
||||||
@ -787,10 +788,12 @@ class StackTest(HeatTestCase):
|
|||||||
self.assertEqual(1, stack.total_resources())
|
self.assertEqual(1, stack.total_resources())
|
||||||
|
|
||||||
def _setup_nested(self, name):
|
def _setup_nested(self, name):
|
||||||
nested_tpl = ('{"Resources":{'
|
nested_tpl = ('{"HeatTemplateFormatVersion" : "2012-12-12",'
|
||||||
|
'"Resources":{'
|
||||||
'"A": {"Type": "GenericResourceType"},'
|
'"A": {"Type": "GenericResourceType"},'
|
||||||
'"B": {"Type": "GenericResourceType"}}}')
|
'"B": {"Type": "GenericResourceType"}}}')
|
||||||
tpl = {'Resources':
|
tpl = {'HeatTemplateFormatVersion': "2012-12-12",
|
||||||
|
'Resources':
|
||||||
{'A': {'Type': 'AWS::CloudFormation::Stack',
|
{'A': {'Type': 'AWS::CloudFormation::Stack',
|
||||||
'Properties':
|
'Properties':
|
||||||
{'TemplateURL': 'http://server.test/nested.json'}},
|
{'TemplateURL': 'http://server.test/nested.json'}},
|
||||||
|
@ -92,6 +92,7 @@ class ProviderTemplateTest(HeatTestCase):
|
|||||||
def test_to_parameters(self):
|
def test_to_parameters(self):
|
||||||
"""Tests property conversion to parameter values."""
|
"""Tests property conversion to parameter values."""
|
||||||
provider = {
|
provider = {
|
||||||
|
'HeatTemplateFormatVersion': '2012-12-12',
|
||||||
'Parameters': {
|
'Parameters': {
|
||||||
'Foo': {'Type': 'String'},
|
'Foo': {'Type': 'String'},
|
||||||
'AList': {'Type': 'CommaDelimitedList'},
|
'AList': {'Type': 'CommaDelimitedList'},
|
||||||
@ -163,6 +164,7 @@ class ProviderTemplateTest(HeatTestCase):
|
|||||||
|
|
||||||
def test_attributes_extra(self):
|
def test_attributes_extra(self):
|
||||||
provider = {
|
provider = {
|
||||||
|
'HeatTemplateFormatVersion': '2012-12-12',
|
||||||
'Outputs': {
|
'Outputs': {
|
||||||
'Foo': {'Value': 'bar'},
|
'Foo': {'Value': 'bar'},
|
||||||
'Blarg': {'Value': 'wibble'},
|
'Blarg': {'Value': 'wibble'},
|
||||||
@ -221,6 +223,7 @@ class ProviderTemplateTest(HeatTestCase):
|
|||||||
|
|
||||||
def test_properties_normal(self):
|
def test_properties_normal(self):
|
||||||
provider = {
|
provider = {
|
||||||
|
'HeatTemplateFormatVersion': '2012-12-12',
|
||||||
'Parameters': {
|
'Parameters': {
|
||||||
'Foo': {'Type': 'String'},
|
'Foo': {'Type': 'String'},
|
||||||
'Blarg': {'Type': 'String', 'Default': 'wibble'},
|
'Blarg': {'Type': 'String', 'Default': 'wibble'},
|
||||||
@ -417,7 +420,9 @@ class ProviderTemplateTest(HeatTestCase):
|
|||||||
parser.Template({}),
|
parser.Template({}),
|
||||||
stack_id=str(uuid.uuid4()))
|
stack_id=str(uuid.uuid4()))
|
||||||
|
|
||||||
minimal_temp = json.dumps({'Parameters': {}, 'Resources': {}})
|
minimal_temp = json.dumps({'HeatTemplateFormatVersion': '2012-12-12',
|
||||||
|
'Parameters': {},
|
||||||
|
'Resources': {}})
|
||||||
self.m.StubOutWithMock(urlfetch, "get")
|
self.m.StubOutWithMock(urlfetch, "get")
|
||||||
urlfetch.get(test_templ_name,
|
urlfetch.get(test_templ_name,
|
||||||
allowed_schemes=('http', 'https',
|
allowed_schemes=('http', 'https',
|
||||||
|
@ -35,6 +35,7 @@ ws_res_snippet = {"Type": "some_magic_type",
|
|||||||
|
|
||||||
param_template = '''
|
param_template = '''
|
||||||
{
|
{
|
||||||
|
"AWSTemplateFormatVersion" : "2010-09-09",
|
||||||
"Parameters" : {
|
"Parameters" : {
|
||||||
"KeyName" : {
|
"KeyName" : {
|
||||||
"Description" : "KeyName",
|
"Description" : "KeyName",
|
||||||
@ -54,6 +55,7 @@ param_template = '''
|
|||||||
|
|
||||||
simple_template = '''
|
simple_template = '''
|
||||||
{
|
{
|
||||||
|
"AWSTemplateFormatVersion" : "2010-09-09",
|
||||||
"Parameters" : {},
|
"Parameters" : {},
|
||||||
"Resources" : {
|
"Resources" : {
|
||||||
"WebServer": {
|
"WebServer": {
|
||||||
|
@ -60,8 +60,6 @@ class JsonToYamlTest(HeatTestCase):
|
|||||||
del(yml[u'HeatTemplateFormatVersion'])
|
del(yml[u'HeatTemplateFormatVersion'])
|
||||||
|
|
||||||
jsn = template_format.parse(json_str)
|
jsn = template_format.parse(json_str)
|
||||||
template_format.default_for_missing(jsn, 'AWSTemplateFormatVersion',
|
|
||||||
template_format.CFN_VERSIONS)
|
|
||||||
|
|
||||||
if u'AWSTemplateFormatVersion' in jsn:
|
if u'AWSTemplateFormatVersion' in jsn:
|
||||||
del(jsn[u'AWSTemplateFormatVersion'])
|
del(jsn[u'AWSTemplateFormatVersion'])
|
||||||
@ -81,18 +79,6 @@ class JsonToYamlTest(HeatTestCase):
|
|||||||
|
|
||||||
class YamlMinimalTest(HeatTestCase):
|
class YamlMinimalTest(HeatTestCase):
|
||||||
|
|
||||||
def test_minimal_yaml(self):
|
|
||||||
yaml1 = ''
|
|
||||||
yaml2 = '''HeatTemplateFormatVersion: '2012-12-12'
|
|
||||||
Parameters: {}
|
|
||||||
Mappings: {}
|
|
||||||
Resources: {}
|
|
||||||
Outputs: {}
|
|
||||||
'''
|
|
||||||
tpl1 = template_format.parse(yaml1)
|
|
||||||
tpl2 = template_format.parse(yaml2)
|
|
||||||
self.assertEqual(tpl1, tpl2)
|
|
||||||
|
|
||||||
def test_long_yaml(self):
|
def test_long_yaml(self):
|
||||||
template = {'HeatTemplateVersion': '2012-12-12'}
|
template = {'HeatTemplateVersion': '2012-12-12'}
|
||||||
config.cfg.CONF.set_override('max_template_size', 1024)
|
config.cfg.CONF.set_override('max_template_size', 1024)
|
||||||
@ -105,6 +91,16 @@ Outputs: {}
|
|||||||
msg = 'Request limit exceeded: Template exceeds maximum allowed size.'
|
msg = 'Request limit exceeded: Template exceeds maximum allowed size.'
|
||||||
self.assertEqual(msg, str(ex))
|
self.assertEqual(msg, str(ex))
|
||||||
|
|
||||||
|
def test_parse_no_version_format(self):
|
||||||
|
yaml = ''
|
||||||
|
self.assertRaises(ValueError, template_format.parse, yaml)
|
||||||
|
yaml2 = '''Parameters: {}
|
||||||
|
Mappings: {}
|
||||||
|
Resources: {}
|
||||||
|
Outputs: {}
|
||||||
|
'''
|
||||||
|
self.assertRaises(ValueError, template_format.parse, yaml2)
|
||||||
|
|
||||||
|
|
||||||
class YamlParseExceptions(HeatTestCase):
|
class YamlParseExceptions(HeatTestCase):
|
||||||
|
|
||||||
@ -143,13 +139,9 @@ class JsonYamlResolvedCompareTest(HeatTestCase):
|
|||||||
|
|
||||||
def compare_stacks(self, json_file, yaml_file, parameters):
|
def compare_stacks(self, json_file, yaml_file, parameters):
|
||||||
t1 = self.load_template(json_file)
|
t1 = self.load_template(json_file)
|
||||||
template_format.default_for_missing(t1, 'AWSTemplateFormatVersion',
|
|
||||||
template_format.CFN_VERSIONS)
|
|
||||||
del(t1[u'AWSTemplateFormatVersion'])
|
|
||||||
|
|
||||||
t2 = self.load_template(yaml_file)
|
t2 = self.load_template(yaml_file)
|
||||||
del(t2[u'HeatTemplateFormatVersion'])
|
del(t2[u'HeatTemplateFormatVersion'])
|
||||||
|
del(t1[u'AWSTemplateFormatVersion'])
|
||||||
stack1 = utils.parse_stack(t1, parameters)
|
stack1 = utils.parse_stack(t1, parameters)
|
||||||
stack2 = utils.parse_stack(t2, parameters)
|
stack2 = utils.parse_stack(t2, parameters)
|
||||||
|
|
||||||
|
Loading…
Reference in New Issue
Block a user