Armadillo – 一个用 Gleam 编写的 Homelab DNS 服务器
摘要
Armadillo 是一个用 Gleam 编写的自托管 DNS 服务器,适用于 homelab 环境。它首先检查本地记录,然后将未知查询转发到上游解析器,并带有可配置的区域文件和 ETS 缓存。
查看缓存全文
缓存时间: 2026/06/28 10:56
vshakitskiy/armadillo
来源:https://github.com/vshakitskiy/armadillo
armadillo 图标 Armadillo
一个用于家庭实验室的自托管 DNS 服务器,使用 Gleam 编写。
armadillo 演示 (https://github.com/user-attachments/assets/7361e6b2-c761-4eea-82d8-22f95c104324)
在路由器上配置一次作为 DNS 解析器后,网络上的所有设备都会自动解析你的本地域名。
工作原理
当 DNS 查询到达时,服务器首先检查本地记录存储。如果存在匹配的记录,它会立即响应配置的 IP。如果没有匹配记录,查询会被转发到可配置的上游解析器,响应按 TTL 缓存,然后返回给客户端。
本地记录存储在一个 DNS 区域文件中,并在启动时加载到 ETS 中。所有运行时的查询解析仅通过 ETS 进行,查询处理期间永远不会读取区域文件。
容器镜像
可在 ghcr.io/vshakitskiy/armadillo:latest 获取。
| 变量 | 默认值 | 描述 |
|---|---|---|
DNS_PORT | 53 | DNS 服务器监听的端口 |
DNS_UPSTREAM | 8.8.8.8 | 未知域名的上游解析器 |
DNS_TTL | 300 | 区域记录的默认 TTL(秒) |
DNS_SOA_MINIMUM | 3600 | 负缓存的最小 SOA TTL(秒) |
API_PORT | 3000 | Web UI 和 REST API 的端口 |
API_SECRET_KEY_BASE | 随机密钥 | 用于签名会话 cookie 的密钥 |
ZONE_FILE | /data/local.zone | DNS 区域文件路径 |
挂载卷到 /data 以在重启后持久化区域文件。如果文件不存在,区域文件会自动创建。
部署指南
部署指南位于 examples/ 目录。
- Podman — 使用 Podman Quadlet 的 systemd 服务,Caddy 作为反向代理。
- Docker Compose — 多容器应用,Caddy 作为反向代理。
域名命名建议
服务器接受任何域名字符串。但应避免使用 .local。它被保留用于 mDNS/Bonjour (RFC 6762),Apple 设备不会将 .local 查询发送到单播 DNS 服务器。.lan 或 .internal 是常见的替代方案。
贡献
欢迎任何贡献和反馈!问题和拉取请求都欢迎!
项目包含三个包:server 运行 DNS 解析器和 HTTP API,client 是 Web UI,shared 包含两者共用的模块。每个包独立开发,在 server/ 中运行 gleam run,在 client/ 中运行 gleam run -m lustre/dev。
在本地开发时管理环境变量,建议使用 direnv (https://direnv.net)。
要在不需要 sudo 的情况下本地绑定到端口 53,请对 BEAM 二进制文件运行 setcap:
# 查找二进制文件:
$(which erl) -noshell -eval 'io:format("~s~n",[os:find_executable("beam.smp")]),halt().'
# > /path/to/beam.smp
sudo setcap cap_net_bind_service=+ep /path/to/beam.smp
通过 VPN 解析
个人备忘:以防再次遇到 VPN 导致 DNS 问题。
当运行 vless 等 VPN 并在代理或 tun 模式下时,确保 VPN 通过正确的 DNS 解析域名非常重要。假设路由器的 IP 192.168.1.1 是配置 DNS 服务器的地址:
- 将路由器添加为 DNS 服务器,并为 xray 直接路由局域网 IP:
{
"dns": {
"servers": [
{ "address": "192.168.1.1", "port": 53 },
"1.1.1.1"
]
},
"routing": {
"rules": [
{
"ip": ["10.0.0.0/8", "172.16.0.0/12", "192.168.0.0/16"],
"outboundTag": "direct"
}
]
}
}
- 为 sing-box 标记本地 DNS 服务器并路由私有 IP:
{
"dns": {
"servers": [
{ "tag": "dns-local", "address": "192.168.1.1", "detour": "direct" },
{ "tag": "dns-remote", "address": "1.1.1.1", "detour": "proxy" }
],
"rules": [{ "ip_is_private": true, "server": "dns-local" }],
"final": "dns-remote"
},
"route": {
"rules": [{ "ip_is_private": true, "outbound": "direct" }]
}
}
相似文章
DNSGlobe – 用 Rust 编写的 TUI 工具,监控 DNS 在全球的传播情况
DNSGlobe 是一款用 Rust 编写的终端应用,可并行查询全球 34 个 DNS 解析器,在世界地图上检查并显示传播状态,并提供持续监控的观察模式。
Light-Heart-Labs/DreamServer
Dream Server 是一个开源的、本地优先的 AI 栈,允许用户通过一条命令在自己的硬件上部署 LLM 推理、聊天、语音、代理、RAG、图像生成和隐私工具,从而消除对云提供商的依赖。
@VincentLogic: 一个程序员突发奇想: DNS 解析器会把域名记几天—— 那能不能拿来存文件? ↓ 他找到了全网 390 万个开放 DNS 解析器 把文件切碎 撒遍整个互联网 没有硬盘 没有数据库 没有云 文件活在无数台服务器的缓存里 而那些服务器根本不知…
一个程序员利用全网390万个开放DNS解析器的缓存来存储文件碎片,创建了一个名为dnsfs的荒诞开源项目,文件随着缓存过期而消失。
DELIGHT – 自托管AI工程自动驾驶仪:本地大模型 + 浏览器农场 + 仓库图谱 + 点对点计算
DELIGHT 是一个自托管的AI工程自动驾驶仪,它结合了本地大语言模型、浏览器农场和语义仓库图谱,可在不将数据发送到云端的情况下自动完成开发任务。
Show HN: Mezz, 一个可通过curl使用的WiFi沙箱,用于物联网渗透测试
Mezz 是一个自包含的WiFi沙箱工具,用于检查物联网设备流量,提供一个隔离网络,带有DNS日志记录和可选的MITM代理,全部可通过Docker部署在具有AP功能的WiFi的Linux主机上。