Skip to content

Commit 7735c6d

Browse files
committed
Initial Version
1 parent 4f56be0 commit 7735c6d

File tree

3 files changed

+168
-0
lines changed

3 files changed

+168
-0
lines changed
Lines changed: 129 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,129 @@
1+
#
2+
# Create a random id to ensure no conflicts.
3+
resource "random_id" "id" {
4+
byte_length = 4
5+
}
6+
#
7+
# Create the assume role policy document for the Lambda function.
8+
data "aws_iam_policy_document" "assume_role" {
9+
statement {
10+
effect = "Allow"
11+
12+
principals {
13+
type = "Service"
14+
identifiers = ["lambda.amazonaws.com"]
15+
}
16+
17+
actions = ["sts:AssumeRole"]
18+
}
19+
}
20+
#
21+
# Create the inline policy document for the Lambda function role.
22+
data "aws_iam_policy_document" "inline_permissions" {
23+
#
24+
# The frist two statements are required for the lambda function to write logs to CloudWatch.
25+
# While not required, are useful for debugging.
26+
statement {
27+
sid = "Sid0"
28+
effect = "Allow"
29+
actions = ["logs:CreateLogGroup"]
30+
resources = ["arn:aws:logs:${var.region}:${var.awsAccountId}:*"]
31+
}
32+
statement {
33+
sid = "Sid1"
34+
effect = "Allow"
35+
actions = [
36+
"logs:PutLogEvents",
37+
"logs:CreateLogStream"
38+
]
39+
resources = ["arn:aws:logs:${var.region}:${var.awsAccountId}:log-group:/aws/lambda/${local.lambdaName}:*"]
40+
}
41+
#
42+
# The third statement is required for the lambda function to rotate the secret.
43+
# Both within the Secrets Manager and the FSx file system.
44+
statement {
45+
sid = "Sid2"
46+
effect = "Allow"
47+
actions = [
48+
"secretsmanager:GetSecretValue",
49+
"secretsmanager:DescribeSecret",
50+
"secretsmanager:PutSecretValue",
51+
"secretsmanager:UpdateSecretVersionStage",
52+
"fsx:UpdateFileSystem"
53+
]
54+
resources = [
55+
aws_secretsmanager_secret.secret.arn,
56+
"arn:aws:fsx:${var.region}:${var.awsAccountId}:file-system/${var.fsxId}"
57+
]
58+
}
59+
#
60+
# The fourth statement is required for the lambda function to generate a random password.
61+
statement {
62+
sid = "sid3"
63+
effect = "Allow"
64+
actions = ["secretsmanager:GetRandomPassword"]
65+
resources = ["*"]
66+
}
67+
}
68+
#
69+
# Create a local variable for the Lambda function name, so it can be used in two places without causing a cycle.
70+
locals {
71+
lambdaName = "fsxn_rotate_secret-${random_id.id.hex}"
72+
}
73+
#
74+
# Create the IAM role for the Lambda function.
75+
resource "aws_iam_role" "iam_for_lambda" {
76+
name = "iam_for_lambda-${random_id.id.hex}"
77+
decription = "IAM role for the Rotate FSxN Secret Lambda function."
78+
assume_role_policy = data.aws_iam_policy_document.assume_role.json
79+
inline_policy {
80+
name = "required_policy"
81+
policy = data.aws_iam_policy_document.inline_permissions.json
82+
}
83+
}
84+
#
85+
# Create the archive file for the Lambda function.
86+
data "archive_file" "lambda" {
87+
type = "zip"
88+
source_file = "${path.module}/../fsxn_rotate_secret.py"
89+
output_path = "fsxn_rotate_secret.zip"
90+
}
91+
#
92+
# Create the Lambda function.
93+
resource "aws_lambda_function" "rotateLambdaFunction" {
94+
function_name = local.lambdaName
95+
role = aws_iam_role.iam_for_lambda.arn
96+
runtime = "python3.12"
97+
handler = "fsxn_rotate_secret.lambda_handler"
98+
filename = "fsxn_rotate_secret.zip"
99+
source_code_hash = data.archive_file.lambda.output_base64sha256
100+
}
101+
#
102+
# Allow Secrets Manager to invoke the Lambda function.
103+
resource "aws_lambda_permission" "allowSecretsManager" {
104+
statement_id = "AllowExecutionFromSecretsManager"
105+
action = "lambda:InvokeFunction"
106+
function_name = aws_lambda_function.rotateLambdaFunction.function_name
107+
principal = "secretsmanager.amazonaws.com"
108+
source_arn = aws_secretsmanager_secret.secret.arn
109+
}
110+
#
111+
# Create the secret with the required tags.
112+
resource "aws_secretsmanager_secret" "secret" {
113+
name = "${var.secretNamePrefix}-${random_id.id.hex}"
114+
115+
tags = {
116+
fsxId = var.fsxId
117+
region = var.region
118+
}
119+
}
120+
#
121+
# Add the rotation Lambda function and rule to the secret.
122+
resource "aws_secretsmanager_secret_rotation" "secretRotation" {
123+
secret_id = aws_secretsmanager_secret.secret.id
124+
rotation_lambda_arn = aws_lambda_function.rotateLambdaFunction.arn
125+
126+
rotation_rules {
127+
schedule_expression = var.rotationFrequency
128+
}
129+
}
Lines changed: 14 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,14 @@
1+
output "secret-ARN" {
2+
description = "The ARN of the secret that was created."
3+
value = aws_secretsmanager_secret.secret.arn
4+
}
5+
6+
output "Rotate-Secret-Lamnda-Function-ARN" {
7+
description = "The ARN of the Lambda function that was created."
8+
value = aws_lambda_function.rotateLambdaFunction.arn
9+
}
10+
11+
output "Rotate-Secret-Lamnda-Function-Name" {
12+
description = "The name of the Lambda function that was created."
13+
value = local.lambdaName
14+
}
Lines changed: 25 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,25 @@
1+
variable "region" {
2+
description = "The AWS region where the FSxN file system resides."
3+
type = string
4+
}
5+
6+
variable "awsAccountId" {
7+
description = "The AWS account ID."
8+
type = string
9+
}
10+
11+
variable "secretNamePrefix" {
12+
description = "The prefix to the secret name that will be created that will contain the FSxN file system's password."
13+
type = string
14+
}
15+
16+
variable "fsxId" {
17+
description = "The FSxN file system ID."
18+
type = string
19+
}
20+
21+
variable "rotationFrequency" {
22+
description = "The rotation frequency of the secret. It should express in AWS's rate() or cron() format. The default is once every 30 days."
23+
type = string
24+
default = "rate(30 days)"
25+
}

0 commit comments

Comments
 (0)