How to Self-Host Plausible Analytics With Docker Compose
Plausible Community Edition (CE) is the self-hosted version of Plausible, a web analytics service. Docker Compose uses a configuration file to run…
On your home network, Pi-hole can use local DNS, which maps names to network addresses, to point a service name such as media.example.com to Caddy. Caddy receives web requests for that name and forwards them to the right service. A reverse proxy like Caddy sits between a browser and a service, directing each request to the correct destination.
To use the same name inside and outside your home, configure Pi-hole to return Caddy’s private network address to devices at home. Configure public DNS to return your home’s public address, and route incoming web traffic from your router to Caddy. This setup is called split-horizon DNS: it directs clients to different addresses depending on whether they are at home or outside, but it does not control who can access a service. The sections below show how to connect these pieces and choose an HTTPS setup.
Pi-hole answers the client’s DNS question: “What address belongs to media.example.com?” For a device on your home network that uses Pi-hole, the answer should be Caddy’s local network address. Caddy then reads the requested hostname and uses its configuration to choose the service that receives the request.
For example, a home client might resolve media.example.com to 192.168.1.10, the address of the Caddy host. Caddy can then forward the request to a media service at 192.168.1.20:8096. An external client follows a different path: public DNS returns your home’s public address, and your router forwards the web request to Caddy.
These paths work only when the client asks the expected DNS server to look up the name and the network lets the request reach Caddy. A phone using cellular data does not use your home Pi-hole. A browser with its own encrypted DNS setting can also bypass Pi-hole while connected to your home network.
Give the Caddy host a local address that stays the same. You can set a fixed address or reserve one for it in your router’s DHCP settings. Then add a local DNS record in Pi-hole for each service name, and point each record to Caddy’s address. For example:
media.example.com → 192.168.1.10
notes.example.com → 192.168.1.10
Pi-hole documents custom DNS records in IP HOSTNAME form, along with host and CNAME records. Pi-hole’s interface labels vary by version; use that version’s local DNS settings instead of relying on a particular screen name. If Docker environment variables configure Pi-hole’s DNS settings, the Pi-hole configuration documentation notes that those values take precedence over other configuration methods until the environment variable is removed.
Next, tell Caddy which service belongs to each hostname:
media.example.com {
reverse_proxy 192.168.1.20:8096
}
notes.example.com {
reverse_proxy 192.168.1.30:3000
}
Use the addresses and ports for the services that Caddy can reach on your network. Both names point to Caddy, which forwards each request to a different upstream service behind the proxy. By default, Caddy’s reverse_proxy directive preserves the request method and path as it sends the request upstream.
If an upstream service uses HTTPS, configure Caddy to connect to its HTTPS address and verify its certificate. Caddy does not trust self-signed upstream certificates by default, as its reverse-proxy quick start explains. Disabling certificate verification should not be the default fix for an upstream trust problem.
To make a service available both at home and over the public internet, use a domain you control, such as media.example.com. Public DNS should direct external clients to your home’s public address; Pi-hole should direct local clients to Caddy’s private address. Caddy can then get a publicly trusted certificate for the hostname if it meets the certificate authority’s validation requirements.
Caddy’s standard HTTP-01 certificate check requires external access to port 80, while TLS-ALPN-01 requires external access to port 443. The router and firewall must forward the relevant traffic to Caddy. Public DNS must point to the correct address. An incorrect IPv6 AAAA record can interfere even when the IPv4 address is correct. Caddy’s automatic HTTPS documentation and troubleshooting guidance describe these requirements. Split DNS alone does not satisfy public certificate validation: Caddy and the certificate authority rely on public DNS and the selected validation path.
Caddy can also use the DNS-01 challenge, which verifies control of a domain through a DNS TXT record. DNS-01 can issue certificates even when the web server is not publicly reachable. It requires a DNS provider that supports the challenge and credentials for that provider. Let’s Encrypt warns that DNS API credentials stored on a web server increase the impact of a server compromise; use narrowly scoped credentials where possible. DNS-01 validates the domain for a certificate, but it does not make the service reachable from outside your network.
For services that should remain local, you can use a name under home.arpa, which the IETF designates for residential home networks. Those names are for local lookups. They do not provide public access or publicly trusted certificates. Caddy’s internal certificate authority can issue certificates for local services, but every client that needs a trusted HTTPS connection must trust Caddy’s root certificate. The IETF’s home.arpa standard and Caddy’s automatic HTTPS documentation describe these separate naming and certificate options.
To reach services from your own devices while away, use a VPN and configure those devices to look up the service names through a private DNS path. That avoids making the service endpoints publicly reachable. The particular VPN and DNS setup depends on your network.
Pi-hole’s local DNS answer directs devices to Caddy. It does not check who users are or block requests to a public address. Protect any service reachable from the internet with its own login and suitable access controls. Do not expose Pi-hole’s DNS service to the public internet as part of this design. Pi-hole warns that accepting DNS queries from any origin can create an open resolver and a DNS-amplification risk; the Pi-hole configuration documentation describes its listening behavior.
Keep Caddy’s certificate data persistent if you rely on its internal CA. If Caddy loses that data, clients that trusted the old CA may no longer trust the certificates Caddy issues later. For public services, also check that both the public IPv4 and IPv6 records match your actual network and that the router forwards the intended traffic to Caddy.
Begin with the client where the connection fails. Check whether the client asks Pi-hole to look up the service name, and note the address Pi-hole returns. On the home network, the answer should be Caddy’s private address. From outside, it should be your public address if you intend to allow public access.
If the client gets the correct address, check whether its request reaches Caddy. Confirm that Caddy listens on the intended web ports and that the firewall and router forward traffic as planned. Then check that the hostname in the request matches a site name in the Caddyfile and that Caddy can connect to the configured upstream address and port.
Treat a certificate error separately from a DNS or routing error. A hostname can point to the correct address while HTTPS still fails. The public validation check might not reach Caddy. The client might not trust the certificate. Public DNS records might not match the validation method. Also check the device’s DNS settings and the browser’s encrypted DNS setting. A client can behave differently when it uses a cached answer instead of asking Pi-hole again. Pi-hole’s FAQ describes how local records interact with its DNS behavior.
Give Vroni a GitHub issue, bug report, spec, or rough idea. It reads the repo, plans the change, writes code, runs checks, and works toward a review-ready pull request.
Take a look at vroni.com