EdgeRouter 配置 dnspod 动态域名更新

测试路由器:UBNT EdgeRouter ER-X

路由器系统:EdgeRouter X v1.9.1.1


使用 Shell 脚本,配置为 pppoe 建立连接后被调用。

系统的 /etc/ppp/ip-up 脚本,会在 pppoe 连接建立后执行,并搜索 /config/scripts/ppp/ip-up.d/ 目录,执行目录下的所有脚本文件。

其中 /config/scripts 是路由器默认的配置目录,如果更新路由器固件,并不会删除其中的文件。


这款路由器支持 ssh 远程登录,可以使用 sftp 上传文件,放到 /config/scripts/ppp/ip-up.d/ 目录下即可,如果目录不存在,先建立目录层级。


脚本文件以下面方式运行(脚本文件名可以任意更改):

  (注:在使用之前,需要修改文件,设置正确的 ACCESS_TOKEN。参考:https://support.dnspod.cn/Kb/showarticle/tsid/227/)

1.  $> /config/scripts/ppp/ip-up.d/ddnspod.sh -q mydomain.com www

    这用来查询 mydomain.com 在平台上的 domainId, www 的 recordId

2. $> /config/scripts/ppp/ip-up.d/ddnspod.sh --test 1111 2222 www 0 10.1.1.1

    这用来提交测试的 IP 地址, 1111 为上面取得的 domainId,2222 为上面取得的 recordId,www 为子域名(可以用 @ 来更新主域名),0 为 record_line_id,最后是要提交的新 IP 地址。

    record_line_id,如果是默认线路,值为 0,更多的可选值请参考:https://www.dnspod.cn/docs/domains.html#record-line

 "line_ids": {
        "默认": 0,
        "国内": "7=0",
        "国外": "3=0",
        "电信": "10=0",
        "联通": "10=1",
        "教育网": "10=2",
        "移动": "10=3",
        "百度": "90=0",
        "谷歌": "90=1",
        "搜搜": "90=4",
        "有道": "90=2",
        "必应": "90=3",
        "搜狗": "90=5",
        "奇虎": "90=6",
        "搜索引擎": "80=0"
    }
    提交的线路 id 值应该与你的设置保持一致。

    如果 id 值中含有等号,请将 '=' 换成 '%3D',进行转义,如 "7%3D0" 

3. 路由器重新建立 pppoe 连接时,自动被调用执行

    这种方式使用,需要修改文件的最后一行,设置由上面第一种方式取得的 domainId 和 recordId,如果有多个域名要更新,复制为多行,并修改相应的 domainId, recordId 即可。

    可以在 /var/log/ppp.log 中查看最后一次记录消息


ddnspod-ubnt.sh 代码:

#!/bin/sh

#################################################
# MosDdns for EdgeRouter X v1.0
# Dynamic DNS using DNSPod API
# Original by mostone<mostone@hotmail.com>, http://www.anrip.com/ddnspod
# Tested on EdgeRouter X v1.9.1.1
#################################################

# Usage:
#  step 1. Set accessToken value at bellow.
#  step 2. Input command in Shell: ddnspod-ubnt.sh -p domainName subdomainName
#            this command will print domainId and recordId.
#  step 3. Add updateDdns function call in the last of this file, replace your
#            real domainId and recordId which get from step 1.
#  step 4. copy this shell script file to ubnt router.
#            path: /config/scripts/ppp/ip-up.d/
#            this file will be call by /etc/ppp/ip-up.
#
#  Done.


# Global Variables:
# Combine your token Id and token together as follows
ACCESS_TOKEN="11111,exxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxx4"

IS_PPP_UP=1
if [ -z $PPP_LOCAL ]; then
	IS_PPP_UP=0
fi

showMsg() {
	echo $1
	if [ $IS_PPP_UP -eq 1 ]; then
		echo $1 >> /var/log/ppp.log
	fi
}

# arguments: apiInterface postParameters
callApi() {
    local agent="MosDdns/1.0(mostone@hotmail.com)"
    local url="https://dnsapi.cn/${1:?'Info.Version'}"
    local params="login_token=${ACCESS_TOKEN}&format=json&${2}"
    curl --silent --request POST --user-agent $agent $url --data $params
}

# arguments: domainName subdomainName
printDomainAndRecordIds() {
    local response domainId recordId lastIp
    
    # Get domain Id
    response=$(callApi "Domain.Info" "domain=${1}")
    # echo "Domain.Info call respone: ${response}"
    domainId=$(echo $response | sed 's/.*{"id":"\([0-9]*\)".*/\1/')
    echo "    Domain[${1}] Id is:		${domainId}" 

    # Get Record Id
    response=$(callApi "Record.List" "domain_id=${domainId}&sub_domain=${2}")
    # echo "Record.List call respone: ${response}"
    recordId=$(echo $response | sed 's/.*\[{"id":"\([0-9]*\)".*/\1/')
    echo "    Record[${2}] Id is:		${recordId}" 
    
    # Print last Ip
    lastIp=$(echo $response | sed 's/.*,"value":"\([0-9\.]*\)".*/\1/')
    echo "    Server side last Ip:		${lastIp}" 
}

# arguments: domainId recordId
getLastIp() {
    local response lastIp
    
    # get last Ip
    response=$(callApi "Record.Info" "domain_id=${1}&record_id=${2}")
    lastIp=$(echo $response | sed 's/.*,"value":"\([0-9\.]*\)".*/\1/')
    
    # validate Ip
    case "$lastIp" in 
      [1-9][0-9]*)
        echo $lastIp
        return 0
        ;;
      *)
        echo $response | sed 's/.*,"message":"\([^"]*\)".*/\1/'
        return 1
        ;;
    esac
}

