First commit
This commit is contained in:
@@ -0,0 +1,127 @@
|
||||
// app/api/submit/route.js
|
||||
|
||||
import nodemailer from 'nodemailer';
|
||||
|
||||
export async function POST(request) {
|
||||
try {
|
||||
const formData = await request.formData();
|
||||
|
||||
// 1. Extract form data (Matching your PHP POST variables)
|
||||
const turnstileToken = formData.get('cf-turnstile-response');
|
||||
const email = formData.get('email');
|
||||
const name = formData.get('name');
|
||||
const team = formData.get('team');
|
||||
const tel = formData.get('tel');
|
||||
const count = formData.get('count');
|
||||
const level = formData.get('level');
|
||||
const message = formData.get('message');
|
||||
const honeypot = formData.get('website');
|
||||
|
||||
// 2. Security Checks (Honeypot & Turnstile)
|
||||
if (honeypot) {
|
||||
return Response.json({ success: false, message: 'Spam detekterat.' }, { status: 400 });
|
||||
}
|
||||
|
||||
// Verify Turnstile
|
||||
const turnstileRes = await fetch('https://challenges.cloudflare.com/turnstile/v0/siteverify', {
|
||||
method: 'POST',
|
||||
headers: { 'Content-Type': 'application/x-www-form-urlencoded' },
|
||||
body: new URLSearchParams({
|
||||
secret: process.env.TURNSTILE_SECRET || '', // Pulls from .env.local
|
||||
response: turnstileToken?.toString() || '',
|
||||
}),
|
||||
});
|
||||
|
||||
const turnstileData = await turnstileRes.json();
|
||||
|
||||
if (!turnstileData.success) {
|
||||
return Response.json({ success: false, message: 'Säkerhetsverifiering misslyckades (Turnstile).' }, { status: 400 });
|
||||
}
|
||||
|
||||
let formattedTel = tel.replace(/\D/g, '');
|
||||
if (formattedTel.startsWith('46')) formattedTel = formattedTel.substring(2);
|
||||
else if (formattedTel.startsWith('0')) formattedTel = formattedTel.substring(1);
|
||||
|
||||
if (formattedTel.length === 9) {
|
||||
formattedTel = `+46 (0)${formattedTel.substring(0, 2)}-${formattedTel.substring(2, 5)} ${formattedTel.substring(5, 7)} ${formattedTel.substring(7, 9)}`;
|
||||
} else {
|
||||
formattedTel = tel;
|
||||
}
|
||||
|
||||
// 4. Send Email via Nodemailer (Replicating PHPMailer)
|
||||
const transporter = nodemailer.createTransport({
|
||||
host: '10.10.0.113', // Your internal SMTP Host
|
||||
port: 25,
|
||||
secure: false,
|
||||
tls: {
|
||||
rejectUnauthorized: false
|
||||
}
|
||||
});
|
||||
|
||||
const cleanMessage = message ? message.replace(/[\r\n;]/g, " ") : "";
|
||||
const dateStr = new Date().toISOString().replace('T', ' ').substring(0, 19);
|
||||
|
||||
const emailHtml = `
|
||||
<html>
|
||||
<body style='font-family: Arial, sans-serif; line-height: 1.6; color: #333;'>
|
||||
<h2 style='color: #cc8124;'>Beach-anmälan</h2>
|
||||
<table style='width: 100%; max-width: 600px; border-collapse: collapse;'>
|
||||
<tr><td style='padding: 5px; font-weight: bold; width: 150px;'>Lagnamn:</td><td>${team}</td></tr>
|
||||
<tr><td style='padding: 5px; font-weight: bold;'>Kontakt:</td><td>${name}</td></tr>
|
||||
<tr><td style='padding: 5px; font-weight: bold;'>E-post:</td><td>${email}</td></tr>
|
||||
<tr><td style='padding: 5px; font-weight: bold;'>Telefon:</td><td>${formattedTel}</td></tr>
|
||||
<tr><td style='padding: 5px; font-weight: bold;'>Spelare:</td><td>${count}</td></tr>
|
||||
<tr><td style='padding: 5px; font-weight: bold;'>Nivå:</td><td>${level}</td></tr>
|
||||
</table>
|
||||
<p><strong>Meddelande:</strong><br>${message ? message.replace(/\n/g, '<br>') : ''}</p>
|
||||
<hr style='border: none; border-top: 1px solid #ddd; margin: 30px 0;'>
|
||||
<table border='1' style='border-collapse: collapse; font-family: Calibri, sans-serif; font-size: 11pt; width: 100%;'>
|
||||
<tr>
|
||||
<td style='padding: 8px; border: 1px solid #ccc;'>${team}</td>
|
||||
<td style='padding: 8px; border: 1px solid #ccc;'>${count}</td>
|
||||
<td style='padding: 8px; border: 1px solid #ccc;'>${level}</td>
|
||||
<td style='padding: 8px; border: 1px solid #ccc;'>${name}</td>
|
||||
<td style='padding: 8px; border: 1px solid #ccc;'>${formattedTel}</td>
|
||||
<td style='padding: 8px; border: 1px solid #ccc;'>${email}</td>
|
||||
<td style='padding: 8px; border: 1px solid #ccc;'>${dateStr}</td>
|
||||
<td style='padding: 8px; border: 1px solid #ccc;'>${cleanMessage}</td>
|
||||
</tr>
|
||||
</table>
|
||||
</body>
|
||||
</html>
|
||||
`;
|
||||
|
||||
// 1. Send the data to the Club
|
||||
await transporter.sendMail({
|
||||
from: `"Anmälan: ${name}" <no-reply@lerbergetsvolleyboll.se>`,
|
||||
to: 'beach@lerbergetsvolleyboll.se',
|
||||
replyTo: email?.toString(),
|
||||
subject: `Beach turnering: ${team}`,
|
||||
html: emailHtml,
|
||||
});
|
||||
|
||||
// 2. Send the friendly auto-reply to the Applicant
|
||||
await transporter.sendMail({
|
||||
from: `"Lerbergets Volleybollsällskap" <no-reply@lerbergetsvolleyboll.se>`,
|
||||
to: email?.toString(),
|
||||
subject: `Bekräftelse på anmälan: ${team}`,
|
||||
html: `
|
||||
<div style="font-family: Arial, sans-serif; color: #333; padding: 20px;">
|
||||
<h2 style="color: #406185;">Hej ${name}!</h2>
|
||||
<p style="font-size: 16px;">Tack för din anmälan vi återkommer så fort vi kan.</p>
|
||||
<br>
|
||||
<p style="font-size: 14px; color: #666;">
|
||||
Med vänliga hälsningar,<br>
|
||||
Lerbergets Volleybollsällskap
|
||||
</p>
|
||||
</div>
|
||||
`,
|
||||
});
|
||||
|
||||
return Response.json({ success: true, message: 'Tack så mycket för anmälan! Vi svarar med en bekräftelse så fort vi kan.' });
|
||||
|
||||
} catch (error) {
|
||||
console.error(error);
|
||||
return Response.json({ success: false, message: 'Ett tekniskt fel uppstod. Försök igen senare.' }, { status: 500 });
|
||||
}
|
||||
}
|
||||
Reference in New Issue
Block a user