I want you to make this BypassCORS proxy script into a fully working CHROME EXTENTION which can communicate with my web app easily and can act as a proxy server for all of the requests and responses for my web app.

This given js script is works as a proxy to bypass CORS related Restrictions for the client.

Use external messaging method to enable the extension and the website to communicate with eachother easily for any request and response cycle.

The chrome extention should listen passively for the request.

Don't compromise anything.

Send the fully working full codes.

// Configuration
const CONFIG = {
  ALLOWED_ORIGINS: new Set(['*']),
  ALLOWED_TARGET_DOMAINS: new Set(['*']),
  ALLOW_ALL_TARGETS: true,
  BLOCKED_TARGET_HOSTS: new Set(['blocked.example.com']),
  FORWARDED_HEADERS: new Set(['accept', 'accept-language', 'content-type', 'cache-control', 'pragma', 'expires', 'last-modified', 'if-modified-since', 'if-none-match', 'connection', 'keep-alive', 'upgrade-insecure-requests']),
  REMOVED_HEADERS: new Set(['cf-connecting-ip', 'x-forwarded-for', 'x-real-ip', 'forwarded', 'via', 'client-ip', 'true-client-ip', 'proxy-connection', 'proxy-authorization', 'proxy-authenticate', 'x-proxy-id', 'x-proxy-location', 'x-proxy-type', 'x-squid-error', 'x-request-id', 'x-correlation-id', 'te', 'trailers', 'transfer-encoding', 'upgrade', 'cookie', 'authorization', 'set-cookie', 'server']),
  SECURITY_HEADERS: {
    'X-Content-Type-Options': 'nosniff',
    'Referrer-Policy': 'no-referrer',
    'Strict-Transport-Security': 'max-age=63072000; includeSubDomains; preload',
    'X-Frame-Options': 'DENY',
    'Content-Security-Policy': "default-src 'none'; frame-ancestors 'none'; base-uri 'none';"
  },
  CUSTOM_ERROR_RESPONSES: {
    400: { error: 'Bad Request' },
    403: { error: 'Forbidden' },
    404: { error: 'Not Found' },
    413: { error: 'Payload Too Large' },
    500: { error: 'Internal Server Error' },
    502: { error: 'Bad Gateway' },
    504: { error: 'Gateway Timeout' },
    508: { error: 'Too Many Redirects' }
  },
  MAX_REQUEST_BODY_SIZE: 5000000,
  TIMEOUT: 29000,
  MAX_REDIRECTS: 5,
  TARGET_URL_HEADER: 'x-target-url',
  TARGET_URL_QUERY_PARAM: 'target'
};

class ProxyError extends Error {
  constructor(message, status) {
    super(message);
    this.name = 'ProxyError';
    this.status = status;
  }
}

export default {
  async fetch(request, env, ctx) {
    try {
      if (request.method === 'OPTIONS') {
        return handlePreflight(request);
      }

      const origin = request.headers.get('Origin');
      if (origin && !isAllowedOrigin(origin)) {
        throw new ProxyError('Forbidden: Origin not allowed', 403);
      }

      return await forwardRequest(request, ctx, 0);
    } catch (error) {
      return handleError(error, request);
    }
  }
};

function isAllowedOrigin(origin) {
  return CONFIG.ALLOWED_ORIGINS.has(origin.toLowerCase()) || CONFIG.ALLOWED_ORIGINS.has('*');
}

function generateCorsHeaders(request, isPreflight = false) {
  const headers = new Headers();
  const origin = request.headers.get('Origin');
  if (origin && isAllowedOrigin(origin)) {
    headers.set('Access-Control-Allow-Origin', origin);
    headers.set('Access-Control-Allow-Credentials', 'true');
    if (isPreflight) {
      const requestedMethod = request.headers.get('Access-Control-Request-Method') || 'GET, POST, PUT, DELETE, OPTIONS, HEAD, PATCH';
      const requestedHeaders = request.headers.get('Access-Control-Request-Headers') || 'Content-Type';
      headers.set('Access-Control-Allow-Methods', requestedMethod);
      headers.set('Access-Control-Allow-Headers', requestedHeaders);
      headers.set('Access-Control-Max-Age', '86400');
    }
    headers.set('Access-Control-Expose-Headers', '*');
    headers.append('Vary', 'Origin');
    if (isPreflight) {
      headers.append('Vary', 'Access-Control-Request-Headers');
      headers.append('Vary', 'Access-Control-Request-Method');
    }
  }
  return headers;
}

function handlePreflight(request) {
  const headers = generateCorsHeaders(request, true);
  return new Response(null, { status: 204, headers });
}

function filterAndForwardHeaders(headers) {
  const result = new Headers();
  for (const [key, value] of headers.entries()) {
    const lowerKey = key.toLowerCase();
    if (CONFIG.FORWARDED_HEADERS.has(lowerKey) && !CONFIG.REMOVED_HEADERS.has(lowerKey)) {
      result.set(key, value);
    }
  }
  return result;
}

