FreshScanSentry Free vulnerability scanning for your network & web apps Run a free scan

Low risk Website cookies · HttpOnly · Secure · SameSite

Cookies missing HttpOnly, Secure or SameSite: what it means and how to fix it

Short answer: cookies are how your website remembers who is logged in. Three small flags control how safely the browser handles them. Without them, a stolen or leaked cookie can let someone take over a logged-in session without knowing the password.

The fix: set login and session cookies with all three flags:

Set-Cookie: session=…; HttpOnly; Secure; SameSite=Lax; Path=/

Most platforms have a setting for this. They're listed below.

What the three flags do

FlagWhat it doesProtects against
HttpOnlyJavaScript in the page can't read the cookieA malicious script (XSS) stealing login sessions
SecureThe cookie is only sent over HTTPSSomeone on public Wi-Fi reading it from unencrypted traffic
SameSiteControls whether the cookie is sent when another site links to or loads yoursCross-site request forgery (CSRF), where another site makes a logged-in visitor's browser act for them

SameSite has three values. Lax fits most sites: the cookie is sent when people click a link to you, but not on hidden requests from other sites. Strict never sends it from other sites, which can log people out when they arrive from an email link. None always sends it, is only for cookies that must work inside other sites (like an embedded widget), and requires Secure.

How serious is it?

On its own it's Low, which is how OWASP ZAP rates it too. These flags limit the damage when something else goes wrong, like a script injection bug or a visitor on an untrusted network. They matter most for sites with logins, shopping carts, customer accounts or admin areas. For a site with no logins, findings about analytics or preference cookies are usually minor.

How it looks in your report shop.example.com
  1. 443 Cookie No HttpOnly Flag Found on 4 URLs Low
  2. 443 Cookie without SameSite Attribute Found on 4 URLs Low
Found by the Deep Scan's web app checks

First, find out which cookies it is

The cookie's name tells you what set it, and whether it needs fixing:

To see your cookies' flags, open your site, press F12, and go to Application (Chrome, Edge) or Storage (Firefox) → Cookies. There are columns for HttpOnly, Secure and SameSite. Or check from the command line:

curl -sI https://your-site.com | grep -i set-cookie

How to fix it on common platforms

PHP (sessions), in php.ini, or ask your host:

session.cookie_httponly = 1
session.cookie_secure = 1
session.cookie_samesite = "Lax"

For cookies your own code sets, pass the options array to setcookie() with 'httponly' => true, 'secure' => true, 'samesite' => 'Lax'.

WordPress. Its login cookies are already HttpOnly. Make sure the whole site uses HTTPS (the WordPress Address and Site Address under Settings → General both start with https://) so they're also Secure. Findings about other cookies usually come from a plugin or theme. The cookie name tells you which, and the plugin's settings or a plugin update may fix it.

Node.js / Express with express-session:

app.set('trust proxy', 1); // if behind a proxy or load balancer
app.use(session({
  secret: process.env.SESSION_SECRET,
  cookie: { httpOnly: true, secure: true, sameSite: 'lax' },
}));

Django, in settings.py (HttpOnly and Lax are already the defaults for the session cookie):

SESSION_COOKIE_SECURE = True
CSRF_COOKIE_SECURE = True
SESSION_COOKIE_SAMESITE = "Lax"

ASP.NET (classic, web.config):

<system.web>
  <httpCookies httpOnlyCookies="true" requireSSL="true" sameSite="Lax" />
</system.web>

On ASP.NET Core, set HttpOnly, SecurePolicy = CookieSecurePolicy.Always and SameSite = SameSiteMode.Lax in the cookie or session options.

nginx in front of an app (version 1.19.3 or later) can add the flags to cookies the app sends:

proxy_cookie_flags ~ secure httponly samesite=lax;

Apache can rewrite cookies with mod_headers when the app itself can't be changed. Fixing it in the app is cleaner, because this rule adds the flags even if a cookie already has them:

Header always edit Set-Cookie ^(.*)$ "$1; HttpOnly; Secure; SameSite=Lax"

Test after the change

Extra credit

Common questions

Browsers already default to SameSite=Lax. Do I still need to set it?

Chrome and Edge treat cookies without SameSite as Lax, but not every browser does the same, and scanners flag the missing attribute. Setting it explicitly gives the same result everywhere.

Why can't my analytics cookie be HttpOnly?

Because the analytics script sets and reads it in the browser. HttpOnly would stop it from working. That's expected. Make sure it's Secure, and focus HttpOnly on login and session cookies.

Will adding Secure break anything?

Only if part of your site still uses plain HTTP. Secure cookies aren't sent there, so users would appear logged out. Move the whole site to HTTPS first.

Sources: MDN: Set-Cookie · OWASP Session Management cheat sheet · ZAP: Cookie No HttpOnly Flag · ZAP: Cookie Without Secure Flag · ZAP: Cookie without SameSite Attribute · PHP session settings · nginx proxy_cookie_flags