From bfa36ebbf8aab3fce8fff1d9f4be8bd3b0db12fd Mon Sep 17 00:00:00 2001 From: Juho Teperi Date: Fri, 24 Jan 2020 19:21:01 +0200 Subject: [PATCH] DIGITALOCEAN: CAA is supported with some caveats (#592) Change the tests to skip test case with CAA `;` value for Digitalocean, because that specific feature isn't supported. Closes #588 --- docs/_providers/digitalocean.md | 5 +++++ integrationTest/integration_test.go | 9 ++++++++- providers/digitalocean/digitaloceanProvider.go | 13 +++++++++++++ 3 files changed, 26 insertions(+), 1 deletion(-) diff --git a/docs/_providers/digitalocean.md b/docs/_providers/digitalocean.md index 72b523795..f7c4cb769 100644 --- a/docs/_providers/digitalocean.md +++ b/docs/_providers/digitalocean.md @@ -35,3 +35,8 @@ D("example.tld", REG_NONE, DnsProvider(DIGITALOCEAN), ## Activation [Create OAuth Token](https://cloud.digitalocean.com/settings/applications) + +## Limitations + +- Digialocean DNS doesn't support `;` value with CAA-records ([DigitalOcean documentation](https://www.digitalocean.com/docs/networking/dns/how-to/create-caa-records/)) +- No support for TXT records with multiple strings, as the API prevents espacing quotes. diff --git a/integrationTest/integration_test.go b/integrationTest/integration_test.go index 8d5058c55..06d2d974c 100644 --- a/integrationTest/integration_test.go +++ b/integrationTest/integration_test.go @@ -493,12 +493,19 @@ func makeTests(t *testing.T) []*TestCase { if !providers.ProviderHasCapability(*providerToRun, providers.CanUseCAA) { t.Log("Skipping CAA Tests because provider does not support them") } else { + manyRecordsTc := tc("CAA many records", caa("@", "issue", 0, "letsencrypt.org"), caa("@", "issuewild", 0, ";"), caa("@", "iodef", 128, "mailto:test@example.com")) + + // Digitalocean doesn't support ";" as value for CAA records + if *providerToRun == "DIGITALOCEAN" { + manyRecordsTc = tc("CAA many records", caa("@", "issue", 0, "letsencrypt.org"), caa("@", "issuewild", 0, "comodoca.com"), caa("@", "iodef", 128, "mailto:test@example.com")) + } + tests = append(tests, tc("Empty"), tc("CAA record", caa("@", "issue", 0, "letsencrypt.org")), tc("CAA change tag", caa("@", "issuewild", 0, "letsencrypt.org")), tc("CAA change target", caa("@", "issuewild", 0, "example.com")), tc("CAA change flag", caa("@", "issuewild", 128, "example.com")), - tc("CAA many records", caa("@", "issue", 0, "letsencrypt.org"), caa("@", "issuewild", 0, ";"), caa("@", "iodef", 128, "mailto:test@example.com")), + manyRecordsTc, tc("CAA delete", caa("@", "issue", 0, "letsencrypt.org")), ) } diff --git a/providers/digitalocean/digitaloceanProvider.go b/providers/digitalocean/digitaloceanProvider.go index 1e60790e5..5ade43b91 100644 --- a/providers/digitalocean/digitaloceanProvider.go +++ b/providers/digitalocean/digitaloceanProvider.go @@ -67,6 +67,10 @@ var features = providers.DocumentationNotes{ providers.DocCreateDomains: providers.Can(), providers.DocOfficiallySupported: providers.Cannot(), providers.CanUseSRV: providers.Can(), + // Digitalocean support CAA records, except + // ";" value with issue/issuewild records: + // https://www.digitalocean.com/docs/networking/dns/how-to/create-caa-records/ + providers.CanUseCAA: providers.Can(), } func init() { @@ -215,6 +219,8 @@ func toRc(dc *models.DomainConfig, r *godo.DomainRecord) *models.RecordConfig { SrvWeight: uint16(r.Weight), SrvPort: uint16(r.Port), Original: r, + CaaTag: r.Tag, + CaaFlag: uint8(r.Flags), } t.SetLabelFromFQDN(name, dc.Name) t.SetTarget(target) @@ -240,6 +246,11 @@ func toReq(dc *models.DomainConfig, rc *models.RecordConfig) *godo.DomainRecordE case "TXT": // TXT records are the one place where DO combines many items into one field. target = rc.GetTargetCombined() + case "CAA": + // DO API requires that value ends in dot + // But the value returned from API doesn't contain this, + // so no need to strip the dot when reading value from API. + target = target + "." default: // no action required } @@ -252,5 +263,7 @@ func toReq(dc *models.DomainConfig, rc *models.RecordConfig) *godo.DomainRecordE Priority: priority, Port: int(rc.SrvPort), Weight: int(rc.SrvWeight), + Tag: rc.CaaTag, + Flags: int(rc.CaaFlag), } }