Advertisement
Not a member of Pastebin yet?
Sign Up,
it unlocks many cool features!
- ###changelog
- ###removed server name from relayed msg
- ###added authentication
- import socket
- import threading
- import time
- import time
- from threading import Lock
- # Configuration for rate limiting (minimum delay in seconds)
- RATE_LIMIT = .5 # Minimum 1.5 seconds between messages per channel/server
- # Dictionary to track last sent times: {server_host: {channel: timestamp}}
- last_sent_times = {}
- rate_limit_lock = Lock() # Ensure thread safety for the shared dictionary
- # Configuration for multiple servers. VERY CASE SENSITIVE FYI
- servers = [
- {
- "host": "irc.rizon.net",
- "port": 6667,
- "nickname": "BridgeBT",
- "password": "",
- "channels": ["#shitposters","#/g/autism","#pleb", "#/g/tv", "#perwl", "#playchan", "#steam"]
- },
- {
- "host": "irc.inet.tele.dk",
- "port": 6667,
- "nickname": "BridgeBT",
- "password": "",
- "channels": ["#2600","#IRC30","#asians", "#hax", "#headshop"]
- }
- ]
- # Shared dictionary to track active connections
- connections = {}
- def parse_message(data, host, channels):
- """
- Parse the raw IRC message to extract user, channel, and message.
- Returns (user, channel, message) or (None, None, None) if the message isn't relevant.
- """
- if "PRIVMSG" in data:
- parts = data.split(":", 2)
- if len(parts) < 3:
- return None, None, None
- prefix = parts[1].split(" ")
- if len(prefix) < 3:
- #logging.warning(f"Received malformed message: {data.strip()}")
- return None, None, None
- user = prefix[0].split("!")[0]
- channel = prefix[2]
- message = parts[2]
- #logging.debug(f"Parsed message from {user} in channel {channel}: {message}")
- # Only process the message if it is from a valid channel in the server
- if channel in channels:
- return user, channel, message
- return None, None, None
- def relay_message(message, source_server, source_channel=None):
- """
- Relay the message to all other channels on all other servers.
- Avoid relaying back to the source server and its channels.
- If `source_channel` is provided, it will relay the message within the same server to other channels.
- """
- print(f"DEBUG: Relaying message '{message}' from {source_channel} on server {source_server['host']}")
- current_time = time.time()
- for server_config in servers:
- host = server_config["host"]
- if host not in last_sent_times:
- last_sent_times[host] = {}
- irc = connections.get(host)
- if not irc:
- continue # Skip if no active connection
- # Cross-server relay
- if server_config["host"] != source_server["host"]:
- for target_channel in server_config["channels"]:
- with rate_limit_lock:
- last_sent = last_sent_times[host].get(target_channel, 0)
- if current_time - last_sent >= RATE_LIMIT:
- irc.send(f"PRIVMSG {target_channel} :{message}\r\n".encode("utf-8"))
- print(f"DEBUG: Sent message to {target_channel} on {host}")
- with rate_limit_lock:
- last_sent_times[host][target_channel] = current_time
- # Intra-server relay
- elif source_channel: # Relay within the same server if source_channel is provided
- for target_channel in server_config["channels"]:
- if target_channel != source_channel: # Avoid sending back to source channel
- with rate_limit_lock:
- last_sent = last_sent_times[host].get(target_channel, 0)
- if current_time - last_sent >= RATE_LIMIT:
- irc.send(f"PRIVMSG {target_channel} :{message}\r\n".encode("utf-8"))
- print(f"DEBUG: Relayed within {host} to {target_channel}")
- with rate_limit_lock:
- last_sent_times[host][target_channel] = current_time
- def handle_server(server_config):
- """
- Connect to a single IRC server and handle messages for relaying.
- """
- host = server_config["host"]
- port = server_config["port"]
- nickname = server_config["nickname"]
- password = server_config["password"]
- channels = server_config["channels"]
- irc = socket.socket(socket.AF_INET, socket.SOCK_STREAM)
- irc.connect((host, port))
- irc.send(f"NICK {nickname}\r\n".encode("utf-8"))
- irc.send(f"USER {nickname} 0 * :Bridge Bot\r\n".encode("utf-8"))
- # Identify with NickServ
- irc.send(f"PRIVMSG NickServ IDENTIFY {password}\r\n".encode("utf-8"))
- # Save the connection object in the global dict for later use
- connections[host] = irc
- while True:
- data = irc.recv(2048).decode("utf-8", errors="ignore")
- print(f"[{host}] Received: {data.strip()}")
- # Respond to PING
- if data.startswith("PING"):
- irc.send(f"PONG {data.split()[1]}\r\n".encode("utf-8"))
- #ident
- if "This nickname is registered" in data or "please choose a different nick" in data:
- irc.send(f"PRIVMSG NickServ :IDENTIFY {password}\r\n".encode("utf-8"))
- identified = True
- continue
- # Join channels upon successful connection
- if "001" in data: # 001 = Successful connection
- for channel in channels:
- irc.send(f"JOIN {channel}\r\n".encode("utf-8"))
- # Relay messages across servers and within the same server's channels
- user, channel, message = parse_message(data, host, channels)
- if user and message:
- relay_message(f"<{user}> {message}", server_config, channel)
- # Start a thread for each server
- for server_config in servers:
- threading.Thread(target=handle_server, args=(server_config,), daemon=True).start()
- # Keep the main thread alive
- while True:
- time.sleep(1) # Sleep to prevent the main thread from exiting
Advertisement
Add Comment
Please, Sign In to add comment
Advertisement