通过 Cloudflare API 实现 DDNS

作者:🧑‍🚀 deadmau5v 发布于 2025/12/13

对于家庭宽带用户,公网 IP 是动态的。想从外网访问家里的 NAS 或 Minecraft 服务器,必须用 DDNS。

相比于花生壳等第三方服务,直接利用 Cloudflare 的 API 是最稳定、最快速的方案,而且完全免费。

Oray DDNS

准备工作

  1. 域名托管:确保你的域名 DNS 已托管在 Cloudflare。
  2. 添加记录:在后台添加一条 A 记录,IP 随意填,比如 1.1.1.1,小黄云设置关闭(仅DNS模式)。
  3. 获取 Key:打开 https://dash.cloudflare.com/profile/api-tokens 复制 Global API Key,替换到脚本中。

DDNS脚本

我们直接使用 Shell 脚本,无需安装任何额外依赖,复制即用。

新建文件 cf_ddns.sh

#!/bin/bash

# ================= 配置区域 =================
# 你的 Cloudflare 注册邮箱
auth_email="your_email@example.com"
# 你的 Global API Key (通常为37位)
auth_key="your_global_api_key"
# 主域名
zone_name="your_domain.com"
# 需要更新的子域名
record_name="your_subdomain.your_domain.com"
# ===========================================

# 日志与缓存路径
ip_file="ip.txt"
id_file="cloudflare.ids"
log_file="cloudflare.log"

log() {
    echo -e "[$(date)] - $1" >> $log_file
}

# 1. 获取当前公网 IP
ip=$(curl -s http://ipv4.icanhazip.com)

# 2. 检查 IP 是否变化
if [ -f $ip_file ]; then
    old_ip=$(cat $ip_file)
    if [ "$ip" == "$old_ip" ]; then
        echo "IP 未改变: $ip"
        exit 0
    fi
fi

# 3. 获取 Zone ID 和 Record ID
# 优先读取缓存,如果文件不存在或行数不对则重新通过 API 获取
if [ -f $id_file ] && [ $(wc -l < $id_file) -eq 2 ]; then
    zone_identifier=$(sed -n '1p' $id_file)
    record_identifier=$(sed -n '2p' $id_file)
else
    # 获取 Zone ID
    zone_identifier=$(curl -s -X GET "https://api.cloudflare.com/client/v4/zones?name=$zone_name" \
        -H "X-Auth-Email: $auth_email" \
        -H "X-Auth-Key: $auth_key" \
        -H "Content-Type: application/json" | grep -o '"id":"[^"]*"' | head -1 | cut -d'"' -f4)

    # 获取 Record ID
    record_identifier=$(curl -s -X GET "https://api.cloudflare.com/client/v4/zones/$zone_identifier/dns_records?type=A&name=$record_name" \
        -H "X-Auth-Email: $auth_email" \
        -H "X-Auth-Key: $auth_key" \
        -H "Content-Type: application/json" | grep -o '"id":"[^"]*"' | head -1 | cut -d'"' -f4)

    echo "$zone_identifier" > $id_file
    echo "$record_identifier" >> $id_file
fi

# 4. 更新 DNS 记录
update=$(curl -s -X PATCH "https://api.cloudflare.com/client/v4/zones/$zone_identifier/dns_records/$record_identifier" \
    -H "X-Auth-Email: $auth_email" \
    -H "X-Auth-Key: $auth_key" \
    -H "Content-Type: application/json" \
    --data "{\"content\":\"$ip\"}")

# 5. 结果判断
if echo "$update" | grep -q '"success":false'; then
    log "API 更新失败: $update"
else
    log "IP 已更新为: $ip"
    echo "$ip" > $ip_file
fi

赋予执行权限:

chmod +x cf_ddns.sh

设置定时任务

脚本写好了,我们需要它每隔几分钟自动运行一次。

输入 crontab -e,添加以下一行:

*/5 * * * * /root/cf_ddns.sh >/dev/null 2>&1

这样,系统每 5 分钟就会检测一次公网 IP。如果 IP 变动,域名解析会自动更新;如果没变,脚本会静默退出,不占用资源。

标签:CloudflareDDNSDNSShell

评论

发表评论

加载评论中...