import { Capability, MatrixCapabilities } from 'matrix-widget-api';

// Conservative v1 capability policy: approve only benign display capabilities.
// Everything else (room-event send/receive, to-device, uploads, user-directory,
// delayed events, TURN servers) is denied — a random widget must not be able to
// act as the user or read room data without an explicit consent flow (follow-up).
export const ALLOWED_WIDGET_CAPABILITIES: ReadonlySet<Capability> = new Set<Capability>([
  MatrixCapabilities.AlwaysOnScreen,
  MatrixCapabilities.RequiresClient,
  MatrixCapabilities.Screenshots,
]);

export const filterWidgetCapabilities = (requested: Set<Capability>): Set<Capability> =>
  new Set([...requested].filter((cap) => ALLOWED_WIDGET_CAPABILITIES.has(cap)));

export type WidgetUrlError = 'empty' | 'invalid' | 'not-https' | 'same-origin';

// A widget URL to ADD must be https and NOT our own origin: a same-origin frame
// with allow-same-origin + allow-scripts can break out of the sandbox against us.
export const validateWidgetUrl = (raw: string, appOrigin: string): WidgetUrlError | undefined => {
  const trimmed = raw.trim();
  if (!trimmed) return 'empty';
  let url: URL;
  try {
    url = new URL(trimmed);
  } catch {
    return 'invalid';
  }
  if (url.protocol !== 'https:') return 'not-https';
  if (url.origin === appOrigin) return 'same-origin';
  return undefined;
};

// Is an already-resolved (complete) widget URL safe to render in a sandboxed
// iframe that carries allow-same-origin? Rejects same-origin URLs (breakout).
export const isWidgetUrlSafe = (completeUrl: string, appOrigin: string): boolean => {
  try {
    return new URL(completeUrl).origin !== appOrigin;
  } catch {
    return false;
  }
};

export const generateWidgetId = (): string =>
  `lotus_${Date.now()}_${Math.random().toString(36).slice(2, 10)}`;
