Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

[DXE-4099] akamai_dns_record does not handle DNS targets greater than 255 characters when using JSON instead of HCL #572

Open
brucep-care opened this issue Jul 26, 2024 · 6 comments

Comments

@brucep-care
Copy link

The terraform provider does not handle DNS targets properly when two conditions are met:

  1. At least one DNS target is greater than 255 characters in length, requiring it to be split into quoted segments
  2. Terraform is using JSON instead of HCL input files

Terraform and Akamai Terraform Provider Versions

Terraform v1.9.2
on linux_amd64
+ provider registry.terraform.io/akamai/akamai v6.3.0

Affected Resource(s)

  • akamai_dns_record

Terraform Configuration Files

HCL configuration:

terraform {
  required_providers {
    akamai = {
      source  = "akamai/akamai"
      version = "~> 6.3.0"
    }
  }
}

# Configure the Akamai Provider
provider "akamai" {
  edgerc = "~/.edgerc"
  config_section = "default"
}


resource "akamai_dns_record" "care_com_care_com_TXT" {
    zone = "care.com"
    name = "care.com"
    recordtype = "TXT"
    target = ["\"8458026\"", "\"MS=ms24770002\"", "\"adobe-idp-site-verification=4d443bb146b2a60fc0c0216c899a6ef9baa971cc3c36ac4b3020b4719b5c2e82\"", "\"apple-domain-verification=gRa8Rp7oPDzgoKmX\"", "\"asv=521ed26c76fff6d1c78b865a5f835387\"", "\"atlassian-domain-verification=vJ5NZGRPZnfOE2rwC8Zc0zb1mRcmpkNscRJqt8KdTo8qoVMkO53uZEq0Qo1QZB7U\"", "\"atlassian-sending-domain-verification=7fba82d1-5619-4701-99d2-68dd83463a5c\"", "\"atlassian-sending-domain-verification=ce852905-9be3-4df4-8061-8c8f81aaf5d7\"", "\"calendly-site-verification=JmFch8Ur7QaUfe1L2dq3vXM9CQ9TsGgE54wkCfBA8\"", "\"canva-site-verification=sXrQQ0AtI80Td_hc1Zqcjw\"", "\"contractworksverify=fa18e02a8432ccd1b61734533a35d70a\"", "\"docusign=3ec16fbe-bc67-43fc-b771-d2cab6886ba4\"", "\"facebook-domain-verification=27qyxi1s4503byc9ss3gbq9j9423sz\"", "\"google-site-verification=ZLkZYqDkJxpPNnuhs4ZBEGldnGAxghqfbnoVoFFaHQQ\"", "\"google-site-verification=Zqj1crTSB0UOx2ICjIPCZeSpq04Z-TLVLcET6fh0UBU\"", "\"google-site-verification=iIEXcCeALcpj3pogFNelBkjGIwMBorsSrDkTGa1nahY\"", "\"h1-domain-verification=ijuKc8sRUoSTAcH3MdcdiHLYtKzs5aPKjGkghCrzFcVpquXZ\"", "\"knowbe4-site-verification=ebcf560236d2679d0c5bc5c7164ddb55\"", "\"logmein-verification-code=360be57c-f9d1-4814-acbc-b59400c285da\"", "\"miro-verification=4a5ee2ebb1bca5d9eeead883effff4a177b3291c\"", "\"onetrust-domain-verification=86049b589103452ba1a05c1cc42a15a7\"", "\"segment-site-verification=sGc3MSJ9TjaOJ5gGu56m4ELrR1qehOfN\"", "\"slack-domain-verification=BzxzbOIFqs2vmsxiCtLsWzACEgvFpwUjSVD2aS8X\"", "\"stripe-verification=6cd90f997daa9ba95867f51ab55f1db1145490b06eb9fdc99e571cbad2f3675c\"", "\"stripe-verification=7b83353573a8642a158e2109a25b0963ee1a327c8aad08149c896b33cbe604da\"", "\"stripe-verification=992d0ce8ae1094bc2322c44ac77614d77c89fd552c898ac6b2c1e914db2954f3\"", "\"teamviewer-sso-verification=49deac81cead4ec89bcd37bc67e70132\"", "\"teamviewer-sso-verification=a9a77c0bc467465792858c608da37907\"", "\"v=spf1 ip4:208.118.226.0/26 include:servers.mcsv.net include:spf.mandrillapp.com include:mg-spf.greenhouse.io include:spf.protection.outlook.com include:_spf.salesforce.com\" \" include:mail.zendesk.com include:_spf.atlassian.net include:318630.spf01.hubspotemail.net ~all\"", "\"docker-verification=a8b7a295-5e0b-40b6-b18d-0cf850efa8ca\""]
    ttl = 3600
}

