The leak-test page says your DNS is fine, the browser badge says secure, and the internal wiki still will not load. All three can be true at once, because a resolver's address is not the same thing as the policy that selected it or the path the query travelled. What people call a DNS leak is really one question: which resolver received the name, and was that choice intentional? Sorting that out takes three checks, and only the last one involves changing a setting.

Myth one: the badge names your resolver

A leak test resolves a probe name and reports the address that answered. It does not report the policy that chose that resolver, and when the query is wrapped in DNS over HTTPS a middlebox on the path cannot see the name at all. Two very different machines produce the same reassuring badge: one where the VPN pushed 10.8.0.1 and the browser uses it, and one where the browser ignored the system list and sent the name to its own encrypted provider through the tunnel.

The distinction matters the moment a private name fails. In the first setup the VPN resolver answers for the corporate zone; in the second the browser never asked it, so the short hostname does not resolve and the failure looks like a broken VPN. The check is not another leak test, it is a lookup against a name only one resolver knows.

Myth two: the browser leaves the tunnel

DNS chooses an address, routing carries the connection, and the two are separate layers. A query sent to a public DoH provider is still TCP port 443 to a routable address. If your route table sends the default route into the tunnel, that query goes through the tunnel too. The resolver brand does not decide the path.

What browser DoH changes is the recipient of the names. That is a real privacy decision and a real policy decision, but it is not a routing bypass. If your requirement is that names stay with the VPN operator, an encrypted query to somebody else fails that requirement while still using the tunnel for the actual connection.

Myth three: every VPN overrides every browser

Secure DNS in a browser has modes, not a switch: off, a default provider with fallback, a custom template, or a policy enforced by the operating system or the organization. The fallback case is the one that produces intermittent reports. When the encrypted endpoint is unreachable, the browser may fall back to the system resolver, so the same laptop resolves a private name correctly on Monday and not on Tuesday.

At the same time, most VPN clients set the system resolver when the connection comes up and restore the previous one when it drops. A browser holding a custom encrypted resolver does not observe that restore at all. This is why the same profile behaves differently on two laptops and why resolv.conf looks correct while the browser still asks somebody else.

resolvectl status                 # per-link DNS servers and split-DNS domains
scutil --dns | head -30           # macOS resolver order for each domain
nslookup intranet.corp 10.8.0.1   # ask the VPN resolver directly

Run those while connected, note the domains each resolver claims, and compare with what the browser reports about its own mode. Mozilla's DoH documentation is a reasonable description of how a browser's default and fallback behaviour is meant to work.

The decision has three inputs, not one

Private names, operator trust and reachability decide the right arrangement. Names that only the VPN resolver knows force split DNS: the private suffix goes to the pushed resolver, everything else follows whatever policy you picked for public names. Operator trust decides whether public names should also go to that resolver or to a separate service. Reachability decides whether your chosen encrypted resolver is even usable on this network.

ConditionWhat it forces
Internal names must resolveSplit DNS: private suffixes to the VPN resolver, the rest to your chosen default
Queries must stay with one operatorPin both the system resolver and the browser mode, and disable fallback
Resolver only reachable through the tunnelKeep the pushed resolver; do not point DoH at an endpoint your routes exclude

None of these rows is a universal recommendation. A resolver operated by the VPN concentrates observations with that operator; a separate service adds another recipient of queried names. Neither arrangement proves anything about retention unless you read the policy.

Write the decision down per profile, because these settings drift. A profile that pushed a resolver last month may push nothing today, and the browser will happily keep an old custom endpoint that still answers. What belongs in the note is the resolver address, the suffixes it owns and the browser mode, not the brand of the service.

Test the policy you think you configured

Test by name, not by badge. Resolve a public name and a private name through the system resolver, then repeat inside the browser with its own secure DNS setting at the mode you intend to use. If the private name fails only in the browser, you have found the recipient mismatch without touching a single VPN setting.

Then reconnect and check restoration, because that is where handoff bugs live: disconnect, confirm the previous resolver came back, reconnect, confirm the pushed one returned. Finally, test a browser with a managed policy if you have one, since that mode may refuse your change entirely and quietly keep the previous resolver.

Start with the namespace question and you will avoid most of this. If the machine has to reach internal names, the browser's encrypted resolver is a decision about the public half only, and the private half stays with whatever the VPN pushed.

Makomi ya ndenge moko