Setup DKIM for email send directly from worker

What is the name of the domain?

[private]

What is the issue you’re encountering

DKIM validation fails on emails send from worker

What are the steps to reproduce the issue?

Send email to verified email directly from worker (not by forwarding it).

Here’s code I use to send emails

async function sendFromCloudflare(SENDER: SendEmail, mailData: MailData, messageData: Message): Promise<{
	success: boolean,
	error?: any
}> {
	const msg = createMimeMessage()
	msg.setSender(mailData.from)
	msg.setRecipient(mailData.to)
	if (mailData.bcc) {
		msg.setBcc(mailData.bcc)
	}
	msg.setHeader('Reply-To', new Mailbox(mailData.replyTo))
	msg.setSubject(mailData.subject)

	if (mailData.headers) {
		for (const key in mailData.headers) {
			try {
				msg.setHeader(key, mailData.headers[key])
			}
			catch (e) {
				console.error(`Failed to set header ${key} to ${mailData.headers[key]}`, e)
			}
		}
	}

	msg.addMessage({
		contentType: 'text/plain',
		data: messageData.plain
	})
	msg.addMessage({
		contentType: 'text/html',
		data: messageData.html
	})

	const message = new EmailMessage(typeof mailData.from == 'object' ? mailData.from.addr : mailData.from, mailData.to, msg.asRaw())
	try {
		await SENDER.send(message)
		return {success: true}
	} catch (e) {
		return {success: false, error: e}
	}
}

Code works as expected but problem exists on email validation. Cloudflare passes DKIM to email and sends it. But validation fails because no valid DKIM TXT entry is present on sender domain.

May I ask if you did added the SPF, DKIM and DMARC records for your domain? :thinking:

Yes, SPF, DKIM and DMARC are added to domain DNS.

Also I made a mistake, problem with DKIM is not with record but with domain alignment (I didn’t know about such thing that’s why I assumed it’s problem with record in domain).
Emails send from worker are signed using cloudflare-email.net domain.

How can I modify it to sign it with my domain?
Do I have to manually generate keypair and write code to sign email? Or is there any existing solution for workers.

The Email Workers shall literally be seen as a DIY (Do-It-Yourself) in this scenario.

If you want something there, you’re going to have to do it on your own.

That spans everywhere, from ensuring that your message boundaries conform to the standards, to adding the DKIM signing, and so forth.

I understand Workers are mainly DIY, but maybe someone already made package that does what I’m looking for.
I’ve tried a few solutions from some mailer packages but all of them work based on node crypto createSign or createHash which are not compatible with workers at the moment.

I think it’s impossible to pass DKIM verification when using Cloudflare Email Routing to sent emails, Every email sent or forward via it are always signed by cloudflare-email.net

It is clear now that unless you manually implement your own DKIM signing logic, messages will be signed with cloudflare-email.net and fail domain alignment checks. I appreciate how everyone here clarified that Workers are truly DIY in this regard. Hopefully in the future we will see more official tooling to make DKIM signing easier for Worker-based solutions — it would open up a lot more flexibility for projects relying on custom domain email sending.

If you’re talking about the classic Email Routing, then it is sender (from before it hits Cloudflare) that you need to blame.

That is not the reason they fail.

The reason is because you don’t have a valid signature, that matches your own domain.

You can technically have 50 different DKIM signatures attached on a single email (although I don’t personally see why you should ever do that).

As long as one single of these signatures are valid, and are matching with the “From:” header of the message, the DKIM alignment will succeed.

I’d be happy to see something like that, too.