Skip to content

Add an Android ECH suite - #4

Merged
yschimke merged 1 commit into
mainfrom
claude/okhttp-testbed-test-6uwzei
Aug 13, 2026
Merged

Add an Android ECH suite#4
yschimke merged 1 commit into
mainfrom
claude/okhttp-testbed-test-6uwzei

Conversation

@yschimke

Copy link
Copy Markdown
Owner

Ports the Encrypted Client Hello test from lysine-dev/okhttp#9652 into the testbed, which is where a container-based test belongs.

What it tests

A DoH resolver answering HTTPS records that carry an ECH config list, and an origin that reports back whether the handshake it accepted used ECH. Three hostnames, three outcomes:

Host Published config Origin offers Expected
green.secret.test current ECH accepted first try
retry.secret.test stale a retry config retried, ECH accepted
disabled.secret.test stale nothing falls back without ECH

Shape

ECH is applied on Android only — JVM platforms take the config list and ignore it — so these are instrumentation tests on API 37, and there is nothing here for the containers suite to assert.

  • ech-fixture — the Go program behind both containers, plus the host-side process that starts them. Not a suite: the device that runs the tests has no Docker, so the containers live on the host, and the fixture publishes its ports and the fixture CA to a file and stays up until that file is deleted.
  • android-ech — the instrumentation tests, public API only (OkHttpClient, Request, DnsOverHttps), under okhttp.testbed.android.ech.
  • android-ech/run-ech-test.sh — starts the fixture, bridges the ports with adb reverse, runs the tests. --smoke-only stops after the fixture is up, for a machine with no emulator.
  • .github/workflows/android-ech.yml — its own workflow on an API 37 emulator, on the same events as containers plus its own daily schedule. Separate so a flaky emulator doesn't colour the container suites.

Version

This suite tests 5.5.0-SNAPSHOT by default, carried as a separate ech-okhttp entry in the catalog. It needs DnsOverHttps.Builder.includeServiceMetadata, and no release has it — 5.4.0 resolves A and AAAA only, so there is no HTTPS record to carry a config list. -PokhttpVersion still overrides, and ech-okhttp can go away once a release ships the API.

Build changes

AGP can't share the root's Kotlin plugin, so suites now apply their own and the root reacts to whichever they applied. The public-API check still applies to every module, and is now wired to connected…AndroidTest as well as check, which doesn't cover instrumentation tests.

Verification

No Docker daemon or emulator in this environment, so the suite has not been run. What was checked: :ech-fixture:compileKotlin, :android-ech:assembleDebugAndroidTest (resolves the snapshot and compiles EncryptedClientHelloTest into the test APK — confirmed in the dex), :containers:compileTestKotlin and checkPublicApiOnly still green, checkPublicApiOnly confirmed in connectedDebugAndroidTest's task graph, the Go fixture built under Go 1.25, and bash -n on the script. The first CI run is the real check.


Generated by Claude Code

Encrypted Client Hello, end to end, against containers: a DoH resolver
answering HTTPS records that carry an ECH config list, and an origin that
reports whether the handshake it accepted used ECH. Three hostnames cover
the three outcomes — accepted, rejected then retried with the origin's
config, and rejected with no config on offer, which should fall back to a
handshake without ECH.

This came from square/okhttp, where container-based tests aren't wanted in
the main test suite. That is what this repository is for.

ECH is applied on Android only — JVM platforms take the config list and
ignore it — so the tests are instrumentation tests on API 37, and the
containers run on the host with `adb reverse` bridging the two. The fixture
is therefore its own module: a process that starts the containers, publishes
its ports and CA to a file, and stays up until that file is deleted.
`run-ech-test.sh` drives it, and `--smoke-only` covers a machine with no
emulator.

The suite tests 5.5.0-SNAPSHOT rather than the pinned release: it needs
`DnsOverHttps.Builder.includeServiceMetadata`, and 5.4.0 resolves A and AAAA
records only, so there is no HTTPS record to carry a config list.

Suites now bring their own Kotlin plugin, since an Android module can't
share one with the JVM suites; the public-API check applies to all of them
either way, and is wired to `connected…AndroidTest` as well as to `check`.

Co-Authored-By: Claude Opus 5 <noreply@anthropic.com>
Claude-Session: https://claude.ai/code/session_01FY1TEudFJ4vQfrfLWA5w3V
@yschimke
yschimke merged commit 507fc17 into main Aug 13, 2026
2 checks passed
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

None yet

Projects

None yet

Development

Successfully merging this pull request may close these issues.

2 participants