Integrating GoDaddy Email with Strapi v4 for Newsletter Delivery

January 29, 2025

After building a newsletter feature in my Strapi v4 backend, I ran into a wall: email integration.
What seemed like a trivial task became a rabbit hole of mismatched documentation, unsupported packages, and hidden configurations—especially when you're using GoDaddy email, powered by Microsoft 365.

This post walks through the journey, what didn’t work, what eventually did, and the hidden landmines I discovered along the way.


The SendGrid Detour

I started with SendGrid, expecting a quick win.
It abstracts away SMTP auth, provides a clean API, and works well in most tutorials.

import os from sendgrid import SendGridAPIClient from sendgrid.helpers.mail import Mail SENDGRID_API_KEY = "xxxx" FROM_EMAIL = "xxx" TO_EMAIL = "xxxx" message = Mail( from_email=FROM_EMAIL, to_emails=TO_EMAIL, subject='Hello JW, following up on the previous message', html_content="<strong>This is a test email</strong>" ) try: sg = SendGridAPIClient(SENDGRID_API_KEY) response = sg.send(message) print(f"Status Code: {response.status_code}") except Exception as e: print(f"Error: {e}")

Pros:

No need to touch SMTP or worry about headers.

Easy to get started.

Cons:

Requires DNS setup for MX and SPF records on GoDaddy.

Free tier is limited, not ideal for early-stage products or stealth mode development.

Learning SMTP (the Hard Way)

Switching gears, I went low-level and explored SMTP integration directly. That’s when I realized GoDaddy email is just a white-labeled Microsoft 365 service. You can't just plug and play.

Hidden SMTP Configuration

You need to enable SMTP Auth in two places:

GoDaddy account console

Microsoft Exchange Admin Center (admin.exchange.microsoft.com)

Look for the option:

"Disable SMTP Auth for this user" — it’s enabled by default. You must turn it off.

I wasted hours chasing failed auths — until I unchecked that hidden setting.

The Python SMTP Proof

Once SMTP auth was properly enabled, I verified it using Python:

import smtplib from email.mime.text import MIMEText SMTP_SERVER = "smtp.office365.com" SMTP_PORT = 587 EMAIL_ADDRESS = "xxx@domain.com" EMAIL_PASSWORD = "xxx" to_email = "xxx@domain.com" msg = MIMEText("This is another test email from Python via SMTP.") msg["Subject"] = "Test Email" msg["From"] = EMAIL_ADDRESS msg["To"] = to_email try: with smtplib.SMTP(SMTP_SERVER, SMTP_PORT, local_hostname='ohwise.com') as server: server.starttls() server.login(EMAIL_ADDRESS, EMAIL_PASSWORD) server.send_message(msg) print(" Email sent successfully") except Exception as e: print(f" Failed to send email: {e}")

Key insight: The local_hostname parameter must match your server’s domain — otherwise the handshake may fail.

The Strapi v4 Email Trap

If you’re using Strapi v4, most legacy email plugins just don’t work. After testing several packages and debugging endless 500 Internal Server Error responses, I found:

You must use @strapi/provider-email-nodemailer.

npm install @strapi/provider-email-nodemailer

Strapi’s own docs are outdated in parts, and many tutorials still reference deprecated packages. Save yourself hours — use this one.

Node.js + Nodemailer Test

Final confirmation? Here’s the working Node.js setup that mirrors Strapi’s backend behavior:

const nodemailer = require('nodemailer'); require('dotenv').config(); async function testEmail() { const transporter = nodemailer.createTransport({ host: 'smtp.office365.com', port: 587, secure: false, auth: { user: process.env.EMAIL_USER, pass: process.env.EMAIL_PASS } }); try { await transporter.verify(); console.log('SMTP connection successful!'); const info = await transporter.sendMail({ from: process.env.EMAIL_USER, to: process.env.EMAIL_USER, subject: 'Test Email', text: 'This is a test email' }); console.log('Test email sent:', info.messageId); } catch (error) { console.error('Error:', error); } } testEmail();

The Take Away

Don’t fully trust outdated docs.

When using GoDaddy, remember it’s really Microsoft 365 behind the scenes.

SMTP is powerful, but requires patience and precision — every checkbox matters.

Building features like newsletters isn’t just about pushing data — it's about understanding the infrastructure underneath. Sometimes, to move forward, you have to go deeper.

Join the Discussion

Share your thoughts and insights about this project.