Overlapping IPRanges are accepted if prefix lengths are different #10180

Closed
opened 2025-12-29 21:27:52 +01:00 by adam · 0 comments
Owner

Originally created by @candlerb on GitHub (Sep 4, 2024).

Originally assigned to: @bctiemann on GitHub.

Deployment Type

Self-hosted

NetBox Version

v4.0.11

Python Version

3.12

Steps to Reproduce

  1. Create an IPRange with start 1.2.3.100/24 and end 1.2.3.200/24
  2. Create an IPRange with start 1.2.3.123/26 and end 1.2.3.124/26

Expected Behavior

The second IPRange should be rejected, as it overlaps with the first. (There is code in IPRange.clean() which is clearly intended to do this)

Observed Behavior

The overlapping range is accepted.

The problem occurs because the Django ORM lte/gte filter for overlapping ranges only works if the prefix lengths match:

>>> ip = "1.2.3.101/24"
>>> IPRange.objects.filter(start_address__lte=ip, end_address__gte=ip, vrf=None)
<RestrictedQuerySet [<IPRange: 1.2.3.100-200/24>]>
>>> ip = "1.2.3.101/26"
>>> IPRange.objects.filter(start_address__lte=ip, end_address__gte=ip, vrf=None)
<RestrictedQuerySet []>

I cannot see an obvious solution here, apart from brute force iterating over all possible prefix lengths:

>>> [IPRange.objects.filter(start_address__lte=f"1.2.3.101/{pl}", end_address__gte=f"1.2.3.101/{pl}", vrf=None).count() for pl in range(33)]
[0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 1, 0, 0, 0, 0, 0, 0, 0, 0]

Alternatively, changing the data model so that a range uses IPAddress instead of IPNetwork for the start/end addresses would eliminate this problem.

Originally created by @candlerb on GitHub (Sep 4, 2024). Originally assigned to: @bctiemann on GitHub. ### Deployment Type Self-hosted ### NetBox Version v4.0.11 ### Python Version 3.12 ### Steps to Reproduce 1. Create an IPRange with start 1.2.3.100/24 and end 1.2.3.200/24 2. Create an IPRange with start 1.2.3.123/26 and end 1.2.3.124/26 ### Expected Behavior The second IPRange should be rejected, as it overlaps with the first. (There is code in `IPRange.clean()` which is clearly intended to do this) ### Observed Behavior The overlapping range is accepted. The problem occurs because the Django ORM lte/gte filter for overlapping ranges only works if the prefix lengths match: ``` >>> ip = "1.2.3.101/24" >>> IPRange.objects.filter(start_address__lte=ip, end_address__gte=ip, vrf=None) <RestrictedQuerySet [<IPRange: 1.2.3.100-200/24>]> >>> ip = "1.2.3.101/26" >>> IPRange.objects.filter(start_address__lte=ip, end_address__gte=ip, vrf=None) <RestrictedQuerySet []> ``` I cannot see an obvious solution here, apart from brute force iterating over all possible prefix lengths: ``` >>> [IPRange.objects.filter(start_address__lte=f"1.2.3.101/{pl}", end_address__gte=f"1.2.3.101/{pl}", vrf=None).count() for pl in range(33)] [0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 1, 0, 0, 0, 0, 0, 0, 0, 0] ``` Alternatively, changing the data model so that a range uses IPAddress instead of IPNetwork for the start/end addresses would eliminate this problem.
adam added the type: bugstatus: acceptednetboxseverity: low labels 2025-12-29 21:27:52 +01:00
adam closed this issue 2025-12-29 21:27:53 +01:00
Sign in to join this conversation.
1 Participants
Notifications
Due Date
No due date set.
Dependencies

No dependencies set.

Reference: starred/netbox#10180