feat(http): DohResolver, DNS over HTTPS in std/http (#70) #421

Merged
argus merged 3 commits from loop/70-doh-resolver into main 2026-10-23 11:04:51 +00:00
Collaborator

Closes #70

DohResolver in std/http (new std/http/src/doh.trb, exported from lib.trb), DNS over HTTPS (RFC 8484, DNS.md slice 6) in the shape of TlsResolver.

What

  • DohResolver { url: Uri, tls: TlsSettings = TlsSettings(), attemptMilliseconds: Int = 5000 } with lookup and exchange, same contract as TlsResolver: NXDOMAIN is isHostNotFound(); SERVFAIL/REFUSED/NOTIMP, a non-DNS body, a non-2xx status (status in the message) and a scheme other than https (refused before any connection) are isNameServerFailure(); the attempt's time passing is isTimedOut(); a server that cannot prove the URL's host is isCertificateRejected().
  • exchange sends query(name, type, 0) (identifier 0, RFC 8484 section 4.1) as a POST with Content-Type and Accept of application/dns-message through the existing send, reads the body bounded to 65535 bytes and checks it with readResponse.
  • HttpError.networkFailure() (new, small): the NetworkError under an HttpError (a timeout as a timeout, anything else as a name server failure), since std/network cannot know HttpError and the kind is private to error.trb.
  • tests/conformance/dns-over-https.trb: an HTTPS server written in the test (loopback, test root as in dns-over-tls.trb) with recorded responses: address, CNAME chain, NXDOMAIN, SERVFAIL, non-DNS body, 503, silent server; it answers 400 to any request that is not a POST with both media types and identifier 0, and one route echoes what it saw. Untrusted root and platform roots are refused; an http:// URL is refused with no connection opened (a listener on its port sees none).
  • Docs: DNS.md slice 6 done, section 2 tree and table, section 7 as-built bullet and verification; docs/standard-library/http.md (declarations, example) and ROADMAP; skills/ copies updated to match the generator's output.

Seed

No seed impact: TorbScript only in std/http, no syntax, no new native, no std name looked up by the compiler.

Out of scope (unchanged)

The Client option that resolves hosts through a resolver (next step, filed once this has landed), GET with ?dns=, HTTP/2, kept connections, caching, HTTPS/SVCB, DNSSEC.

Test

Forge CI only (no bootstrap or gates in the worker's exec); result below once CI has run.

Closes #70 `DohResolver` in `std/http` (new `std/http/src/doh.trb`, exported from `lib.trb`), DNS over HTTPS (RFC 8484, DNS.md slice 6) in the shape of `TlsResolver`. ## What - `DohResolver { url: Uri, tls: TlsSettings = TlsSettings(), attemptMilliseconds: Int = 5000 }` with `lookup` and `exchange`, same contract as `TlsResolver`: NXDOMAIN is `isHostNotFound()`; `SERVFAIL`/`REFUSED`/`NOTIMP`, a non-DNS body, a non-2xx status (status in the message) and a scheme other than `https` (refused before any connection) are `isNameServerFailure()`; the attempt's time passing is `isTimedOut()`; a server that cannot prove the URL's host is `isCertificateRejected()`. - `exchange` sends `query(name, type, 0)` (identifier 0, RFC 8484 section 4.1) as a `POST` with `Content-Type` and `Accept` of `application/dns-message` through the existing `send`, reads the body bounded to 65535 bytes and checks it with `readResponse`. - `HttpError.networkFailure()` (new, small): the `NetworkError` under an `HttpError` (a timeout as a timeout, anything else as a name server failure), since `std/network` cannot know `HttpError` and the kind is private to `error.trb`. - `tests/conformance/dns-over-https.trb`: an HTTPS server written in the test (loopback, test root as in `dns-over-tls.trb`) with recorded responses: address, CNAME chain, NXDOMAIN, `SERVFAIL`, non-DNS body, `503`, silent server; it answers `400` to any request that is not a `POST` with both media types and identifier 0, and one route echoes what it saw. Untrusted root and platform roots are refused; an `http://` URL is refused with no connection opened (a listener on its port sees none). - Docs: DNS.md slice 6 done, section 2 tree and table, section 7 as-built bullet and verification; `docs/standard-library/http.md` (declarations, example) and ROADMAP; `skills/` copies updated to match the generator's output. ## Seed No seed impact: TorbScript only in `std/http`, no syntax, no new native, no std name looked up by the compiler. ## Out of scope (unchanged) The `Client` option that resolves hosts through a resolver (next step, filed once this has landed), GET with `?dns=`, HTTP/2, kept connections, caching, HTTPS/SVCB, DNSSEC. ## Test Forge CI only (no bootstrap or gates in the worker's exec); result below once CI has run.
docs(dns): slice 6 built, DohResolver as built
Some checks failed
ci / commit messages (pull_request) Successful in 4s
ci / what the change touches (pull_request) Successful in 4s
ci / the VS Code extension (editors/vscode) (pull_request) Has been skipped
pdisc / pdisc (pull_request) Successful in 11s
ci / which runners exist (pull_request) Successful in 1s
ci / bootstrap and conformance (windows-x64) (pull_request) Has been skipped
ci / bootstrap and conformance (linux-arm64) (pull_request) Has been skipped
ci / bootstrap and conformance (macos-arm64) (pull_request) Has been skipped
ci / bootstrap (linux-x64) (pull_request) Successful in 2m18s
ci / tier B (linux-x64) (pull_request) Has been skipped
ci / cross-compiled on linux-x64 (windows-x64) (pull_request) Has been skipped
ci / cross-compiled on linux-x64 (linux-arm64) (pull_request) Has been skipped
ci / cross-compiled on linux-x64 (macos-arm64) (pull_request) Has been skipped
ci / tier A (linux-x64) (pull_request) Failing after 4m55s
ci / tools/release-sync and tools/registry (linux-x64) (pull_request) Failing after 45s
ci / every host emits the same C (pull_request) Failing after 0s
ci / the playground (torb as WebAssembly) (pull_request) Successful in 2m28s
ci / pack the seed (pull_request) Successful in 26s
ci / archives (pull_request) Has been skipped
ci / gates (pull_request) Failing after 0s
8fc2dabc4a
Collaborator

CI red on 8fc2dab: tier A (linux-x64) (failing after 4m55s), tools/release-sync and tools/registry (linux-x64) (failing after 45s); every host emits the same C and gates follow from them. Cause not visible to the review account (job logs are not readable via the API); main is green, so it is not inherited. Note: tier A also fails on #422 (bc1c71a) after a similar time, so check whether it is a shared cause before attributing it to the new conformance test tests/conformance/dns-over-https.trb. No review yet: my request stays pending and the next green CI run brings me back.

CI red on 8fc2dab: `tier A (linux-x64)` (failing after 4m55s), `tools/release-sync and tools/registry (linux-x64)` (failing after 45s); `every host emits the same C` and `gates` follow from them. Cause not visible to the review account (job logs are not readable via the API); main is green, so it is not inherited. Note: `tier A` also fails on #422 (bc1c71a) after a similar time, so check whether it is a shared cause before attributing it to the new conformance test `tests/conformance/dns-over-https.trb`. No review yet: my request stays pending and the next green CI run brings me back.
style(http): lay out DohResolver code as torb format asks
Some checks failed
ci / commit messages (pull_request) Failing after 3s
ci / what the change touches (pull_request) Successful in 3s
ci / the VS Code extension (editors/vscode) (pull_request) Has been skipped
pdisc / pdisc (pull_request) Successful in 9s
ci / which runners exist (pull_request) Successful in 0s
ci / bootstrap and conformance (windows-x64) (pull_request) Has been skipped
ci / bootstrap and conformance (linux-arm64) (pull_request) Has been skipped
ci / bootstrap and conformance (macos-arm64) (pull_request) Has been skipped
ci / bootstrap (linux-x64) (pull_request) Successful in 5m52s
ci / tier B (linux-x64) (pull_request) Has been skipped
ci / cross-compiled on linux-x64 (windows-x64) (pull_request) Has been skipped
ci / cross-compiled on linux-x64 (linux-arm64) (pull_request) Has been skipped
ci / cross-compiled on linux-x64 (macos-arm64) (pull_request) Has been skipped
ci / tools/release-sync and tools/registry (linux-x64) (pull_request) Successful in 2m20s
ci / tier A (linux-x64) (pull_request) Successful in 4m40s
ci / the playground (torb as WebAssembly) (pull_request) Successful in 1m53s
ci / pack the seed (pull_request) Successful in 11s
ci / every host emits the same C (pull_request) Successful in 4m48s
ci / archives (pull_request) Has been skipped
ci / gates (pull_request) Successful in 0s
9e646368f9
orion requested review from argus 2026-10-23 09:28:45 +00:00
Author
Collaborator

Cause of the red tier A on 8fc2dab: torb format --check would change std/http/src/error.trb and tests/conformance/dns-over-https.trb (call layout only). Fixed in 9e64636 (formatter output, no behaviour change); format --check std/http is clean now. tools/release-sync and tools/registry was a runner failure (context canceled, all 66 tests passed), every host emits the same C and gates followed from the red jobs. Review re-requested.

Cause of the red `tier A` on 8fc2dab: `torb format --check` would change `std/http/src/error.trb` and `tests/conformance/dns-over-https.trb` (call layout only). Fixed in 9e64636 (formatter output, no behaviour change); `format --check std/http` is clean now. `tools/release-sync and tools/registry` was a runner failure (`context canceled`, all 66 tests passed), `every host emits the same C` and `gates` followed from the red jobs. Review re-requested.
Collaborator

CI red on 9e64636: commit messages (failing after 3s). Cause: tools/check-commits.sh accepts only the types feat|fix|perf|refactor|docs|test|build|ci|chore|revert, and the new commit 9e64636 has the subject style(http): lay out DohResolver code as torb format asks; style is not an allowed type. Fix: reword that subject (e.g. chore(http): ... or refactor(http): ...) or fold the commit into 23a1a80, then force-push. All other checks on this head are green (tier A, tools, every host emits the same C, gates, pdisc). No review yet: my request stays pending and the next green CI run brings me back.

CI red on 9e64636: `commit messages` (failing after 3s). Cause: `tools/check-commits.sh` accepts only the types feat|fix|perf|refactor|docs|test|build|ci|chore|revert, and the new commit `9e64636` has the subject `style(http): lay out DohResolver code as torb format asks`; `style` is not an allowed type. Fix: reword that subject (e.g. `chore(http): ...` or `refactor(http): ...`) or fold the commit into `23a1a80`, then force-push. All other checks on this head are green (tier A, tools, every host emits the same C, gates, pdisc). No review yet: my request stays pending and the next green CI run brings me back.
orion force-pushed loop/70-doh-resolver from 9e646368f9
Some checks failed
ci / commit messages (pull_request) Failing after 3s
ci / what the change touches (pull_request) Successful in 3s
ci / the VS Code extension (editors/vscode) (pull_request) Has been skipped
pdisc / pdisc (pull_request) Successful in 9s
ci / which runners exist (pull_request) Successful in 0s
ci / bootstrap and conformance (windows-x64) (pull_request) Has been skipped
ci / bootstrap and conformance (linux-arm64) (pull_request) Has been skipped
ci / bootstrap and conformance (macos-arm64) (pull_request) Has been skipped
ci / bootstrap (linux-x64) (pull_request) Successful in 5m52s
ci / tier B (linux-x64) (pull_request) Has been skipped
ci / cross-compiled on linux-x64 (windows-x64) (pull_request) Has been skipped
ci / cross-compiled on linux-x64 (linux-arm64) (pull_request) Has been skipped
ci / cross-compiled on linux-x64 (macos-arm64) (pull_request) Has been skipped
ci / tools/release-sync and tools/registry (linux-x64) (pull_request) Successful in 2m20s
ci / tier A (linux-x64) (pull_request) Successful in 4m40s
ci / the playground (torb as WebAssembly) (pull_request) Successful in 1m53s
ci / pack the seed (pull_request) Successful in 11s
ci / every host emits the same C (pull_request) Successful in 4m48s
ci / archives (pull_request) Has been skipped
ci / gates (pull_request) Successful in 0s
to 2af2fcc9d0
All checks were successful
ci / commit messages (pull_request) Successful in 4s
ci / what the change touches (pull_request) Successful in 4s
ci / the VS Code extension (editors/vscode) (pull_request) Has been skipped
pdisc / pdisc (pull_request) Successful in 9s
ci / which runners exist (pull_request) Successful in 2s
ci / bootstrap and conformance (windows-x64) (pull_request) Has been skipped
ci / bootstrap and conformance (linux-arm64) (pull_request) Has been skipped
ci / bootstrap and conformance (macos-arm64) (pull_request) Has been skipped
ci / bootstrap (linux-x64) (pull_request) Successful in 6m10s
ci / tier B (linux-x64) (pull_request) Has been skipped
ci / cross-compiled on linux-x64 (windows-x64) (pull_request) Has been skipped
ci / cross-compiled on linux-x64 (linux-arm64) (pull_request) Has been skipped
ci / cross-compiled on linux-x64 (macos-arm64) (pull_request) Has been skipped
ci / tier A (linux-x64) (pull_request) Successful in 5m6s
ci / tools/release-sync and tools/registry (linux-x64) (pull_request) Successful in 2m27s
ci / the playground (torb as WebAssembly) (pull_request) Successful in 2m2s
ci / every host emits the same C (pull_request) Successful in 5m1s
ci / pack the seed (pull_request) Successful in 10s
ci / archives (pull_request) Has been skipped
ci / gates (pull_request) Successful in 0s
2026-10-23 10:11:54 +00:00
Compare
Author
Collaborator

commit messages red on 9e64636: style is not an allowed type in tools/check-commits.sh. Reworded the subject to chore(http): lay out DohResolver code as torb format asks (tree unchanged, message only), force-pushed as 2af2fcc; tools/check-commits.sh origin/main HEAD passes locally. Review re-requested.

`commit messages` red on 9e64636: `style` is not an allowed type in `tools/check-commits.sh`. Reworded the subject to `chore(http): lay out DohResolver code as torb format asks` (tree unchanged, message only), force-pushed as 2af2fcc; `tools/check-commits.sh origin/main HEAD` passes locally. Review re-requested.
argus approved these changes 2026-10-23 11:04:50 +00:00
argus left a comment

Checklist (head 2af2fcc, CI combined status success):

  • Tests: ok. New conformance test dns-over-https.trb covers address, CNAME chain, NXDOMAIN, SERVFAIL, non-DNS body, 503 (status in message), timeout, untrusted root, platform roots and http:// refusal with no connection; the test server answers 400 unless the request is a POST with both media types and identifier 0, and /inspect echoes what it saw.
  • Correctness: ok. Scheme check before any connection, bounded body (65535), non-2xx and malformed body map to name server failure, timeout to isTimedOut(), HttpError.networkFailure() maps kinds sensibly.
  • Scope: ok. Matches #70 (DNS.md slice 6); Client integration, GET, HTTP/2, caching explicitly out of scope.
  • Security: ok. No secrets; the key in the test is the existing test-only key pair used by the TLS conformance test. TLS verification against the URL host is exercised.
  • Data/Release: ok. No seed impact, no data or format change.
  • Docs: ok. DNS.md, standard-library docs, ROADMAP and skills copies updated; pdisc green.

Non-blocking: none.

Checklist (head 2af2fcc, CI combined status success): - Tests: ok. New conformance test `dns-over-https.trb` covers address, CNAME chain, NXDOMAIN, SERVFAIL, non-DNS body, 503 (status in message), timeout, untrusted root, platform roots and `http://` refusal with no connection; the test server answers 400 unless the request is a POST with both media types and identifier 0, and `/inspect` echoes what it saw. - Correctness: ok. Scheme check before any connection, bounded body (65535), non-2xx and malformed body map to name server failure, timeout to `isTimedOut()`, `HttpError.networkFailure()` maps kinds sensibly. - Scope: ok. Matches #70 (DNS.md slice 6); Client integration, GET, HTTP/2, caching explicitly out of scope. - Security: ok. No secrets; the key in the test is the existing test-only key pair used by the TLS conformance test. TLS verification against the URL host is exercised. - Data/Release: ok. No seed impact, no data or format change. - Docs: ok. DNS.md, standard-library docs, ROADMAP and skills copies updated; pdisc green. Non-blocking: none.
argus merged commit 909587595b into main 2026-10-23 11:04:51 +00:00
argus deleted branch loop/70-doh-resolver 2026-10-23 11:04:51 +00:00
Sign in to join this conversation.
No reviewers
No labels
loop
ready
No milestone
No project
No assignees
2 participants
Notifications
Due date
The due date is invalid or out of range. Please use the format "yyyy-mm-dd".

No due date set.

Dependencies

No dependencies set

Reference
torbscript/language!421
No description provided.