├── README.md └── cloudflare-ddns.sh /README.md: -------------------------------------------------------------------------------- 1 | # 功能 2 | 自动调度Cloudflare云端分钟更新一次
3 | 优选IP速度大于100Mbps
4 | 全天99%在线 5 | 6 | ## 食用方式 7 | ### 准备工作 8 | 一台VPS(国内、国外均可),域名,cloudflare账号 9 | ### 步骤 10 | 1. 登录cloudflare账号,获取Global API Key 11 | ![](http://jinqians.com/wp-content/uploads/2023/12/1-1.png) 12 | 13 | ![](http://jinqians.com/wp-content/uploads/2023/12/2-scaled.jpg) 14 | 15 | 2. 登录VPS,复制下方命令执行 16 | ```shell 17 | wget -O cloudflare-ddns.sh https://raw.githubusercontent.com/jinqians/cloudflare-ddns/main/cloudflare-ddns.sh && chmod +x cloudflare-ddns.sh && ./cloudflare-ddns.sh 18 | ``` 19 | 输入自己的对应信息 20 | ![](http://jinqians.com/wp-content/uploads/2023/12/4.png) 21 | 22 | 3. 执行完成后按照提示,输入下方命令执行 23 | ```shell 24 | ./cloudflare.sh 25 | ``` 26 | 到此,优选IP已绑定到自己的域名 27 | -------------------------------------------------------------------------------- /cloudflare-ddns.sh: -------------------------------------------------------------------------------- 1 | #Telegram:@jinqians_chat 2 | #!/usr/bin/env bash 3 | set -o errexit 4 | set -o nounset 5 | set -o pipefail 6 | 7 | # 欢迎信息 8 | echo "欢迎使用Cloudflare 自动优选IP 群组:@jinqians_chat" 9 | read -p "点击任意键继续.." 10 | 11 | # 用户输入 12 | read -p "请输入您的Cloudflare Global API Key(https://dash.cloudflare.com/profile/api-tokens): " CFKEY 13 | read -p "请输入您的Cloudflare 登录邮箱: " CFUSER 14 | read -p "请输入您的Cloudflare DNS域名(一级域名): " CFZONE_NAME 15 | read -p "请输入您的Cloudflare DDNS域名(二级域名): " CFRECORD_NAME 16 | 17 | # 提醒信息 18 | echo "请注意确保二级域名已随意添加一个解析并未开启代理" 19 | read -p "按任意键回车继续.." 20 | 21 | # 生成新的DDNS脚本文件 22 | cat < cloudflare.sh 23 | #!/usr/bin/env bash 24 | set -o errexit 25 | set -o nounset 26 | set -o pipefail 27 | 28 | # Cloudflare API credentials 29 | CFKEY="$CFKEY" 30 | CFUSER="$CFUSER" 31 | CFZONE_NAME="$CFZONE_NAME" 32 | CFRECORD_NAME="$CFRECORD_NAME" 33 | 34 | # 记录类型,A(IPv4)|AAAA(IPv6),默认为IPv4 35 | CFRECORD_TYPE=A 36 | 37 | # Cloudflare记录的TTL,介于120和86400秒之间 38 | CFTTL=120 39 | 40 | # 无视本地文件,无论如何都更新IP 41 | FORCE=false 42 | 43 | # 获取WAN IP的网站 44 | WANIPSITE="https://ipdb.api.030101.xyz/?type=bestproxy&country=false" 45 | 46 | # 获取参数 47 | while getopts k:u:h:z:t:f: opts; do 48 | case \${opts} in 49 | k) CFKEY=\${OPTARG} ;; 50 | u) CFUSER=\${OPTARG} ;; 51 | h) CFRECORD_NAME=\${OPTARG} ;; 52 | z) CFZONE_NAME=\${OPTARG} ;; 53 | t) CFRECORD_TYPE=\${OPTARG} ;; 54 | f) FORCE=\${OPTARG} ;; 55 | esac 56 | done 57 | 58 | # 如果必需的设置缺失,则退出 59 | if [ "\$CFKEY" = "" ]; then 60 | echo "缺少API密钥,请在 https://www.cloudflare.com/a/account/my-account 获取" 61 | echo "并保存在 \${0} 或使用 -k 参数" 62 | exit 2 63 | fi 64 | if [ "\$CFUSER" = "" ]; then 65 | echo "缺少用户名,可能是您的电子邮件地址" 66 | echo "并保存在 \${0} 或使用 -u 参数" 67 | exit 2 68 | fi 69 | if [ "\$CFRECORD_NAME" = "" ]; then 70 | echo "缺少主机名,您想要更新哪个主机?" 71 | echo "保存在 \${0} 或使用 -h 参数" 72 | exit 2 73 | fi 74 | 75 | # 如果主机名不是完整域名 76 | if [ "\$CFRECORD_NAME" != "\$CFZONE_NAME" ] && ! [ -z "\${CFRECORD_NAME##*\$CFZONE_NAME}" ]; then 77 | CFRECORD_NAME="\$CFRECORD_NAME.\$CFZONE_NAME" 78 | echo " => 主机名不是完整域名,假设为 \$CFRECORD_NAME" 79 | fi 80 | 81 | # 检查IP地址是否有效的函数 82 | is_valid_ip() { 83 | local ip=\$1 84 | if [[ \$ip =~ ^[0-9]+\.[0-9]+\.[0-9]+\.[0-9]+\$ ]]; then 85 | return 0 86 | else 87 | return 1 88 | fi 89 | } 90 | 91 | # 从主要IP源获取当前和旧的WAN IP 92 | WAN_IP=$(curl -s "$WANIPSITE" | head -n 1 | awk -F '#' '{print $1}') 93 | 94 | # 如果WAN_IP无效,尝试备用IP源 95 | if ! is_valid_ip "\$WAN_IP"; then 96 | WAN_IP=$(curl -s "https://ipdb.api.030101.xyz/?type=bestcf&country=false" | grep -oE "\b([0-9]{1,3}\.){3}[0-9]{1,3}\b" | head -n 1) 97 | if ! is_valid_ip "\$WAN_IP"; then 98 | echo "无法获取有效的IPv4地址" 99 | exit 1 100 | fi 101 | fi 102 | 103 | echo "IPv4 \$WAN_IP 已获取" 104 | 105 | WAN_IP_FILE=\$HOME/.cf-wan_ip_\$CFRECORD_NAME.txt 106 | if [ -f \$WAN_IP_FILE ]; then 107 | OLD_WAN_IP=\$(cat \$WAN_IP_FILE) 108 | else 109 | echo "没有找到对应的输出文件 @jinqians_chat" 110 | OLD_WAN_IP="" 111 | fi 112 | 113 | # 如果WAN IP没有变化且没有强制更新标志,则退出 114 | if [ "\$WAN_IP" = "\$OLD_WAN_IP" ] && [ "\$FORCE" = false ]; then 115 | echo "云端没有最新的优选IP @@jinqians_chat" 116 | exit 0 117 | fi 118 | 119 | # 获取区域标识符和记录标识符 120 | ID_FILE=\$HOME/.cf-id_\$CFRECORD_NAME.txt 121 | if [ -f \$ID_FILE ] && [ \$(wc -l \$ID_FILE | cut -d " " -f 1) == 4 ] \ 122 | && [ "\$(sed -n '3,1p' "\$ID_FILE")" == "\$CFZONE_NAME" ] \ 123 | && [ "\$(sed -n '4,1p' "\$ID_FILE")" == "\$CFRECORD_NAME" ]; then 124 | CFZONE_ID=\$(sed -n '1,1p' "\$ID_FILE") 125 | CFRECORD_ID=\$(sed -n '2,1p' "\$ID_FILE") 126 | else 127 | echo "正在更新区域标识符和记录标识符" 128 | CFZONE_ID=\$(curl -s -X GET "https://api.cloudflare.com/client/v4/zones?name=\$CFZONE_NAME" -H "X-Auth-Email: \$CFUSER" -H "X-Auth-Key: \$CFKEY" -H "Content-Type: application/json" | grep -Po '(?<="id":")[^"]*' | head -1 ) 129 | CFRECORD_ID=\$(curl -s -X GET "https://api.cloudflare.com/client/v4/zones/\$CFZONE_ID/dns_records?name=\$CFRECORD_NAME" -H "X-Auth-Email: \$CFUSER" -H "X-Auth-Key: \$CFKEY" -H "Content-Type: application/json" | grep -Po '(?<="id":")[^"]*' | head -1 ) 130 | echo "\$CFZONE_ID" > \$ID_FILE 131 | echo "\$CFRECORD_ID" >> \$ID_FILE 132 | echo "\$CFZONE_NAME" >> \$ID_FILE 133 | echo "\$CFRECORD_NAME" >> \$ID_FILE 134 | fi 135 | 136 | # 更新Cloudflare DNS记录 137 | if is_valid_ip "\$WAN_IP"; then 138 | RESPONSE=\$(curl -s -X PUT "https://api.cloudflare.com/client/v4/zones/\$CFZONE_ID/dns_records/\$CFRECORD_ID" \ 139 | -H "X-Auth-Email: \$CFUSER" \ 140 | -H "X-Auth-Key: \$CFKEY" \ 141 | -H "Content-Type: application/json" \ 142 | --data "{\"id\":\"\$CFZONE_ID\",\"type\":\"\$CFRECORD_TYPE\",\"name\":\"\$CFRECORD_NAME\",\"content\":\"\$WAN_IP\", \"ttl\":\$CFTTL}") 143 | 144 | if [ "\$RESPONSE" != "\${RESPONSE%success*}" ] && [ "\$(echo \$RESPONSE | grep "\"success\":true")" != "" ]; then 145 | echo "已同步到Cloudflare!" 146 | echo \$WAN_IP > \$WAN_IP_FILE 147 | else 148 | echo '出现错误 :(' 149 | echo "响应: \$RESPONSE" 150 | exit 1 151 | fi 152 | else 153 | echo "IP地址无效,无法更新DNS记录" 154 | exit 1 155 | fi 156 | EOF 157 | 158 | # 赋予新脚本执行权限 159 | chmod +x cloudflare.sh 160 | 161 | # 设置计划任务 162 | (crontab -l 2>/dev/null; echo "* * * * * $(pwd)/cloudflare.sh") | crontab - 163 | 164 | # 完成提示 165 | echo "成功生成对应的配置文件,请执行 ./cloudflare.sh" 166 | 167 | # 提示用户计划任务已设置 168 | echo "计划任务已设置,脚本将每分钟运行一次。" 169 | --------------------------------------------------------------------------------