lib/response.js opens with fourteen require lines, most of them single-purpose header utilities. This page covers the ones that shape observable response behavior; each entry names the importing file and the member it backs.

cookie (^0.7.1) and cookie-signature (^1.2.1)

Imported by: lib/response.js.

res.cookie composes the two: cookie.serialize produces the Set-Cookie string (handling attributes like HttpOnly, SameSite, Path), and cookie-signature's HMAC sign protects value integrity when signed: true:

lib/response.js
var val = typeof value === 'object'
  ? 'j:' + JSON.stringify(value)
  : String(value);

if (signed) {
  val = 's:' + sign(val, secret);
}

if (opts.maxAge != null) {
  var maxAge = opts.maxAge - 0

  if (!isNaN(maxAge)) {
    opts.expires = new Date(Date.now() + maxAge)
    opts.maxAge = Math.floor(maxAge / 1000)
  }
}

The j: and s: prefixes are the wire markers that cookie-parser (a dev dependency here, used in examples/cookies) recognizes when reconstructing req.cookies and req.signedCookies. Signing requires a secret, and Express is strict about it: throw new Error('cookieParser("secret") required for signed cookies') when req.secret is missing. Note the split responsibility -- Express writes cookies unaided, but reading them requires the cookie-parser middleware; core never populates req.cookies.

etag (^1.8.1)

Imported by: lib/utils.js, which wraps it into the two generators behind the etag setting:

lib/utils.js
exports.etag = createETagGenerator({ weak: false })
// …
exports.wetag = createETagGenerator({ weak: true })

compileETag maps the setting ('weak' default, 'strong', false, or a custom function) to one of these, and res.send calls the compiled function on every body it sends. The package produces SHA-1-based entity tags -- deterministic, so the suite can assert exact values like W/"3e7-qPnkJ3CVdVhFJQvUBfF10TmVA7g" (test/res.send.js).

mime-types (^3.0.0)

Imported by: lib/response.js and lib/utils.js. Backs the extension-to-MIME conveniences: res.type('json') becomes application/json via mime.contentType, and res.set('Content-Type', 'text/html') gains ; charset=utf-8 automatically inside res.set:

lib/response.js
// add charset to content-type
if (field.toLowerCase() === 'content-type') {
  if (Array.isArray(value)) {
    throw new TypeError('Content-Type cannot be set to an Array');
  }
  value = mime.contentType(value)
}

lib/utils.js uses the same lookup in normalizeType, which is how res.format({ json: ... }) keys map to real MIME types. Unknown types fall back to application/octet-stream.

vary (^1.1.2)

Imported by: lib/response.js. Backs res.vary(field), which appends to the Vary header without duplicating entries. Express calls it on your behalf in one place -- res.format adds Vary: Accept, so negotiated responses are cache-correct by default.

escape-html (^1.0.3) and encodeurl (^2.0.0)

Imported by: lib/response.js. The redirect pair: res.location runs the target through encodeUrl (RFC-safe percent-encoding that leaves existing escapes alone), and res.redirect's HTML body escapes the target before interpolation:

lib/response.js
html: function(){
  var u = escapeHtml(address);
  body = '<!DOCTYPE html><head><title>' + statuses.message[status] + '</title></head>'
   + '<body><p>' + statuses.message[status] + '. Redirecting to ' + u + '</p></body>'
},

Small packages, but they are the line between a redirect and a reflected-XSS vector.

statuses (^2.0.1), http-errors (^2.0.0), content-disposition (^2.0.1), on-finished (^2.4.1)

Four more lib/response.js imports, one sentence each. statuses supplies reason phrases -- res.sendStatus(200) sends the body OK, and redirect bodies say Found. Redirecting to .... http-errors constructs the 406 that res.format forwards to next when nothing matches (examples use it for app-level 400/404s too, see examples/params). content-disposition builds attachment headers with correct RFC 5987 filename encoding for res.download/res.attachment -- examples/downloads deliberately links a non-ASCII filename to prove it. on-finished tells the sendfile helper when the response actually completed, closing the race between stream end and client abort.

Sources: lib/response.js, lib/utils.js · last synced 2026-07-27 · a371447 · version 5.2.1