2021-12-27 09:05:53 -03:00

55 lines
1.5 KiB
TypeScript

import { parse } from 'cache-parser';
import { Header } from '../util/headers';
import type { HeaderInterpreter, HeadersInterpreter } from './types';
export const defaultHeaderInterpreter: HeadersInterpreter = (headers = {}) => {
if (Header.CacheControl in headers) {
// eslint-disable-next-line @typescript-eslint/no-non-null-assertion
return interpretCacheControl(headers[Header.CacheControl]!, headers);
}
if (Header.Expires in headers) {
// eslint-disable-next-line @typescript-eslint/no-non-null-assertion
return interpretExpires(headers[Header.Expires]!, headers);
}
return undefined;
};
const interpretExpires: HeaderInterpreter = (expires) => {
const milliseconds = Date.parse(expires) - Date.now();
return milliseconds >= 0 ? milliseconds : false;
};
const interpretCacheControl: HeaderInterpreter = (cacheControl, headers) => {
const { noCache, noStore, mustRevalidate, maxAge, immutable } = parse(cacheControl);
// Header told that this response should not be cached.
if (noCache || noStore) {
return false;
}
if (immutable) {
// 1 year is sufficient, as Infinity may cause more problems.
// It might not be the best way, but a year is better than none.
return 1000 * 60 * 60 * 24 * 365;
}
// Already out of date, for cache can be saved, but must be requested again
if (mustRevalidate) {
return 0;
}
if (maxAge) {
const age = headers[Header.Age];
if (!age) {
return maxAge * 1000;
}
return (maxAge - Number(age)) * 1000;
}
return undefined;
};