目录
2.3.1 格式:192.168.1.1-192.168.1.10
2.3.4 格式192.168.*.*或192.*.168.*等
1. 背景
各种各样的ip范围,ip通配符等等,判断ip是否符合在这些范围内,搜索耗时耗力,整理出来,后续使用直接复制,有更好用的备注留言
2. 代码使用示例
2.1 分割ip,横杠 (-) 的ip范围
#! -*- coding:utf-8 -*
def split_ip_range(range):
"""
处理以下格式分割
192.168.1.1-10 拆分成192.168.1.1-192.168.1.10
192.168.1-10.* 拆分成192.168.1.*-192.168.10.*
192.168-169.*.* 拆分成192.168.*.*-192.169.*.*
192-193.168.*.* 拆分成192.168.*.*-193.168.*.*
192.168.1.1-10 拆分成192.168.1.1-192.168.1.10
192.168.1.1-192.168.1.10 拆分成192.168.1.1-192.168.1.10
:param range:
:return:
"""
if "-" not in range:
raise ValueError("处理不了其他格式的,拜拜")
start, end = range.split("-")
start_list, end_list = start.split("."), end.split(".")
start_lenght = len(start_list)
end_lenght = len(end_list)
# 暂不简化,逻辑简洁
if start_lenght == 1 and end_lenght == 4:
ret_start = start_list + end_list[1:]
ret_end = end_list
elif start_lenght == 2 and end_lenght == 3:
ret_start = start_list + end_list[1:]
ret_end = start_list[:1] + end_list
elif start_lenght == 3 and end_lenght == 2:
ret_start = start_list + end_list[1:]
ret_end = start_list[:2] + end_list
elif start_lenght == 4 and end_lenght == 1:
ret_start = start_list + end_list[1:]
ret_end = start_list[:3] + end_list
elif start_lenght == 4 and end_lenght == 4:
ret_start = start_list
ret_end = end_list
else:
raise ValueError("处理不了其他格式的,再见")
return ",".join(ret_start), ",".join(ret_end)
if __name__ == '__main__':
# 测试
ranges = [
"192-193.168.*.*",
"192.168-169.*.*",
"192.168.1-10.*",
"192.168.1.1-10",
"192.168.1.1-192.168.1.10"
]
for v in ranges:
print(f"{v},拆分后是:{split_ip_range(v)}")
2.2 判断ip在掩码(/)的范围内
import ipaddress
def is_ip_in_cidr(ip, cidr):
"""
判断一个IP地址是否在一个CIDR掩码范围内。
:param ip: 字符串格式的IP地址
:param cidr: CIDR格式的网络地址(如 "192.168.1.0/24")
:return: 如果IP地址在CIDR范围内返回True,否则返回False
"""
try:
# 创建一个IP地址对象
ip_obj = ipaddress.ip_address(ip)
# 创建一个网络对象
network = ipaddress.ip_network(cidr, strict=False)
# 检查IP地址是否在网络范围内
return ip_obj in network
except ValueError as e:
print(f"Error parsing IP or CIDR: {e}")
return False
# 测试用例
test_cases = [
("192.168.1.5", "192.168.1.0/24"),
("192.168.1.254", "192.168.1.0/24"),
("192.168.2.1", "192.168.1.0/24"),
("192.168.1.10", "192.168.1.8/29"),
("192.168.1.12", "192.168.1.8/29")
]
for ip, cidr in test_cases:
print(f"{ip} 是否在 {cidr} 范围内?{is_ip_in_cidr(ip, cidr)}")
2.3 判断ip在横杠(-)的范围内
2.3.1 格式:192.168.1.1-192.168.1.10
支持ipv4, ipv6网段
import ipaddress
# 支持ipv4, ipv6
def is_ip_in_range(ip_range_str, ip_address_str):
"""
判断一个IP地址是否在一个IP段内。
参数:
ip_range_str (str): IP段,格式为"start_ip-end_ip"。
ip_address_str (str): 要检查的IP地址。
返回:
bool: 如果IP地址在IP段内,返回True;否则返回False。
"""
try:
# 将IP范围字符串拆分为起始IP和结束IP
start_ip, end_ip = ip_range_str.split('-')
# 将起始IP和结束IP以及要检查的IP地址转换为IP地址对象
start_ip_address = ipaddress.ip_address(start_ip)
end_ip_address = ipaddress.ip_address(end_ip)
ip_to_check = ipaddress.ip_address(ip_address_str)
# 判断IP地址是否在起始IP和结束IP之间
return start_ip_address <= ip_to_check <= end_ip_address
except Exception as e:
# print(f"Error: {e}")
return False
2.3.2 格式:192.168.1.1-10
1. 使用2.1的方法分割
2. 使用2.3.1的方法判断
2.3.3 格式 192.168-169.*.*
包含*号的
1. 使用2.1的方法分割
2. 分割后的起始ip,* 做转换
3. 使用2.3.1方法判断
# 开始ip的*换为0
# 结束ip的*换为255
ip_range_str = '192.*.1.1-192.*.10.1' # 2.1方法返回
ip_range_str = '192.0.1.1-192.255.10.1' # 修改
ip_str = '192.168.10.1'
print(is_ip_in_range(ip_range_str, ip_str))
2.3.4 格式192.168.*.*或192.*.168.*等
1. 先如下处理数据
2. 再调用2.3.1方法
ip = "192.168.*.*"
start = ip.replace("*", "0")
end = ip.replace("*", "255")
print(f"{start}-{end}") # 192.0.0.1-192.255.255.1
3. 其他扩展
3.1 校验是否为ipv4/ipv6
import ipaddress
def validate_ip(ip_address: str):
"""
校验是否为ipv4或ipv6
@param ip_address: ip
@return:
"""
try:
ipaddress.ip_address(ip_address)
return True
except ValueError:
return False
3.2 判断一个网段/前缀是另一个的子网
import ipaddress
def is_subnet_of(a, b):
"""
Returns True if network a is a subnet of network b.
网络a是网络b的子网,返回true
@param a: 子网
@param b: 父网
@return: bool
"""
try:
# 将前缀转换为IP网络对象
a_network = ipaddress.ip_network(a, strict=True)
b_network = ipaddress.ip_network(b, strict=True)
return (a_network.network_address >= b_network.network_address and
a_network.broadcast_address <= b_network.broadcast_address)
except Exception as e:
print(e)
return False