From 39b4837fc69c66b937777f0ee862629185a31481 Mon Sep 17 00:00:00 2001 From: William Mantly Date: Fri, 10 Jul 2026 23:17:43 -0400 Subject: [PATCH] Fix DigitalOcean domain sync (never set .domain) DigitalOcean.listDomains ran the API response through __parseRes, which does not map anything to `.domain` and additionally rewrites each item's `.name` to its subdomain via tld-extract. DO's /v2/domains returns objects keyed `name` with no zone id, so the domain objects had no usable `.domain` and Domain.create threw ObjectValidateError ("domain is not string type"), aborting the sync. Map name -> domain the way CloudFlare.listDomains does and skip __parseRes (it is for record responses). DO has no zone id; the earlier zoneId-omit fix covers that. Also request per_page=200 so accounts with >20 domains aren't truncated. Co-Authored-By: Claude Opus 4.8 --- nodejs/models/dns_provider/digitalocean.js | 12 ++++++++++-- 1 file changed, 10 insertions(+), 2 deletions(-) diff --git a/nodejs/models/dns_provider/digitalocean.js b/nodejs/models/dns_provider/digitalocean.js index 264c827..fc3cad8 100644 --- a/nodejs/models/dns_provider/digitalocean.js +++ b/nodejs/models/dns_provider/digitalocean.js @@ -40,9 +40,17 @@ class DigitalOcean extends DnsApi{ } async listDomains(){ - let res = await this.axios('get', '/domains'); + // DO returns {domains:[{name, ttl, zone_file}]} keyed by `name` and has no + // zone id (API paths use the domain name directly). Map name -> domain the + // way CloudFlare.listDomains does; do NOT run this through __parseRes, which + // rewrites `.name` to its subdomain and would leave no usable domain name. + let res = await this.axios('get', '/domains?per_page=200'); - return this.__parseRes(res.data.domains); + for(let domain of res.data.domains){ + domain.domain = domain.name; + } + + return res.data.domains; } async getRecords(domain, options){