MCPcopy Create free account
hub / github.com/nodejs/undici / canCacheResponse

Function canCacheResponse

lib/handler/cache-handler.js:492–552  ·  view source on GitHub ↗

* @see https://www.rfc-editor.org/rfc/rfc9111.html#name-storing-responses-to-authen * * @param {import('../../types/cache-interceptor.d.ts').default.CacheOptions['type']} cacheType * @param {number} statusCode * @param {import('../../types/header.d.ts').IncomingHttpHeaders} resHeaders * @param

(cacheType, statusCode, resHeaders, cacheControlDirectives, reqHeaders)

Source from the content-addressed store, hash-verified

490 * @param {import('../../types/header.d.ts').IncomingHttpHeaders} [reqHeaders]
491 */
492function canCacheResponse (cacheType, statusCode, resHeaders, cacheControlDirectives, reqHeaders) {
493 // Status code must be final and understood.
494 if (statusCode < 200 || arrayIncludes(NOT_UNDERSTOOD_STATUS_CODES, statusCode)) {
495 return false
496 }
497 // Responses with neither status codes that are heuristically cacheable, nor "explicit enough" caching
498 // directives, are not cacheable. "Explicit enough": see https://www.rfc-editor.org/rfc/rfc9111.html#section-3
499 if (!arrayIncludes(HEURISTICALLY_CACHEABLE_STATUS_CODES, statusCode) && !resHeaders['expires'] &&
500 !cacheControlDirectives.public &&
501 cacheControlDirectives['max-age'] === undefined &&
502 // RFC 9111: a private response directive, if the cache is not shared
503 !(cacheControlDirectives.private && cacheType === 'private') &&
504 !(cacheControlDirectives['s-maxage'] !== undefined && cacheType === 'shared')
505 ) {
506 return false
507 }
508
509 if (cacheControlDirectives['no-store']) {
510 return false
511 }
512
513 if (cacheType === 'shared' && cacheControlDirectives.private === true) {
514 return false
515 }
516
517 // https://www.rfc-editor.org/rfc/rfc9111.html#section-4.1-5
518 if (resHeaders.vary && hasVaryStar(resHeaders.vary)) {
519 return false
520 }
521
522 // https://www.rfc-editor.org/rfc/rfc9111.html#name-storing-responses-to-authen
523 if (reqHeaders != null && Object.hasOwn(reqHeaders, 'authorization')) {
524 if (
525 !cacheControlDirectives.public &&
526 !cacheControlDirectives['s-maxage'] &&
527 !cacheControlDirectives['must-revalidate']
528 ) {
529 return false
530 }
531
532 if (typeof reqHeaders.authorization !== 'string') {
533 return false
534 }
535
536 if (
537 Array.isArray(cacheControlDirectives['no-cache']) &&
538 arrayIncludes(cacheControlDirectives['no-cache'], 'authorization')
539 ) {
540 return false
541 }
542
543 if (
544 Array.isArray(cacheControlDirectives['private']) &&
545 arrayIncludes(cacheControlDirectives['private'], 'authorization')
546 ) {
547 return false
548 }
549 }

Callers 1

onResponseStartMethod · 0.85

Calls 2

hasVaryStarFunction · 0.85
arrayIncludesFunction · 0.70

Tested by

no test coverage detected