Testing with DNS
Whenever I need to setup HTTPS for a system I’m working on I eventually need to use a domain. For example, when I set up a CloudFront distribution with a custom name, I need a Route53 Hosted Zone and an ACM certificate and that requires the Hosted Zone to be the authoritative name server. And for that, I need to own a domain name. Fortunately, I have one that I can use for this.
But this requirement makes it hard for people to follow a tutorial involving domain names. Not everybody has a domain just lying around for testing purposes.
That’s why I searched for a free alternative to owning a domain. Many services offer a free subdomain, but as I’ve found not all of them allow adding NS records, which is a requirement in most scenarios.
When a live domain is needed
The DNS system translates names to IP addresses. Since your computer can only connect to IP addresses, whenever you use a domain name this translation process starts and finds the address you need.
The domain name resolution happens using a trust chain. There are several root name servers and the IP addresses of those are baked into any DNS resolver (this is called the root hints). Whenever you enter a domain to the address bar, your browser goes to a resolver that in turn contacts the root name servers.
This is where the chain starts. The root name server responds with an NS record that points to another DNS name server. Then the resolver connects to that server, which also responds with an NS record pointing to another name server. This process goes on until it reaches the authoritative name server that responds with the IP address your browser will connect to.
Because of this, you can create name servers for any domain name you want, but it will only go live if there is a chain from the root name servers. And that usually involves buying a domain name.
When it becomes more pressing is when you need to configure HTTPS. You need a valid certificate, and for that, you need to prove that you own the domain name. This involves adding a record to the authoritative name server for the domain, and that requires a name server that you control and is referenced by the root name servers.
And while you can use a self-signed certificate to test HTTPS for a webserver, it is not a possibility in many cases. For example, if you want to configure a CloudFront distribution to use a custom domain name, you need to add an ACM certificate. And that requires an Amazon-issued HTTPS certificate, and you can only get one if you can prove domain ownership. As a result, you need a domain name for testing the CloudFront configuration.
Free subdomain providers
My first thought was to find an ngrok-like service that provides a temporary subdomain where I can configure NS records. Unfortunately, ngrok itself does not support this use-case.
So I opened the Free for developers list and started out the free DNS services listed there searching for a suitable one.
FreeDNS (does not work)
I soon found out that most services use FreeDNS under the hood. Its webpage looks like it’s something from the early 2000s, and sure enough, it’s operational since 2001. This is a big plus, as it’s unlikely to go away in the next years, not like some modern services that come and go.
I registered a free account and tried to add an NS record to a subdomain:
Which did not work, apparently this feature needs additional administration and is not provided for free accounts by default:
Because of this, FreeDNS and the solutions built on it are not a good fit for this use-case.
The next service I tried was ClouDNS. It has been around since 2010, and unlike FreeDNS it allows adding NS records to free subdomains.
After registration, I added a new DNS zone:
Which supports a free zone:
Gave it a name and then it shows the current name servers:
While changing these NS records did not work, I could add another layer of subdomains with the name servers I needed and that worked.
Testing with Route53 and ACM
Let’s see how to use the ClouDNS subdomain to make a Route53 Hosted Zone the authoritative name server for a domain and then ACM to get an Amazon-issued HTTPS certificate for it!
First, we’ll need to create a Route53 Hosted Zone for the domain name. The domain here is a subdomain of the ClouDNS zone, such as
cloudns.cl is the ClouDNS domain, the
route53testing subdomain is the free zone, and finally the
dnstest part is the name I’ll use for the NS records.
The Route53 Hosted Zone lists its name servers, which will be the targets of the ClouDNS zone:
On the ClouDNS console, add the NS records to the name that matches the Route53 Hosted Zone name:
It takes ~1 minute to update (in theory, it can take a lot longer, but in practice it’s quite fast) then you can test that the DNS resolution reaches the AWS name servers.
To see inside the hood, use
dig @220.127.116.11 dnstest.route53testing.cloudns.cl +trace ; <<>> DiG 9.11.3-1ubuntu1.13-Ubuntu <<>> @18.104.22.168 dnstest.route53testing.cloudns.cl +trace ; (1 server found) ;; global options: +cmd . 86669 IN NS m.root-servers.net. . 86669 IN NS b.root-servers.net. . 86669 IN NS c.root-servers.net. . 86669 IN NS d.root-servers.net. . 86669 IN NS e.root-servers.net. . 86669 IN NS f.root-servers.net. . 86669 IN NS g.root-servers.net. . 86669 IN NS h.root-servers.net. . 86669 IN NS a.root-servers.net. . 86669 IN NS i.root-servers.net. . 86669 IN NS j.root-servers.net. . 86669 IN NS k.root-servers.net. . 86669 IN NS l.root-servers.net. ;; Received 525 bytes from 22.214.171.124#53(126.96.36.199) in 0 ms cl. 172800 IN NS cl1-tld.d-zone.ca. cl. 172800 IN NS b.nic.cl. cl. 172800 IN NS a.nic.cl. cl. 172800 IN NS cl1.dnsnode.net. cl. 172800 IN NS cl-ns.anycast.pch.net. cl. 172800 IN NS c.nic.cl. cl. 172800 IN NS cl2-tld.d-zone.ca. ;; Received 871 bytes from 188.8.131.52#53(g.root-servers.net) in 11 ms cloudns.cl. 3600 IN NS ns101.cloudns.net. cloudns.cl. 3600 IN NS ns103.cloudns.net. cloudns.cl. 3600 IN NS ns102.cloudns.net. cloudns.cl. 3600 IN NS ns104.cloudns.net. ;; Received 678 bytes from 184.108.40.206#53(cl2-tld.d-zone.ca) in 18 ms dnstest.route53testing.cloudns.cl. 3600 IN NS ns-1125.awsdns-12.org. dnstest.route53testing.cloudns.cl. 3600 IN NS ns-922.awsdns-51.net. dnstest.route53testing.cloudns.cl. 3600 IN NS ns-371.awsdns-46.com. dnstest.route53testing.cloudns.cl. 3600 IN NS ns-1865.awsdns-41.co.uk. ;; Received 202 bytes from 220.127.116.11#53(ns102.cloudns.net) in 94 ms dnstest.route53testing.cloudns.cl. 900 IN SOA ns-922.awsdns-51.net. awsdns-hostmaster.amazon.com. 1 7200 900 1209600 86400 ;; Received 146 bytes from 18.104.22.168#53(ns-922.awsdns-51.net) in 1 ms
It’s easy to see the chain the DNS resolution followed:
ns-922.awsdns-51.net. That last part is the Route53 Hosted Zone, meaning it is the authoritative name server for that domain.
To get an HTTPS certificate, go to ACM, enter the domain name, and choose DNS validation:
This validation method requires adding a CNAME record to the domain name. Since the Route53 Hosted Zone is the authoritative name server for this domain, you need to add the record to that zone. The ACM Console makes it easy as it provides a button to do just that:
The ACM service makes a DNS resolution to the subdomain in the CNAME record. You can see that it resolves to the value:
dig _a68d896074b22046947bfec9950cc84a.dnstest.route53testing.cloudns.cl ; <<>> DiG 9.11.3-1ubuntu1.13-Ubuntu <<>> _a68d896074b22046947bfec9950cc84a.dnstest.route53testing.cloudns.cl ;; global options: +cmd ;; Got answer: ;; ->>HEADER<<- opcode: QUERY, status: NOERROR, id: 3480 ;; flags: qr rd ra; QUERY: 1, ANSWER: 1, AUTHORITY: 0, ADDITIONAL: 1 ;; OPT PSEUDOSECTION: ; EDNS: version: 0, flags:; udp: 65494 ;; QUESTION SECTION: ;_a68d896074b22046947bfec9950cc84a.dnstest.route53testing.cloudns.cl. IN A ;; ANSWER SECTION: _a68d896074b22046947bfec9950cc84a.dnstest.route53testing.cloudns.cl. 274 IN CNAME _9615577b1c950f5a6db40ad7dd3c2321.rlltrpyzyf.acm-validations.aws. ;; Query time: 0 msec ;; SERVER: 127.0.0.53#53(127.0.0.53) ;; WHEN: Thu Dec 10 12:02:28 CET 2020 ;; MSG SIZE rcvd: 174
ANSWER SECTION contains the validation record. Since it matches the record ACM requires, it issues a certificate in a few seconds:
This is a valid ACM certificate for a domain that is publicly resolvable and you can use it for testing anything that requires a live domain name.
Testing features that require a live domain name requires some preparation. You need either a domain name you bought, or you need to opt for a free subdomain from a service that offers them. I’ve tried some such providers and found that ClouDNS allows setting NS records for a subdomain.