开发背景:

公司有台嵌入式拨号上网设备,内置busybox和完整wget命令(支持https协议),但没有curl、python、ruby、php等扩展工具可用。网上现有基于DNSPod实现的Linux脚本无法在该设备上运行,于是写了个Shell版动态域名客户端(ddnspod),现在发布出来希望能给需要的朋友带来一些方便。

项目源码:

https://github.com/anrip/dnspod-shell

DnsPod官方文档

https://support.dnspod.cn/Support/api

功能介绍:

  • 优雅的函数封装,灵活的更新策略
  • 基于DNSPod最新用户API实现动态域名客户端
  • 支持基于系统计划任务实现更新,防止脚本意外终止
  • 可运行于多数类unix系统中,包括部分嵌入式小型系统
  • 依赖sed/wget/nslookup命令,wget也可使用curl替代

更新说明:

2015年7月7日

  • 使用D+服务获取域名解析

2013年8月9日

  • 修正一处笔误

2013年8月8日

  • 默认DNS查询服务器更换为114.114.114.114

2013年5月23日

  • [[]]替换为[],防止一些嵌入设备无此命令

2013年4月1日

  • 完善说明文档
  • 优化全局变量定义
  • 刚发现DnsPod官方API示例已收录本文

2013年3月29日

  • 从dns服务器获取子域名IP
  • 实现仅IP变更后才提交更新

2013年3月28日

  • 现在是13年3月,故而第一个版本就定为v3.3吧
  • 使用APIv4.6实现简单的动态更新功能

常见问题:

record line invailid 将脚本保存为utf-8格式即可
Record id invalid 检查账号权限、是否冲突等

标签: shell, linux, dns, 域名

