/**
 * Structured-error introspection for `payments/billing:getCustomerPortalUrl`.
 *
 * Mirrors the edge-runtime `extractConvexErrorKind` helper in
 * `api/_convex-error.js`, scoped to the data shapes this Convex action
 * produces: `{ kind: 'NO_CUSTOMER' | 'DODO_API_KEY_MISSING' |
 * 'USER_ID_REQUIRED' | 'DODO_PORTAL_ERROR' }`.
 *
 * Zero deps so it can be unit-tested from `node --test` without pulling
 * the rest of `src/services/billing.ts`' browser-only import graph
 * (Sentry SDK, Convex client) into the test runner.
 */

/**
 * Extract the structured `kind` field from a thrown Convex object-data
 * ConvexError, falling back to a legacy substring match on the message
 * during the deploy-ordering window where the browser bundle and the
 * Convex action may briefly disagree on the throw shape.
 *
 * Returns null when neither path matches — letting the caller default
 * unknown shapes to error-level Sentry capture.
 */
export function extractBillingErrorKind(err: unknown): string | null {
  const data = (err as { data?: unknown } | null | undefined)?.data;
  if (data && typeof data === 'object' && 'kind' in data) {
    const kind = (data as Record<string, unknown>).kind;
    if (typeof kind === 'string') return kind;
  }
  // Legacy substring fallback for the deploy-ordering window where the
  // browser bundle ships ahead of the Convex action update (or vice-versa).
  // Pre-fix, the action threw `new Error('No Dodo customer found for this
  // user')`; if a stale Convex deployment is still serving that text we
  // can still classify the event correctly. Removable once both layers
  // have soaked on the structured-throw rollout.
  const msg = err instanceof Error ? err.message : '';
  if (/No Dodo customer found for this user/.test(msg)) return 'NO_CUSTOMER';
  return null;
}
