Skip to main content

Favicon Not Updating After Change? Here's Why

10 min read

You changed the favicon file but the browser still shows the old logo because favicons are cached aggressively at multiple layers: your browser, your CDN, and sometimes a service worker. The new file is often live on the server while clients keep serving the cached version from the same URL.

This guide explains why that happens and how to force an update without guessing. After each fix, scan your production URL with Favicon Check to confirm the server returns the new file.

Favicon not showing vs not updating

These look similar but need different fixes.

SituationWhat you seeRoot cause
Not showingGeneric globe or blank tabMissing file, broken path, no tags
Not updatingOld logo after deployCache at browser, CDN, or same filename

If the icon never appeared, start with Favicon Not Showing in Browser? Fix It. If you had a working icon and replaced it, stay here.

Why browsers cache favicons so hard

Favicons load on almost every page view. Browsers store them in a dedicated favicon cache separate from normal HTTP cache in some cases. Chrome, Firefox, and Safari can keep an icon for days or weeks even after the file on disk changed.

That design made sense when favicons rarely changed. It is painful when you rebrand.

Layers that can serve stale icons:

  1. Browser favicon cache - local, per profile
  2. HTTP cache headers on the icon file itself
  3. CDN edge cache - Cloudflare, Fastly, Vercel, etc.
  4. Service worker cache - if your PWA caches static assets broadly
  5. Reverse proxy - nginx or Apache with long expires on static files

You may need to clear more than one layer.

Step 1: Confirm the server has the new file

Before blaming cache, verify production actually serves the updated icon.

Open the icon URL directly in a private window:

https://yourdomain.com/favicon.ico

Compare what you see to the old design. If the old icon still loads in incognito on a URL you never visited before, the problem is server-side or CDN-side, not your local browser.

Paste the same URL into Favicon Check. The preview thumbnail should match your new artwork. If it shows the old icon, your deploy did not replace the file or a CDN node is stale.

Check view-source for the declared href

View page source on your homepage. Note every href on rel="icon" tags:

<link rel="icon" href="/favicon.ico" sizes="any">
<link rel="icon" type="image/png" sizes="32x32" href="/favicon-32x32.png">

Open each URL in a new tab. All of them must return the new image. Updating only favicon.ico while HTML still points at an old PNG is a common miss.

Step 2: Cache bust with a new filename

The most reliable fix is to stop reusing the same URL.

Instead of overwriting /favicon.ico in place, ship a new name:

<link rel="icon" href="/favicon-2026.ico" sizes="any">
<link rel="icon" type="image/png" sizes="32x32" href="/favicon-32x32-v2.png">

Deploy, hard refresh once, and the browser treats it as a new resource. No cache entry exists for that URL yet.

You do not need query strings for this to work, though they help too:

<link rel="icon" href="/favicon.ico?v=3">

Query strings bust browser cache in most cases. Some CDNs ignore query strings unless configured to vary on them. A new filename is safer for CDNs that strip or normalize query params.

After renaming, update every reference:

  • HTML link tags in layout templates
  • manifest.json icon paths
  • CMS theme settings
  • Framework metadata in Next.js or similar

See How to Add a Favicon to Your Website for the full tag set.

Step 3: Fix CDN and server cache headers

Static assets often ship with long Cache-Control values:

Cache-Control: public, max-age=31536000, immutable

That is fine for hashed build files. It is wrong for favicons you replace without renaming.

nginx example

location = /favicon.ico {
add_header Cache-Control "public, max-age=3600";
}

Shorter TTL on icon paths, or use versioned filenames and keep long cache on those.

Cloudflare

Purge cache for /favicon.ico and any PNG icon paths after deploy. Caching > Configuration > Purge Cache > Custom Purge with exact URLs.

If you use Cloudflare "Cache Everything" page rules, favicon requests may bypass your origin for weeks.

Vercel and Netlify

Redeploy replaces files, but edge cache may still serve old bytes briefly. Purge through the dashboard or rename the file so the edge sees a cache miss.

Step 4: Clear browser favicon cache locally

Once the server is correct, your main browser may still show the old tab icon.

Try in order:

  1. Private or incognito window - quickest sanity check
  2. Hard refresh - Cmd+Shift+R (Mac) or Ctrl+Shift+R (Windows)
  3. Different browser you have not used for that site
  4. Clear site data - Chrome: lock icon > Site settings > Clear data
  5. Chrome favicon cache (last resort on desktop): close all tabs for the site, clear browsing data limited to "Cached images and files"

Safari on macOS caches favicons per domain. Quit Safari completely and reopen if incognito is not enough.

Mobile browsers cache even longer. On iOS, removing the site from history rarely clears favicon cache. A new filename in HTML is the practical fix for mobile users without asking them to clear all website data.

Step 5: Service workers and PWAs

If your site registers a service worker, it may cache /favicon.ico under a static assets strategy:

