From 2b4f2c8750e3fb7bf2648f90ad228dc4e087c120 Mon Sep 17 00:00:00 2001 From: Charles Ulrich Date: Sun, 16 Dec 2018 19:11:13 -0500 Subject: [PATCH] Fix for using apex domains with cloudflare DDNS When refactoring the Cloudflare DDNS code, I removed a bunch of assumptions but inadvertently added one. The refactored code did not allow for "apex" domain records, records for which there is no hostname, just the bare domain. (Traditionally, these have been referred to as '@' records but with the Cloudflare API, you just hand it the name of the zone.) Ideally there would be a checkbox or something in the UI for this, or even better a way to specify the record and zone separately but in lieu of that, we first try to break the provided string down into hostname and domain portions and look up the zoneId from that. If that fails, we try to look up the zondId using the whole string. And then finally fail if neither return a zone from the API. Hopefully fixes #926 and possibly the issue reported in PR #861. --- .../etc/inc/plugins.inc.d/dyndns/phpDynDNS.inc | 17 ++++++++++++++--- 1 file changed, 14 insertions(+), 3 deletions(-) diff --git a/dns/dyndns/src/etc/inc/plugins.inc.d/dyndns/phpDynDNS.inc b/dns/dyndns/src/etc/inc/plugins.inc.d/dyndns/phpDynDNS.inc index 72e45d73b..556fe2166 100644 --- a/dns/dyndns/src/etc/inc/plugins.inc.d/dyndns/phpDynDNS.inc +++ b/dns/dyndns/src/etc/inc/plugins.inc.d/dyndns/phpDynDNS.inc @@ -713,9 +713,6 @@ class updatedns case 'cloudflare-v6': $baseUrl = 'https://api.cloudflare.com/client/v4'; $fqdn = str_replace(' ', '', $this->_dnsHost); - $fqdnParts = explode('.', $fqdn); - $hostName = array_shift($fqdnParts); - $domainName = implode('.', $fqdnParts); $recordType = ($this->_useIPv6) ? 'AAAA' : 'A'; $hostData = array( "content" => "{$this->_dnsIP}", @@ -732,10 +729,24 @@ class updatedns // Get zone ID $zonesUrl = "$baseUrl/zones"; + // First, try removing the first part of the FQDN, + // under the assumption that it is probably the hostname, + // and look up the zone from what's left + $fqdnParts = explode('.', $fqdn); + $hostName = array_shift($fqdnParts); + $domainName = implode('.', $fqdnParts); $getZoneId = "$zonesUrl/?name=$domainName"; curl_setopt($ch, CURLOPT_URL, $getZoneId); $output = json_decode(curl_exec($ch)); $zoneId = $output->result[0]->id; + if (empty($zoneId)) { + // now try the full "hostname" as provided by the UI + $getZoneId = "$zonesUrl/?name=$fqdn"; + curl_setopt($ch, CURLOPT_URL, $getZoneId); + $output = json_decode(curl_exec($ch)); + $zoneId = $output->result[0]->id; + } + if ($zoneId) { // If zone ID was found get host ID $dnsRecordsUrl = "$zonesUrl/$zoneId/dns_records"; $getHostId = "$dnsRecordsUrl?name=$fqdn&type=$recordType";