Prerequisites
🚀 Feature Proposal
Device Bound Session Credentials (DBSC) are a new web standard proposal to protect authenticated sessions against cookie theft by binding session refresh to a hardware-protected key pair on the user's device. It is already implemented in Chrome browser and subject for implementation in other browsers as well.
DBSC does not replace traditional session handling and should be fully backward-compatible.
The core concept of DBSC is to reduce session cookie lifetime on DBSC-aware clients. The client generates a hardware-backed public-private key pair and registers the public key with a new endpoint after establishing a traditional session. In response, it receives the path of the session-refresh endpoint and a replaced short-lived session cookie. When the short-lived session cookie is about to expire, the client can refresh it by contacting the session-refresh endpoint which returns a challenge. The client solves this challenge using the hardware-backed private key and sends the result back to that endpoint. This results in a fresh short-lived session cookie to be issued. The core of this works using a set of new headers like for example Secure-Session-Registration. Clients that don't support DBSC would keep the long-lived session cookie as before.
The fastify session middleware could implement the following:
- a new config option to opt in to DBSC with configurable paths for the register and refresh endpoints
- an extension to the session store for keeping the session's associated public key
- a map to associate short-lived session cookies with one stored session
- the register endpoint on the user-specified path which associates the public key with a session
- the refresh endpoint on the user-specified path which issues and verifies challenge and can issue a new short-lived session cookie
The specification draft contains a few extras to maintain federated/shared DBSC state across multiple origins as well as specifying a well-known document. This could be added in a later revision if desired.
The specification can be found here: https://w3c.github.io/webappsec-dbsc/
Some further information and examples were published by Google: https://developer.chrome.com/docs/web-platform/device-bound-session-credentials
Motivation
Session cookies are a common target for infostealer malware. The amount of credential-stealing malware has risen to new highs in 2025 (see for example this report), especially with waves of supply chain attacks.
By binding sessions to hardware-backed key material ownership proofs can reduce the impact of compromised short-living session cookies.
I propose the integration into fastify session as a popular session handling system in order to raise adoption rates for secure session handling. This should make it easier for people to actually use DBSC.
Example
An example registration of the session middleware could look like this. The lifetime of the traditional session cookie is set to 6 hours, while DBSC-aware clients would refresh the session every 10 minutes.
const fastify = require('fastify');
const fastifySession = require('@fastify/session');
const fastifyCookie = require('@fastify/cookie');
const app = fastify();
app.register(fastifyCookie);
app.register(fastifySession, {
secret: 'a secret with minimum length of 32 characters',
cookie: {
maxAge: 21600 * 1000
},
dbsc: {
registerEndpoint: "/dbsc/register",
refreshEndpoint: "/dbsc/refresh",
shortMaxAge: 600 * 1000
}
});
This will result in a new header being returned for requests:
Secure-Session-Registration: (ES256 RS256); path="/dbsc/register"
The endpoint /dbsc/register is intercepted by the middleware to receive a JWT with the public key of the client and issue a short-lived session cookie. It returns some information (specified in the standard) to the client like this:
{
"session_identifier": "...",
"refresh_url": "/dbsc/refresh",
"scope": {
"origin": "https://example.com",
"include_site": true,
"scope_specification": []
},
"credentials": [{
"type": "cookie",
"name": "sessionId",
"attributes": "Domain=example.com; Secure; SameSite=Lax"
}]
}
The client can then refresh the session by performing a POST request to the /dbsc/refresh endpoint including the session ID as a header: Sec-Secure-Session-Id: .... This endpoint is intercepted by the fastify session middleware as well and issues a challenge to the client using a header as well:
Secure-Session-Challenge: "challenge_value"
The client signs the challenge using its private key and performs a second POST request to the /dbsc/refresh endpoint including the session ID and the challenge result as a header: Secure-Session-Response: .... The middleware verifies this request and returns a new short-lived session cookie.
Prerequisites
🚀 Feature Proposal
Device Bound Session Credentials (DBSC) are a new web standard proposal to protect authenticated sessions against cookie theft by binding session refresh to a hardware-protected key pair on the user's device. It is already implemented in Chrome browser and subject for implementation in other browsers as well.
DBSC does not replace traditional session handling and should be fully backward-compatible.
The core concept of DBSC is to reduce session cookie lifetime on DBSC-aware clients. The client generates a hardware-backed public-private key pair and registers the public key with a new endpoint after establishing a traditional session. In response, it receives the path of the session-refresh endpoint and a replaced short-lived session cookie. When the short-lived session cookie is about to expire, the client can refresh it by contacting the session-refresh endpoint which returns a challenge. The client solves this challenge using the hardware-backed private key and sends the result back to that endpoint. This results in a fresh short-lived session cookie to be issued. The core of this works using a set of new headers like for example
Secure-Session-Registration. Clients that don't support DBSC would keep the long-lived session cookie as before.The fastify session middleware could implement the following:
The specification draft contains a few extras to maintain federated/shared DBSC state across multiple origins as well as specifying a well-known document. This could be added in a later revision if desired.
The specification can be found here: https://w3c.github.io/webappsec-dbsc/
Some further information and examples were published by Google: https://developer.chrome.com/docs/web-platform/device-bound-session-credentials
Motivation
Session cookies are a common target for infostealer malware. The amount of credential-stealing malware has risen to new highs in 2025 (see for example this report), especially with waves of supply chain attacks.
By binding sessions to hardware-backed key material ownership proofs can reduce the impact of compromised short-living session cookies.
I propose the integration into fastify session as a popular session handling system in order to raise adoption rates for secure session handling. This should make it easier for people to actually use DBSC.
Example
An example registration of the session middleware could look like this. The lifetime of the traditional session cookie is set to 6 hours, while DBSC-aware clients would refresh the session every 10 minutes.
This will result in a new header being returned for requests:
The endpoint
/dbsc/registeris intercepted by the middleware to receive a JWT with the public key of the client and issue a short-lived session cookie. It returns some information (specified in the standard) to the client like this:{ "session_identifier": "...", "refresh_url": "/dbsc/refresh", "scope": { "origin": "https://example.com", "include_site": true, "scope_specification": [] }, "credentials": [{ "type": "cookie", "name": "sessionId", "attributes": "Domain=example.com; Secure; SameSite=Lax" }] }The client can then refresh the session by performing a POST request to the
/dbsc/refreshendpoint including the session ID as a header:Sec-Secure-Session-Id: .... This endpoint is intercepted by the fastify session middleware as well and issues a challenge to the client using a header as well:The client signs the challenge using its private key and performs a second POST request to the
/dbsc/refreshendpoint including the session ID and the challenge result as a header:Secure-Session-Response: .... The middleware verifies this request and returns a new short-lived session cookie.