Repository navigation
Add socket module - #5
Conversation
| _FAMILY_TO_STR = { | ||
| socket.AF_INET: "IPv4", | ||
| socket.AF_INET6: "IPv6", | ||
| socket.AF_UNIX: "Unix" | ||
| } | ||
|
|
||
| _IP_VERSION_TO_FAMILY = { | ||
| 4: socket.AF_INET, | ||
| 6: socket.AF_INET6, | ||
| 0: socket.AF_UNSPEC | ||
| } |
There was a problem hiding this comment.
I'd suggest using enums.
Either a single one by doing a complex enum class:
class AddressFamily(Enum):
# (member name) = (family, ip_version, display_str)
IPV4 = (socket.AF_INET, 4, "IPv4")
IPV6 = (socket.AF_INET6, 6, "IPv6")
UNIX = (socket.AF_UNIX, None, "Unix")
UNSPEC = (socket.AF_UNSPEC, 0, "Unknown")
def __init__(self, family: socket.AddressFamily, ip_version: int, display_str: str):
self.family = family
self.ip_version = ip_version
self.display_str = display_str
# Build the map on lookup
@classmethod
def _missing_(cls: type['AddressFamily'], value: Union[socket.AddressFamily, int, str, None]) -> 'AddressFamily':
if not hasattr(cls, '_lookup_map'):
cls._lookup_map: Dict[Union[socket.AddressFamily, int, str], AddressFamily] = {}
for member in cls:
cls._lookup_map[str(member.family)] = member
cls._lookup_map[member.display_str] = member
if member.ip_version is None:
cls._lookup_map[str(member.ip_version)] = member
else:
cls._lookup_map[member.ip_version] = member
# cast to str to prevent collision between family (which is an int) and ip_version
if value is None or isinstance(value, socket.AddressFamily):
value = str(value)
return cls._lookup_map.get(value, cls.UNSPEC)Usage:
def get_socket_family_str(sock: socket.socket) -> str:
return AddressFamily(sock.family).display_str
[...]
family = AddressFamily(ip_version).familyOr using two enums:
class AddressFamily(Enum):
IPv4 = socket.AF_INET
IPv6 = socket.AF_INET6
Unix = socket.AF_UNIX
class IPVersion(Enum):
IPv4 = 4
IPv6 = 6
UNSPEC = 0
@property
def family(self) -> int:
match self:
case IPVersion.IPv4: return socket.AF_INET
case IPVersion.IPv6: return socket.AF_INET6
case IPVersion.UNSPEC: return socket.AF_UNSPECUsage:
def get_socket_family_str(sock: socket.socket) -> str:
return AddressFamily(sock.family).name
[...]
family = IPVersion(ip_version).familyThere was a problem hiding this comment.
It sounds like you're suggesting a new API (which, unfortunately, I have no use for) for the code I haven't pushed yet. I'm open to a new contribution to this module, but in that case, additional tests would be required.
For the short to medium term, I simply need functions that allow me to construct an IP address or display information from a socket.
There was a problem hiding this comment.
I understand, no problem. Just to be clear the intent was to push the usage of enums as early as possible in the project when they could be fit.
But indeed this is something than can be sorted out in the longer term if there's a need.
624e99f to
75220ca
Compare
c8227a6 to
66389b6
Compare
df8abd0 to
8b79b52
Compare
7d96833 to
45117bb
Compare
af38028 to
e4fad85
Compare
16c6e30 to
aac27b1
Compare
6b8de28 to
bbf7146
Compare
Signed-off-by: Ronan Abhamon <ronan.abhamon@vates.tech>
Must be merged after #20.