| 123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280281 |
- #!/usr/bin/env sh
- # shellcheck disable=SC2034
- dns_beget_info='Beget.com
- Site: Beget.com
- Docs: github.com/acmesh-official/acme.sh/wiki/dnsapi2#dns_beget
- Options:
- BEGET_User API user
- BEGET_Password API password
- Issues: github.com/acmesh-official/acme.sh/issues/6200
- Author: ARNik <[email protected]>
- '
- Beget_Api="https://api.beget.com/api"
- #################### Public functions ####################
- # Usage: add _acme-challenge.www.domain.com "XKrxpRBosdIKFzxW_CT3KLZNf6q0HG9i01zxXp5CPBs"
- # Used to add txt record
- dns_beget_add() {
- fulldomain=$1
- txtvalue=$2
- _debug "dns_beget_add() $fulldomain $txtvalue"
- fulldomain=$(echo "$fulldomain" | _lower_case)
- Beget_Username="${Beget_Username:-$(_readaccountconf_mutable Beget_Username)}"
- Beget_Password="${Beget_Password:-$(_readaccountconf_mutable Beget_Password)}"
- if [ -z "$Beget_Username" ] || [ -z "$Beget_Password" ]; then
- Beget_Username=""
- Beget_Password=""
- _err "You must export variables: Beget_Username, and Beget_Password"
- return 1
- fi
- #save the credentials to the account conf file.
- _saveaccountconf_mutable Beget_Username "$Beget_Username"
- _saveaccountconf_mutable Beget_Password "$Beget_Password"
- _info "Prepare subdomain."
- if ! _prepare_subdomain "$fulldomain"; then
- _err "Can't prepare subdomain."
- return 1
- fi
- _info "Get domain records"
- data="{\"fqdn\":\"$fulldomain\"}"
- res=$(_api_call "$Beget_Api/dns/getData" "$data")
- if ! _is_api_reply_ok "$res"; then
- _err "Can't get domain records."
- return 1
- fi
- _info "Add new TXT record"
- data="{\"fqdn\":\"$fulldomain\",\"records\":{"
- data=${data}$(_parce_records "$res" "A")
- data=${data}$(_parce_records "$res" "AAAA")
- data=${data}$(_parce_records "$res" "CAA")
- data=${data}$(_parce_records "$res" "MX")
- data=${data}$(_parce_records "$res" "SRV")
- data=${data}$(_parce_records "$res" "TXT")
- data=$(echo "$data" | sed 's/,$//')
- data=${data}'}}'
- str=$(_txt_to_dns_json "$txtvalue")
- data=$(_add_record "$data" "TXT" "$str")
- res=$(_api_call "$Beget_Api/dns/changeRecords" "$data")
- if ! _is_api_reply_ok "$res"; then
- _err "Can't change domain records."
- return 1
- fi
- return 0
- }
- # Usage: fulldomain txtvalue
- # Used to remove the txt record after validation
- dns_beget_rm() {
- fulldomain=$1
- txtvalue=$2
- _debug "dns_beget_rm() $fulldomain $txtvalue"
- fulldomain=$(echo "$fulldomain" | _lower_case)
- Beget_Username="${Beget_Username:-$(_readaccountconf_mutable Beget_Username)}"
- Beget_Password="${Beget_Password:-$(_readaccountconf_mutable Beget_Password)}"
- _info "Get current domain records"
- data="{\"fqdn\":\"$fulldomain\"}"
- res=$(_api_call "$Beget_Api/dns/getData" "$data")
- if ! _is_api_reply_ok "$res"; then
- _err "Can't get domain records."
- return 1
- fi
- _info "Remove TXT record"
- data="{\"fqdn\":\"$fulldomain\",\"records\":{"
- data=${data}$(_parce_records "$res" "A")
- data=${data}$(_parce_records "$res" "AAAA")
- data=${data}$(_parce_records "$res" "CAA")
- data=${data}$(_parce_records "$res" "MX")
- data=${data}$(_parce_records "$res" "SRV")
- data=${data}$(_parce_records "$res" "TXT")
- data=$(echo "$data" | sed 's/,$//')
- data=${data}'}}'
- str=$(_txt_to_dns_json "$txtvalue")
- data=$(_rm_record "$data" "$str")
- res=$(_api_call "$Beget_Api/dns/changeRecords" "$data")
- if ! _is_api_reply_ok "$res"; then
- _err "Can't change domain records."
- return 1
- fi
- return 0
- }
- #################### Private functions below ####################
- # Create subdomain if needed
- # Usage: _prepare_subdomain [fulldomain]
- _prepare_subdomain() {
- fulldomain=$1
- _info "Detect the root zone"
- if ! _get_root "$fulldomain"; then
- _err "invalid domain"
- return 1
- fi
- _debug _domain_id "$_domain_id"
- _debug _sub_domain "$_sub_domain"
- _debug _domain "$_domain"
- if [ -z "$_sub_domain" ]; then
- _debug "$fulldomain is a root domain."
- return 0
- fi
- _info "Get subdomain list"
- res=$(_api_call "$Beget_Api/domain/getSubdomainList")
- if ! _is_api_reply_ok "$res"; then
- _err "Can't get subdomain list."
- return 1
- fi
- if _contains "$res" "\"fqdn\":\"$fulldomain\""; then
- _debug "Subdomain $fulldomain already exist."
- return 0
- fi
- _info "Subdomain $fulldomain does not exist. Let's create one."
- data="{\"subdomain\":\"$_sub_domain\",\"domain_id\":$_domain_id}"
- res=$(_api_call "$Beget_Api/domain/addSubdomainVirtual" "$data")
- if ! _is_api_reply_ok "$res"; then
- _err "Can't create subdomain."
- return 1
- fi
- _debug "Cleanup subdomen records"
- data="{\"fqdn\":\"$fulldomain\",\"records\":{}}"
- res=$(_api_call "$Beget_Api/dns/changeRecords" "$data")
- if ! _is_api_reply_ok "$res"; then
- _debug "Can't cleanup $fulldomain records."
- fi
- data="{\"fqdn\":\"www.$fulldomain\",\"records\":{}}"
- res=$(_api_call "$Beget_Api/dns/changeRecords" "$data")
- if ! _is_api_reply_ok "$res"; then
- _debug "Can't cleanup www.$fulldomain records."
- fi
- return 0
- }
- # Usage: _get_root _acme-challenge.www.domain.com
- #returns
- # _sub_domain=_acme-challenge.www
- # _domain=domain.com
- # _domain_id=32436365
- _get_root() {
- fulldomain=$1
- i=1
- p=1
- _debug "Get domain list"
- res=$(_api_call "$Beget_Api/domain/getList")
- if ! _is_api_reply_ok "$res"; then
- _err "Can't get domain list."
- return 1
- fi
- while true; do
- h=$(printf "%s" "$fulldomain" | cut -d . -f "$i"-100)
- _debug h "$h"
- if [ -z "$h" ]; then
- return 1
- fi
- if _contains "$res" "$h"; then
- _domain_id=$(echo "$res" | _egrep_o "\"id\":[0-9]*,\"fqdn\":\"$h\"" | cut -d , -f1 | cut -d : -f2)
- if [ "$_domain_id" ]; then
- if [ "$h" != "$fulldomain" ]; then
- _sub_domain=$(echo "$fulldomain" | cut -d . -f 1-"$p")
- else
- _sub_domain=""
- fi
- _domain=$h
- return 0
- fi
- return 1
- fi
- p="$i"
- i=$(_math "$i" + 1)
- done
- return 1
- }
- # Parce DNS records from json string
- # Usage: _parce_records [j_str] [record_name]
- _parce_records() {
- j_str=$1
- record_name=$2
- res="\"$record_name\":["
- res=${res}$(echo "$j_str" | _egrep_o "\"$record_name\":\[.*" | cut -d '[' -f2 | cut -d ']' -f1)
- res=${res}"],"
- echo "$res"
- }
- # Usage: _add_record [data] [record_name] [record_data]
- _add_record() {
- data=$1
- record_name=$2
- record_data=$3
- echo "$data" | sed "s/\"$record_name\":\[/\"$record_name\":\[$record_data,/" | sed "s/,\]/\]/"
- }
- # Usage: _rm_record [data] [record_data]
- _rm_record() {
- data=$1
- record_data=$2
- echo "$data" | sed "s/$record_data//g" | sed "s/,\+/,/g" |
- sed "s/{,/{/g" | sed "s/,}/}/g" |
- sed "s/\[,/\[/g" | sed "s/,\]/\]/g"
- }
- _txt_to_dns_json() {
- echo "{\"ttl\":600,\"txtdata\":\"$1\"}"
- }
- # Usage: _api_call [api_url] [input_data]
- _api_call() {
- api_url="$1"
- input_data="$2"
- _debug "_api_call $api_url"
- _debug "Request: $input_data"
- # res=$(curl -s -L -D ./http.header \
- # "$api_url" \
- # --data-urlencode login=$Beget_Username \
- # --data-urlencode passwd=$Beget_Password \
- # --data-urlencode input_format=json \
- # --data-urlencode output_format=json \
- # --data-urlencode "input_data=$input_data")
- url="$api_url?login=$Beget_Username&passwd=$Beget_Password&input_format=json&output_format=json"
- if [ -n "$input_data" ]; then
- url=${url}"&input_data="
- url=${url}$(echo "$input_data" | _url_encode)
- fi
- res=$(_get "$url")
- _debug "Reply: $res"
- echo "$res"
- }
- # Usage: _is_api_reply_ok [api_reply]
- _is_api_reply_ok() {
- _contains "$1" '^{"status":"success","answer":{"status":"success","result":.*}}$'
- }
|