Do QR codes expire?
Two kinds of code look identical and behave nothing alike. How to tell them apart before you send anything to a printer, and what to do when one has already died.
Free toolQR Code GeneratorLinks, Wi-Fi, contacts and more, drawn in your own tab and saved as PNG or SVG. Static codes, so nothing expires.Open the generatorThe short answer
A static QR code never expires. A dynamic one stops working the moment somebody stops paying for it. The two look the same, and most free generators quietly hand you the second kind, because the second kind is a subscription and the first kind is not.
If your code goes straight to the destination, nothing can take it away. If it goes through a short link on the generator's domain, that company is now a permanent dependency of anything you print.
What is actually inside a QR code
A QR code is text drawn as squares. That is the whole of it. There is no lookup, no expiry field and no clock. A code carrying https://example.com/menu holds those 28 characters in the pattern, and a scanner reads them off the paper with no network involved at all.
This is why a static code cannot expire. There is nothing between the paper and the destination to fail. Photocopy it, print it on a mug, laminate it and find it in a drawer in fifteen years: it still says the same 28 characters.
So why do so many of them stop working?
Because a dynamic code does not carry your link. It carries a short address on the generator's own domain, something like qr.example-co.com/a4Xk2, and their server looks that up and redirects. Two things follow.
The good one is that you can change where it goes after printing. Point the same poster at a new page without reprinting it. That is a genuinely useful thing and it is why dynamic codes exist.
The bad one is that the code now depends on a company staying in business, keeping that domain, and choosing to keep answering for a code you made on a free trial in 2023. When any of those stops being true, the code is dead. The pattern is still perfect. It leads to a parked domain or a page asking you to upgrade.
The commercial pressure runs one way here. A static code is made once and never earns anything again. A dynamic code is a monthly bill with a printed poster as collateral. That is why the free tier on most of the big generators is dynamic by default, often with the scan tracking already switched on.
Telling them apart before you print
Scan your own code with an app that shows you the URL rather than opening it. On iOS the Camera app shows the domain in the notification before you tap it. Read what it says.
- Your own domain, or the real destination. Static. Nothing can withdraw it.
- A domain belonging to the generator. Dynamic. It works for exactly as long as they let it.
There is a rough visual tell as well. A dynamic code carries about 20 characters, so it is usually a small grid of 25 or 29 modules a side. A static code carrying a real link is typically denser. It is a hint, not a test, because a short static link looks the same.
Check for the words too. "Dynamic", "editable", "trackable", "scan analytics" and "manage your codes" all mean the same thing: the code goes through them. So does a sign-up wall, because a code nobody has to log in to manage does not need an account.
Getting editable links without the dependency
You can have both, and almost nobody tells you this. Make a static code that points at a URL on your own domain, and put the redirect there.
A restaurant printing table cards points the code at yoursite.com/menu. That page redirects to wherever the menu currently lives. Change the menu, change the redirect, and every card already on every table follows within the minute. The code itself is static, so no third party can withdraw it, and there is no monthly bill.
You lose the scan analytics unless you add your own, which for most people is a line in a server log or a page view in whatever analytics they already run. That is the entire trade, and it is a much better one than it is usually presented as.
When a dynamic code is genuinely the right call
There are cases, and pretending otherwise would be as dishonest as the free trials. Use a paid dynamic code when you need per-scan data you cannot get from your own server: scan location, device breakdown, time of day, campaign comparison across twenty printed placements. Agencies need this and it is worth paying for.
Use one when you do not control a domain to redirect from, which rules out the trick above. And use one when the destination will change often and unpredictably, and the codes are already in the world.
In each case, pay for it. A free dynamic code is the worst of both: it can be withdrawn, it is being counted by someone else, and you have no contract saying otherwise.
What to do when one has already stopped working
Scan it and read the URL. If it is a generator's domain, the redirect is gone and there is no recovering it. The printed copies are waste. Make a static replacement, point it at your own domain, and reprint.
If it is your own URL and the page 404s, nothing is wrong with the code at all. Fix the redirect and every copy in the world starts working again. This is the difference the choice buys you, and it only shows up on the day something breaks.
The other reasons a code fails, which are not expiry
Most "expired" codes were never dynamic. They were printed badly, and the failure looked like the same thing.
- The quiet zone was cropped. A code needs a blank border of about four modules. A designer trimming it flush to the artwork is the single most common cause.
- It was printed too small. A big grid needs a big code. A version 20 pattern shrunk onto a business card has modules finer than a phone camera can resolve.
- The contrast was inverted. Light modules on a dark background have plenty of contrast and still fail, because scanners assume the pattern is the darker of the two.
- The ink faded. Thermal receipt paper in a sunny window goes blank in months. That is the paper, not the code.
- A logo covered too much. Error correction can rebuild a quarter of a code at most, and only if the level was raised to match.
The generator reports the smallest size a given code can be printed at and warns when the two colours will not separate, which covers three of those five before anything reaches a printer.
A short checklist before you print a thousand of anything
- Scan it and read the URL. Is it yours, or somebody else's short link?
- Point it at a redirect on your own domain, so the destination stays editable.
- Raise the error correction to High if it will be handled, scuffed or printed small.
- Keep the quiet zone. Do not let anyone trim it flush.
- Print one proof at final size and scan it on two different phones, one iPhone and one Android.
- Save the vector file, not just the PNG, so a reprint at another size does not mean regenerating from memory.