← back to Dear Bubbe Nextjs
app/api/email/route.ts
213 lines
import { NextRequest, NextResponse } from 'next/server'
import { updateStat } from '../stats/route'
interface EmailRequest {
to: string | string[]
subject: string
body: string
html?: string
from?: string
}
// Mock email sending - replace with actual email service
async function sendEmail(emailData: EmailRequest): Promise<{ success: boolean; messageId?: string; error?: string }> {
try {
// This is a mock implementation - replace with your email service
// Examples: SendGrid, AWS SES, Nodemailer with SMTP, etc.
console.log(`[EMAIL] Sending email to: ${Array.isArray(emailData.to) ? emailData.to.join(', ') : emailData.to}`)
console.log(`[EMAIL] Subject: ${emailData.subject}`)
console.log(`[EMAIL] Body length: ${emailData.body.length} characters`)
// Simulate email sending delay
await new Promise(resolve => setTimeout(resolve, 1000))
// Mock success response
const messageId = `msg_${Date.now()}_${Math.random().toString(36).substr(2, 9)}`
return {
success: true,
messageId
}
} catch (error) {
console.error('[EMAIL] Error sending email:', error)
return {
success: false,
error: error instanceof Error ? error.message : String(error)
}
}
}
// Generate email template
function generateEmailTemplate(subject: string, body: string): string {
return `
<!DOCTYPE html>
<html>
<head>
<meta charset="utf-8">
<meta name="viewport" content="width=device-width, initial-scale=1.0">
<title>${subject}</title>
<style>
body {
font-family: -apple-system, BlinkMacSystemFont, "Segoe UI", Roboto, sans-serif;
line-height: 1.6;
color: #333;
max-width: 600px;
margin: 0 auto;
padding: 20px;
background-color: #f5f5f5;
}
.email-container {
background: white;
padding: 30px;
border-radius: 8px;
box-shadow: 0 2px 10px rgba(0,0,0,0.1);
}
.header {
border-bottom: 2px solid #f093fb;
padding-bottom: 20px;
margin-bottom: 30px;
}
.content {
white-space: pre-wrap;
}
.footer {
margin-top: 30px;
padding-top: 20px;
border-top: 1px solid #eee;
font-size: 12px;
color: #666;
text-align: center;
}
a {
color: #f5576c;
text-decoration: none;
}
a:hover {
text-decoration: underline;
}
</style>
</head>
<body>
<div class="email-container">
<div class="header">
<h1 style="margin: 0; color: #f5576c;">${subject}</h1>
</div>
<div class="content">
${body}
</div>
<div class="footer">
<p>Sent from Bubbe.ai | <a href="https://bubbe.ai">Visit Website</a></p>
<p>This email was sent by an automated system. Please do not reply to this email.</p>
</div>
</div>
</body>
</html>
`.trim()
}
export async function POST(request: NextRequest) {
try {
const startTime = Date.now()
const body = await request.json()
const { to, subject, body: emailBody, html, from } = body
// Validation
if (!to || !subject || !emailBody) {
return NextResponse.json({
error: 'Missing required fields: to, subject, body'
}, { status: 400 })
}
// Validate email addresses
const emailRegex = /^[^\s@]+@[^\s@]+\.[^\s@]+$/
const toEmails = Array.isArray(to) ? to : [to]
for (const email of toEmails) {
if (!emailRegex.test(email)) {
return NextResponse.json({
error: `Invalid email address: ${email}`
}, { status: 400 })
}
}
const emailData: EmailRequest = {
to,
subject,
body: emailBody,
html: html || generateEmailTemplate(subject, emailBody),
from: from || 'noreply@bubbe.ai'
}
console.log(`[EMAIL] Processing email request`)
const result = await sendEmail(emailData)
if (result.success) {
// Update stats
updateStat('emailCampaignsDrafted', 1)
updateStat('tasksCompleted', 1)
const responseTime = Date.now() - startTime
console.log(`[EMAIL] Email sent successfully in ${responseTime}ms`)
return NextResponse.json({
success: true,
messageId: result.messageId,
recipients: toEmails.length,
responseTime
})
} else {
// Update error stats
updateStat('errorsToday', 1)
return NextResponse.json({
error: 'Failed to send email',
details: result.error
}, { status: 500 })
}
} catch (error) {
console.error('[EMAIL] Error processing email request:', error)
// Update error stats
updateStat('errorsToday', 1)
return NextResponse.json({
error: 'Internal server error',
details: error instanceof Error ? error.message : String(error)
}, { status: 500 })
}
}
export async function GET(request: NextRequest) {
try {
// Return email sending capabilities and templates
return NextResponse.json({
service: 'Bubbe.ai Email Service',
features: [
'HTML email templates',
'Multiple recipients',
'Custom subjects and content',
'Automatic template generation'
],
limits: {
maxRecipients: 100,
maxSubjectLength: 200,
maxBodyLength: 50000
},
templates: {
marketing: 'Professional marketing email template',
notification: 'Simple notification template',
welcome: 'Welcome message template'
},
usage: 'POST with { to, subject, body } to send email'
})
} catch (error) {
console.error('[EMAIL] Error in GET request:', error)
return NextResponse.json({
error: 'Failed to process request',
details: error instanceof Error ? error.message : String(error)
}, { status: 500 })
}
}