-
Notifications
You must be signed in to change notification settings - Fork 1
/
Copy pathindex.js
86 lines (70 loc) · 2.98 KB
/
index.js
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
const R = require('ramda');
const ignoreMethods = ['post', 'put', 'patch', 'delete'];
const cacheHeaders = ['expires', 'cache-control'];
const cacheHeadersAlreadySet = (response) =>
R.pipe(R.propOr([], 'headers'), R.pick(cacheHeaders), R.filter(Boolean), R.keys)(response).length > 0;
const generateCacheHeaders = (routeSettings, currentHeaders = {}) => {
const generatedHeaders = currentHeaders;
if (routeSettings !== false) {
// First check if we have client and varnish max age defined in the route config
// If we don't have, see if we have standard maxAge options, if not fallback to server defaults
const cacheControl = {
maxAge: R.prop('clientTime', routeSettings),
sMaxAge: R.prop('serverTime', routeSettings),
directive: R.propOr('', 'directive', routeSettings),
};
if (R.isNil(cacheControl.maxAge)) {
return generatedHeaders;
}
// max-age is how long the client will cache the response
// s-maxage is how long varnish will cache the response
if (!currentHeaders['cache-control']) {
generatedHeaders['cache-control'] = `max-age=${cacheControl.maxAge},s-maxage=${cacheControl.sMaxAge}${
cacheControl.directive ? `,${cacheControl.directive}` : ''
}`;
}
if (!currentHeaders['surrogate-control']) {
generatedHeaders['surrogate-control'] = `max-age=${cacheControl.sMaxAge}`;
}
} else {
generatedHeaders['cache-control'] = 'no-cache, no-store';
}
return generatedHeaders;
};
const shouldAddCachingHeaders = (handler) => {
if (
(handler.event.version === '1.0' &&
ignoreMethods.includes(R.pathOr('', ['event', 'httpMethod'], handler).toLowerCase())) ||
(handler.event.version === '2.0' &&
ignoreMethods.includes(R.pathOr('', ['event', 'requestContext', 'http', 'method'], handler).toLowerCase()))
) {
return false;
}
// Don't touch headers if something else has already set them
if (cacheHeadersAlreadySet(handler.response)) {
return false;
}
return true;
};
const cachingMiddleware = ({ success = {}, errors = {} } = {}) => ({
after: async (handler) => {
if (!shouldAddCachingHeaders(handler)) {
return;
}
// eslint-disable-next-line no-param-reassign
handler.response.headers = generateCacheHeaders(success, handler.response.headers);
},
onError: async (handler) => {
if (!shouldAddCachingHeaders(handler)) {
return;
}
const errorCacheConfiguration = R.propOr(R.prop('default', errors), handler.error.statusCode, errors);
// eslint-disable-next-line no-param-reassign
handler.response = R.assocPath(
['headers'],
generateCacheHeaders(errorCacheConfiguration, R.path(['response', 'headers'], handler)),
handler.response
);
},
});
module.exports = cachingMiddleware;