JSON configuration

{
    "terraform": {
        "required_providers": {
            "akamai": {
                "source": "akamai/akamai",
                "version": "~> 6.3.0"
            }
        }
    },
    "resource": {
        "akamai_dns_record": {
            "care_com_care_com_TXT": {
                "name": "care.com",
                "recordtype": "TXT",
                "target": [
                    "google-site-verification=Zqj1crTSB0UOx2ICjIPCZeSpq04Z-TLVLcET6fh0UBU",
                    "google-site-verification=iIEXcCeALcpj3pogFNelBkjGIwMBorsSrDkTGa1nahY",
                    "segment-site-verification=sGc3MSJ9TjaOJ5gGu56m4ELrR1qehOfN",
                    "stripe-verification=7b83353573a8642a158e2109a25b0963ee1a327c8aad08149c896b33cbe604da",
                    "knowbe4-site-verification=ebcf560236d2679d0c5bc5c7164ddb55",
                    "miro-verification=4a5ee2ebb1bca5d9eeead883effff4a177b3291c",
                    "8458026",
                    "atlassian-sending-domain-verification=ce852905-9be3-4df4-8061-8c8f81aaf5d7",
                    "teamviewer-sso-verification=49deac81cead4ec89bcd37bc67e70132",
                    "MS=ms24770002",
                    "apple-domain-verification=gRa8Rp7oPDzgoKmX",
                    "onetrust-domain-verification=86049b589103452ba1a05c1cc42a15a7",
                    "logmein-verification-code=360be57c-f9d1-4814-acbc-b59400c285da",
                    "facebook-domain-verification=27qyxi1s4503byc9ss3gbq9j9423sz",
                    "docusign=3ec16fbe-bc67-43fc-b771-d2cab6886ba4",
                    "asv=521ed26c76fff6d1c78b865a5f835387",
                    "atlassian-domain-verification=vJ5NZGRPZnfOE2rwC8Zc0zb1mRcmpkNscRJqt8KdTo8qoVMkO53uZEq0Qo1QZB7U",
                    "\"v=spf1 ip4:208.118.226.0/26 include:servers.mcsv.net include:spf.mandrillapp.com include:mg-spf.greenhouse.io include:spf.protection.outlook.com include:_spf.salesforce.com\" \" include:mail.zendesk.com include:_spf.atlassian.net include:318630.spf01.hubspotemail.net ~all\"",
                    "contractworksverify=fa18e02a8432ccd1b61734533a35d70a",
                    "slack-domain-verification=BzxzbOIFqs2vmsxiCtLsWzACEgvFpwUjSVD2aS8X",
                    "teamviewer-sso-verification=a9a77c0bc467465792858c608da37907",
                    "atlassian-sending-domain-verification=7fba82d1-5619-4701-99d2-68dd83463a5c",
                    "calendly-site-verification=JmFch8Ur7QaUfe1L2dq3vXM9CQ9TsGgE54wkCfBA8",
                    "stripe-verification=992d0ce8ae1094bc2322c44ac77614d77c89fd552c898ac6b2c1e914db2954f3",
                    "stripe-verification=6cd90f997daa9ba95867f51ab55f1db1145490b06eb9fdc99e571cbad2f3675c",
                    "adobe-idp-site-verification=4d443bb146b2a60fc0c0216c899a6ef9baa971cc3c36ac4b3020b4719b5c2e82",
                    "h1-domain-verification=ijuKc8sRUoSTAcH3MdcdiHLYtKzs5aPKjGkghCrzFcVpquXZ",
                    "google-site-verification=ZLkZYqDkJxpPNnuhs4ZBEGldnGAxghqfbnoVoFFaHQQ",
                    "canva-site-verification=sXrQQ0AtI80Td_hc1Zqcjw",
                    "docker-verification=a8b7a295-5e0b-40b6-b18d-0cf850efa8ca"
                ],
                "ttl": 3600,
                "zone": "care.com"
            }
        }
    }
}

