The word propagation suggests that when you change a DNS record, the update is pushed outward across the internet like ripples in a pond. Nothing of the sort happens. No central system announces your change, and nobody receives a notification. What actually happens is far duller and much easier to reason about.
Every DNS answer comes with a number called a TTL, short for time to live, measured in seconds. It says: you may remember this answer for this long before asking again. Resolvers all over the world cache answers according to their TTLs. When you change a record, the authoritative nameservers update immediately. But every resolver that already has the old answer will keep serving it until its own timer runs out.
That single idea explains nearly every "DNS change not working" complaint I have handled. The person made the change correctly, the nameserver holds the right value, and the person is looking at it through a cache that has not expired yet. There is nothing to wait for in the sense of a process being carried out somewhere. There is only a set of countdowns, running independently, in places you do not control.
This piece walks through where those caches sit, how long they hold on, why the famous "up to 48 hours" is mostly folklore, and how to plan a change so that your visitors barely notice it.
Who remembers what: the lookup chain
To see why changes appear gradually, follow a lookup from the visitor's end. When you type example.com into a browser, the browser first checks its own memory. If it has no answer, it asks the operating system, which has a small cache of its own. If that fails too, the request goes to a recursive resolver, normally run by the visitor's internet provider or by a public service such as 8.8.8.8 or 1.1.1.1.
The recursive resolver does the real legwork. If it has no cached answer, it asks a root server where to find the .com servers, asks those where to find the nameservers for example.com, and finally asks those nameservers for the record. The answer travels back down the chain and is remembered by the resolver, by the operating system and by the browser, each for as long as the TTL allows.
So how long does it take?
As long as the old TTL, give or take. If the record had a TTL of 3600 seconds, then any resolver that looked it up a minute before your change will keep the old answer for another 59 minutes. A resolver that looked it up at the worst possible moment could hold it for the full hour. After that, it asks again and gets the new value.
The key is that each resolver started its countdown at a different moment. Picture three resolvers, each with a one-hour TTL. One fetched the record at 09:05, one at 09:40 and one at 09:58. You change the record at 10:00. The first expires at 10:05, the second at 10:40 and the third at 10:58. Nobody is wrong, and nobody is out of sync with a plan. They are on their own clocks.
On average, then, you would expect half the TTL before about half of visitors see the change, and the full TTL before nearly all do. With a 300 second TTL, that is five minutes. With 86400, it is a day.
Where the "48 hours" comes from
The "48 hours" figure that gets repeated everywhere comes from a time when TTLs were routinely set to a day or more, nameserver changes involved the registry as well, and some resolvers behaved badly. You can still occasionally see long delays, especially when changing nameservers rather than records, but for ordinary record edits with a modest TTL, minutes to a few hours is normal.
Part of the reason the number survives is that it is safe to say. A support agent who tells a customer "up to 48 hours" will never be wrong, and the customer will stop refreshing the page every thirty seconds. The cost is that people then assume nothing is wrong when something really is. A mistyped IP address does not fix itself in 48 hours. If the value you see from the authoritative server is wrong, no amount of waiting helps.
Another part is misbehaving resolvers. A small number of networks ignore short TTLs and impose their own minimum, sometimes several hours. They are rarer than they used to be, but they are the reason a few visitors may see the old site long after everyone else has moved. You cannot fix those, and you do not need to. The old server should therefore stay up, serving a working copy of the site, for a day or two after a move.
Records versus nameservers
Changing an A record and changing the nameservers for a domain sound alike but behave differently, and mixing them up causes most of the long delays.
An A or AAAA record change happens in your zone. The nameservers you already use update at once, and caches expire according to the TTL of that record. Everything is in your control.
A nameserver change happens at the registry. When you tell your registrar to use new nameservers, it passes the change up to the registry for the top-level domain, which publishes new NS records in the parent zone (for .com, that zone is run by the registry). Those parent-zone records carry their own TTL, commonly 24 or 48 hours for .com, and you cannot change it. Resolvers that already know your old nameservers will keep asking them until that parent TTL runs out. This is the real source of the long waits, and it is why nameserver changes are the one case where "a day or two" is a realistic estimate.
One practical consequence follows. During a nameserver move, the old nameservers keep receiving questions for a day or more. If they have been switched off, or their zone deleted, those visitors get errors. So fill in the zone at the new provider first, copy every record including mail and verification entries, and leave the old zone intact until the traffic stops.
| What you change | Where it lives | Who controls the TTL | Typical wait |
|---|---|---|---|
| A, AAAA, CNAME, MX, TXT | Your zone | You | The old TTL, often minutes to a few hours |
| NS records at the registrar | The parent zone at the registry | The registry | Often 24 to 48 hours |
| Brand-new name that never existed | Your zone | The zone's negative caching value | Up to the SOA minimum if anyone looked it up first |
The two caches people forget
Your browser keeps its own short-lived DNS memory, and so does your operating system. That is why you might see the new site on your phone but the old one on your laptop. Restarting the browser or flushing the OS cache often fixes it, and testing from a different network settles whether the problem is local.
The commands differ by system. These are the usual ones:
# Windows
ipconfig /flushdns
# macOS
sudo dscacheutil -flushcache; sudo killall -HUP mDNSResponder
# Linux with systemd-resolved
resolvectl flush-caches
In Chrome, chrome://net-internals/#dns has a button to clear the browser's own host cache, and a private window or a different browser is a quick workaround. A VPN or a router that caches lookups can add a fourth layer, which is one reason testing from mobile data is such a clean experiment: it bypasses your home network entirely.
There is one more local cache that surprises people: the hosts file. If someone set up a test entry in /etc/hosts or C:\Windows\System32\drivers\etc\hosts during development, that entry overrides DNS completely and for ever. A developer who tested a new server by pinning the name to its address, then forgot, will see the new site while everyone else sees the old one, and will swear that DNS is stuck.
Negative caching
There is also negative caching. If someone looked up a name before you created the record, the resolver may remember that it did not exist, for a period controlled by the zone's SOA settings. This explains the baffling case where a brand-new subdomain works for you and not for your colleague, who tried it five minutes earlier.
The relevant value is the last number in the SOA record, which most modern setups treat as the negative caching time. You can see it with dig example.com SOA +short:
ns1.example.net. hostmaster.example.com. 2026100501 7200 3600 1209600 300
Here the final figure, 300, means a resolver that got "no such name" will remember that for up to five minutes. A zone left at an old default of 86400 would remember the absence for a day, which is a nasty surprise when you create shop.example.com and your team has already tried the address once. A low value, such as 300 to 3600, is kinder.
How to plan around it
- A day or two before a planned move, lower the TTL on the records you will change to something like 300 seconds.
- Make the change. Within minutes, most of the world sees it.
- Once everything is confirmed, raise the TTL again. Short TTLs mean more lookups and slightly more exposure if your DNS provider has a bad day.
- To check, query specific resolvers directly, for example
dig example.com @8.8.8.8anddig example.com @1.1.1.1, and compare with what your authoritative nameserver says.
The lowering step is the one people skip, and it is the one that matters. The lowered TTL only helps once the old, long TTL has expired everywhere, so you must lower it at least as long before the change as the old value. If the TTL was 86400 and you drop it to 300 an hour before the move, most resolvers will still be holding the day-long copy. The TTL planner works out the timing for you, and the DNS cheatsheet lists the records you are likely to touch.
A worked example: moving a shop to a new server
A small online shop runs on one server at 203.0.113.10 and is moving to a new one at 203.0.113.50. The A records for example.com and www.example.com have a TTL of 14400 (four hours). The owner plans the move for Saturday at 06:00, when traffic is lowest.
- Thursday evening. Lower the TTL on both A records to 300. The old four-hour copies will have worn out everywhere by Friday evening at the latest, so there is a day of margin.
- Friday. Build and test the new server. To test without touching DNS, use
curl --resolve example.com:443:203.0.113.50 https://example.com/, which forces the name to the new address for that one request. - Saturday 05:30. Put the old shop into a read-only or maintenance mode, take the final database export, import it on the new server, and check an order can be placed.
- Saturday 06:00. Change both A records to 203.0.113.50. The authoritative servers answer with the new address at once.
- Saturday 06:05 onwards. Within about five minutes most visitors are on the new server. Keep the old one running, reading from a copy of the data, so the stragglers on slow resolvers still reach a working shop, and watch the access logs on both until the old one goes quiet.
- Monday. When the old server's logs have been empty for a day, raise the TTL back to 14400 and retire it.
When a proxy or CDN muddies the picture
If your site sits behind a CDN or a reverse proxy, a record change can look different again. Visitors do not connect to your server's address at all. They connect to the proxy's addresses, which are what your public DNS returns, and the proxy then connects to your origin using the address you configured in its dashboard. That has two consequences for a move.
First, changing the origin address in the proxy's settings takes effect on the proxy's schedule, which is usually near-instant and not subject to your DNS TTL at all. Second, DNS lookups tell you nothing about where the content really comes from. dig will keep showing the proxy's addresses before, during and after the move, and you have to look at response headers or server logs to see which origin answered.
The proxy may also cache pages and files for its own period. After a move, a visitor can get the old version of a page from the CDN's edge even though DNS is entirely settled. That is a content caching question, not a propagation one, and the cure is to purge the CDN cache from its dashboard. Telling the two apart saves a lot of fruitless waiting: if dig returns the right answer and the page is stale, it is a different cache.
Mistakes that look like propagation
Quite a few problems that arrive labelled "DNS is still propagating" are nothing of the kind. A short list, in the order I check them:
- The record was edited at the wrong provider. The domain uses nameservers at one company, but the change was made in the zone editor at the registrar or the old host, which no longer answers for the domain. The authoritative check above exposes this at once.
- A typo in the address, or a trailing dot added to an IP address in a form that expects a name.
- A CNAME placed on the bare domain, where it conflicts with the SOA and NS records that must exist there. Many providers refuse it, and a few apply it in odd ways.
- A second record left behind. Two A records means resolvers hand out both addresses in rotation, so half of the visitors reach the old server and half the new, which looks like random flapping.
- An AAAA record still pointing to the old server's IPv6 address, after the A record was updated. Visitors with IPv6 go to the old place while IPv4-only visitors reach the new one.
- The new server is not configured to answer for the domain name, so the connection works but the wrong site, or a default page, appears.
Every one of these is visible by asking the authoritative nameserver for all the records on the name and by testing the new server directly with curl --resolve. Neither needs any waiting.
Checking it yourself
You can watch the process happen instead of guessing. The following checks take under a minute.
- Ask your authoritative nameserver directly. Find it with
dig example.com NS +short, then rundig example.com A @ns1.example.net +short. This is the truth, uncached. If it is wrong, fix the record and stop waiting. - Ask a public resolver:
dig example.com A @1.1.1.1. The second column of the answer shows the TTL counting down. Run it twice a few seconds apart and you can watch the number fall. When it reaches zero, the resolver fetches fresh data and the number jumps back up to the full value. - Follow the whole chain with
dig example.com +trace, which skips your resolver and walks from the root servers down. - Check your own machine with
dig example.comwithout an@. The answer comes from whatever resolver your system uses. - Compare with a phone on mobile data. If it differs from your laptop, the difference is local to your network or your machine.
$ dig example.com A @1.1.1.1 +noall +answer
example.com. 212 IN A 203.0.113.10
$ sleep 10; dig example.com A @1.1.1.1 +noall +answer
example.com. 202 IN A 203.0.113.10
That 212 falling to 202 is the countdown in action: this resolver will serve that address for another 202 seconds, then ask again. If you want a plain-language definition of the terms, the glossary covers TTL, SOA and resolver.
Questions that come up
Can I force the internet to refresh?
No. You can ask the big public resolvers to flush a specific name through their web tools, and you can clear your own caches, but you have no control over the thousands of other resolvers. The lowered TTL is the only real lever, and it must be pulled in advance.
Why does my site work in one browser and not another?
Often each browser holds its own copy of the lookup, or one of them is using encrypted DNS to a different resolver than the system. Closing and reopening the browser, or trying a private window, usually clears it.
Is a very low TTL always better?
No. Every cache miss is a fresh lookup, which adds a few milliseconds for the visitor and load for your DNS provider. For a stable site, an hour or more is perfectly reasonable. Lower it only when you are about to change something.
Does email follow the same rules?
Yes. MX records are cached the same way, so mail may keep flowing to the old server for the length of the old TTL. Keep the old mail server accepting messages through that window, and check that SPF and DKIM records are in place on the new side before you switch.
Why do some tools show a different answer from mine?
Because they ask different resolvers at different moments. Treat any one reading as a single sample. The authoritative answer is the definitive one, and the rest are cached copies in various stages of ageing.