// Example: overly broad precache
workbox.precaching.precacheAndRoute([
{ url: '/favicon.ico', revision: null },
]);

Bump the revision or remove favicon from precache. After deploy, users with an old service worker keep the old icon until the worker updates.

In DevTools > Application > Service Workers, click "Update" and "Unregister" while testing.

Step 6: CMS and build pipeline gotchas

WordPress and theme caches

Some themes store favicon URLs in the database. Uploading a new file to the media library does not update the stored URL. Change the Site Icon in Appearance > Customize and save again.

Page cache plugins (WP Rocket, W3 Total Cache) may cache HTML with old href values. Purge all caches after favicon changes.

Next.js and static export

Icons in public/ deploy with the build. If you only changed the file locally but did not redeploy, production stays old. Confirm the CI pipeline ran and the artifact contains the new bytes.

App Router metadata icons in app/icon.png generate routes at build time. Replace the source file and rebuild.

Git and case sensitivity

Renaming Favicon.ico to favicon.ico on macOS may not register in git. Linux production still serves the old file. Use git mv explicitly.

Step 7: apple-touch-icon and manifest lag separately

You updated the tab icon but iOS home screen still shows the old tile. That is a different file:

<link rel="apple-touch-icon" sizes="180x180" href="/apple-touch-icon.png">

iOS caches home screen icons aggressively. Users must remove and re-add the shortcut, or you must change the apple-touch-icon URL. See Apple Touch Icon Missing on iOS if the tile never updated at all.

PWA manifest icons in site.webmanifest follow the same rule. Update paths and bump manifest version if your tooling supports it.

Common mistakes when favicon won't update

Overwriting the file without purging CDN

You FTP'd a new favicon.ico. Cloudflare still serves the 2023 version from Frankfurt.

Only updating one format

New ICO, old 32×32 PNG still in HTML. Chrome picks PNG on some displays. Both must match.

Testing on localhost then assuming production updated

Localhost serves from disk. Production serves from CDN. Always verify the public URL.

Blurry new icon mistaken for old icon

You shipped a upscaled logo. It looks different but bad. Check Favicon Looks Blurry? Fix Pixelation before chasing cache ghosts.

Same browser tab left open for days

Some browsers only refresh favicons on navigation or restart. Close the tab and open a fresh one.

Step-by-step update workflow

  1. Replace icon files on the server or in your repo.
  2. Rename files or add version query strings in HTML, manifest, and CMS settings.
  3. Deploy to production over HTTPS.
  4. Purge CDN cache for all icon URLs.
  5. Scan with Favicon Check. Confirm previews show new artwork.
  6. Test in incognito across Chrome, Firefox, and Safari.
  7. Optional: run the Open Graph scanner on the same URL for a full site metadata check.

When to wait vs when to act

If incognito shows the new icon and your regular profile shows the old one, you are done on the server side. Local cache will expire or you can clear it.

If incognito still shows the old icon after CDN purge and rename, trace the request in Network tab. Check which server responded and the Cache-Control header on the response.

Google Search favicons in SERPs update on their own schedule after recrawl. Tab icon fix does not instantly change SERP icons.

FAQ

Why is my favicon not updating after I changed the file?

Browsers and CDNs cache favicon URLs aggressively. Overwriting the same path often leaves clients serving stale bytes until you rename the file, purge CDN cache, or wait for TTL expiry.

Does hard refresh always update the favicon?

No. Hard refresh reloads the page HTML but may not invalidate the favicon cache entry. Incognito or a new filename is more reliable.

Should I use ?v=2 on favicon URLs?

Query strings work for many browsers and origins. CDNs that ignore query strings need a renamed file instead. Both approaches are valid; filename versioning is safer for CDN-heavy setups.

How long does favicon cache last?

Browser favicon cache can persist for days to weeks. CDN cache depends on your Cache-Control headers, often hours to one year. There is no universal expiry.

I purged Cloudflare but still see the old icon locally

Local browser cache is separate from CDN. Test incognito after purge. If incognito is correct, clear site data in your main profile or wait.

Do I need to update favicon.ico and PNG?

If HTML declares both, yes. Browsers pick different formats per context. Keep all declared URLs in sync after a rebrand.

Favicon updated in Chrome but not Safari?

Safari maintains its own favicon store. Quit and reopen Safari, or use a new href. macOS and iOS do not share identical cache behavior.

How do I verify the live file without browser cache?

Use Favicon Check or curl the icon URL with cache-busting: curl -I "https://example.com/favicon.ico?nocache=$(date +%s)".

Bottom line

A favicon that will not update is almost always cache at the browser, CDN, or both, combined with reusing the same URL. Ship versioned filenames, purge CDN after deploy, shorten cache headers on icon paths, and confirm the live file with Favicon Check. New visitors should see the new icon immediately; returning users get it as soon as their cache misses the new URL.