Expected Behavior

Using either of the above input flies, terraform plan will report no changes to be made. Edit both files and change one of the target values (such as MS=ms24770002-test) and run terraform plan again. The expected behavior is both the HCL and JSON inputs would want to change that one data record.

Actual Behavior

Modifying the HCL and running terraform plan works as expected. It reports that only the MS data is to be updated:

Terraform will perform the following actions:

  # akamai_dns_record.care_com_care_com_TXT will be updated in-place
  ~ resource "akamai_dns_record" "care_com_care_com_TXT" {
        id         = "care.com#care.com#TXT"
        name       = "care.com"
      ~ target     = [
            "\"8458026\"",
          ~ "\"MS=ms24770002\"" -> "\"MS=ms24770002-test\"",
            "\"adobe-idp-site-verification=4d443bb146b2a60fc0c0216c899a6ef9baa971cc3c36ac4b3020b4719b5c2e82\"",
            # (27 unchanged elements hidden)
        ]
        # (4 unchanged attributes hidden)
    }

Plan: 0 to add, 1 to change, 0 to destroy.

However modifying the JSON and running terraform plan results in unexpected changes:

Terraform will perform the following actions:

  # akamai_dns_record.care_com_care_com_TXT will be updated in-place
  ~ resource "akamai_dns_record" "care_com_care_com_TXT" {
        id         = "care.com#care.com#TXT"
        name       = "care.com"
      ~ target     = [
            "\"8458026\"",
          ~ "\"MS=ms24770002\"" -> "google-site-verification=iIEXcCeALcpj3pogFNelBkjGIwMBorsSrDkTGa1nahY",
            "\"adobe-idp-site-verification=4d443bb146b2a60fc0c0216c899a6ef9baa971cc3c36ac4b3020b4719b5c2e82\"",
            # (27 unchanged elements hidden)
        ]
        # (4 unchanged attributes hidden)
    }

Plan: 0 to add, 1 to change, 0 to destroy.

Steps to Reproduce

Please list the steps required to reproduce the issue, for example:

  1. Identify a DNS TXT record with multiple targets, at least one of which exceeds 255 characters in length.
  2. Generate a JSON file (not HCL) that matches the record.
  3. terraform import the record
  4. Edit one of the TXT targets in the JSON
  5. Run terraform plan

Important Factoids

In my testing it appears the issue revolves around our SPF record, which is greater than 255 characters, so it is split into multiple quoted strings. In the JSON file it is this record:

"\"v=spf1 ip4:208.118.226.0/26 include:servers.mcsv.net include:spf.mandrillapp.com include:mg-spf.greenhouse.io include:spf.protection.outlook.com include:_spf.salesforce.com\" \" include:mail.zendesk.com include:_spf.atlassian.net include:318630.spf01.hubspotemail.net ~all\"",

If I delete this record as well as making the other changes then terraform plan output looks correct.

References

@PawelSnoch PawelSnoch changed the title akamai_dns_record does not handle DNS targets greater than 255 characters when using JSON instead of HCL [DXE-4099] akamai_dns_record does not handle DNS targets greater than 255 characters when using JSON instead of HCL Jul 30, 2024
@PawelSnoch
Copy link

