const EMPTY_FAVICON = 'data:,';
const INVALID_BRAND_PATHS = new Set(['null', 'undefined']);
const ABSOLUTE_URL_RE = /^(?:[a-z][a-z\d+.-]*:)?\/\//i;

let faviconRequestId = 0;

function normalizeBrandPath(value?: null | string) {
  const path = value?.trim();
  return path && !INVALID_BRAND_PATHS.has(path.toLowerCase()) ? path : '';
}

function resolveBrandAssetUrl(value?: null | string, apiUrl = '') {
  const path = normalizeBrandPath(value);
  if (!path || ABSOLUTE_URL_RE.test(path) || path.startsWith('blob:') || path.startsWith('data:')) return path;

  return `${apiUrl.replace(/\/$/, '')}/${path.replace(/^\//, '')}`;
}

function getFaviconLink() {
  let link = document.querySelector<HTMLLinkElement>('link[rel="icon"]');
  if (link) return link;

  link = document.createElement('link');
  link.rel = 'icon';
  document.head.append(link);
  return link;
}

function preloadImage(url: string) {
  return new Promise<void>((resolve, reject) => {
    const image = new Image();
    image.addEventListener('load', () => resolve(), { once: true });
    image.addEventListener('error', () => reject(new Error(`Failed to load brand image: ${url}`)), { once: true });
    image.src = url;
  });
}

async function applyFavicon(configuredUrl?: null | string) {
  const requestId = ++faviconRequestId;
  const link = getFaviconLink();
  const url = normalizeBrandPath(configuredUrl);

  if (!url) {
    link.href = EMPTY_FAVICON;
    return;
  }

  try {
    await preloadImage(url);
    if (requestId === faviconRequestId) link.href = url;
  } catch {
    if (requestId === faviconRequestId) link.href = EMPTY_FAVICON;
  }
}

export { applyFavicon, EMPTY_FAVICON, normalizeBrandPath, resolveBrandAssetUrl };
