Skip to content

Expired domain causes plan failure during refresh phase #327

@weppos

Description

@weppos

Hi there,

Terraform Version

Terraform v1.7+ (using Terraform Cloud)

Affected Resource(s)

  • dnsimple_registered_domain
  • dnsimple_domain_delegation

Terraform Configuration Files

resource "dnsimple_domain" "example_org" {
  name = "example-domain.org"
}

resource "dnsimple_registered_domain" "example_org" {
  name                  = dnsimple_domain.example_org.name
  contact_id            = 12345
  auto_renew_enabled    = false
  transfer_lock_enabled = true
  whois_privacy_enabled = false
  dnssec_enabled        = false
}

resource "dnsimple_domain_delegation" "example_org" {
  domain = dnsimple_domain.example_org.name
  name_servers = [
    "ns1.dnsimple.com",
    "ns2.dnsimple-edge.net",
    "ns3.dnsimple.com",
    "ns4.dnsimple-edge.org",
  ]
}

Expected Behavior

When a domain registration expires and I remove the dnsimple_registered_domain and dnsimple_domain_delegation resources from my configuration, Terraform should plan to remove them from state (since they no longer exist in config) without failing.

Actual Behavior

When the domain expires, all Terraform operations fail during the refresh phase before even reaching the plan:

Error: failed to read domain delegation for domain example-domain.org

GET https://api.dnsimple.com/v2/xxx/registrar/domains/example-domain.org/delegation: 400 Change rejected: domain is not registered or expired

The refresh phase tries to query the API for all resources in state, including the ones I've just removed from configuration. Since the domain is expired, the API returns a 400 error and the entire operation fails.

Steps to Reproduce

  1. Have a registered domain managed by Terraform with dnsimple_registered_domain and dnsimple_domain_delegation resources
  2. Let the domain expire (or have auto_renew_enabled = false and wait for expiration)
  3. Remove the dnsimple_registered_domain and dnsimple_domain_delegation resources from your Terraform configuration
  4. Run terraform plan or terraform apply
  5. Observe the failure during refresh

Workaround

The only current workaround is to use Terraform's removed block with destroy = false:

removed {
  from = dnsimple_registered_domain.example_org

  lifecycle {
    destroy = false
  }
}

removed {
  from = dnsimple_domain_delegation.example_org

  lifecycle {
    destroy = false
  }
}

Or manually run terraform state rm for each affected resource.

Simply deleting the resources from the configuration is not sufficient.

Suggested Improvement

A few options to improve this experience:

  1. Handle expired domains gracefully in the provider: During refresh, if the API returns a "domain is not registered or expired" error, the provider could treat the resource as already gone (similar to how some providers handle 404s) rather than failing the entire operation.

  2. Documentation: At minimum, document this behavior and the workaround in the resource documentation for dnsimple_registered_domain and dnsimple_domain_delegation.

This is particularly problematic for users who intentionally let domains expire - the Terraform workflow completely breaks until they learn about removed blocks or terraform state rm.

Metadata

Metadata

Assignees

No one assigned

    Labels

    Type

    No type

    Projects

    No projects

    Milestone

    No milestone

    Relationships

    None yet

    Development

    No branches or pull requests

    Issue actions