已有 67 条评论

  1. 若海 若海

    若提示 [: not found ,请使用管理员权限运行,或使用 test 语法替代。

    [ "$A" = "$B" ] 等价于 test "$A" = "$B"

  2. 写的不错!

  3. shenzhi shenzhi

    执行这一句wget --quiet --no-check-certificate --output-document=- $inter
    报错:
    Segmentation fault
    如果不加--no-check-certificate,则无错。

    1. 需要wget支持才能获取到远程的url信息,若系统不支持wget,也可以用curl替换。

  4. hostIP: 131.143.134.35 lastIP: 132.225.217.192#53***Can'tfindwww.songweiqi789.tk:Noanswer ./dns1.sh: 50: [: 26: unexpected operator postRS: Record line invalid

    是我的域名出问题了还是别的问题?请直接:qq179834480

    1. [:错误,是系统无命令造成的,尝试使用管理员账号执行或删除[和]命令。参考一楼回复的方法。

  5. hostIP: 116.227.134.146 lastIP: Server:114.114.114.114Address:114.114.114.114#53Non-authoritativeanswer:Name:y36.xchun.netAddress:113.121.42.19 postRS: Record id invalid

    请问为什么会postRS: Record id invalid
    我用的是raspberry pi

    1. 这个是从dns服务器返回当前解析记录出错,请告知你的版子使用的系统信息,我测试下。

  6. surpass_hww surpass_hww

    nslookup y36.xchun.net $dnsvr | tr -d '\n[:blank:]' | sed 's/.+1 ([0-9.]+)/\1/'
    这里的y36.xchun.net是什么意思?是指自己的域名吗?

    1. 是的,换成自己的域名即可

  7. gao_m1 gao_m1

    lastIP: Server:114.114.114.114Address:114.114.114.114#53Non-authoritativeanswer:***Can'tfindlab.xxx.xxxx.com:Noanswer
    后面提示不能找到我的那个域名是什么意思啊??

    1. 应该是无法解析域名造成的

  8. pan pan

    试了下和看了下脚本,好像只能更新子域名?

    另外我两个linux环境,一个成功,另一个始终不成功。。。好奇怪。

    不成功的现象就是无法解析DNS

  9. crazygit crazygit

    感谢楼主的分享,要是代码能放到github上,做成gist就好了,再代码里面加上自己更新代码的语句,那我们就可以及时获取更新了

    1. 可以的,我整理下

  10. neilzhang neilzhang

    非常感谢,在NAS上面部署了,运作很完美!

  11. 检查更新域名

    arDdnsCheck "anrip.com" "lab"
    arDdnsCheck "anrip.net" "lab"
    请问"lab"问题,如解析anrip.com和www.anrip.com, "lab"应该怎么添.
    "lab"替换成”www",www.anrip.com可以正常,但是anrip.com没有被设置到位.
    如添加一行arDdnsCheck "anrip.com" "@"出现lastIP: Server:114.114.114.114Address:114.114.114.114#53Non-authoritativeanswer:***Can'tfind@.anrip.com:Noanswer
    或添加一行arDdnsCheck "anrip.com" "",出现nslookup: '.anrip.com' is not a legal name (unexpected end of input)
    hostIP: xx.xx.xx.xx
    lastIP:

    额外问下,我如添加系统启动,如何做到循环检测,比方说几分钟自动运行循环一遍.
    谢谢大佬了

    1. 目前脚本不支持更新主域名,后续我可以更新下支持。不过,不建议你去更新主域名的IP地址,可以做一条url转向。

      想要循环执行,可以添加一条系统的计划任务,Ubuntu下可以用 crontab -e

  12. dhf dhf

    赞!何不将代码丢到github

  13. Jack Sun Jack Sun

    我的也出现"postRS: Record line invalid" 报错, 请问是怎么回事? 谢谢

    1. 经测试,record line invailid是脚本里中文字符导致的,将脚本保存为utf-8格式即可

  14. astankvai astankvai

    我的出现 line 68: syntax error: Unterminated quoted string.请问这个怎么解?确定代码没有写错。

    1. 修改下文件的编码,或者把中文去掉,或者就是把文件改成使用linux换行

  15. astankvai astankvai

    要么就出现wget: illegal option -- -
    BusyBox V1.12.1
    Usage: wget [-csq] [-O file] [-Y on/off] [-P DIR] [-U agent] url

    ...

    1. 这是 wget 不支持 https 协议造成的,换用 curl 或者编译独立的 wget 可以解决的

  16. 上面所示的项目源码没有执行循环、开机启动等行为吧?
    原谅我不想学shell

  17. 娃娃脾气 娃娃脾气

    如何设置顶级域名?使用“@”好像提示未找到。

  18. 要更新主域名,直接把lab换成空字符串就可以

    1. 雷迅 雷迅

      root@OpenWrt:~# dnspod
      nslookup: can't resolve '.leixunpc.com': Name or service not known
      hostIP: 113.225.147.137
      lastIP: 114.114.114.114 puic1.114ds.com
      postRS: 113.225.147.137
      hostIP: 113.225.147.137
      lastIP: 113.225.147.137

      主域名 换成@ 和空格都有这样的提示

      1. 去掉.试试,因为这个脚本使用的第三方解析服务造成的。

  19. jenkins jenkins

    出错信息Record id invalid 怎么回事呢?

    1. 可能会账号没有权限,冲突

  20. edward edward

    你好 我重新编写了一个适合自己小米路由的版本 但是不知道为什么传上去会显示record line invalid
    已经尝试过utf-8的问题了
    链接: http://pan.baidu.com/s/1sjDU1Wx 密码: m64a

  21. wztx wztx

    你好,请问DNSPOD一个域最多支持动态解析几个域名?

    1. 理论上没有限制

      1. wztx wztx

        好像是超过三个就不行了,我五台设备,最多成功三个

      2. wztx wztx

        不能正常更新的LOG
        Jan 18 03:30:25 admin: 开始更新dnspod 的域名IP指向
        Jan 18 03:30:26 admin: 目前的IP: 106.88.200.95
        Jan 18 03:30:26 admin: 原来的IP: 125.84.13.184
        Jan 18 03:30:27 admin: 提交的IP:

        能正常更新的LOG
        Jan 18 03:31:11 admin: 开始更新dnspod 的域名IP指向
        Jan 18 03:31:11 admin: 目前的IP: 125.84.15.126
        Jan 18 03:31:11 admin: 原来的IP: 14.105.89.225
        Jan 18 03:31:14 admin: 125.84.15.126
        Jan 18 03:31:14 admin: 提交的IP:

  22. shupan shupan

    没有使用说明呀。。我改了ddnspod.sh最后的设置用户参数ermail和erpass为dnspod的账户和密码,然后检查更新域名改成了自己的域名。运行起来有显示hostIP,lastIP不显示。postRS提示Record id invalid 失败了。CentOS 7

    1. 一般情况下,需要检查账号是否错误,域名是否有权限设置。网络是否可达。

  23. shupan shupan

    我想上面的原因可能是因为我在另外一台PC上也登陆了一个dnspodclient客户端导致的。将它停止后没有再报这个错误。

  24. silence silence

    咨询一下:

    复制dns.conf.example到同一目录下的dns.conf并根据你的配置修改即可。

    同一目录下的dns.conf  这句话没明白。(新手不好意思)

  25. dts dts

    感谢!在树莓派Raspbian 上完美工作。

    请教几个问题:1.我发现dnspod.com(国际版)的api和dnspod.cn是一样的,只是地址不同。所以我尝试使用dnspod.com的账户和api,并改动了ddnspod.sh第121行,结果(以账户、密码方式dns.conf):

    Linux hostIP: 116.12.x.x lastIP: postRS: Missing user token, login failed

    查源码,对比中英的api文档也找不到问题所在。我只是个初学者,请教有什么解决办法或者方向么?谢谢

  26. dts dts

    2.dnspod.com没有提供可视化的token生成界面,也得通过api的方式获取。

    https://www.dnspod.com/docs/info.html#get-the-user-token

    可是.sh代码应该怎么写呢……

    1. 请从github上获取更新,支持token

  27. copperfiled copperfiled

    如何把脚本改为直接读取wan口的ip,而不是在网站获取外网ip,因为路由有开ss,经常把ss的外网识别到域名上去,而不是真正的wan口自己拨号的外网ip。

    1. 可以使用 ifconfig 来读取wan口ip,然后使用grep取出来。

  28. shit shit

    admin@CntR6300V2:/jffs/scripts# ./ddnspod.sh
    Linux
    ./ddnspod.sh: line 96: command: not found
    ./ddnspod.sh: line 96: command: not found
    ./ddnspod.sh: line 96: command: not found
    ./ddnspod.sh: line 96: command: not found
    ./ddnspod.sh: line 96: command: not found
    hostIP: 192.168.1.6 192.168.6.1
    lastIP:
    postRS: Record line invalid

    我出现这写问题,我的路由器的上级路由器链接外网

    1. deangelx deangelx

      把 ddnspod.sh 的第96行的

      DIR=$(dirname -- "$(rreadlink "$0")")

      改为 DIR=$(dirname -- "$0") 就可以了

  29. shit shit

    admin@CntR6300V2:/jffs/scripts# ./ddnspod.sh
    Linux
    ddnspod.sh: line 96: command: not found
    ddnspod.sh: line 96: command: not found
    ddnspod.sh: line 96: command: not found
    ddnspod.sh: line 96: command: not found
    ddnspod.sh: line 96: command: not found
    hostIP: 192.168.1.6 192.168.6.1
    lastIP:
    postRS: Record line invalid

    我出现这写问题,我的路由器的上级路由器链接外网

  30. shit23 shit23

    admin@CntR6300V2:/jffs/scripts# ./ddnspod.sh
    Linux
    ddnspod.sh: line 96: command: not found
    ddnspod.sh: line 96: command: not found
    ddnspod.sh: line 96: command: not found
    ddnspod.sh: line 96: command: not found
    ddnspod.sh: line 96: command: not found
    hostIP: 192.168.1.6 192.168.6.1
    lastIP:
    postRS: Record line invalid

    我出现这写问题,我的路由器的上级路由器链接外网

  31. 长城 长城

    你好。我用的路由器启用 DNSPod 域名解析 然后也添加A套餐了。

     

    A套餐的地址是当前ip然后不能我把路由器解析了。A套餐还是显示我当前地址啊。。。

  32. 陈

    为什么我取得是本机IP,不是公网IP,请指教,谢谢

    1. Anakie Anakie

       

      arIpAddress() {

      }

      里面的内容全删掉  ,花括号里只留下面一句

       

      wget -qO - ifconfig.co

      1. ad ad

        获得外网IP了,但是Get Record Info Failed! 高手,还有办法吗

  33. 我用这个更新了ip,怎么设置ttl 目前ttl值是10  需要怎么修改

  34. jack jack

    root@OpenWrt:/usr/lib/ddns# ./ddnspod.sh
    Linux
    ./ddnspod.sh: /usr/lib/ddns/dns.conf: line 1: arToken=***: not found
    ./ddnspod.sh: /usr/lib/ddns/dns.conf: line 2: ip: not found
    ./ddnspod.sh: /usr/lib/ddns/dns.conf: line 2: ip: not found
    Updating Domain: .blocks
    hostIP:
    wget: can't execute 'openssl': No such file or directory
    wget: error getting response: Connection reset by peer
    wget: can't execute 'openssl': No such file or directory
    wget: error getting response: Connection reset by peer
    wget: can't execute 'openssl': No such file or directory
    wget: error getting response: Connection reset by peer
    Get Record Info Failed!
    ./ddnspod.sh: /usr/lib/ddns/dns.conf: line 3: ip: not found
    ./ddnspod.sh: /usr/lib/ddns/dns.conf: line 3: ip: not found
    Updating Domain: *
    hostIP:
    wget: can't execute 'openssl': No such file or directory
    wget: error getting response: Connection reset by peer
    wget: can't execute 'openssl': No such file or directory
    wget: error getting response: Connection reset by peer
    wget: can't execute 'openssl': No such file or directory
    wget: error getting response: Connection reset by peer
    Get Record Info Failed!
    root@OpenWrt:/usr/lib/ddns# wget: can't execute 'openssl': No such file or direc
    tory

    1. jack jack

      在openwrt中安装openssl-util就解决了openssl的问题。

      1. jack jack

        root@OpenWrt:/# /usr/lib/ddns/ddnspod.sh
        Linux
        /usr/lib/ddns/ddnspod.sh: /usr/lib/ddns/dns.conf: line 1: #: not found
        /usr/lib/ddns/ddnspod.sh: /usr/lib/ddns/dns.conf: line 8: ip: not found
        /usr/lib/ddns/ddnspod.sh: /usr/lib/ddns/dns.conf: line 8: ip: not found
        Updating Domain: **
        hostIP:
        Get Record Info Failed!
        新问题
        貌似没有获取IP地址。

      2. 因为dnspod现在是通过https协议请求数据,所以必须使用openssl

        1. ddht ddht

          大神,
          我的centos用openssl version -a,检查了是有openssl的,为什么还是不行。

          1. 主要看是否支持 curl 或者 wget with https

  35. hiben hiben

    Get Record Info Failed!
    请问怎么解决。

    1. 运行环境请贴下

  36. 好学的小王 好学的小王

    ArDNSPod可以同时解析ipv4和ipv6么

  37. 毛阿花 毛阿花

    大神 openwrt 18.06.04 路由器重启后 日志报“Get Record Info Failed!” 怎么解决 以前没有这种问题

    1. 信息太少无法判断

添加新评论