Cookies
- Most of the time, cookies are set by a web server.
- Then they are automatically added to every request to the same domain.
- We can access cookies from the browser, using
document.cookie
property.
- The value of
document.cookie
consists of name=value
pairs, delimited by ;
. Each one is a separate cookie.
- To find a particular cookie, we can split
document.cookie
by ;
, and then find the right name.
- We can use either a regular expression or array functions to do that.
console.log(document.cookie); // cookie1=value1; cookie2=value2;...
- We can write to
document.cookie,
but it’s not a data property, it’s an accessor.
- A write operation to
document.cookie
passes through the browser that updates cookies mentioned in it, but doesn’t touch other cookies.
document.cookie = "user=John"; // update only cookie named 'user'
alert(document.cookie); // show all cookies
- If you run it, then probably you’ll see multiple cookies.
- That’s because
document.cookie=
operation does not overwrite all cookies.
- It only sets the mentioned cookie
user
.
- Technically, name and value can have any characters, but to keep the formatting valid they should be escaped using a built-in
encodeURIComponent
function:
// special values, need encoding
let name = "my name";
let value = "John Smith"
// encodes the cookie as my%20name=John%20Smith
document.cookie = encodeURIComponent(name) + '=' + encodeURIComponent(value);
console.log(document.cookie); // ...; my%20name=John%20Smith
- There are few limitations:
- The
name=value
pair, after encodeURIComponent
, should not exceed 4kb. So we can’t store anything huge in a cookie.
- The total number of cookies per domain is limited to around 20+, the exact limit depends on a browser.
- Cookies have several options, many of them are important and should be set.
- The options are listed after
key=value
, delimited by ;
, like this:
document.cookie = "user=John; path=/; expires=Tue, 19 Jan 2038 03:14:07 GMT"
- The url path prefix is where the cookie is accessible. Must be absolute. By default, it’s the current path.
- If a cookie is set with
path=/admin
, it’s visible at pages /admin
and /admin/something
, but not at /home
or /adminpage
.
- Usually, we set
path=/
to make the cookie accessible from all website pages.
- Domain is where the cookie is accessible. In practice though, there are limitations. We can’t set any domain.
- By default, a cookie is accessible only at the domain that set it. So, if the cookie was set by
site.com
, we won’t get it other.com
.
- But what’s more tricky, we also won’t get the cookie at a subdomain
forum.site.com
!
- There’s no way to let a cookie be accessible from another 2nd-level domain, so
other.com
will never receive a cookie set at site.com
.
- It’s a safety restriction, to allow us to store sensitive data in cookies.
- But if we’d like to grant access to subdomains like
forum.site.com
, that’s possible. We should explicitly set domain
option to the root domain: domain=site.com
.
- For historical reasons,
domain=.site.com
(a dot at the start) also works this way, it might better to add the dot to support very old browsers.
- So,
domain
option allows to make a cookie accessible at subdomains.
- By default, if a cookie doesn’t have one of these options, it disappears when the browser is closed. Such cookies are called “session cookies”
- To let cookies survive browser close, we can set either
expires
or max-age
option.
expires=Tue, 19 Jan 2038 03:14:07 GMT
- Cookie expiration date, when the browser will delete it automatically.
- The date must be exactly in this format, in GMT timezone. We can use
date.toUTCString
to get it.
- If we set expires to a date in the past, the cookie is deleted.
- An alternative to
expires
, specifies the cookie expiration in seconds from the current moment.
- If zero or negative, then the cookie is deleted.
secure
indicates that the cookie should be transferred only over HTTPS.
- By default, if we set a cookie at
http://site.com
, then it also appears at https://site.com
and vice versa.
- That is, cookies are domain-based, they do not distinguish between the protocols.
- With this option, if a cookie is set by
https://site.com
, then it doesn’t appear when the same site is accessed by HTTP, as http://site.com
. So if a cookie has sensitive content that should never be sent over unencrypted HTTP, then the flag is the right thing.