"""mumble — INSTALL overlay (Phase 1e HC3): assertion-only + additive, runs alongside the generic install tier (which proves the mumble-web HTTP sidecar serves over Traefik — the readiness signal). This overlay ADDS the assertion that mumble's actual purpose — the voice server — is up: the murmur control channel accepts a TLS connection on the host-published 64738. F2-14c: the install tier runs against the upgrade BASE, which is the previous published version 0.2.0+v1.6.870-0. That version PREDATES compose.host-ports.yml (added upstream in 1.0.0), so the base deploys minimally without it and the voice port is NOT host-published — this on-host voice check is then not applicable on the base and is SKIPPED (recorded). The voice server is asserted listening on the post-upgrade LATEST via the READY_PROBE (tcp 3x, gates backup) and the custom-tier full TLS protocol handshake. When this overlay runs against a host-ports deploy (latest), it asserts the listening server. """ import os import socket import sys import time import pytest sys.path.insert(0, os.path.join(os.path.dirname(__file__), "..", "..", "runner")) from harness import abra # noqa: E402 def test_voice_server_listening(live_app): cf = abra.env_get(live_app, "COMPOSE_FILE") or "" if "compose.host-ports.yml" not in cf: pytest.skip( "upgrade base (0.2.0) predates compose.host-ports.yml (added in 1.0.0) → voice port not " "host-published; voice listening asserted on post-upgrade latest (READY_PROBE tcp 3x + " "custom-tier protocol handshake)" ) deadline = time.time() + 120 last_err = None while time.time() < deadline: try: with socket.create_connection(("127.0.0.1", 64738), timeout=10): return except OSError as e: # noqa: PERF203 last_err = e time.sleep(3) raise AssertionError( f"mumble voice server not listening on 127.0.0.1:64738 after install — {last_err}" )