function validateTargetUrl(url) {
  let parsedUrl;
  try {
    parsedUrl = new URL(url);
  } catch {
    throw new ProxyError('Bad Request: Invalid target URL', 400);
  }

  const protocol = parsedUrl.protocol.toLowerCase();
  if (!['http:', 'https:'].includes(protocol)) {
    throw new ProxyError('Forbidden: Unsupported protocol', 403);
  }

  const hostname = parsedUrl.hostname.toLowerCase();
  if (CONFIG.BLOCKED_TARGET_HOSTS.has(hostname)) {
    throw new ProxyError('Forbidden: Target host is blocked', 403);
  }

  if (!CONFIG.ALLOW_ALL_TARGETS && !CONFIG.ALLOWED_TARGET_DOMAINS.has(hostname)) {
    throw new ProxyError('Forbidden: Target domain not allowed', 403);
  }

  return parsedUrl;
}

function getTargetUrl(request) {
  const headerTarget = request.headers.get(CONFIG.TARGET_URL_HEADER);
  if (headerTarget) {
    return headerTarget;
  }

  const url = new URL(request.url);
  return url.searchParams.get(CONFIG.TARGET_URL_QUERY_PARAM);
}

function modifyAndReturnResponse(response, request) {
  const corsHeaders = generateCorsHeaders(request);
  const newHeaders = new Headers(response.headers);

  CONFIG.REMOVED_HEADERS.forEach(header => {
    newHeaders.delete(header);
  });

  if (request.headers.get('Origin')) {
    for (const [key, value] of corsHeaders.entries()) {
      newHeaders.set(key, value);
    }
  }

  for (const [key, value] of Object.entries(CONFIG.SECURITY_HEADERS)) {
    newHeaders.set(key, value);
  }

  newHeaders.set('Cache-Control', 'no-store');

  return new Response(response.body, {
    status: response.status,
    statusText: response.statusText,
    headers: newHeaders
  });
}

function handleError(error, request) {
  const status = error instanceof ProxyError ? error.status : 500;
  const errorMessage = CONFIG.CUSTOM_ERROR_RESPONSES[status] ? CONFIG.CUSTOM_ERROR_RESPONSES[status].error : 'An unexpected error occurred';
  const corsHeaders = generateCorsHeaders(request);
  const headers = new Headers({
    'Content-Type': 'application/json',
    ...CONFIG.SECURITY_HEADERS
  });

  if (request.headers.get('Origin')) {
    for (const [key, value] of corsHeaders.entries()) {
      headers.set(key, value);
    }
  }

  const body = JSON.stringify({ error: errorMessage });
  return new Response(body, { status, headers });
}

async function forwardRequest(request, ctx, redirectCount) {
  if (redirectCount > CONFIG.MAX_REDIRECTS) {
    throw new ProxyError('Too Many Redirects', 508);
  }

  const targetUrl = getTargetUrl(request);
  if (!targetUrl) {
    throw new ProxyError('Bad Request: Missing target URL', 400);
  }

  const parsedTarget = validateTargetUrl(targetUrl);
  const proxiedHeaders = filterAndForwardHeaders(request.headers);
  proxiedHeaders.set('Host', parsedTarget.host);

  const fetchOptions = {
    method: request.method,
    headers: proxiedHeaders,
    redirect: 'manual',
    cf: { requestTimeout: CONFIG.TIMEOUT }
  };

  if (!['GET', 'HEAD'].includes(request.method)) {
    const contentLength = parseInt(request.headers.get('Content-Length') || '0', 10);
    if (isNaN(contentLength) || contentLength > CONFIG.MAX_REQUEST_BODY_SIZE) {
      throw new ProxyError('Payload Too Large', 413);
    }
    fetchOptions.body = request.body;
  }

  let response;
  try {
    response = await fetch(parsedTarget.toString(), fetchOptions);
  } catch (err) {
    if (err instanceof TypeError && err.message.includes('network')) {
      throw new ProxyError('Bad Gateway: Network Error', 502);
    }
    if (err.name === 'AbortError') {
      throw new ProxyError('Gateway Timeout', 504);
    }
    throw new ProxyError('Bad Gateway: Unknown Error', 502);
  }

  if (response.status >= 300 && response.status < 400 && response.headers.has('Location')) {
    const location = response.headers.get('Location');
    if (location) {
      let redirectUrl;
      try {
        redirectUrl = new URL(location, parsedTarget);
      } catch {
        throw new ProxyError('Bad Gateway: Invalid redirect URL', 502);
      }
      if (!isAllowedOrigin(redirectUrl.hostname)) {
        throw new ProxyError('Forbidden: Redirected domain not allowed', 403);
      }
      const newRequest = new Request(redirectUrl.toString(), request);
      return await forwardRequest(newRequest, ctx, redirectCount + 1);
    }
  }

  return modifyAndReturnResponse(response, request);
}