Hello @brucep-care ,

Thank you for creating this ticket.
Unfortunately I'm not able to reproduce your issue. Could you verify your .tfstate file just before terraform plan and confirm that "target" value looks correct?

Best regards,
Pawel

@brucep-care
Copy link
Author

@PawelSnoch If I delete and recreate my .tfstate file I'm still able to easily reproduce this. In fact if I delete absolutely everything and start from scratch then it's easy for me to reproduce.

$ ls -lA
total 4
-rw-r--r-- 1 bpennypacker Domain Users 3256 Jul 30 13:07 care.tf.json

So care.tf.json is the only file in my test directory. Its contents are identical to the JSON I posted in the initial report. I then do the following:

$ terraform init
Initializing the backend...
Initializing provider plugins...
- Finding akamai/akamai versions matching "~> 6.3.0"...
- Installing akamai/akamai v6.3.0...
- Installed akamai/akamai v6.3.0 (signed by a HashiCorp partner, key ID A26ECDD8F0BCBA73)
...

$ terraform import akamai_dns_record.care_com_care_com_TXT care.com#care.com#TXT
akamai_dns_record.care_com_care_com_TXT: Importing from ID "care.com#care.com#TXT"...
akamai_dns_record.care_com_care_com_TXT: Import prepared!
  Prepared akamai_dns_record for import
