A containerized BIND9 DNS server solution for managing domain names and DNS resolution within your local network. Perfect for internal network DNS management, development environments, and local domain hosting.
Quick Start β’ Configuration β’ Features β’ Troubleshooting
This project provides a fully containerized BIND9 DNS server setup using Docker and Docker Compose. It enables you to:
- Host custom domain names on your local network
- Manage DNS records for internal services
- Control query resolution with ACL-based access control
- Forward DNS queries to external resolvers as fallback
- Deploy easily with pre-configured Docker setup
β οΈ Important Note: This configuration requires static IP addresses for reliable DNS resolution. Ensure all devices and the DNS server have fixed IPs before deployment.
- π³ Docker Containerized - Consistent environment across platforms
- π ACL-Based Security - Control which networks can query the DNS
- π DNS Forwarding - Fallback to external resolvers (e.g., Cloudflare 1.1.1.1)
- βοΈ Easy Configuration - Simple YAML-based setup
- π§ Customizable Zones - Add multiple DNS zones and records
- π¦ Persistent Storage - Data retained in named volumes
- Docker (Install Docker)
- Docker Compose (Install Docker Compose)
- Git
- Network with static IP configuration
-
Clone the repository:
git clone https://github.com/ctrlcoded/Bind-DNS.git cd Bind-DNS -
Update network configuration (see Configuration section)
-
Start the DNS server:
docker-compose up -d
-
Verify the service:
docker-compose logs bind9
Edit config/named.conf to specify which networks can query your DNS server:
acl internal {
192.168.0.0/24; # Your local network subnet
172.21.30.0/24; # DNS server subnet
172.18.0.0/24; # Additional authorized networks
172.21.0.0/24; # Add more as needed
};
options {
forwarders {
1.1.1.1; # Cloudflare DNS (or use 8.8.8.8, 9.9.9.9, etc.)
};
allow-query { internal; }; # Only allow configured networks
allow-query-cache { internal; }; # Cache for authorized networks
};
Update the ACL with your actual network ranges and DNS server IP.
Configure your DNS zones in config/named.conf:
zone "example.home" IN {
type master;
file "/etc/bind/example-home.zone";
};
Edit config/example-home.zone to add your DNS records:
$TTL 10d
$ORIGIN example.home.
@ IN SOA ns.example.home. info.example.home. (
2024052900 ; Serial
12h ; Refresh
15m ; Retry
3w ; Expire
2h ; Minimum TTL
)
IN NS ns.example.home.
ns IN A 172.21.30.44 # Your DNS server IP
; DNS Records
mail IN A 192.168.0.10
web IN A 192.168.0.20
db IN A 192.168.0.30
The docker-compose.yml configuration:
version: '3'
services:
bind9:
container_name: bind9-dns
image: ubuntu/bind9:latest
environment:
- TZ=Asia/Kolkata
- BIND9_USER=root
ports:
- "53:53/tcp" # DNS over TCP
- "53:53/udp" # DNS over UDP
volumes:
- ./config:/etc/bind
- .cache:/var/cache/bind
- .records:/var/lib/bind
restart: unless-stopped
networks:
- bind-network
networks:
bind-network:
driver: bridgePort Requirements:
- Port 53/TCP - DNS queries over TCP
- Port 53/UDP - DNS queries over UDP
# Start in detached mode (background)
docker-compose up -d
# Start with logs visible
docker-compose up
# Start specific service
docker-compose up bind9# View current logs
docker-compose logs bind9
# Follow logs in real-time
docker-compose logs -f bind9
# View last 50 lines
docker-compose logs --tail=50 bind9# Stop container (data persists)
docker-compose stop
# Stop and remove containers
docker-compose downFrom any device on your network:
# macOS/Linux
nslookup mail.example.home 192.168.X.X
dig mail.example.home @192.168.X.X
# Windows
nslookup mail.example.home 192.168.X.XReplace 192.168.X.X with your DNS server's IP address.
Windows:
- Open Network Settings β Change adapter options
- Right-click network connection β Properties
- Select "IPv4" β Properties
- Set DNS server to your BIND DNS server IP
macOS:
- System Preferences β Network β Advanced
- DNS tab β Add your DNS server IP
Linux:
# Edit /etc/resolv.conf (Ubuntu/Debian)
echo "nameserver 192.168.X.X" | sudo tee /etc/resolv.confConfigure your router's DHCP settings to use the BIND DNS server as the primary DNS resolver for all devices.
bind-dns/
βββ docker-compose.yml # Docker Compose configuration
βββ config/
β βββ named.conf # BIND configuration & ACLs
β βββ example-home.zone # DNS zone file
βββ .cache/ # BIND cache (auto-created)
βββ .records/ # BIND records (auto-created)
βββ README.md # This file
Note: Folders
.cacheand.recordsare created automatically on first run. If not created, manually create them with:mkdir .cache .records
Check logs:
docker-compose logs bind9Verify named.conf syntax:
docker-compose exec bind9 named-checkconf /etc/bind/named.conf- Check ACL configuration - Ensure your network is in the
acl internalblock - Verify server IP - Confirm clients are querying the correct DNS server IP
- Check firewall - Ensure port 53 (TCP/UDP) is open on the server
- Restart service:
docker-compose restart bind9
Validate zone file:
docker-compose exec bind9 named-checkzone example.home /etc/bind/example-home.zoneReset permissions:
docker-compose exec bind9 chown -R bind:bind /var/cache/bind /var/lib/bind| Type | Purpose | Example |
|---|---|---|
| A | IPv4 address | web IN A 192.168.0.10 |
| AAAA | IPv6 address | web IN AAAA 2001:db8::1 |
| CNAME | Alias | alias IN CNAME web.example.home. |
| MX | Mail server | example.home IN MX 10 mail.example.home. |
| NS | Nameserver | @ IN NS ns.example.home. |
| TXT | Text records | example.home IN TXT "v=spf1 -all" |
Contributions are welcome! To contribute:
- Fork the repository
- Create your feature branch (
git checkout -b feature/amazing-feature) - Commit your changes (
git commit -m 'Add some amazing feature') - Push to the branch (
git push origin feature/amazing-feature) - Open a Pull Request
For issues, questions, or suggestions:
- Open an Issue
- Submit a Pull Request
Made with β€οΈ for the open-source community
β If you found this helpful, please consider giving it a star!