/** Player-facing deposit audit log remark formatting — strips internal order codes & API templates. */

const ORDER_NO_SUFFIX = /\s+[A-Z0-9]{10,}\s*$/i;

const INTERNAL_REMARK_EXACT = [
  /^Revoke approved deposit\s*[A-Z0-9]*\s*$/i,
  /^撤销已通过充值\s*[A-Z0-9]*\s*$/,
  /^Deposit order\s+[A-Z0-9]+\s*$/i,
];

export type DepositAuditLogLike = {
  action: string;
  remark: string | null;
};

export type DepositAuditRemarkDisplay =
  | { kind: 'reject'; text: string }
  | { kind: 'note'; text: string }
  | null;

function normalizeRemark(value: string | null | undefined) {
  return value?.trim() ?? '';
}

/** True when remark is empty or only internal/system text — hide from player UI. */
export function isHiddenDepositAuditRemark(log: DepositAuditLogLike): boolean {
  const remark = normalizeRemark(log.remark);
  if (!remark) return true;

  if (log.action === 'REVOKED') {
    return INTERNAL_REMARK_EXACT.some((pattern) => pattern.test(remark));
  }

  return INTERNAL_REMARK_EXACT.some((pattern) => pattern.test(remark));
}

function sanitizePlayerRemark(raw: string): string | null {
  let text = raw.trim();
  if (!text) return null;

  if (/^Revoke approved deposit/i.test(text)) {
    return null;
  }
  if (/^撤销已通过充值/.test(text)) {
    return null;
  }
  if (/^Deposit order\s+/i.test(text)) {
    return null;
  }

  text = text.replace(ORDER_NO_SUFFIX, '').trim();
  return text || null;
}

/** Format remark for timeline; returns null when nothing meaningful to show. */
export function formatDepositAuditRemark(
  log: DepositAuditLogLike,
  t: (key: string, params?: Record<string, unknown>) => string,
): DepositAuditRemarkDisplay {
  const remark = normalizeRemark(log.remark);
  if (!remark) return null;

  if (log.action === 'REVOKED' && isHiddenDepositAuditRemark(log)) {
    return { kind: 'note', text: t('wallet.remark_deposit_revoke_generic') };
  }

  const sanitized = sanitizePlayerRemark(remark);
  if (!sanitized) return null;

  if (log.action === 'REJECTED') {
    return { kind: 'reject', text: sanitized };
  }

  return { kind: 'note', text: sanitized };
}

/** Skip reject remark in timeline when card-level reject reason already shows the same text. */
export function shouldShowAuditRejectInTimeline(
  log: DepositAuditLogLike,
  orderRejectReason: string | null | undefined,
): boolean {
  if (log.action !== 'REJECTED') return true;
  const remark = normalizeRemark(log.remark);
  if (!remark) return false;
  const cardReason = normalizeRemark(orderRejectReason);
  return remark !== cardReason;
}

export function auditActionTone(action: string): 'submitted' | 'approved' | 'rejected' | 'revoked' | 'reopened' | 'default' {
  switch (action.toUpperCase()) {
    case 'SUBMITTED':
      return 'submitted';
    case 'APPROVED':
      return 'approved';
    case 'REJECTED':
      return 'rejected';
    case 'REVOKED':
      return 'revoked';
    case 'REOPENED':
      return 'reopened';
    default:
      return 'default';
  }
}

/** Secondary actor line — only when it adds meaning beyond the action title. */
export function auditActorSecondary(log: { action: string; actorType: string }, t: (key: string) => string): string | null {
  if (log.actorType === 'PLAYER' && (log.action === 'SUBMITTED' || log.action === 'REOPENED')) {
    return t('recharge.audit_by_player');
  }
  return null;
}
