Adding reCAPTCHA to Secure Your Next.js Contact Form
In my last post, I walked through the steps of creating a contact form with Next.js and Nodemailer for email handling. However, as I continued to test it, I realized I hadn't considered spam prevention. This opened my inbox to potential spam attacks by bots. To tackle this, I integrated Google reCAPTCHA into the form, and I'll walk you through the process.
What is reCAPTCHA?
Google reCAPTCHA is a service that protects your site from bots by ensuring that the user interacting with your form is human. It’s easy to implement and very effective at blocking unwanted automated submissions.
Steps to Integrate reCAPTCHA in Your Next.js Form
Get reCAPTCHA keys from Google
First, you need to obtain your site key and secret key from Google. Head over to the reCAPTCHA admin console and register your site. Choose reCAPTCHA v2 or v3 depending on your preference (I’ll be using v2 checkbox in this example). After registration, you'll receive yoursite key
andsecret key
.Install
react-google-recaptcha
We'll need a library to embed reCAPTCHA in our Next.js form. Run:npm install react-google-recaptcha
Add reCAPTCHA to the Contact Form
Modify your
Contact.tsx
file to include reCAPTCHA. We'll importReCAPTCHA
from the installed library, and place the component right above the submit button.import ReCAPTCHA from "react-google-recaptcha"; const Contact = () => { const [captchaValue, setCaptchaValue] = useState<string | null>(null); const handleCaptchaChange = (value: string | null) => { setCaptchaValue(value); }; const handleSubmit = async (e: FormEvent<HTMLFormElement>) => { e.preventDefault(); if (!captchaValue) { alert('Please complete the CAPTCHA'); return; } const mail: Email = { email, subject, message }; // rest of your code for submitting the form }; return ( <form onSubmit={handleSubmit}> {/* form fields */} <ReCAPTCHA sitekey={process.env.NEXT_PUBLIC_RECAPTCHA_SITE_KEY || ""} onChange={handleCaptchaChange} /> <Button type="submit">Send message</Button> </form> ); };
Validate reCAPTCHA on the Server
In your
api/send-email.ts
, you'll now verify the reCAPTCHA token server-side using the secret key you received from Google. This ensures that the request came from a human.import axios from 'axios'; export default async function handler(req: NextApiRequest, res: NextApiResponse) { if (req.method === 'POST') { const { email, subject, message, token } = req.body; // Verify the reCAPTCHA token with Google const verificationURL = `https://www.google.com/recaptcha/api/siteverify?secret=${process.env.RECAPTCHA_SECRET_KEY}&response=${token}`; const { data } = await axios.post(verificationURL); if (!data.success) { return res.status(400).json({ error: 'reCAPTCHA verification failed' }); } // Proceed with sending the email } }
Make sure to update the form submission code in
Contact.tsx
to send the reCAPTCHA token along with the email data:const mail: Email = { email, subject, message, token: captchaValue };
Testing After setting this up, test your form to ensure reCAPTCHA is working correctly. You'll need to complete the reCAPTCHA challenge before submitting the form.
And that's it! You've successfully secured your Next.js contact form with reCAPTCHA to keep those pesky bots out of your inbox. Happy coding!