Linux shell 阿里云IPV6 DNS解析

该教程介绍了如何在OpenWRT系统中使用LinuxShell脚本,结合阿里云DNS服务,自动更新家用网络设备的IPv6DNS解析记录。这样即使没有公网IPv4,也能通过IPv6访问家中的智能设备,包括Webdav、SMB、RDP等服务。
摘要由CSDN通过智能技术生成

Linux shell 阿里云IPV6 DNS解析

记录一下本地服务器自动更新IPV6 DNS解析的过程

需求

由于移动不提供动态公网IPV4(联通,电信有动态公网IP),需要在外访问家中的网络设备。
只要有IPV6网络,就可以访问家中的设备,无需购买有公网IP的服务器,可以做域名解析,速度还是很快的,跟局域网访问差不多,速度差别根据你的带宽而定,主要有以下用途:。

  1. 搭建IPV6网站
  2. Webdav文件服务
  3. 远程SMB服务
  4. 远程RDP桌面连接
  5. 远程管理家中智能设备
  6. 只要能用IPV6地址的地方

本教程以OPENWRT为例

// 安装必要依赖
opkg update
opkg install openssl-util bash curl jq

配置阿里DNS的登录ID和秘钥并设置你需要自动更新的域名,记录,解析类型

# -----------------------------------------------------------------------------
api_domain='alidns.aliyuncs.com'

# https://ram.console.aliyun.com/manage/ak
ak_id="yourid"
ak_secret="yoursecret"

# Fixed, only one
signature_method='HMAC-SHA1'

# Alidns Domain properties
# -----------------------------------------------------------------------------
domain="yourdomain"
records=('yourrecord')
records_type="AAAA"

获取本机IPV6地址,RE正则匹配

语法 ipconfig [interface] | egrep -o [re] | head -n 1
移动IPV6 2409开头
电信IPV6 240e开头
联通IPV6 2408开头

get_public_ip() {
  public_ip= ifconfig pppoe-wan | egrep -o "2409:.*:[a-z0-9]{3,4}:[a-z0-9]{3,4}" | head -n 1

  echo $public_ip
  return $public_ip
}

完整代码

#!/bin/bash

# Alidns properties
# -----------------------------------------------------------------------------
api_domain='alidns.aliyuncs.com'

# https://ram.console.aliyun.com/manage/ak
ak_id="yourid"
ak_secret="yoursecret"

# Fixed, only one
signature_method='HMAC-SHA1'

# Alidns Domain properties
# -----------------------------------------------------------------------------
domain="yourdomain"
records=('yourrecord')
records_type="AAAA"



# get public ip
# -----------------------------------------------------------------------------
get_public_ip() {
  public_ip= ifconfig pppoe-wan | egrep -o "2409:.*:[a-z0-9]{3,4}:[a-z0-9]{3,4}" | head -n 1

  echo $public_ip
  return $public_ip
}

# build param & signed
# -----------------------------------------------------------------------------
param_encode() {
  params=$1
  str=""
  for (( i=0; i<${#params}; i++ )); do
    char="${params:$i:1}"
    if [[ $char == [a-zA-Z0-9.~_-] ]]; then
      str="$str$char"
    else
      hex=`printf '%%%02X' "'$char"`
      str="$str$hex"
    fi
  done
  echo $str | sed -e 's/+/%20/g' -e 's/*/%21/g' -e 's/%7E/~/g'
}

# TODO: ':' hex is '%3A', but, alidns api return '%253A'
# I didn't find the reason, so I made a replacement first, there may be other problems.
param_tosign() {
  echo -n "GET&$(param_encode "/")&$(param_encode $1)" \
    | sed -e "s/\%3A/\%253A/g" \
    | openssl sha1 -binary -hmac "$ak_secret&" \
    | openssl base64
}


# dns actions
# -----------------------------------------------------------------------------

request() {
  timestamp=`date -u +%Y-%m-%dT%TZ`
  signature_nonce=`date +%d-%m-%Y_%H-%M-%S`
  params="AccessKeyId=$ak_id&DomainName=$1&Format=json&SignatureMethod=$signature_method&SignatureNonce=$signature_nonce&SignatureVersion=1.0&Timestamp=$timestamp&Version=2015-01-09&Action=$2"
  if [ ! -z "$3" ]; then
    params=$params"&"$3
  fi
  # dictionary sorting
  params=`awk 'BEGIN{split('"\"$params\""',arr,"&"); for(i in arr) {v=arr[i]"&"; print v}}' | sort | xargs echo | sed 's/ //g;s/&$//g'`
  sign=$(param_encode $(param_tosign $params))
  echo `curl -k -s "https://$api_domain/?$params&Signature=$sign"`
}

fetch_domain_records() {
  echo $(request $1 "DescribeDomainRecords")
}

update_domain_record() {
  request $1 "UpdateDomainRecord" "RR=$2&RecordId=$3&Type=$records_type&Value=$4"
}

add_domain_record() {
  request $1 "AddDomainRecord" "RR=$2&Type=$records_type&Value=$3"
}

batch_update() {
  ip=`get_public_ip`
  if [ "$?" != "0" ]; then
    echo "cannot get public ip"
    exit 1
  fi

  echo ""
  echo "Public IP: $ip"
  echo "-----------------------------------------------------------------------"
  echo ""
  #bellow set your domain
  existed_records=`fetch_domain_records "$domain" | jq .DomainRecords.Record`
  for i in "${records[@]}"; do
    echo $i
    if [ "$existed_records" = "null" ]; then
      add_domain_record $domain $i $ip
    else
      record=`echo $existed_records | jq -c '.[] | select( .RR | contains("'$i'"))'`
      if [ -z $record ]; then
        add_domain_record $domain $i $ip
      else
        record_id=`echo $record | jq .RecordId | sed -e "s/\"//g"`
        old_value=`echo $record | jq .Value | sed -e "s/\"//g"`
        if [ "$old_value" != "$ip" ]; then
          if [ "$record_id" = "null" ]; then
            add_domain_record $domain $i $ip
		echo "add records"
          else
            update_domain_record $domain $i $record_id $ip
		echo "update records"
          fi
        fi
      fi
    fi
    echo ""
    sleep 1
  done
}

batch_update

定时任务执行脚本,每隔十分钟执行一次

*/10 * * * * bash /root/aliddns.sh
  • 0
    点赞
  • 1
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值