Back to Blog
CookiesPrivacyBrowserSessionSecurity

Cookies, localStorage, and Why Your Browser Sessions Aren't as Private as You Think

How cookies, localStorage, and session storage create invisible links between your activities. Understanding browser storage is key to real isolation.

Raven Wallet Team

Cleared my cookies last week on my main browser. Went to a site I use regularly. It greeted me by name.

Not because I was logged in. Not because I had an account cookie. Because localStorage still had my preferences, my user ID, and about 2MB of other data that survived the cookie purge.

Most people treat "clear cookies" as the nuclear option for browser privacy. It's more like sweeping the front porch while the house is still on fire.

The storage zoo

Your browser has way more storage mechanisms than most people realize. Here's what's actually sitting on your machine right now for any given website:

Cookies. The classic. Small key-value pairs, max 4KB each. Sent to the server with every request. These are what everyone knows about and clears.

localStorage. Up to 10MB per origin. Never expires. Never sent to the server automatically. Survives browser restarts, computer restarts, cookie clearing. Just sits there forever unless the site deletes it or you manually wipe it.

sessionStorage. Same as localStorage but dies when you close the tab. Sounds safe, right? Except "closing the tab" in Chrome doesn't always mean what you think. Chrome's tab restore feature can bring sessionStorage back from the dead. Fun.

IndexedDB. A full database in your browser. No practical size limit on most browsers. Can store structured data, binary blobs, whatever. Many dApps use this for caching blockchain data. MetaMask uses it extensively.

Cache API and Service Workers. A site can install a Service Worker that intercepts network requests and serves cached responses. This worker persists across sessions, across cookie clears, across everything short of manually unregistering it. Sites can embed tracking identifiers in the cached responses.

That's five different places a site can stash identifiers. Clearing cookies touches exactly one of them.

The ones nobody thinks about

ETags are probably the sneakiest tracking mechanism I've come across. Here's how they work:

You request an image from a server. Server sends it back with an ETag header - basically a version identifier. Next time your browser requests that image, it sends the ETag back saying "hey, has this changed?" The server recognizes YOUR specific ETag and knows exactly who you are. No cookies involved. Lives in the browser cache.

Clear cookies? ETag survives. Use incognito? Fresh start, sure, but go back to normal mode and the ETag is still there.

HSTS supercookies are even wilder. When a site tells your browser "only connect to me over HTTPS," the browser remembers that. By controlling many subdomains and selectively setting HSTS flags, a site can encode a binary identifier into your browser's HSTS database. Each bit is a subdomain. It's been demonstrated in research papers and yeah, people do use it in the wild. Probably not most dApps, but the technique exists.

(Not getting into browser cache partitioning here - that's a different rabbit hole. Chrome has been partitioning caches by top-level site since around version 86, which helps, but the implementation has gaps.)

Why this matters for crypto specifically

Here's where it gets real for anyone running multiple wallets.

You connect Wallet A to a DeFi protocol. The protocol stores data in localStorage - your preferred slippage, your last few transactions, maybe some analytics identifiers. Pretty standard stuff.

Now you disconnect Wallet A and connect Wallet B in the same browser. The dApp sees a "new" wallet. But localStorage still has all the data from Wallet A's session. The site doesn't even need to be malicious about it. Standard analytics code can correlate "User who had these preferences and this transaction history is now connecting with a different wallet."

I've checked this on several popular dApps. Most of them store analytics IDs in localStorage that persist across wallet switches. Not because they're trying to catch farmers. It's just how modern web analytics works. But the data is there for anyone who wants to query it.

This is exactly why separate browser profiles exist. Different profile, different localStorage, different everything. Switching wallets in the same profile is like changing your shirt but keeping the same name tag.

The MetaMask problem

This one bit me personally.

MetaMask (and most browser wallet extensions) shares state across all tabs in a browser profile. If you have three accounts in MetaMask, every dApp you connect to can see that you have three accounts. Even if you only connect one of them, the extension's presence in the browser is shared.

Some dApps explicitly check for the number of accounts available. Others check window.ethereum properties that reveal extension version, installed chains, and configuration. All of this is shared within a single browser profile.

It gets worse with newer wallet extensions that support multiple chains. Your Ethereum wallet and your Solana wallet running in the same browser profile share the same extension storage. A clever dApp on Ethereum could theoretically detect your Solana extension and vice versa.

The fix is the same as everything else here: one profile per identity. Not one tab. Not one window. One isolated profile with its own extension installations.

Saw a thread on Reddit where someone was running 15 wallets all as separate accounts in a single MetaMask installation. Inside one Chrome profile. Every dApp they connected to could enumerate all 15 addresses through the extension API. That's not farming - that's handing over a list of your Sybil cluster.

"But I use incognito mode"

Yeah, about that.

Incognito gives you a fresh session. No cookies from your main profile, no localStorage, clean slate. When you close the window, everything is deleted. Sounds perfect?

Two problems. First, you can't install extensions in incognito unless you specifically allow them. And when you do, those extensions share storage with the main profile's extension installation. Your MetaMask in incognito is the same MetaMask as in your normal window.

Second, your browser fingerprint in incognito is nearly identical to your normal browsing. Same fonts, same GPU, same canvas hash, same screen resolution. Incognito is invisible to the website. They see the same browser with the same characteristics, just without cookies.

Incognito was designed for not leaving traces on your local machine. It was never designed for being anonymous to websites. Big difference.

Service Workers: the persistent ghost

These deserve special attention because they're genuinely hard to get rid of.

A Service Worker is JavaScript code that a website installs in your browser. It runs in the background, even when you're not on the site. It can intercept network requests, serve cached content, and send push notifications.

From a tracking perspective, a Service Worker can:

  • Store identifiers that survive cookie clearing
  • Intercept outgoing requests and append tracking headers
  • Cache responses with embedded identifiers
  • Communicate with the server even when you're on a different site

To check if you have Service Workers installed, go to chrome://serviceworker-internals/ in Chrome. I just checked mine. 47 Service Workers registered. Most from sites I haven't visited in months.

Clearing cookies doesn't touch them. You have to manually unregister each one, or use a tool that handles full profile isolation.

What actual isolation looks like

Real isolation isn't about clearing data. It's about never sharing data in the first place.

Each browser profile needs:

  • Its own cookie jar (obviously)
  • Its own localStorage and sessionStorage
  • Its own IndexedDB
  • Its own cache (including ETags)
  • Its own Service Worker registrations
  • Its own extension installations and extension storage
  • Its own fingerprint configuration

This is what antidetect browsers actually do. It's not just changing your fingerprint. It's creating a completely separate browser environment where nothing leaks between identities.

Regular Chrome profiles partially achieve this. They separate cookies and localStorage. But they share some system-level data, extension configurations can leak, and fingerprints are identical.

Tools like Raven Wallet create fully isolated profiles with separate storage AND unique fingerprints. Each profile is its own little universe. Nothing in Profile A knows Profile B exists.

The practical takeaway

Stop thinking about cookies as the main privacy mechanism. They're the most visible piece of a much larger puzzle. If you're managing multiple wallets or multiple identities online, you need full storage isolation.

A few things you can do right now:

Check chrome://settings/content/all in Chrome to see how much data each site has stored beyond cookies. You'll probably be surprised.

Check chrome://serviceworker-internals/ for persistent workers.

Look at the actual opsec checklist for browser security and think about whether your current setup actually isolates storage or just isolates cookies.

And if you're still switching wallets in the same browser profile, stop. Every wallet switch in a shared profile leaves breadcrumbs that are trivial to connect. That's not paranoia. That's just how browsers work.