Api Key Exposure in Restify with Session Cookies
Api Key Exposure in Restify with Session Cookies — how this specific combination creates or exposes the vulnerability
Api key exposure occurs when an API key is unintentionally accessible to clients or intermediaries. In Restify, pairing session cookies with improper handling of keys can create scenarios where an API key is derivable from or exposed through the session mechanism.
Restify is an HTTP server framework for Node.js commonly used to build APIs. When session cookies are used to maintain authentication state, developers sometimes store or derive an API key from the session or use the session as a gateway to an endpoint that returns the key. If the session does not properly isolate access or the cookie is transmitted over insecure channels, an attacker who can read or predict the session identifier may be able to obtain the associated API key.
Consider a scenario where an endpoint like /api/config returns sensitive configuration including an API key, and access is controlled only by the presence of a session cookie. If session fixation or session hijacking is possible—due to missing secure flags, missing SameSite attributes, or transmission over non-HTTPS—an attacker can reuse a valid session and retrieve the API key. Additionally, if the session store maps session IDs to API keys in a way that is not properly guarded, an attacker who can enumerate or guess session IDs may directly map a session to its key.
Another vector involves logging or debugging endpoints that expose session contents. If a developer inadvertently exposes an endpoint such as /debug/session in production, and that session includes the API key either as a value or as a lookup key, the key is effectively exposed. This aligns with common weaknesses in access control (BOLA/IDOR) where one user can access another’s data through predictable identifiers.
Furthermore, if the API key is used to sign requests and the signing secret is stored server-side but retrievable via a session-privileged endpoint, an attacker who compromises the session can escalate privileges by obtaining the key and then making unauthorized calls on behalf of other users. This intersects with BFLA and privilege escalation when role checks are bypassed by presenting a valid session that should not grant access to key material.
Because middleBrick tests unauthenticated attack surfaces, it can detect endpoints that return API keys when only a session cookie is provided, flagging data exposure and missing proper authorization boundaries. Findings often map to OWASP API Top 10 A01:2023 broken object level authorization and A05:2023 security misconfiguration, and may also relate to PCI-DSS and SOC2 controls around secret management.
Session Cookies-Specific Remediation in Restify — concrete code fixes
To remediate exposure when using session cookies in Restify, ensure that sensitive material such as API keys is never returned to the client and is not derivable from the session. Enforce strict transport security, use HttpOnly and Secure cookies, and apply proper authorization checks before allowing any access to sensitive endpoints.
Secure Session Cookie Setup in Restify
Configure session cookies with security attributes to mitigate hijacking and fixation. Use cookie.signed to prevent tampering and set httpOnly, secure, and sameSite appropriately.
const restify = require('restify');
const cookieParser = require('restify-cookies');
const session = require('express-session');
const MemoryStore = require('memorystore')(session);
const server = restify.createServer();
server.use(cookieParser());
// Example session configuration with secure defaults
server.use(session({
store: new MemoryStore(),
secret: process.env.SESSION_SECRET,
resave: false,
saveUninitialized: false,
cookie: {
httpOnly: true,
secure: true, // only sent over HTTPS
sameSite: 'strict',
maxAge: 3600000
}
}));
server.get('/api/me', (req, res, next) => {
if (!req.session || !req.session.userId) {
return res.send(401, { error: 'unauthorized' });
}
// Do NOT include API key in response
res.send({ userId: req.session.userId });
return next();
});
server.listen(8080, () => {
console.log('Server running on port 8080');
};
Never Expose API Keys via Session-Accessible Endpoints
Ensure that endpoints which require authentication do not return API keys or secrets. If the API key must be used server-side for signing or proxying, keep it in environment variables or a secrets manager and never serialize it into the session object or response body.
// BAD: Exposing key via session-derived data
app.get('/api/key', (req, res, next) => {
if (!req.session || !req.session.apiKey) {
return res.send(401);
}
// This exposes the key to the client
res.send({ apiKey: req.session.apiKey });
});
// GOOD: Use session to reference access, not to store or return the key
app.get('/api/resource', (req, res, next) => {
if (!req.session || !req.session.userId) {
return res.send(401);
}
// Retrieve key from secure server-side store using session-bound userId
const apiKey = getApiKeyForUser(req.session.userId); // server-side only
// Use apiKey for internal operations, do not send to client
res.send({ data: 'protected resource' });
});
Authorization and Validation
Implement strict BOLA/IDOR checks so that one session cannot access another user’s data. Validate that the session’s subject matches the requested resource before proceeding. Combine with rate limiting and input validation to reduce abuse surfaces.