Skip to content

Commit

Permalink
fix(irc-puppet): pick a random IPv6 address to connect to IRC hosts (#…
Browse files Browse the repository at this point in the history
  • Loading branch information
TrueBrain authored Mar 14, 2024
1 parent 43d3ce6 commit fc5c9f5
Showing 1 changed file with 35 additions and 4 deletions.
39 changes: 35 additions & 4 deletions dibridge/irc_puppet.py
Original file line number Diff line number Diff line change
@@ -1,6 +1,7 @@
import asyncio
import irc.client_aio
import logging
import random
import socket


Expand Down Expand Up @@ -135,20 +136,50 @@ async def reclaim_nick(self):
self._client.nick(self._nickname)

async def connect(self):
self._log.info("Connecting to IRC from %s ...", self._ipv6_address)

local_addr = (str(self._ipv6_address), 0)
use_ssl = self._irc_port == 6697

while self._reconnect:
# As per RFC, getaddrinfo() sorts IPv6 results in some complicated way.
# In result, even if the IRC host has multiple IPv6 addresses listed,
# we will pick almost always the same one. This gives unneeded pressure
# on a single host, instead of distributing the load. So instead, we do
# the lookup ourselves, and pick a random one.
try:
await self.connection.connect(
ipv6s = await self.loop.getaddrinfo(
self._irc_host,
None,
family=socket.AF_INET6,
type=socket.SOCK_STREAM,
proto=socket.IPPROTO_TCP,
)
except socket.gaierror:
ipv6s = []

if not ipv6s:
self._log.warning("Failed DNS lookup, retrying in 5 seconds")
# When we can't connect, try again in 5 seconds.
await asyncio.sleep(5)
continue

irc_host_ipv6 = random.choice(ipv6s)[4][0]

self._log.info(
"Connecting to IRC from %s to %s (%s) ...", self._ipv6_address, self._irc_host, irc_host_ipv6
)

try:
await self.connection.connect(
irc_host_ipv6,
self._irc_port,
self._nickname,
username=self._username,
# We force an IPv6 connection, as we need that for the puppet source address.
connect_factory=irc.connection.AioFactory(
family=socket.AF_INET6, local_addr=local_addr, ssl=self._irc_port == 6697
family=socket.AF_INET6,
local_addr=local_addr,
ssl=use_ssl,
server_hostname=self._irc_host if use_ssl else None,
),
)
break
Expand Down

0 comments on commit fc5c9f5

Please sign in to comment.