feat: BIND DNS Web Manager - Web interface for managing BIND9 DNS server

- Flask + SQLite web app with user authentication
- Zone management: create/delete zones, edit raw zone files
- Record management: add/delete A/AAAA/CNAME/MX/TXT/NS/PTR/SRV/CAA records
- Service control: start/stop/restart/reload BIND via systemctl/rndc
- Configuration editor: edit named.conf.options/local with syntax validation
- DNS query testing: online dig tool
- Audit log: all operations logged with user/timestamp
- BIND9 backend, listening on port 53
This commit is contained in:
AI Agent
2026-07-09 17:24:44 +08:00
commit 0a18b94d84
19 changed files with 2587 additions and 0 deletions
+242
View File
@@ -0,0 +1,242 @@
# DNS Web Manager
基于 BIND9 的 DNS 服务器 Web 管理界面,使用 Flask + SQLite 构建。
## 功能概览
| 功能 | 说明 |
|------|------|
| 仪表盘 | BIND 服务状态、域名/记录统计、服务控制(启动/停止/重启/重载) |
| 域名管理 | 创建/删除 Zone(支持 master/slave)、查看 Zone 详情、编辑原始 zone 文件 |
| 记录管理 | 添加/删除 DNS 记录(A、AAAA、CNAME、MX、TXT、NS、PTR、SRV、CAA |
| DNS 查询 | 在线 dig 测试,支持所有记录类型 |
| 配置管理 | 在线编辑 `named.conf.options``named.conf.local`,带语法校验 |
| 操作日志 | 全部操作的审计日志,支持分页 |
| 用户认证 | 登录/登出/修改密码 |
## 截图
### 仪表盘
- BIND 服务状态卡片(运行状态、开机自启)
- 域名数量、记录总数统计
- 服务控制按钮(启动/停止/重启/重载)
- 域名概览表格
- 最近操作日志
### 域名管理
- 域名列表(域名、类型、Zone 文件、记录数)
- 创建域名表单(域名、类型、NS 服务器、管理员邮箱)
- Zone 详情页:SOA 信息、记录列表、添加记录表单、原始文件编辑
### DNS 查询
- 输入域名 + 记录类型 + DNS 服务器,执行 dig 查询
- 显示完整 dig 输出
## 技术栈
- **DNS 服务器**: BIND 9.18+named
- **Web 框架**: Flask 3.0
- **数据库**: SQLite(用户认证 + 审计日志)
- **前端**: Jinja2 模板 + 原生 CSS(无前端框架依赖)
- **WSGI 服务器**: Gunicorn
## 目录结构
```
dns-service/
├── app.py # Flask 应用主文件(路由、模型、BIND 操作)
├── wsgi.py # Gunicorn 入口
├── init_db.py # 数据库初始化脚本
├── requirements.txt # Python 依赖
├── README.md
├── templates/ # Jinja2 模板
│ ├── base.html # 布局模板(导航栏 + 页脚)
│ ├── login.html # 登录页
│ ├── dashboard.html # 仪表盘
│ ├── zones.html # 域名列表
│ ├── zone_form.html # 创建域名表单
│ ├── zone_detail.html # Zone 详情 + 记录管理
│ ├── zone_raw.html # 原始 Zone 文件编辑
│ ├── query.html # DNS 查询测试
│ ├── config.html # BIND 配置管理
│ ├── logs.html # 操作日志
│ ├── change_password.html
│ └── error.html # 错误页
├── static/
│ └── style.css # 全部样式
└── instance/ # SQLite 数据库(运行时生成)
└── dns_web.db
```
## BIND 配置文件
| 文件 | 用途 | 路径 |
|------|------|------|
| `named.conf` | 主配置 | `/etc/bind/named.conf` |
| `named.conf.options` | 全局选项(监听端口、转发器、查询权限) | `/etc/bind/named.conf.options` |
| `named.conf.local` | Zone 声明(由 Web UI 自动管理) | `/etc/bind/named.conf.local` |
| zone files | DNS 记录文件 | `/etc/bind/zones/db.*` |
## 安装部署
### 1. 安装 BIND9
```bash
apt-get update
apt-get install -y bind9 bind9utils dnsutils
```
### 2. 配置 BIND
```bash
# 创建 zone 文件目录
mkdir -p /etc/bind/zones
chown bind:bind /etc/bind/zones
# named.conf.options(监听 53 端口)
cat > /etc/bind/named.conf.options << 'EOF'
options {
directory "/var/cache/bind";
listen-on port 53 { any; };
listen-on-v6 { none; };
forwarders { 8.8.8.8; 8.8.4.4; };
allow-query { any; };
allow-recursion { 127.0.0.0/8; 10.168.1.0/24; };
dnssec-validation auto;
auth-nxdomain no;
};
EOF
# named.conf(包含 options + local + default-zones
cat > /etc/bind/named.conf << 'EOF'
include "/etc/bind/named.conf.options";
include "/etc/bind/named.conf.local";
include "/etc/bind/named.conf.default-zones";
EOF
# named.conf.local(空,由 Web UI 自动填充)
cat > /etc/bind/named.conf.local << 'EOF'
// Local zone configurations - managed by DNS Web UI
EOF
# 启动 BIND
systemctl enable named
systemctl start named
```
### 3. 安装 Web 应用
```bash
git clone ssh://git@git.cnbugs.com:10022/AI-Agent/dns-service.git
cd dns-service
# 安装 Python 依赖
pip install -r requirements.txt
# 初始化数据库(创建默认 admin/admin 账号)
python3 init_db.py
# 启动(开发模式)
python3 app.py
```
### 4. 生产部署(Gunicorn + Systemd
```bash
# 创建 systemd 服务
cat > /etc/systemd/system/dns-web.service << 'EOF'
[Unit]
Description=DNS Web Manager
After=network.target named.service
[Service]
Type=notify
User=root
WorkingDirectory=/root/dns-service
ExecStart=/usr/local/bin/gunicorn --workers 2 --bind 0.0.0.0:5300 wsgi:app
Restart=always
RestartSec=5
[Install]
WantedBy=multi-user.target
EOF
systemctl daemon-reload
systemctl enable dns-web
systemctl start dns-web
```
## 使用说明
### 登录
- 访问 `http://<服务器IP>:5300`
- 默认账号: `admin` / 密码: `admin`
- 首次登录后请修改密码
### 创建域名
1. 进入「域名管理」→「+ 添加域名」
2. 填写域名(如 `example.com`)、选择类型(master/slave
3. 可选填写 NS 服务器和管理员邮箱(留空则自动生成)
4. 点击「创建域名」
### 添加 DNS 记录
1. 进入域名详情页
2. 点击「+ 添加记录」
3. 填写记录名称、类型、TTL、数据
4. 点击「添加」
**记录类型说明:**
| 类型 | 数据格式 | 示例 |
|------|----------|------|
| A | IPv4 地址 | `10.168.1.100` |
| AAAA | IPv6 地址 | `2001:db8::1` |
| CNAME | 别名(FQDN,以 `.` 结尾) | `www.example.com.` |
| MX | 优先级 + 邮件服务器(FQDN) | `10 mail.example.com.` |
| TXT | 文本内容 | `"v=spf1 ~all"` |
| NS | NS 服务器(FQDN | `ns1.example.com.` |
| PTR | 反向解析目标(FQDN | `host.example.com.` |
| SRV | 优先级 权重 端口 目标 | `10 5 5060 sip.example.com.` |
### DNS 查询测试
1. 进入「DNS 查询」页面
2. 输入域名和记录类型
3. DNS 服务器留空默认查询本地 BIND127.0.0.1:53
4. 点击「查询」查看结果
### 配置管理
1. 进入「配置管理」页面
2. 可在线编辑 `named.conf.options`(监听端口、转发器等)
3. 可在线编辑 `named.conf.local`Zone 声明)
4. 保存时自动执行 `named-checkconf` 校验,通过后自动 `rndc reload`
### 服务控制
在「仪表盘」页面可控制 BIND 服务:
- **启动** - `systemctl start named`
- **停止** - `systemctl stop named`
- **重启** - `systemctl restart named`
- **重载配置** - `rndc reload`(不中断服务,热加载 zone 变更)
## 注意事项
1. **权限要求**: Web 应用需要 root 权限运行(用于操作 BIND 配置文件和 systemctl 命令)
2. **端口冲突**: 如果 53 端口被其他服务占用(如 dnsmasq),需先停掉对应服务
3. **Zone 文件权限**: zone 文件需要 `bind:bind` 所有权,Web UI 自动设置
4. **Serial 自动递增**: 每次添加/删除记录时,SOA Serial 自动递增(YYYYMMDDNN 格式)
5. **配置备份**: 编辑配置文件时自动创建 `.bak` 备份
## API 接口
| 方法 | 路径 | 说明 |
|------|------|------|
| GET | `/api/status` | 获取 BIND 服务状态(需登录) |
## License
MIT