import React, { useEffect, useState } from 'react'; import { useParams, useNavigate } from 'react-router-dom'; import api from '../../utils/api'; import { Card } from '../../components/ui/card'; import { Button } from '../../components/ui/button'; import { Badge } from '../../components/ui/badge'; import { ArrowLeft, Mail, Phone, MapPin, Calendar, Lock, AlertTriangle } from 'lucide-react'; import { toast } from 'sonner'; import ConfirmationDialog from '../../components/ConfirmationDialog'; const AdminUserView = () => { const { userId } = useParams(); const navigate = useNavigate(); const [user, setUser] = useState(null); const [loading, setLoading] = useState(true); const [resetPasswordLoading, setResetPasswordLoading] = useState(false); const [resendVerificationLoading, setResendVerificationLoading] = useState(false); const [subscriptions, setSubscriptions] = useState([]); const [subscriptionsLoading, setSubscriptionsLoading] = useState(true); const [confirmDialogOpen, setConfirmDialogOpen] = useState(false); const [pendingAction, setPendingAction] = useState(null); useEffect(() => { fetchUserProfile(); fetchSubscriptions(); }, [userId]); const fetchUserProfile = async () => { try { const response = await api.get(`/admin/users/${userId}`); setUser(response.data); } catch (error) { toast.error('Failed to load user profile'); navigate('/admin/members'); } finally { setLoading(false); } }; const fetchSubscriptions = async () => { try { const response = await api.get(`/admin/subscriptions?user_id=${userId}`); setSubscriptions(response.data); } catch (error) { console.error('Failed to fetch subscriptions:', error); } finally { setSubscriptionsLoading(false); } }; const handleResetPasswordRequest = () => { setPendingAction({ type: 'reset_password' }); setConfirmDialogOpen(true); }; const handleResendVerificationRequest = () => { setPendingAction({ type: 'resend_verification' }); setConfirmDialogOpen(true); }; const confirmAction = async () => { if (!pendingAction) return; const { type } = pendingAction; setConfirmDialogOpen(false); if (type === 'reset_password') { setResetPasswordLoading(true); try { await api.put(`/admin/users/${userId}/reset-password`, { force_change: true }); toast.success(`Password reset email sent to ${user.email}`); } catch (error) { const errorMessage = error.response?.data?.detail || 'Failed to reset password'; toast.error(errorMessage); } finally { setResetPasswordLoading(false); setPendingAction(null); } } else if (type === 'resend_verification') { setResendVerificationLoading(true); try { await api.post(`/admin/users/${userId}/resend-verification`); toast.success(`Verification email sent to ${user.email}`); // Refresh user data to get updated email_verified status if changed await fetchUserProfile(); } catch (error) { const errorMessage = error.response?.data?.detail || 'Failed to send verification email'; toast.error(errorMessage); } finally { setResendVerificationLoading(false); setPendingAction(null); } } }; const getActionMessage = () => { if (!pendingAction || !user) return {}; const { type } = pendingAction; const userName = `${user.first_name} ${user.last_name}`; if (type === 'reset_password') { return { title: 'Reset Password?', description: `This will send a temporary password to ${user.email}. ${userName} will be required to change it on their next login.`, variant: 'warning', confirmText: 'Yes, Reset Password', }; } if (type === 'resend_verification') { return { title: 'Resend Verification Email?', description: `This will send a new verification email to ${user.email}. ${userName} will need to click the link to verify their email address.`, variant: 'info', confirmText: 'Yes, Resend Email', }; } return {}; }; if (loading) return
Loading...
; if (!user) return null; return ( <> {/* Back Button */} {/* User Profile Header */}
{/* Avatar */}
{user.first_name?.[0]}{user.last_name?.[0]}
{/* User Info */}

{user.first_name} {user.last_name}

{/* Status & Role Badges */} {user.status} {user.role}
{/* Contact Info */}
{user.email}
{user.phone}
{user.city}, {user.state} {user.zipcode}
Joined {new Date(user.created_at).toLocaleDateString()}
{/* Admin Actions */}

Admin Actions

{!user.email_verified && ( )}
User will receive a temporary password via email
{/* Additional Details */}

Additional Information

{user.address}

{new Date(user.date_of_birth).toLocaleDateString()}

{user.partner_first_name && (

{user.partner_first_name} {user.partner_last_name}

)} {user.referred_by_member_name && (

{user.referred_by_member_name}

)} {user.lead_sources && user.lead_sources.length > 0 && (
{user.lead_sources.map((source, idx) => ( {source} ))}
)}
{/* Subscription Info (if applicable) */} {user.role === 'member' && (

Subscription Information

{subscriptionsLoading ? (

Loading subscriptions...

) : subscriptions.length === 0 ? (

No subscriptions found for this member.

) : (
{subscriptions.map((sub) => (

{sub.plan.name}

{sub.plan.billing_cycle}

{sub.status}

{new Date(sub.start_date).toLocaleDateString()}

{sub.end_date && (

{new Date(sub.end_date).toLocaleDateString()}

)}

${(sub.base_subscription_cents / 100).toFixed(2)}

{sub.donation_cents > 0 && (

${(sub.donation_cents / 100).toFixed(2)}

)}

${(sub.amount_paid_cents / 100).toFixed(2)}

{sub.payment_method && (

{sub.payment_method}

)} {sub.stripe_subscription_id && (

{sub.stripe_subscription_id}

)}
))}
)}
)} {/* Admin Action Confirmation Dialog */} ); }; export default AdminUserView;