How send email on contact submission using Next.js 13

How send email on contact submission using Next.js 13

In this article, we’ll seamlessly integrate Nodemailer within Next.js 13, showing you how to leverage Nodemailer’s capabilities to send emails effortlessly from your Next.js applications.

Table of Contents

  • Setup Next.js 13 Project Environment
  • Dependencies Installation
  • Setting Up Gmail
  • Creating The Nodemailer API Route
  • Creating A Simple Contact Form

Dependencies Installation

  1. Open a terminal within your project directory, and execute one of the following commands to get started:
    
    npm install nodemailer
    yarn add nodemailer 
    pnpm add nodemailer 
    

Setting Up Gmail

  1. For this tutorial, I will be using Gmail for my SMTP server, but feel free to use another SMTP server of your choice if you feel confident enough.🏆
    1. Visit this URL and make sure 2FA is activated on your google account before proceeding with step 2. I personally recommend using the authenticator app as it’s trivial to verify with and configure.
    2. Go back to this URL and scroll to the bottom of the page where you will find a section called App passwords.
    3. Create an app password with the app set to Mail and the device set to your preferred device, I personally put Windows Computer.
    4. Hit GENERATE and copy your App Password somewhere safe, we will need this shortly.

Create a .env.local file in the root of your Next.js project and add the following:

NODEMAILER_EMAIL=<YOUR-GOOGLE-EMAIL>
NODEMAILER_PASSWORD=<YOUR-APP-PASSWORD>

It’s very important that you use the previously generated app password since your personal password will not work.

  1. 2. Inside your app/ directory, create a folder called api/ with a sub-folder called email and a file called route.js; the structure should be as follows: app/api/email/route.js
Copy the following code:

import nodemailer from "nodemailer"


export  default async function POST(request,res) {
  const { email, message } =  request.body
    console.log(email, message)
  const transport = nodemailer.createTransport({
    service: "gmail",
    auth: {
      user: process.env.NODEMAILER_EMAIL,
      pass: process.env.NODEMAILER_PASSWORD,
    },
  })

  const mailOptions = {
    from: email,
    to: process.env.NODEMAILER_EMAIL,
    subject: `Message from (${email})`,
    text: message,
  }

  try {
    await transport.sendMail(mailOptions)
    return res.status(200).send("success")
} catch (error) {
     console.log(error)
  return res.status(500).send(error);
  }
}
  • We await the email and message which will be sent from the client; we will implement the client-side shortly.
  • Next we define a transport, which configures your Gmail SMTP server under the hood.
  • Next we configure the mailOptions to send an email to yourself, with the user’s email as the subject and the message written as the body.
  • Lastly, we perform the sendMail operation, and handle success or failure appropriately using a try-catch block.

Creating The Contact Form

Now that the API endpoint ready, we need to write client-side code to communicate with this endpoint, and hence send an email via nodemailer.

  1. Within app/page.jsx, copy the following code:
import ContactForm from "@/components/ContactForm"

const page = () => {
  return (
    <main className="flex grow flex-col items-center justify-center">
      <div className="space-y-4">
        <h1 className="text-4xl">Contact Us</h1>
        <ContactForm />
      </div>
    </main>
  )
}

export default page

2. At the same level as the app/ directory, create a folder called components/ with a file named ContactForm.jsx inside it.

3. Copy the following code for ContactForm.jsx:

"use client"

import { useState } from "react"

function ContactForm() {
  const [email, setEmail] = useState("")
  const [message, setMessage] = useState("")

  const handleSubmit = async (e: React.FormEvent) => {
    e.preventDefault()

    await fetch("/api/email", {
      method: "POST",
      headers: {
        "Content-Type": "application/json",
      },
      body: JSON.stringify({ email, message }),
    })
  }

  return (
    <div>
      <h2>Contact Us</h2>
      <form onSubmit={handleSubmit} className="space-y-10">
        <div>
          <label>Email:</label>
          <input
            type="email"
            value={email}
            onChange={(e) => setEmail(e.target.value)}
            required
          />
        </div>
        <div>
          <label>Message:</label>
          <textarea
            value={message}
            onChange={(e) => setMessage(e.target.value)}
            required
          ></textarea>
        </div>
        <button type="submit">Submit</button>
      </form>
    </div>
  )
}

export default ContactForm
  • This is a basic form that takes in the user’s email and message.
  • The email and message is sent to the api/email endpoint when the user submits the form, executing the code inside route.js, hence sending an email.

Conclusion:

By following these steps, you can easily integrate Nodemailer with Next.js 13 to automate sending 100+ emails daily.

# Details

Published on January 31, 2024 3 min read

Web dev

Next JS