Cookies, sessionStorage, localStorage. What's the difference?!

This post is about different storage possibilities in your browser. There are cookies, and different kinds of storage that can be accessed through JavaScript APIs in your client side code. They're used for authentication, tracking tools like Google Analytics and a lot of other stuff, so let's have a look at how they work!

sessionStorage

Session Storage can come off as a bit confusing, because it's called Session storage. The session we're referring to is the current browser tab, not the same browser or window or anything like that.

This means it's not commonly used for managing authenticated user sessions, like for example when you log into facebook and facebook remembers it's you, even though you close the page and you open it again. That's a cookie, not the Storage.

A striking advantage of sessionStore over just setting a global JavaScript variable is that it persists through page reloads. This means that if you have different server side rendered pages, you can have some data persist on the client, given that the same tab is used. For a long time, especially before localStorage and complex change detection on the frontend, that was a super important feature!

sessionStorage thereby still is a very volatile store. It doesn't last very long, you can think of it as a text document without a save button, everything that's in it will just evaporate into the cyber ether when you close that browser tab. Well, almost. Before that, some JavaScript could technically send it off to another server that will remember that data for you.

Let's try it out anyways!

sessionStorage.setItem("name", "Jonathan");
let data = sessionStorage.getItem("name");
console.log(data);

If you paste this into your browsers console or put it in a simple <script> tag and access it through a small dummy web server, you can see that it prints Jonathan to your console. On top of that, if you open your developer tools and look at Storage in Firefox or Application in Chrome, then switching to the Session Storage tab, you can see that the key and value are saved there.

If you want to see it persist through a change, you can change the key name to something else, reload the page and then see two values! The store persisted your refresh!

Alright, if you don't think it's that cool you might as well clean up after yourself and sessionStorage.removeItem('name'); or just sessionStorage.clear();.

Otherwise, read more about it at the Mozilla Development Network: sessionStorage

localStorage

Let's talk about something more fun, localStorage! In contrast to the pesky sessionStorage, it persists application wide, the application being your browser. As a security measure, your browser will automatically file the saved values by domain (just like with the sessionStorage), so you can kind of put secret stuff in there.

When I say secret stuff, I don't mean like... passwords, but maybe an expiring secret token (yes, that sounds like a session cookie to me too) or a JWT (JSON Web Token).

Why into localStorage you ask? Well, because the localStorage doesn't have an expiration time when the browser tab gets closed. It'll stick around for (potentially) ever or until the JavaScript you ship to your client deletes it. Technically the user can delete it was well, but we kind of expect them to do silly things like that.

There are some unfortunate limitations with this and writing to localStorage can not be guaranteed, iOS Safari for example throws an error message that fails writes to localStorage when it's in private mode.

Error: QUOTA_EXCEEDED_ERR: DOM Exception 22

Apart from that it's actually very nice to work with, also using the setItem, getItem and clear functions, and you can even snapshot your apps state into localStorage and then on the next startup first try to restore from localStorage (if you're moving a lot of data back and forth) and then worry about getting the up to date info back to your user.

Cookies

Right, now for the tasty part. Cookies have actually made it into mainstream media by being the subject that several different legislations touch upon. Cookies are also domain specific, can persist for a long time and they, in contrast to the previously covered stores, can be sent along every HTTP request to the same domain.

As a very simplified example, imagine you're at an ice cream stand and when reaching it you are greeted by the ice cream man with a paper slip that has some characters on it. Let's say: 5axhz. Now every time you talk to the ice cream man, you'll attach that information with every request you make.

Oh, that magenta one looks lovely, what flavor is that? 5axhz

He responds:

That's pink and it's raspberry

You continue:

Oh 5axhz

Well then I'd like to have two of those 5axhz

Actually, two of those and one vanilla 5axhz

The privacy problem with that arises is that every restaurant that shows you a picture of that ice cream truck, will now enable your original ice cream truck man to know that you're now looking at pictures of ice cream, even though you're no where near it.

Now, in real life, printed photographs can't tell the photographer that they're being viewed by a specific person (yet?). On the internet, every externally included resource, can tell the owner that they're being viewed by someone and if that someone has been seen before, they can identify that person, no matter if they logged out in the meantime.

Getting and Setting Cookies with Vanilla JavaScript

In your browser you can access

document.cookie;

in your JavaScript console to get access to the cookies, so let's set one!

document.cookie = "my_favourite_ice_cream" + "=" + "vanilla";
document.cookie = "my_favourite_burger" + "=" + "cheeseburger";

console.log(document.cookie);
// my_favourite_ice_cream=vanilla; my_favourite_burger=cheeseburger

As you can see the cookie key/values are concatenated by ;, which can make changing them a bit tricky, but luckily there are some neat JavaScript libraries like js-cookie, to make that all a bit easier.

Without specifying an expiry, the cookie will expire after this session (browser tab).

We can inspect the Cookies using the browser inspector, like we did with the other storages, just click into the Cookie tab this time.

Setting Cookies with HTTP / PHP / Express.js / Whatever

Cookies can be set server side as well, so you don't need to ship anything that then maybe executes JavaScript on the client, but you can respond with a HTTP header for this purpose:

HTTP/2.0 200 OK
Content-type: text/html
Set-Cookie: favourite_hero=aquaman
Set-Cookie: favourite_khal=drogo

Even if you can write directly to the HTTP headers with your web framework, I'd recommend you make use of the features that are designed for this, throw errors if your payload is too long and similar, like setcookie in PHP

setcookie( "previous_orders", "65" );

Or res.cookie in Express.js:

// express
res.cookie("cookieName", "cookieValue", { maxAge: 50000 });

Summary

So now we have looked at a few methods to store things like JSON Web Tokens or tracking IDs in a browser, even though we mainly thought of ice cream while doing that.

What we have not looked at is indexedDB, which we will have a look at in another post, because it has a couple of cool features as well!

We also have not looked at what to use all of this for or the numerous security precautions and additional cookie flags that can be set to mitigate risks, please do follow up on those before deploying sensitive data applications.

Tagged with: #cookies #localStorage #sessionstorage

Thank you for reading! If you have any comments, additions or questions, please tweet or toot them at me!