diff options
author | Jenkins <jenkins@review.openstack.org> | 2015-12-23 03:41:45 +0000 |
---|---|---|
committer | Gerrit Code Review <review@openstack.org> | 2015-12-23 03:41:45 +0000 |
commit | 7e521c12a05c94f7d5e35ae6efef5a23f41f0e7e (patch) | |
tree | 887d37e188477cf035497ac1bb5bc39f175ebc1d /contrib | |
parent | 68a8a2e34354b5dc77fbeb09ff624a60a3b7a509 (diff) | |
parent | 58624d4f1cfbdf2238cd25f028f18956b902ae49 (diff) | |
download | heat-7e521c12a05c94f7d5e35ae6efef5a23f41f0e7e.tar.gz |
Merge "Support RackConnect V3 LB in Rackspace AutoScaleGroup Resource"
Diffstat (limited to 'contrib')
-rw-r--r-- | contrib/rackspace/rackspace/resources/auto_scale.py | 31 | ||||
-rw-r--r-- | contrib/rackspace/rackspace/tests/test_auto_scale.py | 92 | ||||
-rw-r--r-- | contrib/rackspace/requirements.txt | 2 |
3 files changed, 120 insertions, 5 deletions
diff --git a/contrib/rackspace/rackspace/resources/auto_scale.py b/contrib/rackspace/rackspace/resources/auto_scale.py index 69d08f2a0..498eeec38 100644 --- a/contrib/rackspace/rackspace/resources/auto_scale.py +++ b/contrib/rackspace/rackspace/resources/auto_scale.py @@ -15,6 +15,7 @@ import copy +from heat.common import exception from heat.common.i18n import _ from heat.engine import attributes from heat.engine import constraints @@ -130,8 +131,7 @@ class Group(resource.Resource): ), LAUNCH_CONFIG_ARGS_LOAD_BALANCER_PORT: properties.Schema( properties.Schema.INTEGER, - _('Server port to connect the load balancer to.'), - required=True + _('Server port to connect the load balancer to.') ), }, ) @@ -294,6 +294,11 @@ class Group(resource.Resource): lbs = copy.deepcopy(lb_args) if lbs: for lb in lbs: + # if the port is not specified, the lbid must be that of a + # RackConnectV3 lb pool. + if not lb[self.LAUNCH_CONFIG_ARGS_LOAD_BALANCER_PORT]: + del lb[self.LAUNCH_CONFIG_ARGS_LOAD_BALANCER_PORT] + continue lbid = int(lb[self.LAUNCH_CONFIG_ARGS_LOAD_BALANCER_ID]) lb[self.LAUNCH_CONFIG_ARGS_LOAD_BALANCER_ID] = lbid personality = server_args.get( @@ -391,6 +396,28 @@ class Group(resource.Resource): else: return True + def _check_rackconnect_v3_pool_exists(self, pool_id): + pools = self.client("rackconnect").list_load_balancer_pools() + if pool_id in (p.id for p in pools): + return True + return False + + def validate(self): + super(Group, self).validate() + launchconf = self.properties[self.LAUNCH_CONFIGURATION] + lcargs = launchconf[self.LAUNCH_CONFIG_ARGS] + lb_args = lcargs.get(self.LAUNCH_CONFIG_ARGS_LOAD_BALANCERS) + lbs = copy.deepcopy(lb_args) + for lb in lbs: + lb_port = lb.get(self.LAUNCH_CONFIG_ARGS_LOAD_BALANCER_PORT) + lb_id = lb[self.LAUNCH_CONFIG_ARGS_LOAD_BALANCER_ID] + if not lb_port: + # check if lb id is a valid RCV3 pool id + if not self._check_rackconnect_v3_pool_exists(lb_id): + msg = _('Could not find RackConnectV3 pool ' + 'with id %s') % (lb_id) + raise exception.StackValidationFailed(msg) + def auto_scale(self): return self.client('auto_scale') diff --git a/contrib/rackspace/rackspace/tests/test_auto_scale.py b/contrib/rackspace/rackspace/tests/test_auto_scale.py index eda56c443..06a9dde24 100644 --- a/contrib/rackspace/rackspace/tests/test_auto_scale.py +++ b/contrib/rackspace/rackspace/tests/test_auto_scale.py @@ -15,6 +15,7 @@ import copy import itertools import mock +import six from heat.common import exception from heat.common import template_format @@ -200,6 +201,10 @@ class ScalingGroupTest(common.HeatTestCase): networks: - uuid: "00000000-0000-0000-0000-000000000000" - uuid: "11111111-1111-1111-1111-111111111111" + loadBalancers: + - loadBalancerId: 234 + port: 80 + ''') def setUp(self): @@ -238,9 +243,12 @@ class ScalingGroupTest(common.HeatTestCase): 'disk_config': None, 'flavor': 'flavor-ref', 'image': 'image-ref', - 'launch_config_type': 'launch_server', - 'load_balancers': None, + 'load_balancers': [{ + 'loadBalancerId': 234, + 'port': 80, + }], 'key_name': "my-key", + 'launch_config_type': u'launch_server', 'max_entities': 25, 'group_metadata': {'group': 'metadata'}, 'metadata': {'server': 'metadata'}, @@ -669,3 +677,83 @@ class WebHookTest(common.HeatTestCase): del self.fake_auto_scale.webhooks['0'] scheduler.TaskRunner(resource.delete)() self.assertEqual({}, self.fake_auto_scale.webhooks) + + +@mock.patch.object(resource.Resource, "client_plugin") +@mock.patch.object(resource.Resource, "client") +class AutoScaleGroupValidationTests(common.HeatTestCase): + def setUp(self): + super(AutoScaleGroupValidationTests, self).setUp() + self.mockstack = mock.Mock() + self.mockstack.has_cache_data.return_value = False + self.mockstack.db_resource_get.return_value = None + + def test_validate_no_rcv3_pool(self, mock_client, mock_plugin): + asg_properties = { + "groupConfiguration": { + "name": "My Group", + "cooldown": 60, + "minEntities": 1, + "maxEntities": 25, + "metadata": { + "group": "metadata", + }, + }, + "launchConfiguration": { + "type": "launch_server", + "args": { + "loadBalancers": [{ + "loadBalancerId": 'not integer!', + }], + "server": { + "name": "sdfsdf", + "flavorRef": "ffdgdf", + "imageRef": "image-ref", + }, + }, + }, + } + rsrcdef = rsrc_defn.ResourceDefinition( + "test", auto_scale.Group, properties=asg_properties) + asg = auto_scale.Group("test", rsrcdef, self.mockstack) + + mock_client().list_load_balancer_pools.return_value = [] + error = self.assertRaises( + exception.StackValidationFailed, asg.validate) + self.assertEqual( + 'Could not find RackConnectV3 pool with id not integer!: ', + six.text_type(error)) + + def test_validate_rcv3_pool_found(self, mock_client, mock_plugin): + asg_properties = { + "groupConfiguration": { + "name": "My Group", + "cooldown": 60, + "minEntities": 1, + "maxEntities": 25, + "metadata": { + "group": "metadata", + }, + }, + "launchConfiguration": { + "type": "launch_server", + "args": { + "loadBalancers": [{ + "loadBalancerId": 'pool_exists', + }], + "server": { + "name": "sdfsdf", + "flavorRef": "ffdgdf", + "imageRef": "image-ref", + }, + }, + }, + } + rsrcdef = rsrc_defn.ResourceDefinition( + "test", auto_scale.Group, properties=asg_properties) + asg = auto_scale.Group("test", rsrcdef, self.mockstack) + + mock_client().list_load_balancer_pools.return_value = [ + mock.Mock(id='pool_exists'), + ] + self.assertIsNone(asg.validate()) diff --git a/contrib/rackspace/requirements.txt b/contrib/rackspace/requirements.txt index de418f324..5d197dd52 100644 --- a/contrib/rackspace/requirements.txt +++ b/contrib/rackspace/requirements.txt @@ -1 +1 @@ -pyrax>=1.9.2 +-e git+https://github.com/rackerlabs/heat-pyrax.git#egg=pyrax |