Implement Cloudflare DDNS updater

This commit is contained in:
LC mac
2026-01-13 01:50:13 +08:00
parent da61fa7093
commit ce5a0a87ba
7 changed files with 627 additions and 1 deletions

152
README.md
View File

@@ -1,3 +1,153 @@
# ddns-updater
Cloudfare DDNS updater
A small Go daemon that keeps Cloudflare A records in sync with your current public IPv4 address.
It reads a YAML config, checks your IP periodically, compares it to existing DNS records, and only updates when needed.
## Features
- Uses Cloudflare API token (modern auth)
- Supports multiple subdomains in one zone
- IPv4 only (A records)
- User-defined check interval (minutes)
- Retries on failure, then logs and skips
- Structured JSON logging to file
## Requirements
- Go 1.21+ (tested with 1.23)
- A Cloudflare account
- API token with:
- Zone:DNS:Edit
- Zone:Zone:Read
- Existing zone and A records for your subdomains
## Installation
```bash
# 1. Create project directory
mkdir ddns-updater
cd ddns-updater
# 2. Initialize module
go mod init github.com/yourname/ddns-updater
# 3. Add files
# - main.go
# - config.yaml
# - (this README.md)
# 4. Fetch dependencies
go mod tidy
# 5. Build binary (current platform)
go build -o ddns-updater
# 6. Build for Linux (LXC, etc.)
GOOS=linux GOARCH=amd64 go build -o ddns-updater-linux
```
Copy the resulting binary and `config.yaml` onto your target machine or LXC container, e.g. `/opt/ddns-updater`.
## Configuration
Create `config.yaml` in the same directory as the binary:
```yaml
check_interval: 5 # minutes (e.g. 5, 15, 30)
cloudflare:
api_token: "YOUR_CF_API_TOKEN"
zone_id: "YOUR_ZONE_ID"
subdomains:
- name: "lc"
proxied: false
- name: "git"
proxied: false
- name: "mempool"
proxied: false
logging:
file: "ddns-updater.log"
level: "info" # debug, info, warn, error
retry:
max_attempts: 3
delay_seconds: 5
webhook:
enabled: false
url: ""
```
- `check_interval`: how often to check your current IP (in minutes).
- `subdomains`: just the left part of the name (e.g. `git` for `git.example.com`).
- `proxied`: `true` for orange-cloud (proxied), `false` for DNS only.
- `logging.file`: log file path, relative to the working directory.
- `retry`: per-subdomain retry behavior when the Cloudflare API or network fails temporarily.
## Usage
### Direct run
From the directory containing the binary and `config.yaml`:
```bash
./ddns-updater
```
The process will:
1. Load `config.yaml`.
2. Detect current public IPv4 using external services.
3. For each subdomain:
- Fetch its current A record from Cloudflare.
- If the IP differs, update the record.
4. Sleep for `check_interval` minutes and repeat.
5. Log events to `ddns-updater.log`.
### Run in background (simple)
```bash
nohup ./ddns-updater >/dev/null 2>&1 &
```
### Example systemd service (on Linux/LXC)
Create `/etc/systemd/system/ddns-updater.service`:
```ini
[Unit]
Description=Cloudflare DDNS Updater
After=network-online.target
Wants=network-online.target
[Service]
Type=simple
WorkingDirectory=/opt/ddns-updater
ExecStart=/opt/ddns-updater/ddns-updater
Restart=on-failure
RestartSec=10
[Install]
WantedBy=multi-user.target
```
Then:
```bash
sudo systemctl daemon-reload
sudo systemctl enable ddns-updater
sudo systemctl start ddns-updater
sudo systemctl status ddns-updater
```
Logs will go to `ddns-updater.log` in `/opt/ddns-updater` plus systemds journal.
## Updating
To update the binary:
```bash
git pull # if you put it in a repo
go build -o ddns-updater
sudo systemctl restart ddns-updater