akamai_dns_record.care_com_care_com_TXT: Refreshing state... [id=care.com#care.com#TXT]

Import successful!

$ terraform plan
akamai_dns_record.care_com_care_com_TXT: Refreshing state... [id=care.com#care.com#TXT]

No changes. Your infrastructure matches the configuration.

So at this point my care.tf.json file exactly matches the current DNS record. If I then modify the care.tf.json file by changing "MS=ms24770002" to "MS=ms24770002-test" and rerun terraform plan then I get this result:

$ terraform plan
akamai_dns_record.care_com_care_com_TXT: Refreshing state... [id=care.com#care.com#TXT]

Terraform used the selected providers to generate the following execution plan. Resource actions are indicated with the following symbols:
  ~ update in-place

Terraform will perform the following actions:

  # akamai_dns_record.care_com_care_com_TXT will be updated in-place
  ~ resource "akamai_dns_record" "care_com_care_com_TXT" {
        id         = "care.com#care.com#TXT"
        name       = "care.com"
      ~ target     = [
            "\"8458026\"",
          ~ "\"MS=ms24770002\"" -> "google-site-verification=iIEXcCeALcpj3pogFNelBkjGIwMBorsSrDkTGa1nahY",
            "\"adobe-idp-site-verification=4d443bb146b2a60fc0c0216c899a6ef9baa971cc3c36ac4b3020b4719b5c2e82\"",
            # (27 unchanged elements hidden)
        ]
        # (4 unchanged attributes hidden)
    }

Plan: 0 to add, 1 to change, 0 to destroy.

If I edit care.tf.json further by removing the v=spf1 record that exceeds 255 characters then the plan output looks correct. The SPF record is deleted and the "MS=ms24770002" is properly updated

$ terraform plan
akamai_dns_record.care_com_care_com_TXT: Refreshing state... [id=care.com#care.com#TXT]

Terraform used the selected providers to generate the following execution plan. Resource actions are indicated with the following symbols:
  ~ update in-place

Terraform will perform the following actions:

  # akamai_dns_record.care_com_care_com_TXT will be updated in-place
  ~ resource "akamai_dns_record" "care_com_care_com_TXT" {
        id         = "care.com#care.com#TXT"
        name       = "care.com"
      ~ target     = [
          - "\"8458026\"",
          - "\"MS=ms24770002\"",
          - "\"adobe-idp-site-verification=4d443bb146b2a60fc0c0216c899a6ef9baa971cc3c36ac4b3020b4719b5c2e82\"",
          - "\"apple-domain-verification=gRa8Rp7oPDzgoKmX\"",
          - "\"asv=521ed26c76fff6d1c78b865a5f835387\"",
          - "\"atlassian-domain-verification=vJ5NZGRPZnfOE2rwC8Zc0zb1mRcmpkNscRJqt8KdTo8qoVMkO53uZEq0Qo1QZB7U\"",
          - "\"atlassian-sending-domain-verification=7fba82d1-5619-4701-99d2-68dd83463a5c\"",
          - "\"atlassian-sending-domain-verification=ce852905-9be3-4df4-8061-8c8f81aaf5d7\"",
          - "\"calendly-site-verification=JmFch8Ur7QaUfe1L2dq3vXM9CQ9TsGgE54wkCfBA8\"",
          - "\"canva-site-verification=sXrQQ0AtI80Td_hc1Zqcjw\"",
          - "\"contractworksverify=fa18e02a8432ccd1b61734533a35d70a\"",
          - "\"docusign=3ec16fbe-bc67-43fc-b771-d2cab6886ba4\"",
          - "\"facebook-domain-verification=27qyxi1s4503byc9ss3gbq9j9423sz\"",
          - "\"google-site-verification=ZLkZYqDkJxpPNnuhs4ZBEGldnGAxghqfbnoVoFFaHQQ\"",
          - "\"google-site-verification=Zqj1crTSB0UOx2ICjIPCZeSpq04Z-TLVLcET6fh0UBU\"",
          - "\"google-site-verification=iIEXcCeALcpj3pogFNelBkjGIwMBorsSrDkTGa1nahY\"",
          - "\"h1-domain-verification=ijuKc8sRUoSTAcH3MdcdiHLYtKzs5aPKjGkghCrzFcVpquXZ\"",
          - "\"knowbe4-site-verification=ebcf560236d2679d0c5bc5c7164ddb55\"",
          - "\"logmein-verification-code=360be57c-f9d1-4814-acbc-b59400c285da\"",
          - "\"miro-verification=4a5ee2ebb1bca5d9eeead883effff4a177b3291c\"",
          - "\"onetrust-domain-verification=86049b589103452ba1a05c1cc42a15a7\"",
          - "\"segment-site-verification=sGc3MSJ9TjaOJ5gGu56m4ELrR1qehOfN\"",
          - "\"slack-domain-verification=BzxzbOIFqs2vmsxiCtLsWzACEgvFpwUjSVD2aS8X\"",
          - "\"stripe-verification=6cd90f997daa9ba95867f51ab55f1db1145490b06eb9fdc99e571cbad2f3675c\"",
          - "\"stripe-verification=7b83353573a8642a158e2109a25b0963ee1a327c8aad08149c896b33cbe604da\"",
          - "\"stripe-verification=992d0ce8ae1094bc2322c44ac77614d77c89fd552c898ac6b2c1e914db2954f3\"",
          - "\"teamviewer-sso-verification=49deac81cead4ec89bcd37bc67e70132\"",
          - "\"teamviewer-sso-verification=a9a77c0bc467465792858c608da37907\"",
          - "\"v=spf1 ip4:208.118.226.0/26 include:servers.mcsv.net include:spf.mandrillapp.com include:mg-spf.greenhouse.io include:spf.protection.outlook.com include:_spf.salesforce.com\" \" include:mail.zendesk.com include:_spf.atlassian.net include:318630.spf01.hubspotemail.net ~all\"",
          - "\"docker-verification=a8b7a295-5e0b-40b6-b18d-0cf850efa8ca\"",
          + "google-site-verification=Zqj1crTSB0UOx2ICjIPCZeSpq04Z-TLVLcET6fh0UBU",
          + "google-site-verification=iIEXcCeALcpj3pogFNelBkjGIwMBorsSrDkTGa1nahY",
          + "segment-site-verification=sGc3MSJ9TjaOJ5gGu56m4ELrR1qehOfN",
          + "stripe-verification=7b83353573a8642a158e2109a25b0963ee1a327c8aad08149c896b33cbe604da",
          + "knowbe4-site-verification=ebcf560236d2679d0c5bc5c7164ddb55",
          + "miro-verification=4a5ee2ebb1bca5d9eeead883effff4a177b3291c",
          + "8458026",
          + "atlassian-sending-domain-verification=ce852905-9be3-4df4-8061-8c8f81aaf5d7",
          + "teamviewer-sso-verification=49deac81cead4ec89bcd37bc67e70132",
          + "MS=ms24770002-test",
          + "apple-domain-verification=gRa8Rp7oPDzgoKmX",
          + "onetrust-domain-verification=86049b589103452ba1a05c1cc42a15a7",
          + "logmein-verification-code=360be57c-f9d1-4814-acbc-b59400c285da",
          + "facebook-domain-verification=27qyxi1s4503byc9ss3gbq9j9423sz",
          + "docusign=3ec16fbe-bc67-43fc-b771-d2cab6886ba4",
          + "asv=521ed26c76fff6d1c78b865a5f835387",
          + "atlassian-domain-verification=vJ5NZGRPZnfOE2rwC8Zc0zb1mRcmpkNscRJqt8KdTo8qoVMkO53uZEq0Qo1QZB7U",
          + "contractworksverify=fa18e02a8432ccd1b61734533a35d70a",
          + "slack-domain-verification=BzxzbOIFqs2vmsxiCtLsWzACEgvFpwUjSVD2aS8X",
          + "teamviewer-sso-verification=a9a77c0bc467465792858c608da37907",
          + "atlassian-sending-domain-verification=7fba82d1-5619-4701-99d2-68dd83463a5c",
          + "calendly-site-verification=JmFch8Ur7QaUfe1L2dq3vXM9CQ9TsGgE54wkCfBA8",
          + "stripe-verification=992d0ce8ae1094bc2322c44ac77614d77c89fd552c898ac6b2c1e914db2954f3",
          + "stripe-verification=6cd90f997daa9ba95867f51ab55f1db1145490b06eb9fdc99e571cbad2f3675c",
          + "adobe-idp-site-verification=4d443bb146b2a60fc0c0216c899a6ef9baa971cc3c36ac4b3020b4719b5c2e82",
          + "h1-domain-verification=ijuKc8sRUoSTAcH3MdcdiHLYtKzs5aPKjGkghCrzFcVpquXZ",
          + "google-site-verification=ZLkZYqDkJxpPNnuhs4ZBEGldnGAxghqfbnoVoFFaHQQ",
          + "canva-site-verification=sXrQQ0AtI80Td_hc1Zqcjw",
          + "docker-verification=a8b7a295-5e0b-40b6-b18d-0cf850efa8ca",
        ]
        # (4 unchanged attributes hidden)
    }

Plan: 0 to add, 1 to change, 0 to destroy.

@PawelSnoch
Copy link

@brucep-care , thank you for adding more details. I need to know how you created your zone with recordset. Did you use terraform or another option?

@brucep-care
Copy link
Author

@PawelSnoch How the zone was created shouldn't matter at all. We've had this zone hosted by Akamai for close to ten years now, long before we started working with terraform. We've backported this zone and many other resources into terraform.

@FilipAntkowiak
Copy link
Contributor

FilipAntkowiak commented Aug 20, 2024

@brucep-care, It looks like the problem is caused by an incorrect order of DNS targets in the json file. With the same order as in the HCL example, the problem shouldn't happen.

@brucep-care
Copy link
Author

@FilipAntkowiak reordering target list in the json isn't a viable solution. It would require us to compare this JSON with the HCL every time we make a change, and we're not using HCL at all in our environment. That would be not trivial when dealing with many dozens of records across multiple zones. Given the provider will accept the target list in any order and appears to successfully apply them (as far as terraform is concerned) I would expect the provider to re-order the targets if necessary.

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Development

No branches or pull requests

5 participants