func deleteAllRecordsInHostedZoneId(hostedZoneId, hostedZoneName string, conn *route53.Route53) error { input := &route53.ListResourceRecordSetsInput{ HostedZoneId: aws.String(hostedZoneId), } var lastDeleteErr, lastErrorFromWaiter error var pageNum = 0 err := conn.ListResourceRecordSetsPages(input, func(page *route53.ListResourceRecordSetsOutput, isLastPage bool) bool { sets := page.ResourceRecordSets pageNum += 1 changes := make([]*route53.Change, 0) // 100 items per page returned by default for _, set := range sets { if *set.Name == hostedZoneName+"." && (*set.Type == "NS" || *set.Type == "SOA") { // Zone NS & SOA records cannot be deleted continue } changes = append(changes, &route53.Change{ Action: aws.String("DELETE"), ResourceRecordSet: set, }) } log.Printf("[DEBUG] Deleting %d records (page %d) from %s", len(changes), pageNum, hostedZoneId) req := &route53.ChangeResourceRecordSetsInput{ HostedZoneId: aws.String(hostedZoneId), ChangeBatch: &route53.ChangeBatch{ Comment: aws.String("Deleted by Terraform"), Changes: changes, }, } var resp interface{} resp, lastDeleteErr = deleteRoute53RecordSet(conn, req) if out, ok := resp.(*route53.ChangeResourceRecordSetsOutput); ok { log.Printf("[DEBUG] Waiting for change batch to become INSYNC: %#v", out) if out.ChangeInfo != nil && out.ChangeInfo.Id != nil { lastErrorFromWaiter = waitForRoute53RecordSetToSync(conn, cleanChangeID(*out.ChangeInfo.Id)) } else { log.Printf("[DEBUG] Change info was empty") } } else { log.Printf("[DEBUG] Unable to wait for change batch because of an error: %s", lastDeleteErr) } return !isLastPage }) if err != nil { return fmt.Errorf("Failed listing/deleting record sets: %s\nLast error from deletion: %s\nLast error from waiter: %s", err, lastDeleteErr, lastErrorFromWaiter) } return nil }