{[{name:'Gmail',pct:44,color:'#ff6200'},{name:'Apple Mail',pct:28,color:'#3b82f6'},{name:'Outlook',pct:16,color:'#8b5cf6'},{name:'Yahoo Mail',pct:8,color:'#10b981'},{name:'Others',pct:4,color:'var(--border-strong)'}].map((e,i)=>
);
};
// AUTOMATION
const AutomationPage=({addToast})=>{
const [workflows]=useState([{id:1,name:'Welcome Series',trigger:'New Subscriber',status:'active',enrolled:2840,completed:1920,emails:3},{id:2,name:'Re-engagement Flow',trigger:'Inactive 90 days',status:'active',enrolled:640,completed:280,emails:4},{id:3,name:'Post-Purchase Follow-up',trigger:'Tag: purchased',status:'inactive',enrolled:0,completed:0,emails:2},{id:4,name:'Abandoned Cart Recovery',trigger:'Tag: cart_abandoned',status:'draft',enrolled:0,completed:0,emails:3}]);
const [showBuilder,setShowBuilder]=useState(false);
const nodes=[{type:'trigger',label:'New Subscriber',icon:'π―',color:'#ff6200'},{type:'wait',label:'Wait 1 day',icon:'β±οΈ',color:'#3b82f6'},{type:'email',label:'Welcome Email',icon:'π§',color:'#10b981'},{type:'wait',label:'Wait 3 days',icon:'β±οΈ',color:'#3b82f6'},{type:'condition',label:'Opened first email?',icon:'π',color:'#8b5cf6'},{type:'email',label:'Follow-up Email',icon:'π§',color:'#10b981'}];
return(
Automation Workflows
Automate your email sequences
{workflows.map(w=>
{w.name}
Trigger: {w.trigger}
{w.status}
{[{v:w.enrolled,l:'Enrolled'},{v:w.completed,l:'Completed'},{v:w.emails,l:'Emails'},{v:`${w.enrolled>0?Math.round(w.completed/w.enrolled*100):0}%`,l:'Rate',o:true}].map((s,i)=>
{typeof s.v==='number'?s.v.toLocaleString():s.v}
{s.l}
)}
{w.status==='active'?:}
)}
setShowBuilder(false)} title="Workflow Builder" size="lg" footer={<>>}>
Available Actions
{[{icon:'π§',label:'Send Email'},{icon:'β±οΈ',label:'Wait / Delay'},{icon:'π',label:'Condition'},{icon:'π·οΈ',label:'Add Tag'},{icon:'π',label:'Update Field'}].map((a,i)=>
{a.icon}{a.label}
)}
Workflow Flow
{nodes.map((n,i)=>
{i})}
);
};
// SMTP
const SmtpPage=({addToast})=>{
const [configs,setConfigs]=useState(mockSmtp);
useEffect(()=>{
api.get('/smtp').then(res=>{
if(res.success && res.data && res.data.length > 0) setConfigs(res.data);
}).catch(()=>{});
},[]);
const [showAdd,setShowAdd]=useState(false);
const [testingId,setTestingId]=useState(null);
const [form,setForm]=useState({name:'',host:'',port:'587',encryption:'tls',username:'',password:'',from_email:'',from_name:''});
const providers=[{name:'SendGrid',host:'smtp.sendgrid.net'},{name:'Mailgun',host:'smtp.mailgun.org'},{name:'Amazon SES',host:'email-smtp.us-east-1.amazonaws.com'},{name:'Gmail',host:'smtp.gmail.com'},{name:'Postmark',host:'smtp.postmarkapp.com'},{name:'Brevo',host:'smtp-relay.brevo.com'}];
return(
SMTP Configuration
Configure email delivery providers
{configs.map(c=>
π¬
{c.name}
{c.host}:{c.port}
{c.is_default===1&&Default}{c.is_verified===1&&β Verified}
{[['From Email',c.from_email],['From Name',c.from_name],['Encryption',(c.encryption||'tls').toUpperCase()]].map(([k,v])=>
{k}{v}
)}
)}
{providers.map((p,i)=>
{e.currentTarget.style.borderColor='var(--orange)';e.currentTarget.style.background='var(--orange-dim)';}} onMouseLeave={e=>{e.currentTarget.style.borderColor='var(--border)';e.currentTarget.style.background='transparent';}} onClick={()=>{setForm(f=>({...f,name:p.name,host:p.host}));setShowAdd(true);}}>
{p.name}
{p.host}
)}
setShowAdd(false)} title="Add SMTP Configuration" size="md" footer={<>>}>
);
};
// SETTINGS
const SettingsPage=({addToast})=>{
const [tab,setTab]=useState('general');
return(
Settings
{['general','notifications','security','api','billing'].map(t=>
setTab(t)}>{t}
)}
{tab==='general'&&
}
{tab==='security'&&
}
{tab==='api'&&
Webhooks
https://yourapp.com/webhooks/email
Events: open, click, bounce, unsubscribe
Active
}
{tab==='notifications'&&
{[{l:'Campaign sent',d:'When a campaign finishes sending'},{l:'Campaign failed',d:'When errors occur'},{l:'Weekly digest',d:'Weekly performance summary'},{l:'New unsubscribes',d:'Daily unsubscribe report'},{l:'Bounce alerts',d:'When bounce rate exceeds threshold'},{l:'Import completed',d:'When a contact import finishes'}].map((n,i)=>
)}
}
{tab==='billing'&&
Current Plan
Professional
$49/month Β· Renews March 1, 2025
50,000 emails/month Β· Unlimited contacts Β· Priority support
{[{n:'Starter',p:'$19',e:'10,000',c:'5,000'},{n:'Pro',p:'$49',e:'50,000',c:'Unlimited',cur:true},{n:'Enterprise',p:'Custom',e:'Unlimited',c:'Unlimited'}].map((pl,i)=>
{pl.n}
{pl.p}
/month
π§ {pl.e} emails
π₯ {pl.c} contacts
)}
}
);
};
// USERS
const UsersPage=({addToast})=>{
const [users]=useState([{id:1,name:'Super Admin',email:'admin@mailflow.io',role:'super_admin',status:'active',last_login:'2024-02-24'},{id:2,name:'Jane Manager',email:'jane@company.com',role:'manager',status:'active',last_login:'2024-02-23'},{id:3,name:'Bob Editor',email:'bob@company.com',role:'editor',status:'active',last_login:'2024-02-22'},{id:4,name:'Alice Viewer',email:'alice@company.com',role:'viewer',status:'suspended',last_login:'2024-02-10'}]);
const roles={super_admin:'Super Admin',admin:'Admin',manager:'Manager',editor:'Editor',viewer:'Viewer'};
const roleColors={super_admin:'#ff6200',admin:'#8b5cf6',manager:'#3b82f6',editor:'#10b981',viewer:'#999'};
return(
Users & Roles
{users.length} team members
| User | Role | Status | Last Active | Actions |
{users.map(u=> | {roles[u.role]} | | {u.last_login} | {u.id!==1&&} |
)}
| Role | Campaigns | Contacts | Templates | Analytics | Settings | Users |
{[{role:'Super Admin',color:'#ff6200',campaigns:'Full',contacts:'Full',templates:'Full',analytics:'Full',settings:'Full',users:'Full'},{role:'Admin',color:'#8b5cf6',campaigns:'Full',contacts:'Full',templates:'Full',analytics:'Full',settings:'Full',users:'View'},{role:'Manager',color:'#3b82f6',campaigns:'Full',contacts:'Full',templates:'Full',analytics:'View',settings:'β',users:'β'},{role:'Editor',color:'#10b981',campaigns:'Create/Edit',contacts:'View',templates:'Full',analytics:'β',settings:'β',users:'β'},{role:'Viewer',color:'#999',campaigns:'View',contacts:'View',templates:'View',analytics:'View',settings:'β',users:'β'}].map((r,i)=>| {r.role} | {['campaigns','contacts','templates','analytics','settings','users'].map(p=>{r[p]==='Full'?'β Full':r[p]==='β'?'β':r[p]} | )}
)}
);
};
// QUEUE PAGE
const QueuePage=({addToast})=>{
const [jobs]=useState([{id:1001,campaign:'Spring Newsletter',email:'alice@example.com',status:'sent',attempts:1,scheduled_at:'2024-02-20 09:00',sent_at:'2024-02-20 09:01'},{id:1002,campaign:'Spring Newsletter',email:'bob@techcorp.io',status:'sent',attempts:1,scheduled_at:'2024-02-20 09:00',sent_at:'2024-02-20 09:01'},{id:1003,campaign:'Weekly Digest #47',email:'carol@startup.co',status:'pending',attempts:0,scheduled_at:'2024-02-22 10:00',sent_at:null},{id:1004,campaign:'Weekly Digest #47',email:'david@enterprise.com',status:'processing',attempts:1,scheduled_at:'2024-02-22 10:00',sent_at:null},{id:1005,campaign:'Re-engagement',email:'emma@agency.net',status:'failed',attempts:3,scheduled_at:'2024-02-22 09:00',sent_at:null},{id:1006,campaign:'Re-engagement',email:'frank@mail.com',status:'failed',attempts:3,scheduled_at:'2024-02-22 09:00',sent_at:null}]);
const [sf,setSf]=useState('all');
const sm={sent:'badge-sent',pending:'badge-scheduled',processing:'badge-sending',failed:'badge-failed'};
const qs=[{label:'Pending',value:1842,color:'#3b82f6'},{label:'Processing',value:124,color:'#ff6200'},{label:'Sent Today',value:48291,color:'#10b981'},{label:'Failed',value:38,color:'#ef4444'}];
const fj=sf==='all'?jobs:jobs.filter(j=>j.status===sf);
return(
Email Queue
Monitor outgoing email jobs in real-time
{qs.map((s,i)=>
{s.label}
{s.value.toLocaleString()}
)}
Queue Jobs
{['all','pending','processing','sent','failed'].map(s=>)}
| #ID | Campaign | Recipient | Status | Attempts | Scheduled | Sent At |
{fj.map(j=>| #{j.id} | {j.campaign} | {j.email} | {j.status==='processing'&&}{j.status} | | {j.scheduled_at} | {j.sent_at||'β'} |
)}
Showing {fj.length} of 50,295 total
);
};
// ACTIVITY LOGS
const ActivityPage=()=>{
const logs=[{id:1,user:'Super Admin',action:'campaign.sent',desc:"Campaign 'Spring Newsletter 2024' sent to 8,420 recipients",time:'2024-02-20 09:01',ip:'192.168.1.1'},{id:2,user:'Jane Manager',action:'contact.imported',desc:'847 contacts imported from spring_list.csv',time:'2024-02-20 08:30',ip:'192.168.1.45'},{id:3,user:'Super Admin',action:'smtp.tested',desc:"SMTP 'Primary SMTP' test email sent successfully",time:'2024-02-19 16:22',ip:'192.168.1.1'},{id:4,user:'Bob Editor',action:'template.created',desc:"Template 'Summer Sale 2024' created",time:'2024-02-19 14:10',ip:'10.0.0.12'},{id:5,user:'Super Admin',action:'user.login',desc:'User logged in from 192.168.1.1',time:'2024-02-19 09:00',ip:'192.168.1.1'},{id:6,user:'Jane Manager',action:'campaign.created',desc:"Campaign 'Weekly Digest #47' created",time:'2024-02-18 17:45',ip:'192.168.1.45'},{id:7,user:'Alice Viewer',action:'user.login',desc:'User logged in from 10.0.0.55',time:'2024-02-18 11:30',ip:'10.0.0.55'},{id:8,user:'Super Admin',action:'contact.deleted',desc:'Contact frank@mail.com removed from system',time:'2024-02-17 15:20',ip:'192.168.1.1'}];
const ac={'campaign.sent':'#10b981','campaign.created':'#3b82f6','contact.imported':'#8b5cf6','smtp.tested':'#ff6200','template.created':'#f59e0b','user.login':'#999','contact.deleted':'#ef4444'};
const ai={'campaign.sent':'π€','campaign.created':'π','contact.imported':'π₯','smtp.tested':'π¬','template.created':'π¨','user.login':'π','contact.deleted':'ποΈ'};
return(
Activity Logs
Full audit trail of all platform actions
{logs.map((log,i)=>
e.currentTarget.style.background='var(--surface-2)'} onMouseLeave={e=>e.currentTarget.style.background='transparent'}>
{ai[log.action]||'β‘'}
{log.user}{log.action}
{log.desc}
π {log.time}π {log.ip}
)}
);
};
// LOGIN PAGE
const LoginPage=({onLogin})=>{
const [email,setEmail]=useState('admin@mailflow.io');
const [password,setPassword]=useState('Admin@123');
const [loading,setLoading]=useState(false);
const [error,setError]=useState('');
const handle=async()=>{
if(!email||!password){setError('Please enter email and password');return;}
setError('');setLoading(true);
try {
const data = await Auth.login(email, password);
onLogin(data.user);
} catch(e) {
setError(e.message || 'Login failed. Check your credentials.');
} finally {
setLoading(false);
}
};
return(
Email marketing
that delivers.
Send beautiful campaigns, grow your audience, and track every click β all in one powerful platform.
{[{icon:'π',stat:'34.8%',label:'Average open rate'},{icon:'β‘',stat:'< 2s',label:'Delivery time'},{icon:'π',stat:'99.9%',label:'Platform uptime'}].map((s,i)=>(
))}
Welcome back
Sign in to your MailFlow account
{error&&
{error}
}
{setEmail(e.target.value);setError('');}} onKeyDown={e=>e.key==='Enter'&&handle()}/>
Demo Credentials
Emailadmin@mailflow.io
PasswordAdmin@123
);
};
// NOTIFICATION PANEL
const NotificationPanel=({onClose})=>{
const notifs=[{id:1,type:'success',title:'Campaign Sent',message:"'Spring Newsletter 2024' sent to 8,420 recipients",time:'2 min ago',read:false},{id:2,type:'info',title:'Import Complete',message:'847 contacts imported successfully',time:'32 min ago',read:false},{id:3,type:'warning',title:'Bounce Alert',message:'Bounce rate for Weekly Digest exceeded 2%',time:'1 hr ago',read:false},{id:4,type:'success',title:'SMTP Verified',message:"'Primary SMTP' connection verified",time:'3 hr ago',read:true},{id:5,type:'info',title:'Workflow Active',message:"'Welcome Series' automation is now live",time:'Yesterday',read:true}];
return(
Notifications 3
{notifs.map((n,i)=>(
e.currentTarget.style.background='var(--surface-2)'} onMouseLeave={e=>e.currentTarget.style.background=n.read?'transparent':'rgba(255,98,0,0.03)'}>
{n.type==='success'?'β
':n.type==='warning'?'β οΈ':'βΉοΈ'}
{n.title}
{!n.read&&
}
{n.message}
{n.time}
))}
);
};
// TOAST
let toastId=0;
const ToastContainer=({toasts,remove})=>(
{toasts.map(t=>(
{t.type==='success'?'β
':t.type==='error'?'β':'βΉοΈ'}
{t.message}
))}
);
// MAIN APP
const App=()=>{
const [isLoggedIn,setIsLoggedIn]=useState(Auth.isLoggedIn());
const [currentUser,setCurrentUser]=useState(null);
const [page,setPage]=useState('dashboard');
const [theme,setTheme]=useState(localStorage.getItem('mf_theme')||'light');
const [sidebarOpen,setSidebarOpen]=useState(false);
const [toasts,setToasts]=useState([]);
const [showNotifs,setShowNotifs]=useState(false);
// Restore session on page load
useEffect(()=>{
if(Auth.isLoggedIn() && !currentUser){
Auth.me().then(u=>{ if(u) setCurrentUser(u); else { Auth.logout(); setIsLoggedIn(false); } });
}
},[]);
useEffect(()=>{
document.documentElement.setAttribute('data-theme',theme);
localStorage.setItem('mf_theme',theme);
},[theme]);
const addToast=useCallback((message,type='info')=>{
const id=++toastId;
setToasts(p=>[...p,{id,message,type}]);
setTimeout(()=>setToasts(p=>p.filter(t=>t.id!==id)),4200);
},[]);
const removeToast=useCallback((id)=>setToasts(p=>p.filter(t=>t.id!==id)),[]);
const handleLogin=(user)=>{setCurrentUser(user);setIsLoggedIn(true);addToast(`Welcome back, ${user.name}! π`,'success');};
const handleLogout=()=>{Auth.logout();setIsLoggedIn(false);setCurrentUser(null);setPage('dashboard');addToast('Logged out successfully','info');};
const pageTitle={dashboard:'Dashboard',campaigns:'Campaigns',contacts:'Contacts',templates:'Email Templates',analytics:'Analytics',automation:'Automation Workflows',smtp:'SMTP Configuration',users:'Users & Roles',settings:'Settings',queue:'Email Queue',activity:'Activity Logs'};
if(!isLoggedIn)return(<>
>);
const renderPage=()=>{
const p={addToast};
switch(page){
case 'dashboard': return ;
case 'campaigns': return ;
case 'contacts': return ;
case 'templates': return ;
case 'analytics': return ;
case 'automation':return ;
case 'smtp': return ;
case 'users': return ;
case 'settings': return ;
case 'queue': return ;
case 'activity': return ;
default: return ;
}
};
const navSections=[
{section:'Main',items:[{id:'dashboard',label:'Dashboard',icon:'dashboard'},{id:'campaigns',label:'Campaigns',icon:'campaigns'},{id:'contacts',label:'Contacts',icon:'contacts'},{id:'templates',label:'Templates',icon:'templates'}]},
{section:'Growth',items:[{id:'automation',label:'Automation',icon:'automation',badge:'New'},{id:'analytics',label:'Analytics',icon:'analytics'}]},
{section:'System',items:[{id:'smtp',label:'SMTP Config',icon:'smtp'},{id:'queue',label:'Email Queue',icon:'activity',qc:true},{id:'users',label:'Users & Roles',icon:'users'},{id:'activity',label:'Activity Logs',icon:'zap'},{id:'settings',label:'Settings',icon:'settings'}]},
];
return(
{sidebarOpen&&
setSidebarOpen(false)}/>}
{pageTitle[page]||'MailFlow'}
{page==='campaigns'&&}
{page==='contacts' &&}
{page==='templates'&&}
{showNotifs&&
setShowNotifs(false)}/>}
setPage('settings')}>
{currentUser?.name?.[0]}
{currentUser?.name?.split(' ')[0]}
{renderPage()}
);
};
ReactDOM.createRoot(document.getElementById('root')).render(
);