Sending emails with Mailgun in Go

Krzysztof Kowalczyk
Sep 11 · 1 min read · 461 views
As a result of rampant abuse of e-mail for spam, it's hard to set up your own e-mail server that can send e-mails that will be accepted by others.
Because of that there are companies that provide reliable email delivery as a service.
SparkPost, SendGrid and Mailgun are services providing transactional email delivery via API.
This article describes how to use Mailgun from Go.
I picked Mailgun over others due to pricing.
MailGun gives 10.000 free emails a month.
SendGrid gives 100 free emails a day (3.000 a month).
SparkPost only offers 500 free emails a month.

Setting up for sending

First, you need to create an account with Mailgun.
They give you one sending domain (a subdomain of mailgun.org).
Sending domain is what the receiver sees in From field in the email.
If you're sending to other people, it's a good idea to add a sending domain for a domain you own.
This involves adding DNS entries in your DNS provider, to prove that you own the domain and set things up so that emails to that domain go to MailGun servers.
Finally, you need to take note of the API key.

Sending via API

Mailgun has an official Go library github.com/mailgun/mailgun-go/v3
// Your available domain names can be found here:
// (https://app.mailgun.com/app/domains)
var mailgunEmailDomain string = "SET ME" // e.g. mg.yourcompany.com

// You can find the Private API Key in your Account Menu, under "Settings":
// (https://app.mailgun.com/app/account/security)
var mailgunPrivateAPIKey string = "SET ME"

func sendEmail(body []byte, recipient string) error {
	// Create an instance of the Mailgun Client
	mg := mailgun.NewMailgun(mailgunEmailDomain, mailgunPrivateAPIKey)

  // TODO: set sender to the right e-mail address
	sender := "me@" + mailgunEmailDomain
	subject := "Presstige daily tasks on " + time.Now().Format("2006-01-02")

	// The message object allows you to add attachments and Bcc recipients
	message := mg.NewMessage(sender, subject, string(body), recipient)

	ctx, cancel := context.WithTimeout(context.Background(), time.Second*10)
	defer cancel()

	// Send the message	with a 10 second timeout
	resp, id, err := mg.Send(ctx, message)

	return err
}
The library offers more functionality:
  • monitoring events related to email delivery
  • validating e-mail addresses (so that you don't send emails that are guaranteed to bounce)
  • helpers for handling webhook callbacks

More resources

Updating...

Share on