fix: patch pymumble protocol version and harden mumble connections
- Update reported protocol version from 1.2.4 to 1.5.0 so modern Murmur servers treat PyMumble as a compatible client - Fix OS string to report actual platform instead of "PyMumble 1.6.1" (was shown as [Invalid] by Murmur) - Raise pymumble reconnect retry interval to 15s to prevent autoban when running multiple bots from the same IP - Enable TCP keepalive on control socket (10s idle) to prevent NAT gateways from dropping long-lived connections Co-Authored-By: Claude Opus 4.6 <noreply@anthropic.com>
This commit is contained in:
@@ -2,6 +2,7 @@
|
||||
|
||||
1. pymumble: ssl.wrap_socket was removed in 3.13
|
||||
2. opuslib: ctypes.util.find_library fails on musl-based distros
|
||||
3. pymumble: protocol version 1.2.4 is rejected by modern servers
|
||||
"""
|
||||
|
||||
import pathlib
|
||||
@@ -65,5 +66,29 @@ new_init = """\
|
||||
self.control_socket = None"""
|
||||
|
||||
assert old_init in src, "pymumble init_connection socket patch target not found"
|
||||
p.write_text(src.replace(old_init, new_init))
|
||||
src = src.replace(old_init, new_init)
|
||||
print("pymumble reconnect socket patch applied")
|
||||
|
||||
p.write_text(src)
|
||||
|
||||
# -- pymumble: report modern protocol version --
|
||||
# PyMumble 1.6.1 reports protocol version 1.2.4, which modern Murmur
|
||||
# (1.5.x) treats as an invalid/legacy client. Update to 1.5.0 so the
|
||||
# server enables full feature set and stops sending warnings.
|
||||
p = pathlib.Path(f"{site}/pymumble_py3/constants.py")
|
||||
src = p.read_text()
|
||||
|
||||
old_ver = "PYMUMBLE_PROTOCOL_VERSION = (1, 2, 4)"
|
||||
new_ver = "PYMUMBLE_PROTOCOL_VERSION = (1, 5, 0)"
|
||||
|
||||
assert old_ver in src, "pymumble version patch target not found"
|
||||
src = src.replace(old_ver, new_ver)
|
||||
|
||||
old_os = 'PYMUMBLE_OS_STRING = "PyMumble %s" % PYMUMBLE_VERSION'
|
||||
new_os = 'PYMUMBLE_OS_STRING = platform.system()'
|
||||
|
||||
assert old_os in src, "pymumble OS string patch target not found"
|
||||
src = src.replace(old_os, new_os)
|
||||
|
||||
p.write_text(src)
|
||||
print("pymumble version patch applied (1.5.0, native OS string)")
|
||||
|
||||
@@ -218,11 +218,27 @@ class MumbleBot:
|
||||
self._on_sound_received,
|
||||
)
|
||||
self._mumble.set_receive_sound(self._receive_sound)
|
||||
# Raise retry interval so 2+ bots on the same IP don't trip
|
||||
# the server's autoban (default: 10 attempts / 120s).
|
||||
import pymumble_py3.mumble as _pm
|
||||
if getattr(_pm, "PYMUMBLE_CONNECTION_RETRY_INTERVAL", 0) < 15:
|
||||
_pm.PYMUMBLE_CONNECTION_RETRY_INTERVAL = 15
|
||||
self._mumble.start()
|
||||
self._mumble.is_ready()
|
||||
|
||||
def _on_connected(self) -> None:
|
||||
"""Callback from pymumble thread: connection established."""
|
||||
# Enable TCP keepalive on the control socket to prevent NAT
|
||||
# gateways from dropping the mapping during idle periods.
|
||||
try:
|
||||
import socket as _sock
|
||||
raw = self._mumble.control_socket
|
||||
raw.setsockopt(_sock.SOL_SOCKET, _sock.SO_KEEPALIVE, 1)
|
||||
raw.setsockopt(_sock.IPPROTO_TCP, _sock.TCP_KEEPIDLE, 10)
|
||||
raw.setsockopt(_sock.IPPROTO_TCP, _sock.TCP_KEEPINTVL, 5)
|
||||
raw.setsockopt(_sock.IPPROTO_TCP, _sock.TCP_KEEPCNT, 3)
|
||||
except Exception:
|
||||
pass
|
||||
self._connect_count += 1
|
||||
kind = "reconnected" if self._connect_count > 1 else "connected"
|
||||
session = getattr(self._mumble.users, "myself_session", "?")
|
||||
|
||||
Reference in New Issue
Block a user