From: Zane Bitter Date: Mon, 19 Aug 2013 18:51:45 +0000 (+0200) Subject: Create a Schema from a parameter X-Git-Tag: 2014.1~185^2 X-Git-Url: https://review.fuel-infra.org/gitweb?a=commitdiff_plain;h=de4158bff299897668527807e532516f0ea76848;p=openstack-build%2Fheat-build.git Create a Schema from a parameter Add a classmethod to create a property Schema object directly from a parameter schema. Change-Id: I335ec48086ea5aeb1fb2afd9af8e93529d9b6051 --- diff --git a/heat/engine/properties.py b/heat/engine/properties.py index fe0c6e19..821960c4 100644 --- a/heat/engine/properties.py +++ b/heat/engine/properties.py @@ -174,6 +174,47 @@ class Schema(collections.Mapping): constraints=list(constraints()), implemented=schema_dict.get(IMPLEMENTED, True)) + @classmethod + def from_parameter(cls, param): + """ + Return a property Schema corresponding to a parameter. + + Convert a parameter schema from a provider template to a property + Schema for the corresponding resource facade. + """ + param_type_map = { + parameters.STRING: STRING, + parameters.NUMBER: NUMBER, + parameters.COMMA_DELIMITED_LIST: LIST, + parameters.JSON: MAP + } + + def constraints(): + def get_num(key): + val = param.get(key) + if val is not None: + val = Property.str_to_num(val) + return val + + desc = param.get(parameters.CONSTRAINT_DESCRIPTION) + + if parameters.MIN_VALUE in param or parameters.MAX_VALUE in param: + yield Range(get_num(parameters.MIN_VALUE), + get_num(parameters.MAX_VALUE)) + if (parameters.MIN_LENGTH in param or + parameters.MAX_LENGTH in param): + yield Length(get_num(parameters.MIN_LENGTH), + get_num(parameters.MAX_LENGTH)) + if parameters.ALLOWED_VALUES in param: + yield AllowedValues(param[parameters.ALLOWED_VALUES], desc) + if parameters.ALLOWED_PATTERN in param: + yield AllowedPattern(param[parameters.ALLOWED_PATTERN], desc) + + return cls(param_type_map.get(param[parameters.TYPE], MAP), + description=param.get(parameters.DESCRIPTION), + required=parameters.DEFAULT not in param, + constraints=list(constraints())) + def validate_constraints(self, value): for constraint in self.constraints: constraint.validate(value) diff --git a/heat/tests/test_properties.py b/heat/tests/test_properties.py index 67d4df45..003338e1 100644 --- a/heat/tests/test_properties.py +++ b/heat/tests/test_properties.py @@ -15,6 +15,7 @@ import testtools +from heat.engine import parameters from heat.engine import properties from heat.engine import resource from heat.common import exception @@ -403,6 +404,257 @@ class SchemaTest(testtools.TestCase): properties.Schema.from_legacy, {'Type': 'String', 'Foo': 'Bar'}) + def test_from_string_param(self): + description = "WebServer EC2 instance type" + allowed_values = ["t1.micro", "m1.small", "m1.large", "m1.xlarge", + "m2.xlarge", "m2.2xlarge", "m2.4xlarge", + "c1.medium", "c1.xlarge", "cc1.4xlarge"] + constraint_desc = "Must be a valid EC2 instance type." + param = parameters.ParamSchema({ + "Type": "String", + "Description": description, + "Default": "m1.large", + "AllowedValues": allowed_values, + "ConstraintDescription": constraint_desc, + }) + + schema = properties.Schema.from_parameter(param) + + self.assertEqual(properties.STRING, schema.type) + self.assertEqual(description, schema.description) + self.assertEqual(None, schema.default) + self.assertFalse(schema.required) + self.assertEqual(1, len(schema.constraints)) + + allowed_constraint = schema.constraints[0] + + self.assertEqual(tuple(allowed_values), allowed_constraint.allowed) + self.assertEqual(constraint_desc, allowed_constraint.description) + + def test_from_string_allowed_pattern(self): + description = "WebServer EC2 instance type" + allowed_pattern = "[A-Za-z0-9]*" + constraint_desc = "Must contain only alphanumeric characters." + param = parameters.ParamSchema({ + "Type": "String", + "Description": description, + "Default": "m1.large", + "AllowedPattern": allowed_pattern, + "ConstraintDescription": constraint_desc, + }) + + schema = properties.Schema.from_parameter(param) + + self.assertEqual(properties.STRING, schema.type) + self.assertEqual(description, schema.description) + self.assertEqual(None, schema.default) + self.assertFalse(schema.required) + self.assertEqual(1, len(schema.constraints)) + + allowed_constraint = schema.constraints[0] + + self.assertEqual(allowed_pattern, allowed_constraint.pattern) + self.assertEqual(constraint_desc, allowed_constraint.description) + + def test_from_string_multi_constraints(self): + description = "WebServer EC2 instance type" + allowed_pattern = "[A-Za-z0-9]*" + constraint_desc = "Must contain only alphanumeric characters." + param = parameters.ParamSchema({ + "Type": "String", + "Description": description, + "Default": "m1.large", + "MinLength": "7", + "AllowedPattern": allowed_pattern, + "ConstraintDescription": constraint_desc, + }) + + schema = properties.Schema.from_parameter(param) + + self.assertEqual(properties.STRING, schema.type) + self.assertEqual(description, schema.description) + self.assertEqual(None, schema.default) + self.assertFalse(schema.required) + self.assertEqual(2, len(schema.constraints)) + + len_constraint = schema.constraints[0] + allowed_constraint = schema.constraints[1] + + self.assertEqual(7, len_constraint.min) + self.assertEqual(None, len_constraint.max) + self.assertEqual(allowed_pattern, allowed_constraint.pattern) + self.assertEqual(constraint_desc, allowed_constraint.description) + + def test_from_param_string_min_len(self): + param = parameters.ParamSchema({ + "Description": "WebServer EC2 instance type", + "Type": "String", + "Default": "m1.large", + "MinLength": "7", + }) + schema = properties.Schema.from_parameter(param) + + self.assertFalse(schema.required) + self.assertEqual(1, len(schema.constraints)) + + len_constraint = schema.constraints[0] + + self.assertEqual(7, len_constraint.min) + self.assertEqual(None, len_constraint.max) + + def test_from_param_string_max_len(self): + param = parameters.ParamSchema({ + "Description": "WebServer EC2 instance type", + "Type": "String", + "Default": "m1.large", + "MaxLength": "11", + }) + schema = properties.Schema.from_parameter(param) + + self.assertFalse(schema.required) + self.assertEqual(1, len(schema.constraints)) + + len_constraint = schema.constraints[0] + + self.assertEqual(None, len_constraint.min) + self.assertEqual(11, len_constraint.max) + + def test_from_param_string_min_max_len(self): + param = parameters.ParamSchema({ + "Description": "WebServer EC2 instance type", + "Type": "String", + "Default": "m1.large", + "MinLength": "7", + "MaxLength": "11", + }) + schema = properties.Schema.from_parameter(param) + + self.assertFalse(schema.required) + self.assertEqual(1, len(schema.constraints)) + + len_constraint = schema.constraints[0] + + self.assertEqual(7, len_constraint.min) + self.assertEqual(11, len_constraint.max) + + def test_from_param_no_default(self): + param = parameters.ParamSchema({ + "Description": "WebServer EC2 instance type", + "Type": "String", + }) + schema = properties.Schema.from_parameter(param) + + self.assertTrue(schema.required) + self.assertEqual(None, schema.default) + self.assertEqual(0, len(schema.constraints)) + + def test_from_number_param_min(self): + default = "42" + param = parameters.ParamSchema({ + "Type": "Number", + "Default": default, + "MinValue": "10", + }) + + schema = properties.Schema.from_parameter(param) + + self.assertEqual(properties.NUMBER, schema.type) + self.assertEqual(None, schema.default) + self.assertFalse(schema.required) + self.assertEqual(1, len(schema.constraints)) + + value_constraint = schema.constraints[0] + + self.assertEqual(10, value_constraint.min) + self.assertEqual(None, value_constraint.max) + + def test_from_number_param_max(self): + default = "42" + param = parameters.ParamSchema({ + "Type": "Number", + "Default": default, + "MaxValue": "100", + }) + + schema = properties.Schema.from_parameter(param) + + self.assertEqual(properties.NUMBER, schema.type) + self.assertEqual(None, schema.default) + self.assertFalse(schema.required) + self.assertEqual(1, len(schema.constraints)) + + value_constraint = schema.constraints[0] + + self.assertEqual(None, value_constraint.min) + self.assertEqual(100, value_constraint.max) + + def test_from_number_param_min_max(self): + default = "42" + param = parameters.ParamSchema({ + "Type": "Number", + "Default": default, + "MinValue": "10", + "MaxValue": "100", + }) + + schema = properties.Schema.from_parameter(param) + + self.assertEqual(properties.NUMBER, schema.type) + self.assertEqual(None, schema.default) + self.assertFalse(schema.required) + self.assertEqual(1, len(schema.constraints)) + + value_constraint = schema.constraints[0] + + self.assertEqual(10, value_constraint.min) + self.assertEqual(100, value_constraint.max) + + def test_from_number_param_allowed_vals(self): + default = "42" + constraint_desc = "The quick brown fox jumps over the lazy dog." + param = parameters.ParamSchema({ + "Type": "Number", + "Default": default, + "AllowedValues": ["10", "42", "100"], + "ConstraintDescription": constraint_desc, + }) + + schema = properties.Schema.from_parameter(param) + + self.assertEqual(properties.NUMBER, schema.type) + self.assertEqual(None, schema.default) + self.assertFalse(schema.required) + self.assertEqual(1, len(schema.constraints)) + + allowed_constraint = schema.constraints[0] + + self.assertEqual(('10', '42', '100'), allowed_constraint.allowed) + self.assertEqual(constraint_desc, allowed_constraint.description) + + def test_from_list_param(self): + param = parameters.ParamSchema({ + "Type": "CommaDelimitedList", + "Default": "foo,bar,baz" + }) + + schema = properties.Schema.from_parameter(param) + + self.assertEqual(properties.LIST, schema.type) + self.assertEqual(None, schema.default) + self.assertFalse(schema.required) + + def test_from_json_param(self): + param = parameters.ParamSchema({ + "Type": "Json", + "Default": {"foo": "bar", "blarg": "wibble"} + }) + + schema = properties.Schema.from_parameter(param) + + self.assertEqual(properties.MAP, schema.type) + self.assertEqual(None, schema.default) + self.assertFalse(schema.required) + class PropertyTest(testtools.TestCase): def test_required_default(self):