# arguments: domainId recordId subdomainName lineId newIp
updateDdns() {
    local response returnCode recordIp lastIp
    
    # get last Ip
    lastIp=$(getLastIp $1 $2)
    if [ $? -eq 1 ]; then
        showMsg $lastIp
        return 1
    fi
    
    # same Ip check
    if [ "$lastIp" = "$5" ]; then
        showMsg "Server side last Ip is the same as current local Ip!"
        return 1
    fi
        
    # update Ip
    response=$(callApi "Record.Ddns" "domain_id=${1}&record_id=${2}&sub_domain=${3}&record_line_id=${4}&value=${5}&record_type=A")
    returnCode=$(echo $response | sed 's/.*{"code":"\([0-9]*\)".*/\1/')
    recordIp=$(echo $response | sed 's/.*,"value":"\([0-9\.]*\)".*/\1/')
    
    showMsg "${response}"
    
    # Output Ip
    if [ "$recordIp" = "$5" ]; then
        if [ "$returnCode" = "1" ]; then
            showMsg "New Ip post success: ${recordIp}"
        else
            # Echo error message
            showMsg $(echo $response | sed 's/.*,"message":"\([^"]*\)".*/\1/')
        fi
    else
        showMsg "Update Failed! Please check your network."
    fi
}

# use -q to print domain and record Ids
if [ "-q" = "$1" ]; then
    printDomainAndRecordIds $2 $3
    exit 0
fi

# use (--test domainId recordId subdomainName lineId newIp) to test update
if [ "--test" = "$1" ]; then
	updateDdns $2 $3 $4 $5 $6
	exit 0
fi

# to sure be call by /etc/ppp/ip-up
if [ $IS_PPP_UP -eq 0 ]; then
    echo "Please copy script file to /config/scripts/ppp/ip-up.d/"
    exit 0
else
	date > /var/log/ppp.log
	echo -e "  PPP_LOCAL:${PPP_LOCAL} \n  PPP_REMOTE:${PPP_REMOTE}" >> /var/log/ppp.log
fi


# Place each domain you want to update as follows
# you can have multiple domainList blocks
#
# updateDdns arguments: domainId recordId subdomainName lineId newIp
#
# lineId samples: "line_ids": {
#        "默认": 0,
#        "国内": "7=0",   请将 '=' 换成 '%3D', "7%3D0"
#        "国外": "3=0",
#        "电信": "10=0",
#        "联通": "10=1", ......
# lineId list refrence: https://www.dnspod.cn/docs/domains.html#record-line
# (note: lineId if include '=', please replace with '%3D')
updateDdns "1111111" "222222" "@" "0" $PPP_LOCAL



补记:开了 VPN Server 之后,有客户端连接时,也会被执行,这时需要加一个 if 判断:

    if [ "$PPP_IFACE" != "pppoe0" ]; then
		#echo -e "PPP_IFACE:[${PPP_IFACE}]\nnot pppoe0" >> /var/log/ppp.log
		exit 0
    fi



参考资料:https://github.com/anrip/ArDNSPod

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值