簡體   English   中英

如何使用 Python 的 ipaddress 模塊查找子網/ip 是否在更大的子網中?

[英]How to use Python's ipaddress module to find if subnet/ip is within a bigger subnet?

import ipaddress
from itertools import zip_longest

internal_subnets=[ipaddress.IPv4Network('192.168.0.0/8'),ipaddress.IPv4Network('10.0.0.0/8')]

my_sg_subnets=[ ipaddress.IPv4Network('10.0.19.1/32'),ipaddress.IPv4Network('192.168.20.0/16'), ipaddress.IPv4Network('21.0.19.1/32') ]

for big_subnet, my_ip in zip_longest(internal_subnets, my_sg_subnets):
      if not my_ip.subnet_of(big_subnet):
         print(f"{my_ip} is not part of {big_subnet}")

對於internal_subnets列表中的最后一個子網,這將失敗,並顯示None 那么,如何再次遍歷 internal_subnet 列表中的前兩個?

最終的 output 應該是 10.0.19.1/32 和 192.168.20.0/16 是internal_subnets的一部分。

請指教。

出於某種原因,您編寫的代碼並行地遍歷internal_subnetsmy_sg_subnets 這就像這樣:在第一次迭代時,它從第一個列表中獲取第一個元素,並從第二個列表中獲取第一個元素。 在第二次迭代中,它從第一個列表中獲取第二個元素,從第二個列表中獲取第二個元素,依此類推。 相反,您需要遍歷internal_subnets ,然后檢查my_sg_subnets中的任何元素是否是子網。 所以這個代碼看起來像這樣:

import ipaddress
# Here i don't import itertools because i don't use them here

internal_subnets=[ipaddress.IPv4Network('192.168.0.0/16'), ipaddress.IPv4Network('10.0.0.0/8')]
# I changed network netmask from 8 to 16, because when it's set to 8 python
# just throws an error (Gino Mempin posted a comment about it). I also
# wrote about that below in my post.
# Changing this from 8 to 16 won't affect the actual result in your case (If there was no error) 

my_sg_subnets=[ipaddress.IPv4Network('10.0.19.1'),
    ipaddress.IPv4Network('192.168.20.0'),
    ipaddress.IPv4Network('21.0.19.1')]

for big_subnet in internal_subnets:
    for my_ip in my_sg_subnets:
        if my_ip.subnet_of(big_subnet):
            # Here instead of printing out everything that is not a subnet,
            # it prints out everything that IS a subnet
            print(f"{my_ip} is part of {big_subnet}")

它按預期工作。 這是 output:

192.168.20.0/32 is part of 192.168.0.0/16
10.0.19.1/32 is part of 10.0.0.0/8

為什么你的代碼拋出ValueError: 192.168.0.0/8 has host bits set

我們知道每個 IP_v4 地址和每個 IP_v4 網絡掩碼都只有 4 個字節的信息。 所以讓我們以二進制格式表示192.168.0.0地址和8個網絡掩碼。

netmask: 11111111 00000000 00000000 00000000 # Netmask of 8 means that it has 8 bits in its beginning 
address: 11000000 10101000 00000000 00000000
                  ˄ ˄ ˄
You can see that this IP address has 1 in place where its netmask has only 
zeros. This should not happen, and this is why python raised this error

例如,如果您的網絡的 ip 地址為10.0.0.0且網絡掩碼為8 (或更大),它將起作用,並且如果用二進制表示:

netmask: 11111111 00000000 00000000 00000000
address: 00001010 00000000 00000000 00000000

您會看到一切正常,因為地址在其網絡掩碼結束后沒有設置任何位。

此外,如果您為網絡10.0.0.0設置網絡掩碼“7”,它也可以正常工作。 但這可能會導致您可能不需要的問題,您會看到11.0.0.0地址在這個10.0.0.0網絡內

netmask : 11111110 00000000 00000000 00000000
address1: 00001010 00000000 00000000 00000000 # This is 10.0.0.0 addr
address2: 00001011 00000000 00000000 00000000 # This is 11.0.0.0 addr
                 ˄
This bit is different in address1 and address2, but because netmask has 0
at this position, it just doesn't matter, so address2 is inside of network
with address1, because all bits that are under those 1's in the 
netmask are the same.
Your program uses the same algorithm to check if some IP address is 
inside of some network

希望它能讓你更好地理解它是如何工作的

暫無
暫無

聲明:本站的技術帖子網頁,遵循CC BY-SA 4.0協議,如果您需要轉載,請注明本站網址或者原文地址。任何問題請咨詢:yoyou2525@163.com.

 
粵ICP備18138465號  © 2020-2024 STACKOOM.COM