Skip to content

Commit

Permalink
feat(communication): create ses-domain module (#17)
Browse files Browse the repository at this point in the history
feat(communication): crate ses-domain module
  • Loading branch information
p5 authored Aug 30, 2024
1 parent 3d5837b commit dfea7c1
Show file tree
Hide file tree
Showing 5 changed files with 161 additions and 0 deletions.
31 changes: 31 additions & 0 deletions modules/aws/communication/ses-domain/dkim.tf
Original file line number Diff line number Diff line change
@@ -0,0 +1,31 @@
# While it's not clean, it's better than some unmaintainable hackiness.
# SES always returns 3 tokens, so rather than looping over them, we can just hardcode each record.
resource "aws_route53_record" "dkim_1" {
count = var.hosted_zone_id != null ? 1 : 0

zone_id = var.hosted_zone_id
name = "${aws_sesv2_email_identity.this.dkim_signing_attributes[0].tokens[0]}._domainkey"
type = "CNAME"
records = ["${aws_sesv2_email_identity.this.dkim_signing_attributes[0].tokens[0]}.dkim.amazonses.com"]
ttl = 1800
}

resource "aws_route53_record" "dkim_2" {
count = var.hosted_zone_id != null ? 1 : 0

zone_id = var.hosted_zone_id
name = "${aws_sesv2_email_identity.this.dkim_signing_attributes[0].tokens[1]}._domainkey"
type = "CNAME"
records = ["${aws_sesv2_email_identity.this.dkim_signing_attributes[0].tokens[1]}.dkim.amazonses.com"]
ttl = 1800
}

resource "aws_route53_record" "dkim_3" {
count = var.hosted_zone_id != null ? 1 : 0

zone_id = var.hosted_zone_id
name = "${aws_sesv2_email_identity.this.dkim_signing_attributes[0].tokens[2]}._domainkey"
type = "CNAME"
records = ["${aws_sesv2_email_identity.this.dkim_signing_attributes[0].tokens[2]}.dkim.amazonses.com"]
ttl = 1800
}
81 changes: 81 additions & 0 deletions modules/aws/communication/ses-domain/main.tf
Original file line number Diff line number Diff line change
@@ -0,0 +1,81 @@
resource "aws_sesv2_email_identity" "this" {
email_identity = var.email_identity
configuration_set_name = aws_sesv2_configuration_set.this.configuration_set_name

dkim_signing_attributes {
next_signing_key_length = "RSA_2048_BIT"
}

tags = var.tags_all
}

resource "aws_sesv2_configuration_set" "this" {
# Replace invalid characters in the configuration set name
configuration_set_name = "${replace(replace(upper(var.email_identity), ".", "_"), "@", "-")}-configuration-set"

delivery_options {
tls_policy = "REQUIRE"
}

reputation_options {
reputation_metrics_enabled = true
}

sending_options {
sending_enabled = true
}

suppression_options {
suppressed_reasons = ["BOUNCE", "COMPLAINT"]
}

tags = var.tags_all
}

resource "aws_sesv2_email_identity_policy" "this" {
for_each = var.identity_policies

email_identity = aws_sesv2_email_identity.this.email_identity
policy_name = each.key
policy = data.aws_iam_policy_document.identity_policy[each.key].json
}

data "aws_iam_policy_document" "identity_policy" {
for_each = var.identity_policies

dynamic "statement" {
for_each = each.value
content {
sid = statement.key
effect = lookup(statement.value, "effect", null)
actions = lookup(statement.value, "actions", null)
not_actions = lookup(statement.value, "not_actions", null)
resources = [aws_sesv2_email_identity.this.arn]

dynamic "principals" {
for_each = lookup(statement.value, "principals", {})
content {
type = principals.key
identifiers = principals.value
}
}

dynamic "not_principals" {
for_each = lookup(statement.value, "not_principals", {})
content {
type = not_principals.key
identifiers = not_principals.value
}
}

dynamic "condition" {
for_each = lookup(statement.value, "condition", {})
content {
test = condition.value.test
variable = condition.value.variable
values = condition.value.values
}
}
}
}
}
17 changes: 17 additions & 0 deletions modules/aws/communication/ses-domain/outputs.tf
Original file line number Diff line number Diff line change
@@ -0,0 +1,17 @@
output "dkim_tokens" {
value = {
"dkim_tokens" = concat(aws_sesv2_email_identity.this.dkim_signing_attributes[*].tokens...)
}
}

output "arn" {
value = aws_sesv2_email_identity.this.arn
}

output "identity_type" {
value = aws_sesv2_email_identity.this.identity_type
}

output "configuration_set_arn" {
value = aws_sesv2_configuration_set.this.arn
}
22 changes: 22 additions & 0 deletions modules/aws/communication/ses-domain/variables.tf
Original file line number Diff line number Diff line change
@@ -0,0 +1,22 @@
variable "email_identity" {
type = string
description = "The email identity to allow sending emails from. Can be a domain or email address."
}

variable "tags_all" {
type = map(string)
default = {}
description = "A map of tags to add to all resources created by this module."
}

variable "hosted_zone_id" {
type = string
description = "The Route 53 hosted zone ID to add the DKIM record to. If not provided, no DKIM record will be created."
default = null
}

variable "identity_policies" {
type = any
description = "A map of SES identity policies to apply to the email identity."
default = {}
}
10 changes: 10 additions & 0 deletions modules/aws/communication/ses-domain/versions.tf
Original file line number Diff line number Diff line change
@@ -0,0 +1,10 @@
terraform {
required_version = ">=1.3"

required_providers {
aws = {
source = "hashicorp/aws"
version = ">=4.0"
}
}
}

0 comments on commit dfea7c1

Please sign in to comment.