Skip to content

Deterministic IPv6 external-IP discovery #220

Closed

Description

@bluet

Background

Surfaced in PR #212 review by @chatgpt-codex-connector (resolver.py:43 thread):

On a dual-stack host this new IPv6-capable service is still selected through _pop_random_ip_host(), so most runs can hit one of the IPv4-only endpoints and store the IPv4 external address. Since Judge.check() later accepts a judge only when that single real_ext_ip appears in the page, any judge reached over IPv6 will be rejected even though IPv6 works.

Why this needs its own ticket

Adding api64.ipify.org to _ip_hosts (PR #212) was a necessary first step — the resolver no longer rejects IPv6 responses. But _pop_random_ip_host() still picks uniformly at random, so on a dual-stack host you get IPv4 ext-IP about 80% of the time (4 of 5 default hosts are v4-only).

The right fix is a design choice with at least three reasonable options:

  1. Prefer api64.ipify.org first (deterministic). Try it; only fall back to others if it fails. Simplest, but loses load-balancing across services.
  2. Probe both v4 and v6 separately and store both real_ext_ip_v4 + real_ext_ip_v6. Judge.check() then accepts whichever appears on the page. Most correct for dual-stack hosts but requires plumbing two values through the comparison sites.
  3. Happy Eyeballs at the IP-discovery layer (race the v4 and v6 probes in parallel, take the first to succeed). Mirrors the DNS layer behavior added in PR feat(ipv6): full IPv6 support across the stack (#201) #212.

Each has different trade-offs (latency, cost, code complexity, observability). PR #212's scope was 'IPv6 first-class across the stack' — this is a follow-up refinement.

Acceptance criteria

  • A user on a dual-stack host running Resolver().get_real_ext_ip() reliably gets an address whose family matches the network the broker will then connect to judges over.
  • If only one family is reachable, that one wins (no false-negative rejections in Judge.check()).
  • Existing IPv4-only contracts preserved (caller passing family=AF_INET or similar should be respected if/when introduced).

Activity

  1. added a commit that references this issue on May 10, 2026
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Metadata

Metadata

Assignees

No one assigned

    Labels

    enhancementNew feature or request

    Projects

    No projects

      Milestone

      No milestone

      Relationships

      None yet

      Development

      No branches or pull requests

      Issue actions