Docker - Pi-hole Container Setup with Unbound

Here I describe my setup of the Pi-hole docker container.

I run this Docker container on a Ubuntu VM that runs via [[ Proxmox VE ]]. I perform the following on the CLI.

(optional) Create Network

To allow Pi-hole to communicate with Unbound, you need to create a Docker network first. You only need to do this if you want to use Unbound as an upstream DNS server from Pi-hole. For example, it is also possible to use the Cloudflare DNS server as an upstream DNS server.

Create the network dns-net:

docker network create --driver=bridge --subnet= --gateway= dns-net

Container Setup

Run the Docker pull command:

docker pull pihole/pihole

Within my home folder I have created a Docker folder where I create a subfolder for each container:

cd ~
mkdir -p docker/pihole
cd docker/pihole

I use the Nano text editor to create a shell script:

sudo nano

With this shell script we are going to create the container. Copy the following into

# Lookups may not work for VPN / tun0
IP_LOOKUP="$(ip route get | awk '{for(i=1;i<=NF;i++) if ($i=="src") print $(i+1)}')"
IPv6_LOOKUP="$(ip -6 route get 2001:4860:4860::8888 | awk '{for(i=1;i<=NF;i++) if ($i=="src") print $(i+1)}')"

# Just hard code these to your docker server's LAN IP if lookups aren't working
IP="${IP:-$IP_LOOKUP}"  # use $IP, if set, otherwise IP_LOOKUP
IPv6="${IPv6:-$IPv6_LOOKUP}"  # use $IPv6, if set, otherwise IP_LOOKUP

docker run -d \
 --name pihole \
 --hostname=pihole \
 --network=dns-net \
 -p 53:53/tcp \
 -p 53:53/udp \
 -p 67:67/udp \
 -p 81:80/tcp \
 -p 444:443/tcp \
 -v $PWD/pihole/:/etc/pihole/ \
 -v $PWD/dnsmasq.d/:/etc/dnsmasq.d/ \
 -e ServerIP="${IP}" \
 -e ServerIPv6="${IPv6}" \
 -e DNS1= \
 -e DNS2=no \
 -e TZ="Europe/Amsterdam" \
 --cap-add=NET_ADMIN \
 --dns \
 --restart=unless-stopped \

If necessary, adjust the following:

-p 81:80/tcp and -p 444:443/tcp
*Change port 81 and 444 to whatever port you want to use to to access the user interface.**

-e DNS1=
This is the upstream DNS server of Pi-hole. In this example it is the IP and port of the Unbound container. Another example would be the Cloudflare DNS server. You can also configure this within the Pi-hole UI

-e DNS2=no
(optional) Replace no with a second upstream DNS server. You can also configure this within the Pi-hole UI

-e “TZ=Europe/Amsterdam”
Pick the right timezone

Replace PASS with your own password which is used with the Pi-hole UI

Sets your container’s resolve settings to localhost so it can resolve DHCP hostnames from Pi-hole’s DNSMasq, may fix resolution errors on container restart. Here is the link to the documentation.

Exit Nano (CTRL-X) and save the changes.

Make sure the ports are available. Check this with netstat. With the following command you can find out which service is running on port 53:

sudo ss -lp "sport = :domain"

When you need to disable systemd-resolved, please read this post.

Now create the container:

sudo sh

Check if the container is running properly.

Using Pi-hole

Pi-hole can now be accessed via the following URL:

http://<IP DOCKER HOST>:81/

You may need to match port 81 to the port you set above as mapping to port 80.

Setup Adlist
I only use one adlist: You can set this up by going to Group Management and adding this address as an adlist. Do not forget to update Gravity.

Setup Conditional Forwarding
Conditional Forwarding is set up as follows (replace with your own network settings):

  • Local network in CIDR notation:
  • IP address of your DHCP server (router):
  • Local domain name (optional): home

See also my notes about updating containers with Portainer or via the CLI. With Synology’s Docker Application, updating a container is also very easy.

Read other notes


    No comments found for this note.

    Join the discussion for this note on this ticket. Comments appear on this page instantly.


    Notes mentioning this note

    Notes Graph