move network constraints from neutron to common constraint
seperate out common network constraints (ip_addr, cidr, and mac_addr) Change-Id: I617035e379c4e86ac0ce4c77f26ebfca5b3d691a
This commit is contained in:
parent
e3608159cd
commit
3f68d5485e
@ -11,13 +11,9 @@
|
|||||||
# License for the specific language governing permissions and limitations
|
# License for the specific language governing permissions and limitations
|
||||||
# under the License.
|
# under the License.
|
||||||
|
|
||||||
import netaddr
|
|
||||||
import six
|
|
||||||
|
|
||||||
from neutronclient.common import exceptions
|
from neutronclient.common import exceptions
|
||||||
from neutronclient.neutron import v2_0 as neutronV20
|
from neutronclient.neutron import v2_0 as neutronV20
|
||||||
from neutronclient.v2_0 import client as nc
|
from neutronclient.v2_0 import client as nc
|
||||||
from oslo_utils import netutils
|
|
||||||
from oslo_utils import uuidutils
|
from oslo_utils import uuidutils
|
||||||
|
|
||||||
from heat.common import exception
|
from heat.common import exception
|
||||||
@ -178,35 +174,3 @@ class SubnetConstraint(constraints.BaseCustomConstraint):
|
|||||||
neutron_client = client.client('neutron')
|
neutron_client = client.client('neutron')
|
||||||
neutronV20.find_resourceid_by_name_or_id(
|
neutronV20.find_resourceid_by_name_or_id(
|
||||||
neutron_client, 'subnet', value)
|
neutron_client, 'subnet', value)
|
||||||
|
|
||||||
|
|
||||||
class IPConstraint(constraints.BaseCustomConstraint):
|
|
||||||
|
|
||||||
def validate(self, value, context):
|
|
||||||
self._error_message = 'Invalid IP address'
|
|
||||||
return netutils.is_valid_ip(value)
|
|
||||||
|
|
||||||
|
|
||||||
class MACConstraint(constraints.BaseCustomConstraint):
|
|
||||||
|
|
||||||
def validate(self, value, context):
|
|
||||||
self._error_message = 'Invalid MAC address.'
|
|
||||||
return netaddr.valid_mac(value)
|
|
||||||
|
|
||||||
|
|
||||||
class CIDRConstraint(constraints.BaseCustomConstraint):
|
|
||||||
|
|
||||||
def _validate_whitespace(self, data):
|
|
||||||
self._error_message = ("Invalid net cidr '%s' contains "
|
|
||||||
"whitespace" % data)
|
|
||||||
if len(data.split()) > 1:
|
|
||||||
return False
|
|
||||||
return True
|
|
||||||
|
|
||||||
def validate(self, value, context):
|
|
||||||
try:
|
|
||||||
netaddr.IPNetwork(value)
|
|
||||||
return self._validate_whitespace(value)
|
|
||||||
except Exception as ex:
|
|
||||||
self._error_message = 'Invalid net cidr %s ' % six.text_type(ex)
|
|
||||||
return False
|
|
||||||
|
@ -12,6 +12,44 @@
|
|||||||
# under the License.
|
# under the License.
|
||||||
|
|
||||||
import iso8601
|
import iso8601
|
||||||
|
import netaddr
|
||||||
|
import six
|
||||||
|
|
||||||
|
from oslo_utils import netutils
|
||||||
|
|
||||||
|
from heat.engine import constraints
|
||||||
|
|
||||||
|
|
||||||
|
class IPConstraint(constraints.BaseCustomConstraint):
|
||||||
|
|
||||||
|
def validate(self, value, context):
|
||||||
|
self._error_message = 'Invalid IP address'
|
||||||
|
return netutils.is_valid_ip(value)
|
||||||
|
|
||||||
|
|
||||||
|
class MACConstraint(constraints.BaseCustomConstraint):
|
||||||
|
|
||||||
|
def validate(self, value, context):
|
||||||
|
self._error_message = 'Invalid MAC address.'
|
||||||
|
return netaddr.valid_mac(value)
|
||||||
|
|
||||||
|
|
||||||
|
class CIDRConstraint(constraints.BaseCustomConstraint):
|
||||||
|
|
||||||
|
def _validate_whitespace(self, data):
|
||||||
|
self._error_message = ("Invalid net cidr '%s' contains "
|
||||||
|
"whitespace" % data)
|
||||||
|
if len(data.split()) > 1:
|
||||||
|
return False
|
||||||
|
return True
|
||||||
|
|
||||||
|
def validate(self, value, context):
|
||||||
|
try:
|
||||||
|
netaddr.IPNetwork(value)
|
||||||
|
return self._validate_whitespace(value)
|
||||||
|
except Exception as ex:
|
||||||
|
self._error_message = 'Invalid net cidr %s ' % six.text_type(ex)
|
||||||
|
return False
|
||||||
|
|
||||||
|
|
||||||
class ISO8601Constraint(object):
|
class ISO8601Constraint(object):
|
||||||
|
@ -182,102 +182,3 @@ class NeutronConstraintsValidate(common.HeatTestCase):
|
|||||||
self.assertFalse(constraint.validate("bar", ctx))
|
self.assertFalse(constraint.validate("bar", ctx))
|
||||||
mock_find.assert_has_calls([mock.call(nc, self.resource_type, 'foo'),
|
mock_find.assert_has_calls([mock.call(nc, self.resource_type, 'foo'),
|
||||||
mock.call(nc, self.resource_type, 'bar')])
|
mock.call(nc, self.resource_type, 'bar')])
|
||||||
|
|
||||||
|
|
||||||
class TestIPConstraint(common.HeatTestCase):
|
|
||||||
|
|
||||||
def setUp(self):
|
|
||||||
super(TestIPConstraint, self).setUp()
|
|
||||||
self.constraint = neutron.IPConstraint()
|
|
||||||
|
|
||||||
def test_validate_ipv4_format(self):
|
|
||||||
validate_format = [
|
|
||||||
'1.1.1.1',
|
|
||||||
'1.0.1.1',
|
|
||||||
'255.255.255.255'
|
|
||||||
]
|
|
||||||
for ip in validate_format:
|
|
||||||
self.assertTrue(self.constraint.validate(ip, None))
|
|
||||||
|
|
||||||
def test_invalidate_ipv4_format(self):
|
|
||||||
invalidate_format = [
|
|
||||||
'1.1.1.',
|
|
||||||
'1.1.1.256',
|
|
||||||
'invalidate format',
|
|
||||||
'1.a.1.1'
|
|
||||||
]
|
|
||||||
for ip in invalidate_format:
|
|
||||||
self.assertFalse(self.constraint.validate(ip, None))
|
|
||||||
|
|
||||||
def test_validate_ipv6_format(self):
|
|
||||||
validate_format = [
|
|
||||||
'2002:2002::20c:29ff:fe7d:811a',
|
|
||||||
'::1',
|
|
||||||
'2002::',
|
|
||||||
'2002::1',
|
|
||||||
]
|
|
||||||
for ip in validate_format:
|
|
||||||
self.assertTrue(self.constraint.validate(ip, None))
|
|
||||||
|
|
||||||
def test_invalidate_ipv6_format(self):
|
|
||||||
invalidate_format = [
|
|
||||||
'2002::2001::1',
|
|
||||||
'2002::g',
|
|
||||||
'invalidate format',
|
|
||||||
'2001::0::',
|
|
||||||
'20c:29ff:fe7d:811a'
|
|
||||||
]
|
|
||||||
for ip in invalidate_format:
|
|
||||||
self.assertFalse(self.constraint.validate(ip, None))
|
|
||||||
|
|
||||||
|
|
||||||
class TestMACConstraint(common.HeatTestCase):
|
|
||||||
|
|
||||||
def setUp(self):
|
|
||||||
super(TestMACConstraint, self).setUp()
|
|
||||||
self.constraint = neutron.MACConstraint()
|
|
||||||
|
|
||||||
def test_valid_mac_format(self):
|
|
||||||
validate_format = [
|
|
||||||
'01:23:45:67:89:ab',
|
|
||||||
'01-23-45-67-89-ab',
|
|
||||||
'0123.4567.89ab'
|
|
||||||
]
|
|
||||||
for mac in validate_format:
|
|
||||||
self.assertTrue(self.constraint.validate(mac, None))
|
|
||||||
|
|
||||||
def test_invalid_mac_format(self):
|
|
||||||
invalidate_format = [
|
|
||||||
'8.8.8.8',
|
|
||||||
'0a-1b-3c-4d-5e-6f-1f',
|
|
||||||
'0a-1b-3c-4d-5e-xx'
|
|
||||||
]
|
|
||||||
for mac in invalidate_format:
|
|
||||||
self.assertFalse(self.constraint.validate(mac, None))
|
|
||||||
|
|
||||||
|
|
||||||
class TestCIDRConstraint(common.HeatTestCase):
|
|
||||||
|
|
||||||
def setUp(self):
|
|
||||||
super(TestCIDRConstraint, self).setUp()
|
|
||||||
self.constraint = neutron.CIDRConstraint()
|
|
||||||
|
|
||||||
def test_valid_cidr_format(self):
|
|
||||||
validate_format = [
|
|
||||||
'10.0.0.0/24',
|
|
||||||
'6000::/64',
|
|
||||||
'8.8.8.8'
|
|
||||||
]
|
|
||||||
for cidr in validate_format:
|
|
||||||
self.assertTrue(self.constraint.validate(cidr, None))
|
|
||||||
|
|
||||||
def test_invalid_cidr_format(self):
|
|
||||||
invalidate_format = [
|
|
||||||
'::/129',
|
|
||||||
'Invalid cidr',
|
|
||||||
'300.0.0.0/24',
|
|
||||||
'10.0.0.0/33',
|
|
||||||
'8.8.8.0/ 24'
|
|
||||||
]
|
|
||||||
for cidr in invalidate_format:
|
|
||||||
self.assertFalse(self.constraint.validate(cidr, None))
|
|
||||||
|
@ -15,6 +15,105 @@ from heat.engine.constraint import common_constraints as cc
|
|||||||
from heat.tests import common
|
from heat.tests import common
|
||||||
|
|
||||||
|
|
||||||
|
class TestIPConstraint(common.HeatTestCase):
|
||||||
|
|
||||||
|
def setUp(self):
|
||||||
|
super(TestIPConstraint, self).setUp()
|
||||||
|
self.constraint = cc.IPConstraint()
|
||||||
|
|
||||||
|
def test_validate_ipv4_format(self):
|
||||||
|
validate_format = [
|
||||||
|
'1.1.1.1',
|
||||||
|
'1.0.1.1',
|
||||||
|
'255.255.255.255'
|
||||||
|
]
|
||||||
|
for ip in validate_format:
|
||||||
|
self.assertTrue(self.constraint.validate(ip, None))
|
||||||
|
|
||||||
|
def test_invalidate_ipv4_format(self):
|
||||||
|
invalidate_format = [
|
||||||
|
'1.1.1.',
|
||||||
|
'1.1.1.256',
|
||||||
|
'invalidate format',
|
||||||
|
'1.a.1.1'
|
||||||
|
]
|
||||||
|
for ip in invalidate_format:
|
||||||
|
self.assertFalse(self.constraint.validate(ip, None))
|
||||||
|
|
||||||
|
def test_validate_ipv6_format(self):
|
||||||
|
validate_format = [
|
||||||
|
'2002:2002::20c:29ff:fe7d:811a',
|
||||||
|
'::1',
|
||||||
|
'2002::',
|
||||||
|
'2002::1',
|
||||||
|
]
|
||||||
|
for ip in validate_format:
|
||||||
|
self.assertTrue(self.constraint.validate(ip, None))
|
||||||
|
|
||||||
|
def test_invalidate_ipv6_format(self):
|
||||||
|
invalidate_format = [
|
||||||
|
'2002::2001::1',
|
||||||
|
'2002::g',
|
||||||
|
'invalidate format',
|
||||||
|
'2001::0::',
|
||||||
|
'20c:29ff:fe7d:811a'
|
||||||
|
]
|
||||||
|
for ip in invalidate_format:
|
||||||
|
self.assertFalse(self.constraint.validate(ip, None))
|
||||||
|
|
||||||
|
|
||||||
|
class TestMACConstraint(common.HeatTestCase):
|
||||||
|
|
||||||
|
def setUp(self):
|
||||||
|
super(TestMACConstraint, self).setUp()
|
||||||
|
self.constraint = cc.MACConstraint()
|
||||||
|
|
||||||
|
def test_valid_mac_format(self):
|
||||||
|
validate_format = [
|
||||||
|
'01:23:45:67:89:ab',
|
||||||
|
'01-23-45-67-89-ab',
|
||||||
|
'0123.4567.89ab'
|
||||||
|
]
|
||||||
|
for mac in validate_format:
|
||||||
|
self.assertTrue(self.constraint.validate(mac, None))
|
||||||
|
|
||||||
|
def test_invalid_mac_format(self):
|
||||||
|
invalidate_format = [
|
||||||
|
'8.8.8.8',
|
||||||
|
'0a-1b-3c-4d-5e-6f-1f',
|
||||||
|
'0a-1b-3c-4d-5e-xx'
|
||||||
|
]
|
||||||
|
for mac in invalidate_format:
|
||||||
|
self.assertFalse(self.constraint.validate(mac, None))
|
||||||
|
|
||||||
|
|
||||||
|
class TestCIDRConstraint(common.HeatTestCase):
|
||||||
|
|
||||||
|
def setUp(self):
|
||||||
|
super(TestCIDRConstraint, self).setUp()
|
||||||
|
self.constraint = cc.CIDRConstraint()
|
||||||
|
|
||||||
|
def test_valid_cidr_format(self):
|
||||||
|
validate_format = [
|
||||||
|
'10.0.0.0/24',
|
||||||
|
'6000::/64',
|
||||||
|
'8.8.8.8'
|
||||||
|
]
|
||||||
|
for cidr in validate_format:
|
||||||
|
self.assertTrue(self.constraint.validate(cidr, None))
|
||||||
|
|
||||||
|
def test_invalid_cidr_format(self):
|
||||||
|
invalidate_format = [
|
||||||
|
'::/129',
|
||||||
|
'Invalid cidr',
|
||||||
|
'300.0.0.0/24',
|
||||||
|
'10.0.0.0/33',
|
||||||
|
'8.8.8.0/ 24'
|
||||||
|
]
|
||||||
|
for cidr in invalidate_format:
|
||||||
|
self.assertFalse(self.constraint.validate(cidr, None))
|
||||||
|
|
||||||
|
|
||||||
class TestISO8601Constraint(common.HeatTestCase):
|
class TestISO8601Constraint(common.HeatTestCase):
|
||||||
|
|
||||||
def setUp(self):
|
def setUp(self):
|
||||||
|
@ -80,9 +80,9 @@ heat.constraints =
|
|||||||
cinder.vtype = heat.engine.clients.os.cinder:VolumeTypeConstraint
|
cinder.vtype = heat.engine.clients.os.cinder:VolumeTypeConstraint
|
||||||
sahara.image = heat.engine.clients.os.sahara:ImageConstraint
|
sahara.image = heat.engine.clients.os.sahara:ImageConstraint
|
||||||
trove.flavor = heat.engine.clients.os.trove:FlavorConstraint
|
trove.flavor = heat.engine.clients.os.trove:FlavorConstraint
|
||||||
ip_addr = heat.engine.clients.os.neutron:IPConstraint
|
ip_addr = heat.engine.constraint.common_constraints:IPConstraint
|
||||||
mac_addr = heat.engine.clients.os.neutron:MACConstraint
|
mac_addr = heat.engine.constraint.common_constraints:MACConstraint
|
||||||
net_cidr = heat.engine.clients.os.neutron:CIDRConstraint
|
net_cidr = heat.engine.constraint.common_constraints:CIDRConstraint
|
||||||
keystone.role = heat.engine.clients.os.keystone:KeystoneRoleConstraint
|
keystone.role = heat.engine.clients.os.keystone:KeystoneRoleConstraint
|
||||||
keystone.domain = heat.engine.clients.os.keystone:KeystoneDomainConstraint
|
keystone.domain = heat.engine.clients.os.keystone:KeystoneDomainConstraint
|
||||||
keystone.project = heat.engine.clients.os.keystone:KeystoneProjectConstraint
|
keystone.project = heat.engine.clients.os.keystone:KeystoneProjectConstraint
|
||||||
|
Loading…
Reference in New Issue
Block a user