log("loading navigator.userAgentData.js");

const originalUserAgentData = navigator.userAgentData;

if (originalUserAgentData) {
  /**
   * Helper to replace HeadlessChrome with Google Chrome in brand lists
   * @param {Array<{brand: string, version: string}>} list - Array of UADataBrand objects
   */
  const filterBrandList = (list) =>
    list.map((b) => (b.brand === "HeadlessChrome" ? { brand: "Google Chrome", version: b.version } : b));

  // Get the NavigatorUAData prototype
  const NavigatorUADataProto = Object.getPrototypeOf(originalUserAgentData);

  // Cache original methods before patching
  const originalGetHighEntropyValues = NavigatorUADataProto.getHighEntropyValues;
  const originalToJSON = NavigatorUADataProto.toJSON;
  const originalBrandsDescriptor = Object.getOwnPropertyDescriptor(NavigatorUADataProto, "brands");

  let cachedFilteredBrands = null;
  // Helper to get filtered brands (cached for identity checks)
  const getFilteredBrands = () => {
    if (cachedFilteredBrands === null) {
      const originalBrands = originalBrandsDescriptor.get.call(originalUserAgentData);
      cachedFilteredBrands = filterBrandList(originalBrands);
    }
    return cachedFilteredBrands;
  };

  // Patch getHighEntropyValues to filter HeadlessChrome from results
  utils.replaceProperty(NavigatorUADataProto, "getHighEntropyValues", {
    value: function (hints) {
      return originalGetHighEntropyValues.call(this, hints).then((data) => {
        const newData = { ...data };
        if (newData.brands) {
          newData.brands = filterBrandList(newData.brands);
        }
        if (newData.fullVersionList) {
          newData.fullVersionList = filterBrandList(newData.fullVersionList);
        }
        return newData;
      });
    },
  });

  // Patch toJSON to filter HeadlessChrome
  utils.replaceProperty(NavigatorUADataProto, "toJSON", {
    value: function () {
      const data = originalToJSON.call(this);
      return {
        brands: filterBrandList(data.brands),
        mobile: data.mobile,
        platform: data.platform,
      };
    },
  });

  // Patch brands getter to return filtered array (same instance each call, like real Chrome)
  utils.replaceProperty(NavigatorUADataProto, "brands", {
    get: function () {
      // Return cached filtered brands, computing and freezing on first access
      return getFilteredBrands();
    },
    enumerable: originalBrandsDescriptor.enumerable,
    configurable: originalBrandsDescriptor.configurable,
  });

  utils.replaceProperty(NavigatorUADataProto, "userAgentData", {
    get: () => originalUserAgentData,
  });
}