You can not select more than 25 topics Topics must start with a letter or number, can include dashes ('-') and can be up to 35 characters long.

210 lines
5.7 KiB

  1. #!/usr/bin/env sh
  2. # shellcheck disable=SC2034
  3. dns_miab_info='Mail-in-a-Box
  4. Site: MailInaBox.email
  5. Docs: github.com/acmesh-official/acme.sh/wiki/dnsapi2#dns_miab
  6. Options:
  7. MIAB_Username Admin username
  8. MIAB_Password Admin password
  9. MIAB_Server Server hostname. FQDN of your_MIAB Server
  10. Issues: github.com/acmesh-official/acme.sh/issues/2550
  11. Author: Darven Dissek, William Gertz
  12. '
  13. ######## Public functions #####################
  14. #Usage: dns_miab_add _acme-challenge.www.domain.com "XKrxpRBosdIKFzxW_CT3KLZNf6q0HG9i01zxXp5CPBs"
  15. dns_miab_add() {
  16. fulldomain=$1
  17. txtvalue=$2
  18. _info "Using miab challange add"
  19. _debug fulldomain "$fulldomain"
  20. _debug txtvalue "$txtvalue"
  21. #retrieve MIAB environemt vars
  22. if ! _retrieve_miab_env; then
  23. return 1
  24. fi
  25. #check domain and seperate into doamin and host
  26. if ! _get_root "$fulldomain"; then
  27. _err "Cannot find any part of ${fulldomain} is hosted on ${MIAB_Server}"
  28. return 1
  29. fi
  30. _debug2 _sub_domain "$_sub_domain"
  31. _debug2 _domain "$_domain"
  32. #add the challenge record
  33. _api_path="custom/${fulldomain}/txt"
  34. _miab_rest "$txtvalue" "$_api_path" "POST"
  35. #check if result was good
  36. if _contains "$response" "updated DNS"; then
  37. _info "Successfully created the txt record"
  38. return 0
  39. else
  40. _err "Error encountered during record add"
  41. _err "$response"
  42. return 1
  43. fi
  44. }
  45. #Usage: dns_miab_rm _acme-challenge.www.domain.com "XKrxpRBosdIKFzxW_CT3KLZNf6q0HG9i01zxXp5CPBs"
  46. dns_miab_rm() {
  47. fulldomain=$1
  48. txtvalue=$2
  49. _info "Using miab challage delete"
  50. _debug fulldomain "$fulldomain"
  51. _debug txtvalue "$txtvalue"
  52. #retrieve MIAB environemt vars
  53. if ! _retrieve_miab_env; then
  54. return 1
  55. fi
  56. #check domain and seperate into doamin and host
  57. if ! _get_root "$fulldomain"; then
  58. _err "Cannot find any part of ${fulldomain} is hosted on ${MIAB_Server}"
  59. return 1
  60. fi
  61. _debug2 _sub_domain "$_sub_domain"
  62. _debug2 _domain "$_domain"
  63. #Remove the challenge record
  64. _api_path="custom/${fulldomain}/txt"
  65. _miab_rest "$txtvalue" "$_api_path" "DELETE"
  66. #check if result was good
  67. if _contains "$response" "updated DNS"; then
  68. _info "Successfully removed the txt record"
  69. return 0
  70. else
  71. _err "Error encountered during record remove"
  72. _err "$response"
  73. return 1
  74. fi
  75. }
  76. #################### Private functions below ##################################
  77. #
  78. #Usage: _get_root _acme-challenge.www.domain.com
  79. #Returns:
  80. # _sub_domain=_acme-challenge.www
  81. # _domain=domain.com
  82. _get_root() {
  83. _passed_domain=$1
  84. _debug _passed_domain "$_passed_domain"
  85. _i=2
  86. _p=1
  87. #get the zones hosed on MIAB server, must be a json stream
  88. _miab_rest "" "zones" "GET"
  89. if ! _is_json "$response"; then
  90. _err "ERROR fetching domain list"
  91. _err "$response"
  92. return 1
  93. fi
  94. #cycle through the passed domain seperating out a test domain discarding
  95. # the subdomain by marching thorugh the dots
  96. while true; do
  97. _test_domain=$(printf "%s" "$_passed_domain" | cut -d . -f ${_i}-100)
  98. _debug _test_domain "$_test_domain"
  99. if [ -z "$_test_domain" ]; then
  100. return 1
  101. fi
  102. #report found if the test domain is in the json response and
  103. # report the subdomain
  104. if _contains "$response" "\"$_test_domain\""; then
  105. _sub_domain=$(printf "%s" "$_passed_domain" | cut -d . -f 1-${_p})
  106. _domain=${_test_domain}
  107. return 0
  108. fi
  109. #cycle to the next dot in the passed domain
  110. _p=${_i}
  111. _i=$(_math "$_i" + 1)
  112. done
  113. return 1
  114. }
  115. #Usage: _retrieve_miab_env
  116. #Returns (from store or environment variables):
  117. # MIAB_Username
  118. # MIAB_Password
  119. # MIAB_Server
  120. #retrieve MIAB environment variables, report errors and quit if problems
  121. _retrieve_miab_env() {
  122. MIAB_Username="${MIAB_Username:-$(_readaccountconf_mutable MIAB_Username)}"
  123. MIAB_Password="${MIAB_Password:-$(_readaccountconf_mutable MIAB_Password)}"
  124. MIAB_Server="${MIAB_Server:-$(_readaccountconf_mutable MIAB_Server)}"
  125. #debug log the environmental variables
  126. _debug MIAB_Username "$MIAB_Username"
  127. _debug MIAB_Password "$MIAB_Password"
  128. _debug MIAB_Server "$MIAB_Server"
  129. #check if MIAB environemt vars set and quit if not
  130. if [ -z "$MIAB_Username" ] || [ -z "$MIAB_Password" ] || [ -z "$MIAB_Server" ]; then
  131. _err "You didn't specify one or more of MIAB_Username, MIAB_Password or MIAB_Server."
  132. _err "Please check these environment variables and try again."
  133. return 1
  134. fi
  135. #save the credentials to the account conf file.
  136. _saveaccountconf_mutable MIAB_Username "$MIAB_Username"
  137. _saveaccountconf_mutable MIAB_Password "$MIAB_Password"
  138. _saveaccountconf_mutable MIAB_Server "$MIAB_Server"
  139. return 0
  140. }
  141. #Useage: _miab_rest "XKrxpRBosdIKFzxW_CT3KLZNf6q0HG9i01zxXp5CPBs" "custom/_acme-challenge.www.domain.com/txt "POST"
  142. #Returns: "updated DNS: domain.com"
  143. #rest interface MIAB dns
  144. _miab_rest() {
  145. _data="$1"
  146. _api_path="$2"
  147. _httpmethod="$3"
  148. #encode username and password for basic authentication
  149. _credentials="$(printf "%s" "$MIAB_Username:$MIAB_Password" | _base64)"
  150. export _H1="Authorization: Basic $_credentials"
  151. _url="https://${MIAB_Server}/admin/dns/${_api_path}"
  152. _debug2 _data "$_data"
  153. _debug _api_path "$_api_path"
  154. _debug2 _url "$_url"
  155. _debug2 _credentails "$_credentials"
  156. _debug _httpmethod "$_httpmethod"
  157. if [ "$_httpmethod" = "GET" ]; then
  158. response="$(_get "$_url")"
  159. else
  160. response="$(_post "$_data" "$_url" "" "$_httpmethod")"
  161. fi
  162. _retcode="$?"
  163. if [ "$_retcode" != "0" ]; then
  164. _err "MIAB REST authentication failed on $_httpmethod"
  165. return 1
  166. fi
  167. _debug response "$response"
  168. return 0
  169. }
  170. #Usage: _is_json "\[\n "mydomain.com"\n]"
  171. #Reurns "\[\n "mydomain.com"\n]"
  172. #returns the string if it begins and ends with square braces
  173. _is_json() {
  174. _str="$(echo "$1" | _normalizeJson)"
  175. echo "$_str" | grep '^\[.*\]$' >/dev/null 2>&1
  176. }