UNPKG

liefern

Version:

Node Webserver without dependencies

107 lines 4.39 kB
import { HeaderFields } from './utils/constants.js'; import { forbidden, methodNotAllow, ok } from './utils/sendHelper.js'; export const cors = (config) => { return ({ response, request }) => { handlePreFlight(config, request, response); if (response.writableEnded) { return; } if (config.origin && config.origin !== '*' && (!request.headers.host || !config.origin.includes(request.headers.host))) { return forbidden(response); } if (config.allowMethods !== '*' && !config.allowMethods .map((method) => method.toLowerCase()) // eslint-disable-next-line @typescript-eslint/no-non-null-assertion .includes(request.method.toLowerCase())) { return methodNotAllow(response); } // handle "credentials" if (config.credentials) { response.setHeader(HeaderFields.AccessControlAllowCredentials, 'true'); } // handle "credentials" if (config.secureContext) { response.setHeader(HeaderFields.CrossOriginOpenerPolicy, 'same-origin'); response.setHeader(HeaderFields.CrossOriginEmbedderPolicy, 'require-corp'); } }; }; const handlePreFlight = (config, request, response) => { // console.log('request headers', request.headers) // console.log('config', config) const requestMethod = request.method?.toLowerCase(); const requestHeaderOrigin = request.headers.origin; const requestHeaderRequestMethod = request.headers['access-control-request-method']?.toLowerCase(); const requestHeaderRequestHeaders = request.headers['access-control-request-headers']?.toLowerCase(); const isPreFlight = requestMethod === 'options' && !!requestHeaderOrigin && !!requestHeaderRequestMethod; // && !!requestHeaderRequestHeaders if (!isPreFlight) { return; } // console.log(config.origin, request.headers) if (!config.origin || config.origin === '*' || config.origin.includes(requestHeaderOrigin)) { response.setHeader(HeaderFields.AccessControlAllowOrigin, requestHeaderOrigin); } else { return forbidden(response); } // if (!config.allowMethods) { response.setHeader(HeaderFields.AccessControlAllowMethods, '*'); } else if (config.allowMethods === '*') { response.setHeader(HeaderFields.AccessControlAllowMethods, '*'); } else { const lowerCaseList = config.allowMethods.map((method) => method.toLowerCase()); if (lowerCaseList.includes(requestHeaderRequestMethod)) { response.setHeader(HeaderFields.AccessControlAllowMethods, config.allowMethods.join(', ')); } else { return forbidden(response); } } if (requestHeaderRequestHeaders) { if (!config.allowHeaders) { response.setHeader(HeaderFields.AccessControlAllowHeaders, '*'); } else if (config.allowHeaders === '*') { response.setHeader(HeaderFields.AccessControlAllowHeaders, '*'); } else { response.setHeader(HeaderFields.AccessControlAllowHeaders, config.allowHeaders.join(', ')); } } // handle "exposeHeaders" if (config.exposeHeaders) { response.setHeader(HeaderFields.AccessControlExposeHeaders, config.exposeHeaders.join(', ')); } // handle "allowHeaders" if (request.headers[HeaderFields.AccessControlRequestHeaders.toLowerCase()] || config.allowHeaders) { response.setHeader(HeaderFields.AccessControlAllowHeaders, !config.allowHeaders || config.allowHeaders === '*' ? '*' : config.allowHeaders.join(', ')); } // handle "maxAge" if (config.maxAge) { response.setHeader(HeaderFields.AccessControlMaxAge, config.maxAge); } // handle "credentials" if (config.credentials) { response.setHeader(HeaderFields.AccessControlAllowCredentials, 'true'); } // handle "privateNetworkAccess" if (config.privateNetworkAccess && request.headers[HeaderFields.AccessControlRequestPrivateNetwork.toLowerCase()]) { response.setHeader(HeaderFields.AccessControlAllowPrivateNetwork, 'true'); } return ok(response); }; //# sourceMappingURL=handleCORS.js.map