import React, { useState, useMemo, useTransition, useEffect } from 'react';

const useDebounce = <T,>(value: T, delay: number): T => {
  const [debouncedValue, setDebouncedValue] = useState(value);
  useEffect(() => {
    const handler = setTimeout(() => setDebouncedValue(value), delay);
    return () => clearTimeout(handler);
  }, [value, delay]);
  return debouncedValue;
};

const useToast = () => {
  const [toasts, setToasts] = useState<Array<{ id: number; message: string; type: string }>>([]);
  const show = (message: string, type = 'info') => {
    const id = Date.now();
    setToasts((prev) => [...prev, { id, message, type }]);
    setTimeout(() => setToasts((prev) => prev.filter((t) => t.id !== id)), 3000);
  };
  return { toasts, show };
};

const mockTransactions = [
  { id: 'txn_1', type: 'charge', amount: 5000, currency: 'usd', description: 'Payment from customer', created: Date.now() - 3600000 },
  { id: 'txn_2', type: 'refund', amount: -1200, currency: 'usd', description: 'Refund to customer', created: Date.now() - 7200000 },
  { id: 'txn_3', type: 'payout', amount: -25000, currency: 'usd', description: 'Payout to bank', created: Date.now() - 86400000 },
  { id: 'txn_4', type: 'charge', amount: 8900, currency: 'usd', description: 'Subscription payment', created: Date.now() - 14400000 },
  { id: 'txn_5', type: 'fee', amount: -150, currency: 'usd', description: 'Stripe fee', created: Date.now() - 18000000 },
];

const App = () => {
  const [searchQuery, setSearchQuery] = useState('');
  const [typeFilter, setTypeFilter] = useState('all');
  const [isPending, startTransition] = useTransition();
  const { toasts, show } = useToast();

  const debouncedSearch = useDebounce(searchQuery, 300);

  const filteredTransactions = useMemo(() => {
    return mockTransactions.filter((txn) => {
      const matchesSearch = txn.id.toLowerCase().includes(debouncedSearch.toLowerCase()) ||
        txn.description.toLowerCase().includes(debouncedSearch.toLowerCase());
      const matchesType = typeFilter === 'all' || txn.type === typeFilter;
      return matchesSearch && matchesType;
    });
  }, [debouncedSearch, typeFilter]);

  const balance = useMemo(() => {
    const available = 45000;
    const pending = 12500;
    const total = available + pending;
    return { available, pending, total };
  }, []);

  const handleFilterChange = (type: string) => {
    startTransition(() => {
      setTypeFilter(type);
      show(`Filtered by: ${type}`, 'info');
    });
  };

  const formatAmount = (amount: number, currency: string) => {
    return new Intl.NumberFormat('en-US', { style: 'currency', currency }).format(amount / 100);
  };

  const formatDate = (timestamp: number) => {
    return new Date(timestamp).toLocaleString();
  };

  return (
    <div className="app-container">
      <header className="app-header">
        <h1>Balance Overview</h1>
        <p className="subtitle">Current balance, pending funds, and transaction history</p>
      </header>

      <div className="stats-grid">
        <div className="stat-card">
          <div className="stat-label">Total Balance</div>
          <div className="stat-value">{formatAmount(balance.total, 'usd')}</div>
        </div>
        <div className="stat-card">
          <div className="stat-label">Available</div>
          <div className="stat-value stat-success">{formatAmount(balance.available, 'usd')}</div>
        </div>
        <div className="stat-card">
          <div className="stat-label">Pending</div>
          <div className="stat-value stat-warning">{formatAmount(balance.pending, 'usd')}</div>
        </div>
      </div>

      <div className="controls">
        <input
          type="text"
          className="search-input"
          placeholder="Search transactions..."
          value={searchQuery}
          onChange={(e) => setSearchQuery(e.target.value)}
        />
        <div className="filter-buttons">
          {['all', 'charge', 'refund', 'payout', 'fee'].map((type) => (
            <button
              key={type}
              className={`filter-btn ${typeFilter === type ? 'active' : ''}`}
              onClick={() => handleFilterChange(type)}
            >
              {type.charAt(0).toUpperCase() + type.slice(1)}
            </button>
          ))}
        </div>
      </div>

      {isPending && <div className="loading-indicator">Filtering...</div>}

      <div className="data-grid">
        {filteredTransactions.length === 0 ? (
          <div className="empty-state">
            <svg width="64" height="64" viewBox="0 0 24 24" fill="none" stroke="currentColor">
              <line x1="12" y1="1" x2="12" y2="23" strokeWidth="2" />
              <path d="M17 5H9.5a3.5 3.5 0 0 0 0 7h5a3.5 3.5 0 0 1 0 7H6" strokeWidth="2" />
            </svg>
            <h3>No transactions found</h3>
            <p>Try adjusting your search or filter</p>
          </div>
        ) : (
          <table className="data-table">
            <thead>
              <tr>
                <th>Transaction ID</th>
                <th>Type</th>
                <th>Description</th>
                <th>Amount</th>
                <th>Created</th>
              </tr>
            </thead>
            <tbody>
              {filteredTransactions.map((txn) => (
                <tr key={txn.id}>
                  <td className="mono">{txn.id}</td>
                  <td>
                    <span className={`badge badge-${txn.type}`}>{txn.type}</span>
                  </td>
                  <td>{txn.description}</td>
                  <td className={`amount ${txn.amount < 0 ? 'negative' : 'positive'}`}>
                    {formatAmount(txn.amount, txn.currency)}
                  </td>
                  <td className="date">{formatDate(txn.created)}</td>
                </tr>
              ))}
            </tbody>
          </table>
        )}
      </div>

      <div className="toast-container">
        {toasts.map((toast) => (
          <div key={toast.id} className={`toast toast-${toast.type}`}>
            {toast.message}
          </div>
        ))}
      </div>
    </div>
  );
};

export default App;
