summaryrefslogtreecommitdiff
path: root/contrib
diff options
context:
space:
mode:
authorJenkins <jenkins@review.openstack.org>2015-12-23 03:41:45 +0000
committerGerrit Code Review <review@openstack.org>2015-12-23 03:41:45 +0000
commit7e521c12a05c94f7d5e35ae6efef5a23f41f0e7e (patch)
tree887d37e188477cf035497ac1bb5bc39f175ebc1d /contrib
parent68a8a2e34354b5dc77fbeb09ff624a60a3b7a509 (diff)
parent58624d4f1cfbdf2238cd25f028f18956b902ae49 (diff)
downloadheat-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.py31
-rw-r--r--contrib/rackspace/rackspace/tests/test_auto_scale.py92
-rw-r--r--contrib/rackspace/requirements.txt2
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