Simplifying DNS Management in a Hub-and-Spoke AWS Account Structure / Foundations

Tim Fraser May 17, 2024

In today's complex cloud environments, managing DNS across multiple AWS accounts can be a daunting task. However, organisations can streamline DNS management while maintaining tight control and governance by implementing a hub-and-spoke account structure with a centralized Route53 hosted zone and cross-account IAM roles.

The Hub-and-Spoke Model

A hub-and-spoke AWS account model consists of a central "hub" account (often called the "Shared Services" account) surrounded by multiple "spoke" accounts, such as production, non-production, and test environments. The hub account contains shared resources, like a Route53 hosted zone, that all spoke accounts can access and utilize.

Benefits of this model include:

  • Centralized control and governance
  • Consistent resource management across accounts
  • Reduced duplication and sprawl
  • Simplified security and compliance

Cross-Account IAM Roles and Trust Relationships

To allow spoke accounts to manage their own resources and DNS records while maintaining centralized control, we leverage IAM cross-account roles and trust relationships. Here's how it works:

  • The hub account creates an IAM role with permissions to manage Route53 resources
  • The hub account establishes a trust relationship with the spoke accounts, allowing them to assume the IAM role
  • Spoke accounts assume the IAM role to gain temporary access to manage DNS records in the central Route53 hosted zone

This approach grants spoke accounts the necessary permissions without giving them direct access to the hub account or other shared resources.

Configuring Route53 and DNS Management

In the hub account, create a Route53 hosted zone for your organization's domain (e.g., example.com). Define access policies to control which actions spoke accounts can perform, such as creating, updating, or deleting DNS records.

When spoke accounts need to manage DNS records, they assume the IAM role from the hub account and make API calls to Route53. This allows them to create, update, or delete DNS records within the scope of their permissions.

Integrating DNS Updates into Deployment Pipelines

To fully automate DNS management, spoke accounts can integrate DNS updates into their deployment pipelines. As new resources are provisioned or updated, the deployment scripts can assume the IAM role and make the necessary API calls to update DNS records in the central Route53 hosted zone.

This integration ensures that DNS records are always in sync with the actual state of resources, reducing manual effort and minimizing the risk of errors.

Best Practices for DNS Management in a Hub-and-Spoke Model

  • Implement least privilege access: Grant spoke accounts only the permissions they need to manage their specific DNS records
  • Use resource tags: Tag Route53 records to easily identify their associated spoke account and purpose
  • Implement DNS naming conventions: Establish consistent naming conventions for DNS records across all accounts
  • Monitor and audit DNS changes: Use AWS CloudTrail to log all Route53 API calls and regularly review changes for anomalies or unauthorized actions
  • Automate DNS management: Integrate DNS updates into deployment pipelines to reduce manual effort and ensure consistency
  • Use ExternalIDs for added security: When creating cross-account IAM roles, use ExternalIDs to provide an additional layer of protection against the "confused deputy" problem. ExternalIDs ensure that only authorized spoke accounts can assume the IAM role, even if the role's ARN is compromised

Real-World Example

Let's consider an organization with a production account (prod), a non-production account (non-prod), and a test account. The organization's domain is hosted in a Route53 hosted zone in the Shared Services account.

When the prod account deploys a new application, the deployment script assumes the IAM role from the Shared Services account and creates a new DNS record (app.example.com) pointing to the application's load balancer. The non-prod and test accounts follow a similar process for their respective environments.

If the organization decides to migrate the application to a new load balancer, the prod account updates the DNS record to point to the new load balancer using the same IAM role and process. All other accounts and environments are unaffected.

By implementing this hub-and-spoke model with centralized DNS management, the organization achieves:

  • Consistent DNS management across all accounts and environments
  • Reduced duplication and sprawl of Route53 hosted zones
  • Centralized control and governance of DNS records
  • Automated and streamlined DNS updates integrated into deployment pipelines

Integrating with BuildKite for CI/CD

BuildKite, a popular CI/CD tool, can be seamlessly integrated into the hub-and-spoke model to deploy resources and manage DNS records across multiple AWS accounts. Here's an example of how BuildKite can be used to deploy resources in a spoke account (e.g., a sandpit account) while leveraging the trust relationship with the Shared Services account for DNS management:

  • In the BuildKite pipeline configuration for the sandpit account, define a step that assumes the IAM role from the Shared Services account:
yaml
steps:
  - label: "Assume Shared Services IAM Role"
    command: |
      aws sts assume-role \
        --role-arn "arn:aws:iam:::role/" \
        --role-session-name "BuildKiteDNSManagement" \
        --external-id ""
  • Use the temporary credentials obtained from assuming the IAM role to manage DNS records in the central Route53 hosted zone:
yaml
steps:
  - label: "Update DNS Record"
    command: |
      aws route53 change-resource-record-sets \
        --hosted-zone-id "" \
        --change-batch '{
          "Changes": [
            {
              "Action": "UPSERT",
              "ResourceRecordSet": {
                "Name": "sandpit.example.com",
                "Type": "A",
                "TTL": 300,
                "ResourceRecords": [
                  {
                    "Value": ""
                  }
                ]
              }
            }
          ]
        }'

In this example, the BuildKite pipeline in the sandpit account assumes the IAM role from the Shared Services account, which grants permissions to manage DNS records in the central Route53 hosted zone. The --external-id parameter is added to the assume-role command to provide an additional layer of security.

The pipeline then uses the AWS CLI to update a specific DNS record (sandpit.example.com) with the IP or hostname of the deployed resource.

By leveraging BuildKite and the trust relationship between the sandpit and Shared Services accounts, organizations can automate resource deployment and DNS management as part of their CI/CD processes, ensuring consistency and reducing manual effort.

Conclusion

Implementing a hub-and-spoke model with centralized DNS management in AWS provides organizations with a scalable, secure, and efficient solution for managing their cloud resources and DNS records across multiple accounts. By leveraging cross-account IAM roles, trust relationships, ExternalIDs, and CI/CD tools like BuildKite, organizations can automate resource deployment and DNS management, enforce governance and best practices, and streamline their AWS operations.

Adopting this approach as part of your AWS foundations sets the stage for a well-architected, easily maintainable, and highly extensible cloud environment that can grow with your organization's needs.