Skip to content

Instantly share code, notes, and snippets.

@pd12bbf7608ae1
Created January 26, 2023 11:11
Show Gist options
  • Save pd12bbf7608ae1/03d0d687dc82571fd190fc3d7768f703 to your computer and use it in GitHub Desktop.
Save pd12bbf7608ae1/03d0d687dc82571fd190fc3d7768f703 to your computer and use it in GitHub Desktop.
ddns_dynv6.sh
#!/bin/bash
# debug=1
tokens="" # dynv6 HTTP token
apiEndpoint='dynv6.com'
apiRootPath='/api/v2'
historyFile=".iphistory_dynv6" # history file
fontRed='\033[31m'
fontGreen='\033[32m'
fontBlue='\033[36m'
fontNormal='\033[0m'
function echoRed() {
echo -e "${fontRed}${*}${fontNormal}"
}
function echoBlue() {
echo -e "${fontBlue}${*}${fontNormal}"
}
function echoGreen() {
echo -e "${fontGreen}${*}${fontNormal}"
}
function debug() {
if [ "$debug" == "1" ]; then
echo "$*"
fi
}
# dynv6 API
function GetZoneId() { # 输入zone名称 返回id
local zone="$1"
echoBlue "查询zoneId..." 1>&2
local curlInfo curlCode
curlInfo=$(curl --retry 3 --retry-max-time 30 -w "Code:%{response_code}" -H "Authorization: Bearer ${tokens}" -H "Accept: application/json" -X "GET" "https://${apiEndpoint}${apiRootPath}/zones/by-name/${zone}")
curlCode="$?"
debug "$curlInfo" 1>&2
if [ "$curlCode" -ne 0 ]; then
echoRed "curl 错误 Code:${curlCode}" 1>&2
return 1
else
local responseCode=$(echo "${curlInfo}" | tr -d "\n" | sed -e "s/.*Code://g")
if [ "$responseCode" != "200" ]; then
echoRed "响应码错误 Code:${responseCode}" 1>&2
return 1
else
local zoneId=$(echo "${curlInfo}" | tr -d '\n' | sed -n -e 's/[^{]*\({.*}\+\).*/\1/p' | sed -e "s/,/\n/g" -e "s/{//g" -e "s/}//g" | grep "\"id\"" | cut -d ":" -f 2)
if [ -z "${zoneId}" ]; then
echoRed "zoneId为空" 1>&2
return 1
else
echo "${zoneId}"
return 0
fi
fi
fi
}
function UpdateZoneIPv4Address() { # 输入zoneId ipv4地址
local zoneId="$1"
local ipv4Address="$2"
echoBlue "更新Zone ipv4..." 1>&2
local curlInfo curlCode
local requestBody="{
\"ipv4address\": \"${ipv4Address}\"
}"
curlInfo=$(curl --retry 3 --retry-max-time 30 -w "Code:%{response_code}" -H "Authorization: Bearer ${tokens}" -H "Accept: application/json" -H "Content-Type: application/json" -X "PATCH" --data "${requestBody}" "https://${apiEndpoint}${apiRootPath}/zones/${zoneId}")
curlCode="$?"
debug "$curlInfo" 1>&2
if [ "$curlCode" -ne 0 ]; then
echoRed "curl 错误 Code:${curlCode}" 1>&2
return 1
else
local responseCode=$(echo "${curlInfo}" | tr -d "\n" | sed -e "s/.*Code://g")
if [ "$responseCode" != "200" ]; then
echoRed "响应码错误 Code:${responseCode}" 1>&2
return 1
else
return 0
fi
fi
}
function UpdateZoneIPv6Prefix() { # 输入zoneId ipv6地址
local zoneId="$1"
local ipv6Prefix="$2"
echoBlue "更新Zone ipv6前缀..." 1>&2
local requestBody="{
\"ipv6prefix\": \"${ipv6Prefix}\"
}"
local curlInfo curlCode
curlInfo=$(curl --retry 3 --retry-max-time 30 -w "Code:%{response_code}" -H "Authorization: Bearer ${tokens}" -H "Accept: application/json" -H "Content-Type: application/json" -X "PATCH" --data "${requestBody}" "https://${apiEndpoint}${apiRootPath}/zones/${zoneId}")
curlCode="$?"
debug "$curlInfo" 1>&2
if [ "$curlCode" -ne 0 ]; then
echoRed "curl 错误 Code:${curlCode}" 1>&2
return 1
else
local responseCode=$(echo "${curlInfo}" | tr -d "\n" | sed -e "s/.*Code://g")
if [ "$responseCode" != "200" ]; then
echoRed "响应码错误 Code:${responseCode}" 1>&2
return 1
else
return 0
fi
fi
}
function GetRecordId() { # 输入zoneId 主机名 记录类型 返回数组 recordId
local zoneId="$1"
local name="$2"
local type="$3"
echoBlue "查询记录编号..." 1>&2
local curlInfo curlCode
curlInfo=$(curl --retry 3 --retry-max-time 30 -w "Code:%{response_code}" -H "Authorization: Bearer ${tokens}" -H "Accept: application/json" -X "GET" "https://${apiEndpoint}${apiRootPath}/zones/${zoneId}/records")
curlCode="$?"
debug "$curlInfo" 1>&2
if [ "$curlCode" -ne 0 ]; then
echoRed "curl 错误 Code:${curlCode}" 1>&2
return 1
else
local responseCode=$(echo "${curlInfo}" | tr -d "\n" | sed -e "s/.*Code://g")
if [ "$responseCode" != "200" ]; then
echoRed "响应码错误 Code:${responseCode}" 1>&2
return 1
else
local recordsList=$(echo "${curlInfo}" | tr -d '\n' | sed -n -e 's/[^{]*\({.*}\+\).*/\1/p' | sed -e "s/},{/\n/g" -e "s/{//g" -e "s/}//g" | grep "\"type\":\"${type}\"" | grep "\"name\":\"${name}\"")
local recordsNum=$(echo "${recordsList}" | wc -l)
for ((i=1; i <= ${recordsNum}; i++)); do
local id=$(echo "${recordsList}" | sed -n "${i}p" | sed -e 's/,\"/\n\"/g' | grep "\"id\":" | cut -d ':' -f 2)
local recordsId=("${recordsId[@]}" "${id}")
done
fi
fi
echo "${recordsId[@]}"
return 0
}
function DeleteRecord() { # 输入zoneId recordID
local zoneId="$1"
local recordId="$2"
echoBlue "删除记录...." 1>&2
local curlInfo curlCode
curlInfo=$(curl --retry 3 --retry-max-time 30 -w "Code:%{response_code}" -H "Authorization: Bearer ${tokens}" -H "Accept: application/json" -X "DELETE" "https://${apiEndpoint}${apiRootPath}/zones/${zoneId}/records/${recordId}")
curlCode="$?"
debug "$curlInfo" 1>&2
if [ "$curlCode" -ne 0 ]; then
echoRed "curl 错误 Code:${curlCode}" 1>&2
return 1
else
local responseCode=$(echo "${curlInfo}" | tr -d "\n" | sed -e "s/.*Code://g")
if [ "$responseCode" != "204" ]; then
echoRed "响应码错误 Code:${responseCode}" 1>&2
return 1
else
echoGreen "删除成功" 1>&2
return 0
fi
fi
}
function UpdateRecord() { # 输入zoneId recordID data
local zoneId="$1"
local recordId="$2"
local data="$3"
echoBlue "更新记录..." 1>&2
local requestBody="{
\"data\": \"${data}\"
}"
local curlInfo curlCode
curlInfo=$(curl --retry 3 --retry-max-time 30 -w "Code:%{response_code}" -H "Authorization: Bearer ${tokens}" -H "Accept: application/json" -H "Content-Type: application/json" -X "PATCH" --data "$requestBody" "https://${apiEndpoint}${apiRootPath}/zones/${zoneId}/records/${recordId}")
curlCode="$?"
debug "$curlInfo" 1>&2
if [ "$curlCode" -ne 0 ]; then
echoRed "curl 错误 Code:${curlCode}" 1>&2
return 1
else
local responseCode=$(echo "${curlInfo}" | tr -d "\n" | sed -e "s/.*Code://g")
if [ "$responseCode" != "200" ]; then
echoRed "响应码错误 Code:${responseCode}" 1>&2
return 1
else
echoGreen "更新成功" 1>&2
return 0
fi
fi
}
function AddRecord() { # 输入zoneId name data type
local zoneId="$1"
local name="$2"
local data="$3"
local type="$4"
echoBlue "增加记录..." 1>&2
local requestBody="{
\"name\": \"${name}\",
\"data\": \"${data}\",
\"type\": \"${type}\"
}"
local curlInfo curlCode
curlInfo=$(curl --retry 3 --retry-max-time 30 -w "Code:%{response_code}" -H "Authorization: Bearer ${tokens}" -H "Accept: application/json" -H "Content-Type: application/json" -X "POST" --data "${requestBody}" "https://${apiEndpoint}${apiRootPath}/zones/${zoneId}/records")
curlCode="$?"
debug "$curlInfo" 1>&2
if [ "$curlCode" -ne 0 ]; then
echoRed "curl 错误 Code:${curlCode}" 1>&2
return 1
else
local responseCode=$(echo "${curlInfo}" | tr -d "\n" | sed -e "s/.*Code://g")
if [ "$responseCode" != "200" ]; then
echoRed "响应码错误 Code:${responseCode}" 1>&2
return 1
else
echoGreen "增加成功" 1>&2
return 0
fi
fi
}
# dynv6 API End
function UpdateHost() { # 更新宿主机的地址 输入 recordName device zone name(可选)
local recordName="$1"
local device="$2"
local zone="$3"
local name="$4"
echoBlue "更新${recordName}" 1>&2
local ipv4History ipv6History
ipv4History=$(echo "$history" | grep "^${recordName} " | cut -d " " -f 2)
ipv6History=$(echo "$history" | grep "^${recordName} " | cut -d " " -f 3)
if [ -n "$device" ]; then
device="dev $device"
fi
local ipv4Address ipv6Address
ipv4Address=$(ip -4 addr list scope global $device | sed -n "s/.*inet \([0-9.]\+\).*/\1/p" | head -n 1) #宿主机ipv4
ipv6Address=$(ip -6 addr list scope global $device | grep -v " fd" | sed -n 's/.*inet6 \([0-9a-f:]\+\).*/\1/p' | head -n 1) #宿主机ipv6
# 更新ipv4
if [[ -n "$ipv4Address" && "$ipv4History" != "$ipv4Address" ]]; then
echoBlue "ipv4变更" 1>&2
debug "记录: ${ipv4History}" 1>&2
debug "实际: ${ipv4Address}" 1>&2
if [ -z "$zoneId" ]; then
local zoneId
zoneId=$(GetZoneId "$zone")
debug "zoneId:${zoneId}" 1>&2
fi
if [ -n "$zoneId" ]; then # 得到zoneId
if [ -n "$name" ]; then # 为zone下的子记录
local recordsId recordsIdStatus
recordsId=($(GetRecordId "$zoneId" "$name" A))
recordsIdStatus="$?"
debug "recordsId: ${recordsId[@]}" 1>&2
if [[ "$recordsIdStatus" -eq 0 ]]; then # 获得成功 可能0个,1个,多个
if [[ "${#recordsId[@]}" -eq 0 ]]; then # 没有记录编号
echoBlue "无记录,添加..." 1>&2
AddRecord "$zoneId" "$name" "$ipv4Address" A
if [[ "$?" -eq 0 ]]; then
ipv4History="$ipv4Address"
fi
elif [[ "${#recordsId[@]}" -eq 1 ]]; then # 只有1个记录
echoBlue "修改现有记录..." 1>&2
UpdateRecord "$zoneId" "${recordsId[0]}" "$ipv4Address"
if [[ "$?" -eq 0 ]]; then
ipv4History="$ipv4Address"
fi
else # 多个记录
echoBlue "有多个记录,删除多余..." 1>&2
local deleteFail=0
for ((i=1;i<"${#recordsId[@]}" ;i++)); do
DeleteRecord "$zoneId" "${recordsId[${i}]}"
if [ "$?" -ne 0 ]; then
deleteFail=1
fi
done
if [ "$deleteFail" -eq 0 ]; then
echoBlue "修改现有记录..." 1>&2
UpdateRecord "$zoneId" "${recordsId[0]}" "$ipv4Address"
if [[ "$?" -eq 0 ]]; then
ipv4History="$ipv4Address"
fi
else
echoRed "删除失败" 1>&2
fi
fi
else # 获得失败 退出
echoRed "recordsId信息查询失败" 1>&2
fi
else # 为zone本身
UpdateZoneIPv4Address "$zoneId" "$ipv4Address"
if [[ "$?" -eq 0 ]]; then
ipv4History="$ipv4Address"
fi
fi
else
echoRed "zoneId获取失败" 1>&2
fi
fi
unset recordsId recordsIdStatus deleteFail
# 更新ipv6
if [[ -n "$ipv6Address" && "$ipv6History" != "$ipv6Address" ]]; then
echoBlue "ipv6变更" 1>&2
debug "记录: ${ipv6History}" 1>&2
debug "实际: ${ipv6Address}" 1>&2
if [ -z "$zoneId" ]; then
local zoneId
zoneId=$(GetZoneId "$zone")
debug "zoneId:${zoneId}" 1>&2
fi
if [ -n "$zoneId" ]; then # 得到zoneId
local recordsId recordsIdStatus
recordsId=($(GetRecordId "$zoneId" "$name" 'AAAA'))
recordsIdStatus="$?"
debug "recordsId: ${recordsId[@]}" 1>&2
if [[ "$recordsIdStatus" -eq 0 ]]; then # 获得成功 可能0个,1个,多个
if [[ "${#recordsId[@]}" -eq 0 ]]; then # 没有记录编号
echoBlue "无记录,添加..." 1>&2
AddRecord "$zoneId" "$name" "$ipv6Address" AAAA
if [[ "$?" -eq 0 ]]; then
ipv6History="$ipv6Address"
fi
elif [[ "${#recordsId[@]}" -eq 1 ]]; then # 只有1个记录
echoBlue "修改现有记录..." 1>&2
UpdateRecord "$zoneId" "${recordsId[0]}" "$ipv6Address"
if [[ "$?" -eq 0 ]]; then
ipv6History="$ipv6Address"
fi
else # 多个记录
echoBlue "有多个记录,删除多余..." 1>&2
local deleteFail=0
for ((i=1;i<"${#recordsId[@]}" ;i++)); do
DeleteRecord "$zoneId" "${recordsId[${i}]}"
if [ "$?" -ne 0 ]; then
deleteFail=1
fi
done
if [ "$deleteFail" -eq 0 ]; then
echoBlue "修改现有记录..." 1>&2
UpdateRecord "$zoneId" "${recordsId[0]}" "$ipv6Address"
if [[ "$?" -eq 0 ]]; then
ipv6History="$ipv6Address"
fi
else
echoRed "删除失败" 1>&2
fi
fi
else # 获得失败 退出
echoRed "recordsId信息查询失败" 1>&2
fi
else
echoRed "zoneId获取失败" 1>&2
fi
fi
unset recordsId recordsIdStatus deleteFail
echo "${recordName} ${ipv4History} ${ipv6History}"
}
function UpdateHostIPv4() { # 更新宿主机的地址 ipv4 Only 输入 recordName device zone name(可选)
local recordName="$1"
local device="$2"
local zone="$3"
local name="$4"
echoBlue "更新${recordName} IPv4Only" 1>&2
local ipv4History ipv6History
ipv4History=$(echo "$history" | grep "^${recordName} " | cut -d " " -f 2)
if [ -n "$device" ]; then
device="dev $device"
fi
local ipv4Address ipv6Address
ipv4Address=$(ip -4 addr list scope global $device | sed -n "s/.*inet \([0-9.]\+\).*/\1/p" | head -n 1) #宿主机ipv4
# 更新ipv4
if [[ -n "$ipv4Address" && "$ipv4History" != "$ipv4Address" ]]; then
echoBlue "ipv4变更" 1>&2
debug "记录: ${ipv4History}" 1>&2
debug "实际: ${ipv4Address}" 1>&2
if [ -z "$zoneId" ]; then
local zoneId
zoneId=$(GetZoneId "$zone")
debug "zoneId:${zoneId}" 1>&2
fi
if [ -n "$zoneId" ]; then # 得到zoneId
if [ -n "$name" ]; then # 为zone下的子记录
local recordsId recordsIdStatus
recordsId=($(GetRecordId "$zoneId" "$name" A))
recordsIdStatus="$?"
debug "recordsId: ${recordsId[@]}" 1>&2
if [[ "$recordsIdStatus" -eq 0 ]]; then # 获得成功 可能0个,1个,多个
if [[ "${#recordsId[@]}" -eq 0 ]]; then # 没有记录编号
echoBlue "无记录,添加..." 1>&2
AddRecord "$zoneId" "$name" "$ipv4Address" A
if [[ "$?" -eq 0 ]]; then
ipv4History="$ipv4Address"
fi
elif [[ "${#recordsId[@]}" -eq 1 ]]; then # 只有1个记录
echoBlue "修改现有记录..." 1>&2
UpdateRecord "$zoneId" "${recordsId[0]}" "$ipv4Address"
if [[ "$?" -eq 0 ]]; then
ipv4History="$ipv4Address"
fi
else # 多个记录
echoBlue "有多个记录,删除多余..." 1>&2
local deleteFail=0
for ((i=1;i<"${#recordsId[@]}" ;i++)); do
DeleteRecord "$zoneId" "${recordsId[${i}]}"
if [ "$?" -ne 0 ]; then
deleteFail=1
fi
done
if [ "$deleteFail" -eq 0 ]; then
echoBlue "修改现有记录..." 1>&2
UpdateRecord "$zoneId" "${recordsId[0]}" "$ipv4Address"
if [[ "$?" -eq 0 ]]; then
ipv4History="$ipv4Address"
fi
else
echoRed "删除失败" 1>&2
fi
fi
else # 获得失败 退出
echoRed "recordsId信息查询失败" 1>&2
fi
else # 为zone本身
UpdateZoneIPv4Address "$zoneId" "$ipv4Address"
if [[ "$?" -eq 0 ]]; then
ipv4History="$ipv4Address"
fi
fi
else
echoRed "zoneId获取失败" 1>&2
fi
fi
unset recordsId recordsIdStatus deleteFail
echo "${recordName} ${ipv4History} ${ipv6History}"
}
function UpdateHostIPv6() { # 更新宿主机的地址 ipv6 Only 输入 recordName device zone name(可选)
local recordName="$1"
local device="$2"
local zone="$3"
local name="$4"
echoBlue "更新${recordName}" 1>&2
local ipv4History ipv6History
ipv6History=$(echo "$history" | grep "^${recordName} " | cut -d " " -f 3)
if [ -n "$device" ]; then
device="dev $device"
fi
local ipv4Address ipv6Address
ipv6Address=$(ip -6 addr list scope global $device | grep -v " fd" | sed -n 's/.*inet6 \([0-9a-f:]\+\).*/\1/p' | head -n 1) #宿主机ipv6
# 更新ipv6
if [[ -n "$ipv6Address" && "$ipv6History" != "$ipv6Address" ]]; then
echoBlue "ipv6变更" 1>&2
debug "记录: ${ipv6History}" 1>&2
debug "实际: ${ipv6Address}" 1>&2
if [ -z "$zoneId" ]; then
local zoneId
zoneId=$(GetZoneId "$zone")
debug "zoneId:${zoneId}" 1>&2
fi
if [ -n "$zoneId" ]; then # 得到zoneId
local recordsId recordsIdStatus
recordsId=($(GetRecordId "$zoneId" "$name" 'AAAA'))
recordsIdStatus="$?"
debug "recordsId: ${recordsId[@]}" 1>&2
if [[ "$recordsIdStatus" -eq 0 ]]; then # 获得成功 可能0个,1个,多个
if [[ "${#recordsId[@]}" -eq 0 ]]; then # 没有记录编号
echoBlue "无记录,添加..." 1>&2
AddRecord "$zoneId" "$name" "$ipv6Address" AAAA
if [[ "$?" -eq 0 ]]; then
ipv6History="$ipv6Address"
fi
elif [[ "${#recordsId[@]}" -eq 1 ]]; then # 只有1个记录
echoBlue "修改现有记录..." 1>&2
UpdateRecord "$zoneId" "${recordsId[0]}" "$ipv6Address"
if [[ "$?" -eq 0 ]]; then
ipv6History="$ipv6Address"
fi
else # 多个记录
echoBlue "有多个记录,删除多余..." 1>&2
local deleteFail=0
for ((i=1;i<"${#recordsId[@]}" ;i++)); do
DeleteRecord "$zoneId" "${recordsId[${i}]}"
if [ "$?" -ne 0 ]; then
deleteFail=1
fi
done
if [ "$deleteFail" -eq 0 ]; then
echoBlue "修改现有记录..." 1>&2
UpdateRecord "$zoneId" "${recordsId[0]}" "$ipv6Address"
if [[ "$?" -eq 0 ]]; then
ipv6History="$ipv6Address"
fi
else
echoRed "删除失败" 1>&2
fi
fi
else # 获得失败 退出
echoRed "recordsId信息查询失败" 1>&2
fi
else
echoRed "zoneId获取失败" 1>&2
fi
fi
unset recordsId recordsIdStatus deleteFail
echo "${recordName} ${ipv4History} ${ipv6History}"
}
function UpdateContainer() { # 更新容器的地址 输入 recordName containerName device zone name(可选)
local recordName="$1"
local containerName="$2"
local device="$3"
local zone="$4"
local name="$5"
echoBlue "更新${recordName}" 1>&2
local ipv4History ipv6History
ipv4History=$(echo "$history" | grep "^${recordName} " | cut -d " " -f 2)
ipv6History=$(echo "$history" | grep "^${recordName} " | cut -d " " -f 3)
if [ -n "$device" ]; then
device="dev $device"
fi
local ipv4Address ipv6Address lxcInfo
lxcInfo="$(timeout 5s lxc exec local:${containerName} -- ip -4 addr list scope global $device)" # lxc IPv4信息
if [[ -n "$lxcInfo" ]]; then # 获取到信息
ipv4Address=$(echo "${lxcInfo}" | sed -n "s/.*inet \([0-9.]\+\).*/\1/p" | head -n 1) #容器ipv4
fi
lxcInfo="$(timeout 5s lxc exec local:${containerName} -- ip -6 addr list scope global $device)" # lxc IPv6信息
if [[ -n "$lxcInfo" ]]; then # 获取到信息
ipv6Address=$(echo "${lxcInfo}" | grep -v " fd" | sed -n 's/.*inet6 \([0-9a-f:]\+\).*/\1/p' | head -n 1) #容器ipv6
fi
# 更新ipv4
if [[ -n "$ipv4Address" && "$ipv4History" != "$ipv4Address" ]]; then
echoBlue "ipv4变更" 1>&2
debug "记录: ${ipv4History}" 1>&2
debug "实际: ${ipv4Address}" 1>&2
if [ -z "$zoneId" ]; then
local zoneId
zoneId=$(GetZoneId "$zone")
debug "zoneId:${zoneId}" 1>&2
fi
if [ -n "$zoneId" ]; then # 得到zoneId
if [ -n "$name" ]; then # 为zone下的子记录
local recordsId recordsIdStatus
recordsId=($(GetRecordId "$zoneId" "$name" A))
recordsIdStatus="$?"
debug "recordsId: ${recordsId[@]}" 1>&2
if [[ "$recordsIdStatus" -eq 0 ]]; then # 获得成功 可能0个,1个,多个
if [[ "${#recordsId[@]}" -eq 0 ]]; then # 没有记录编号
echoBlue "无记录,添加..." 1>&2
AddRecord "$zoneId" "$name" "$ipv4Address" A
if [[ "$?" -eq 0 ]]; then
ipv4History="$ipv4Address"
fi
elif [[ "${#recordsId[@]}" -eq 1 ]]; then # 只有1个记录
echoBlue "修改现有记录..." 1>&2
UpdateRecord "$zoneId" "${recordsId[0]}" "$ipv4Address"
if [[ "$?" -eq 0 ]]; then
ipv4History="$ipv4Address"
fi
else # 多个记录
echoBlue "有多个记录,删除多余..." 1>&2
local deleteFail=0
for ((i=1;i<"${#recordsId[@]}" ;i++)); do
DeleteRecord "$zoneId" "${recordsId[${i}]}"
if [ "$?" -ne 0 ]; then
deleteFail=1
fi
done
if [ "$deleteFail" -eq 0 ]; then
echoBlue "修改现有记录..." 1>&2
UpdateRecord "$zoneId" "${recordsId[0]}" "$ipv4Address"
if [[ "$?" -eq 0 ]]; then
ipv4History="$ipv4Address"
fi
else
echoRed "删除失败" 1>&2
fi
fi
else # 获得失败 退出
echoRed "recordsId信息查询失败" 1>&2
fi
else # 为zone本身
UpdateZoneIPv4Address "$zoneId" "$ipv4Address"
if [[ "$?" -eq 0 ]]; then
ipv4History="$ipv4Address"
fi
fi
else
echoRed "zoneId获取失败" 1>&2
fi
fi
unset recordsId recordsIdStatus deleteFail
# 更新ipv6
if [[ -n "$ipv6Address" && "$ipv6History" != "$ipv6Address" ]]; then
echoBlue "ipv6变更" 1>&2
debug "记录: ${ipv6History}" 1>&2
debug "实际: ${ipv6Address}" 1>&2
if [ -z "$zoneId" ]; then
local zoneId
zoneId=$(GetZoneId "$zone")
debug "zoneId:${zoneId}" 1>&2
fi
if [ -n "$zoneId" ]; then # 得到zoneId
local recordsId recordsIdStatus
recordsId=($(GetRecordId "$zoneId" "$name" 'AAAA'))
recordsIdStatus="$?"
debug "recordsId: ${recordsId[@]}" 1>&2
if [[ "$recordsIdStatus" -eq 0 ]]; then # 获得成功 可能0个,1个,多个
if [[ "${#recordsId[@]}" -eq 0 ]]; then # 没有记录编号
echoBlue "无记录,添加..." 1>&2
AddRecord "$zoneId" "$name" "$ipv6Address" AAAA
if [[ "$?" -eq 0 ]]; then
ipv6History="$ipv6Address"
fi
elif [[ "${#recordsId[@]}" -eq 1 ]]; then # 只有1个记录
echoBlue "修改现有记录..." 1>&2
UpdateRecord "$zoneId" "${recordsId[0]}" "$ipv6Address"
if [[ "$?" -eq 0 ]]; then
ipv6History="$ipv6Address"
fi
else # 多个记录
echoBlue "有多个记录,删除多余..." 1>&2
local deleteFail=0
for ((i=1;i<"${#recordsId[@]}" ;i++)); do
DeleteRecord "$zoneId" "${recordsId[${i}]}"
if [ "$?" -ne 0 ]; then
deleteFail=1
fi
done
if [ "$deleteFail" -eq 0 ]; then
echoBlue "修改现有记录..." 1>&2
UpdateRecord "$zoneId" "${recordsId[0]}" "$ipv6Address"
if [[ "$?" -eq 0 ]]; then
ipv6History="$ipv6Address"
fi
else
echoRed "删除失败" 1>&2
fi
fi
else # 获得失败 退出
echoRed "recordsId信息查询失败" 1>&2
fi
else
echoRed "zoneId获取失败" 1>&2
fi
fi
unset recordsId recordsIdStatus deleteFail
echo "${recordName} ${ipv4History} ${ipv6History}"
}
function UpdateContainerIPv4() { # 更新容器的地址 ipv4 Only 输入 recordName containerName device zone name(可选)
local recordName="$1"
local containerName="$2"
local device="$3"
local zone="$4"
local name="$5"
echoBlue "更新${recordName} IPv4Only" 1>&2
local ipv4History ipv6History
ipv4History=$(echo "$history" | grep "^${recordName} " | cut -d " " -f 2)
if [ -n "$device" ]; then
device="dev $device"
fi
local ipv4Address ipv6Address lxcInfo
lxcInfo="$(timeout 5s lxc exec local:${containerName} -- ip -4 addr list scope global $device)" # lxc IPv4信息
if [[ -n "$lxcInfo" ]]; then # 获取到信息
ipv4Address=$(echo "${lxcInfo}" | sed -n "s/.*inet \([0-9.]\+\).*/\1/p" | head -n 1) #容器ipv4
fi
# 更新ipv4
if [[ -n "$ipv4Address" && "$ipv4History" != "$ipv4Address" ]]; then
echoBlue "ipv4变更" 1>&2
debug "记录: ${ipv4History}" 1>&2
debug "实际: ${ipv4Address}" 1>&2
if [ -z "$zoneId" ]; then
local zoneId
zoneId=$(GetZoneId "$zone")
debug "zoneId:${zoneId}" 1>&2
fi
if [ -n "$zoneId" ]; then # 得到zoneId
if [ -n "$name" ]; then # 为zone下的子记录
local recordsId recordsIdStatus
recordsId=($(GetRecordId "$zoneId" "$name" A))
recordsIdStatus="$?"
debug "recordsId: ${recordsId[@]}" 1>&2
if [[ "$recordsIdStatus" -eq 0 ]]; then # 获得成功 可能0个,1个,多个
if [[ "${#recordsId[@]}" -eq 0 ]]; then # 没有记录编号
echoBlue "无记录,添加..." 1>&2
AddRecord "$zoneId" "$name" "$ipv4Address" A
if [[ "$?" -eq 0 ]]; then
ipv4History="$ipv4Address"
fi
elif [[ "${#recordsId[@]}" -eq 1 ]]; then # 只有1个记录
echoBlue "修改现有记录..." 1>&2
UpdateRecord "$zoneId" "${recordsId[0]}" "$ipv4Address"
if [[ "$?" -eq 0 ]]; then
ipv4History="$ipv4Address"
fi
else # 多个记录
echoBlue "有多个记录,删除多余..." 1>&2
local deleteFail=0
for ((i=1;i<"${#recordsId[@]}" ;i++)); do
DeleteRecord "$zoneId" "${recordsId[${i}]}"
if [ "$?" -ne 0 ]; then
deleteFail=1
fi
done
if [ "$deleteFail" -eq 0 ]; then
echoBlue "修改现有记录..." 1>&2
UpdateRecord "$zoneId" "${recordsId[0]}" "$ipv4Address"
if [[ "$?" -eq 0 ]]; then
ipv4History="$ipv4Address"
fi
else
echoRed "删除失败" 1>&2
fi
fi
else # 获得失败 退出
echoRed "recordsId信息查询失败" 1>&2
fi
else # 为zone本身
UpdateZoneIPv4Address "$zoneId" "$ipv4Address"
if [[ "$?" -eq 0 ]]; then
ipv4History="$ipv4Address"
fi
fi
else
echoRed "zoneId获取失败" 1>&2
fi
fi
unset recordsId recordsIdStatus deleteFail
echo "${recordName} ${ipv4History} ${ipv6History}"
}
function UpdateContainerIPv6() { # 更新容器的地址 ipv6 Only 输入 recordName containerName device zone name(可选)
local recordName="$1"
local containerName="$2"
local device="$3"
local zone="$4"
local name="$5"
echoBlue "更新${recordName} IPv6Only" 1>&2
local ipv4History ipv6History
ipv6History=$(echo "$history" | grep "^${recordName} " | cut -d " " -f 3)
if [ -n "$device" ]; then
device="dev $device"
fi
local ipv4Address ipv6Address lxcInfo
lxcInfo="$(timeout 5s lxc exec local:${containerName} -- ip -6 addr list scope global $device)" # lxc IPv6信息
if [[ -n "$lxcInfo" ]]; then # 获取到信息
ipv6Address=$(echo "${lxcInfo}" | grep -v " fd" | sed -n 's/.*inet6 \([0-9a-f:]\+\).*/\1/p' | head -n 1) #容器ipv6
fi
# 更新ipv6
if [[ -n "$ipv6Address" && "$ipv6History" != "$ipv6Address" ]]; then
echoBlue "ipv6变更" 1>&2
debug "记录: ${ipv6History}" 1>&2
debug "实际: ${ipv6Address}" 1>&2
if [ -z "$zoneId" ]; then
local zoneId
zoneId=$(GetZoneId "$zone")
debug "zoneId:${zoneId}" 1>&2
fi
if [ -n "$zoneId" ]; then # 得到zoneId
local recordsId recordsIdStatus
recordsId=($(GetRecordId "$zoneId" "$name" 'AAAA'))
recordsIdStatus="$?"
debug "recordsId: ${recordsId[@]}" 1>&2
if [[ "$recordsIdStatus" -eq 0 ]]; then # 获得成功 可能0个,1个,多个
if [[ "${#recordsId[@]}" -eq 0 ]]; then # 没有记录编号
echoBlue "无记录,添加..." 1>&2
AddRecord "$zoneId" "$name" "$ipv6Address" AAAA
if [[ "$?" -eq 0 ]]; then
ipv6History="$ipv6Address"
fi
elif [[ "${#recordsId[@]}" -eq 1 ]]; then # 只有1个记录
echoBlue "修改现有记录..." 1>&2
UpdateRecord "$zoneId" "${recordsId[0]}" "$ipv6Address"
if [[ "$?" -eq 0 ]]; then
ipv6History="$ipv6Address"
fi
else # 多个记录
echoBlue "有多个记录,删除多余..." 1>&2
local deleteFail=0
for ((i=1;i<"${#recordsId[@]}" ;i++)); do
DeleteRecord "$zoneId" "${recordsId[${i}]}"
if [ "$?" -ne 0 ]; then
deleteFail=1
fi
done
if [ "$deleteFail" -eq 0 ]; then
echoBlue "修改现有记录..." 1>&2
UpdateRecord "$zoneId" "${recordsId[0]}" "$ipv6Address"
if [[ "$?" -eq 0 ]]; then
ipv6History="$ipv6Address"
fi
else
echoRed "删除失败" 1>&2
fi
fi
else # 获得失败 退出
echoRed "recordsId信息查询失败" 1>&2
fi
else
echoRed "zoneId获取失败" 1>&2
fi
fi
unset recordsId recordsIdStatus deleteFail
echo "${recordName} ${ipv4History} ${ipv6History}"
}
function UpdateHostIPv6Prefix() { # 更新宿主机的地址 ipv6 前缀(64位) Only 输入 recordName device zone
local recordName="$1"
local device="$2"
local zone="$3"
echoBlue "更新${recordName} IPv6Prefix" 1>&2
local ipv4History ipv6History
ipv6History=$(echo "$history" | grep "^${recordName} " | cut -d " " -f 3)
if [ -n "$device" ]; then
device="dev $device"
fi
local ipv4Address ipv6AddressFull ipv6Prefix
ipv6AddressFull=$(ip -6 addr list scope global $device | grep -v " fd" | sed -n 's/.*inet6 \([0-9a-f:]\+\).*/\1/p' | head -n 1) #宿主机ipv6
# 补0
if [[ -n "$ipv6AddressFull" ]]; then
ipv6AddressFull=$(echo $ipv6AddressFull | awk '{if(NF<8){inner = "0"; for(missing = (8 - NF);missing>0;--missing){inner = inner ":0"}; if($2 == ""){$2 = inner} else if($3 == ""){$3 = inner} else if($4 == ""){$4 = inner} else if($5 == ""){$5 = inner} else if($6 == ""){$6 = inner} else if($7 == ""){$7 = inner}}; print $0}' FS=":" OFS=":" | awk '{for(i=1;i<9;++i){len = length($(i)); if(len < 1){$(i) = "0000"} else if(len < 2){$(i) = "000" $(i)} else if(len < 3){$(i) = "00" $(i)} else if(len < 4){$(i) = "0" $(i)} }; print $0}' FS=":" OFS=":")
ipv6Prefix=$(echo "$ipv6AddressFull" | sed -e 's/:[^:]*:[^:]*:[^:]*:[^:]*$/::/g')
fi
# 更新ipv6
if [[ -n "$ipv6Prefix" && "$ipv6History" != "$ipv6Prefix" ]]; then
echoBlue "ipv6前缀变更" 1>&2
debug "记录: ${ipv6History}" 1>&2
debug "实际: ${ipv6Prefix}" 1>&2
if [ -z "$zoneId" ]; then
local zoneId
zoneId=$(GetZoneId "$zone")
debug "zoneId:${zoneId}" 1>&2
fi
if [ -n "$zoneId" ]; then # 得到zoneId
UpdateZoneIPv6Prefix "$zoneId" "$ipv6Prefix"
if [[ "$?" -eq 0 ]]; then
ipv6History="$ipv6Prefix"
fi
else
echoRed "zoneId获取失败" 1>&2
fi
fi
unset recordsId recordsIdStatus deleteFail
echo "${recordName} ${ipv4History} ${ipv6History}"
}
if [ -r "$historyFile" ]; then
history=$(cat "$historyFile")
fi
debug "History:" 1>&2
debug "${history}" 1>&2
{
UpdateHost HOST eth0 'example.org' 'example'
UpdateHostIPv4 HOSTv4 eth0 'example.org' 'v4.example'
UpdateHostIPv6 HOSTv6 eth0 'example.org' 'v6.example'
UpdateHostIPv6Prefix HOSTv6Prefix eth0 'example.org'
UpdateContainer CONTAINER example eth0 'example.org' 'container'
} > "$historyFile"
debug "Update:" 1>&2
debug "$(cat "$historyFile")" 1>&2
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment