def test_update_iprange_user(self): user = factory.make_User() subnet = factory.make_ipv4_Subnet_with_IPRanges() iprange = subnet.get_dynamic_ranges().first() form = IPRangeForm(instance=iprange, data={"user": user.username}) self.assertTrue(form.is_valid(), dict(form.errors)) form.save() self.assertEqual(user, reload_object(iprange).user)
def test_updates_iprange(self): subnet = factory.make_ipv4_Subnet_with_IPRanges() iprange = subnet.get_dynamic_ranges().first() new_comment = factory.make_name("comment") form = IPRangeForm(instance=iprange, data={"comment": new_comment}) self.assertTrue(form.is_valid(), dict(form.errors)) form.save() self.assertEqual(new_comment, reload_object(iprange).comment)
def test_comment_optional(self): subnet = factory.make_Subnet(cidr="10.0.0.0/24") form = IPRangeForm({ "subnet": subnet.id, "type": IPRANGE_TYPE.RESERVED, "start_ip": "10.0.0.100", "end_ip": "10.0.0.150", }) self.assertTrue(form.is_valid(), dict(form.errors)) iprange = form.save() self.assertThat(iprange.comment, Equals(""))
def test_requires_subnet(self): comment = factory.make_name("comment") form = IPRangeForm({ "type": IPRANGE_TYPE.RESERVED, "start_ip": "10.0.0.100", "end_ip": "10.0.0.150", "comment": comment, }) self.assertFalse(form.is_valid(), dict(form.errors)) self.assertThat(form.errors["subnet"], Contains("This field is required."))
def test_subnet_optional_if_it_can_be_found(self): subnet = factory.make_Subnet(cidr="10.0.0.0/24") comment = factory.make_name("comment") form = IPRangeForm({ "type": IPRANGE_TYPE.RESERVED, "start_ip": "10.0.0.100", "end_ip": "10.0.0.150", "comment": comment, }) self.assertTrue(form.is_valid(), dict(form.errors)) iprange = form.save() self.assertEqual(iprange.subnet, subnet)
def test_requires_type(self): subnet = factory.make_Subnet(cidr="10.0.0.0/24") comment = factory.make_name("comment") form = IPRangeForm({ "subnet": subnet.id, "start_ip": "10.0.0.100", "end_ip": "10.0.0.150", "comment": comment, }) self.assertFalse(form.is_valid(), dict(form.errors)) self.assertThat(form.errors["type"], Contains("This field is required."))
def test__requires_end_ip(self): subnet = factory.make_Subnet(cidr='10.0.0.0/24') comment = factory.make_name("comment") form = IPRangeForm({ "subnet": subnet.id, "type": IPRANGE_TYPE.RESERVED, "start_ip": "10.0.0.100", "comment": comment, }) self.assertFalse(form.is_valid(), dict(form.errors)) self.assertThat( form.errors['end_ip'], Contains("This field is required."))
def _configure_iprange_and_gateway(self, parameters): if 'subnet' in parameters and parameters['subnet'] is not None: subnet = Subnet.objects.get(id=parameters['subnet']) else: # Without a subnet, we cannot continue. (We need one to either # add an IP range, or specify a gateway IP.) return gateway = None if ('gateway' in parameters and parameters['gateway'] is not None): gateway_text = parameters['gateway'].strip() if len(gateway_text) > 0: gateway = netaddr.IPAddress(gateway_text) ipnetwork = netaddr.IPNetwork(subnet.cidr) if gateway not in ipnetwork and not (gateway.version == 6 and gateway.is_link_local()): raise ValueError( "Gateway IP must be within specified subnet: %s" % subnet.cidr) if ('start' in parameters and 'end' in parameters and parameters['start'] is not None and parameters['end'] is not None): start_text = parameters['start'].strip() end_text = parameters['end'].strip() # User wishes to add a range. if len(start_text) > 0 and len(end_text) > 0: start_ipaddr = netaddr.IPAddress(start_text) end_ipaddr = netaddr.IPAddress(end_text) if gateway is not None: # If a gateway was specified, validate that it is not # within the range the user wants to define. desired_range = netaddr.IPRange(start_ipaddr, end_ipaddr) if gateway in desired_range: raise ValueError( "Gateway IP must be outside the specified dynamic " "range.") iprange_form = IPRangeForm( data={ "start_ip": str(start_ipaddr), "end_ip": str(end_ipaddr), "type": IPRANGE_TYPE.DYNAMIC, "subnet": subnet.id, "user": self.user.username, "comment": "Added via 'Provide DHCP...' in Web UI." }) iprange_form.save() if gateway is not None: subnet.gateway_ip = str(gateway) subnet.save()
def update(self, request, id): """Update IP range. :param start_ip: Start IP address of this range (inclusive). :param end_ip: End IP address of this range (inclusive). :param comment: A description of this range. (optional) Returns 403 if not owner of IP range. Returns 404 if the IP Range is not found. """ iprange = IPRange.objects.get_iprange_or_404(id) raise_error_if_not_owner(iprange, request.user) form = IPRangeForm(instance=iprange, data=request.data) if form.is_valid(): return form.save() else: raise MAASAPIValidationError(form.errors)
def test_creates_iprange(self): subnet = factory.make_Subnet(cidr="10.0.0.0/24") comment = factory.make_name("comment") form = IPRangeForm({ "subnet": subnet.id, "type": IPRANGE_TYPE.RESERVED, "start_ip": "10.0.0.100", "end_ip": "10.0.0.150", "comment": comment, }) self.assertTrue(form.is_valid(), dict(form.errors)) iprange = form.save() self.assertEqual(iprange.subnet, subnet) self.assertEqual(iprange.start_ip, "10.0.0.100") self.assertEqual(iprange.end_ip, "10.0.0.150") self.assertEqual(iprange.type, IPRANGE_TYPE.RESERVED) self.assertEqual(iprange.comment, comment)
def test__creates_iprange_with_user(self): subnet = factory.make_Subnet(cidr='10.0.0.0/24') comment = factory.make_name("comment") request = Mock() request.user = factory.make_User() form = IPRangeForm(request=request, data={ "subnet": subnet.id, "type": IPRANGE_TYPE.RESERVED, "start_ip": "10.0.0.100", "end_ip": "10.0.0.150", "comment": comment, }) self.assertTrue(form.is_valid(), dict(form.errors)) iprange = form.save() self.assertEqual(iprange.subnet, subnet) self.assertEqual(iprange.start_ip, "10.0.0.100") self.assertEqual(iprange.end_ip, "10.0.0.150") self.assertEqual(iprange.type, IPRANGE_TYPE.RESERVED) self.assertEqual(iprange.comment, comment) self.assertEqual(iprange.user, request.user)
def create(self, request): """@description-title Create an IP range @description Create a new IP range. @param (string) "type" [required=true] Type of this range. (``dynamic`` or ``reserved``) @param (string) "start_ip" [required=true] Start IP address of this range (inclusive). @param (string) "end_ip" [required=true] End IP address of this range (inclusive). @param (string) "subnet" [required=true] Subnet associated with this range. @param (string) "comment" [required=false] A description of this range. @success (http-status-code) "server-success" 200 @success (json) "success-json" A JSON object containing the new IP range. @success-example "success-json" [exkey=ipranges-create] placeholder text @error (http-status-code) "403" 403 @error (content) "no-perms" The user does not have the permissions required to create an IP range. """ if ('type' in request.data and request.data['type'] == IPRANGE_TYPE.DYNAMIC and not request.user.is_superuser): raise MAASAPIForbidden("Unable to create dynamic IP range. " "You don't have sufficient privileges.") form = IPRangeForm(data=request.data, request=request) if form.is_valid(): return form.save() else: raise MAASAPIValidationError(form.errors)
def create(self, request): """Create an IP range. :param type: Type of this range. (`dynamic` or `reserved`) :param start_ip: Start IP address of this range (inclusive). :param end_ip: End IP address of this range (inclusive). :param subnet: Subnet this range is associated with. (optional) :param comment: A description of this range. (optional) Returns 403 if standard users tries to create a dynamic IP range. """ if ('type' in request.data and request.data['type'] == IPRANGE_TYPE.DYNAMIC and not request.user.is_superuser): raise MAASAPIForbidden("Unable to create dynamic IP range. " "You don't have sufficient privileges.") form = IPRangeForm(data=request.data, request=request) if form.is_valid(): return form.save() else: raise MAASAPIValidationError(form.errors)
def update(self, request, id): """@description-title Update an IP range @description Update an IP range with the given id. @param (int) "{id}" [required=true] An IP range id. @param (string) "start_ip" [required=false] Start IP address of this range (inclusive). @param (string) "end_ip" [required=false] End IP address of this range (inclusive). @param (string) "comment" [required=false] A description of this range. (optional) @success (http-status-code) "server-success" 200 @success (json) "success-json" A JSON object containing the requested IP range. @success-example "success-json" [exkey=ipranges-update] placeholder text @error (http-status-code) "403" 403 @error (content) "no-perms" The user does not have the permissions required to update the IP range. @error (http-status-code) "404" 404 @error (content) "not-found" The requested IP range is not found. @error-example "not-found" Not Found """ iprange = IPRange.objects.get_iprange_or_404(id) raise_error_if_not_owner(iprange, request.user) form = IPRangeForm(instance=iprange, data=request.data) if form.is_valid(): return form.save() else: raise MAASAPIValidationError(form.errors)
def test_empty_form_fails_validation(self): form = IPRangeForm({}) self.assertFalse(form.is_valid(), dict(form.errors))