Viewing file: validate.py (4.27 KB) -rw-r--r-- Select action/file-type: (+) | (+) | (+) | Code (+) | Session (+) | (+) | SDB (+) | (+) | (+) | (+) | (+) | (+) |
from enum import Enum from ipaddress import ( IPV4LENGTH, IPV6LENGTH, AddressValueError, IPv4Address, IPv4Network, IPv6Address, IPv6Network, ip_address, ip_network, ) from typing import Literal, Optional, Union
IPVersion = Literal["ipv4", "ipv6"]
class LocalhostIP(str, Enum): ipv4 = "127.0.0.1" ipv6 = "::1"
def __str__(self): return self.value
class NumericIPVersion(int, Enum): """Example: (IPListRecord.version==NumericIPVersion[ip_version])"""
ipv4 = 4 ipv6 = 6
def __str__(self): return str(self.value)
@classmethod def from_ip_version( cls, ip_version: Optional[IPVersion] ) -> Optional["NumericIPVersion"]: if ip_version is None: return None
return cls.ipv4 if ip_version == IP.V4 else cls.ipv6
def is_valid_ipv4_addr(addr): return IP.is_valid_ipv4_addr(addr)
def is_valid_ipv4_network(addr, strict=False): return IP.is_valid_ipv4_network(addr, strict)
class IP: V4: IPVersion = "ipv4" V6: IPVersion = "ipv6"
@classmethod def check_ip_ver(cls, version): return any(version == ver for ver in [cls.V4, cls.V6])
@classmethod def is_valid_ip(cls, addr): try: ip_address(addr) except ValueError: return False return True
@classmethod def is_valid_ip_network(cls, *args, **kwargs): return cls.is_valid_ipv4_network( *args, **kwargs ) or cls.is_valid_ipv6_network(*args, **kwargs)
@classmethod def is_valid_ipv4_addr(cls, addr): try: IPv4Address(addr) except AddressValueError: return False return True
@classmethod def is_valid_ipv6_addr(cls, addr): try: IPv6Address(addr) except AddressValueError: return False return True
@classmethod def is_valid_ipv4_network( cls, addr: Union[str, IPv4Network, IPv6Network], strict=False ): try: ip = IPv4Network(addr) except ValueError: return False
if strict: # IPV4LENGTH - netmask for host return ip.prefixlen != IPV4LENGTH return True
@classmethod def is_valid_ipv6_network( cls, addr: Union[str, IPv4Network, IPv6Network], strict=False ): try: ip = IPv6Network(addr) except ValueError: return False
if strict: # IPV6LENGTH - netmask for host return ip.prefixlen != IPV6LENGTH return True
@classmethod def type_of(cls, addr): if cls.is_valid_ipv4_network(addr): return IP.V4 elif cls.is_valid_ipv6_network(addr): return IP.V6
raise ValueError("Invalid ip address")
@classmethod def convert_to_ipv6_network(cls, ip, mask="/64"): """Conver ipv6 addr to ipv6 network with mask :param str ip: ip for converting :param str mask: ip network mask """
network = IPv6Network(ip + mask, strict=False) return str(network)
@staticmethod def adopt_to_ipvX_network( ip_arg: Union[str, IPv4Address, IPv4Network, IPv6Address, IPv6Network] ) -> Union[IPv4Network, IPv6Network]: """ Eliminate str from the Union :raise ValueError: if cannot convert ip_arg str to ip network """ if isinstance(ip_arg, (IPv4Network, IPv6Network)): return ip_arg elif isinstance(ip_arg, (IPv4Address, IPv6Address)): prefixlen = IPV4LENGTH if ip_arg.version == 4 else IPV6LENGTH return ip_network((int(ip_arg), prefixlen))
return ip_network(ip_arg)
@classmethod def ip_net_to_string(cls, net: Union[IPv4Network, IPv6Network]) -> str: """ IPv4Network('192.168.1.1/32') -> '192.168.1.1' IPv4Network('192.168.1.0/24') -> '192.168.1.0/24' """ if not int(net.hostmask): return str(net.network_address) return str(net)
@classmethod def ipv6_to_64network( cls, ip: Union[IPv4Address, IPv6Address, str] ) -> Union[IPv4Address, IPv6Network]: if isinstance(ip, IPv6Address): return IPv6Network(cls.convert_to_ipv6_network(str(ip))) return ip
|