All files / src/handlers handleIngressAPI.ts

100% Statements 34/34
83.33% Branches 5/6
100% Functions 8/8
100% Lines 31/31

Press n or j to go to the next uncovered block, b, p or k for the previous block.

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                      40x               40x 40x 40x 40x 40x   40x               30x   30x 30x 30x 30x 30x 30x 30x 30x         30x               10x   10x 10x 10x   10x 10x   10x       40x 10x 10x   2x       30x 30x   3x      
import { getIngressBaseHost, WorkerEnv } from '../env'
import {
  addProxyIntegrationHeaders,
  addTrafficMonitoringSearchParamsForVisitorIdRequest,
  createErrorResponseForIngress,
  filterCookies,
  getVisitorIdEndpoint,
  createFallbackErrorResponse,
} from '../utils'
 
function copySearchParams(oldURL: URL, newURL: URL): void {
  newURL.search = new URLSearchParams(oldURL.search).toString()
}
 
function createRequestURL(
  ingressBaseUrl: string,
  receivedRequestURL: string,
  routeMatches: RegExpMatchArray | undefined
) {
  const routeSuffix = routeMatches ? routeMatches[1] : undefined
  const oldURL = new URL(receivedRequestURL)
  const endpoint = getVisitorIdEndpoint(ingressBaseUrl, oldURL.searchParams, routeSuffix)
  const newURL = new URL(endpoint)
  copySearchParams(oldURL, newURL)
 
  return newURL
}
 
async function makeIngressRequest(
  receivedRequest: Request,
  env: WorkerEnv,
  routeMatches: RegExpMatchArray | undefined
) {
  const ingressBaseUrl = getIngressBaseHost(env)!
 
  const requestURL = createRequestURL(ingressBaseUrl, receivedRequest.url, routeMatches)
  addTrafficMonitoringSearchParamsForVisitorIdRequest(requestURL)
  let headers = new Headers(receivedRequest.headers)
  headers = filterCookies(headers, (key) => key === '_iidt')
  addProxyIntegrationHeaders(headers, receivedRequest.url, env)
  const body = await (receivedRequest.headers.get('Content-Type') ? receivedRequest.blob() : Promise.resolve(null))
  console.log(`sending ingress request to ${requestURL}...`)
  const request = new Request<unknown, CfProperties<unknown>>(
    requestURL,
    new Request(receivedRequest, { headers, body })
  )
 
  return fetch(request).then((oldResponse) => new Response(oldResponse.body, oldResponse))
}
 
function makeCacheEndpointRequest(
  receivedRequest: Request,
  env: WorkerEnv,
  routeMatches: RegExpMatchArray | undefined
) {
  const ingressBaseUrl = getIngressBaseHost(env)!
 
  const requestURL = createRequestURL(ingressBaseUrl, receivedRequest.url, routeMatches)
  const headers = new Headers(receivedRequest.headers)
  headers.delete('Cookie')
 
  console.log(`sending cache request to ${requestURL}...`)
  const request = new Request<unknown, CfProperties<unknown>>(requestURL, new Request(receivedRequest, { headers }))
 
  return fetch(request).then((oldResponse) => new Response(oldResponse.body, oldResponse))
}
 
export async function handleIngressAPI(request: Request, env: WorkerEnv, routeMatches: RegExpMatchArray | undefined) {
  if (request.method === 'GET') {
    try {
      return await makeCacheEndpointRequest(request, env, routeMatches)
    } catch (e) {
      return createFallbackErrorResponse(e)
    }
  }
 
  try {
    return await makeIngressRequest(request, env, routeMatches)
  } catch (e) {
    return createErrorResponseForIngress(request, e)
  }
}