How to store and rotate database credentials using AWS Secret Manager
Tags: aws, awssecretmanager, security, rdsauthentication
Published: 2021-06-18 17:14:29

“Challenges faced to find the solution of how to secure the database credentials”. I have checked different ways so that I can give the security to users' credentials such as the database username and password. I got the solution to enable the IAM database authentication option in RDS but due to some limitations of IAM database authentication and requirement from client side to secure their users existing credentials. The option of choosing the IAM database authentication is not a good fit for my scenario. So I have checked the service in AWS as AWS Secret Manager which helps to store and rotate the database credentials in terms of username and password not as authentication token. And it's a good fit for my current scenario. So I have just configured a secret manager to store and even rotate the credentials of the database depending on the defined days. This is really a good option as in terms of cost optimization and security purpose.

AWS Secrets Manager helps you protect secrets needed to access your applications, services, and IT resources. The service enables you to easily rotate, manage, and retrieve database credentials, API keys, and other secrets throughout their lifecycle. Users and applications retrieve secrets with a call to Secrets Manager APIs, eliminating the need to hard code sensitive information in plain text.

Secrets Manager offers secret rotation with built-in integration for Amazon RDS, Amazon Redshift, and Amazon DocumentDB. Also, the service is extensible to other types of secrets, including API keys and OAuth tokens. In addition, Secrets Manager enables you to control access to secrets using fine-grained permissions and audit secret rotation centrally for resources in the AWS Cloud, third-party services, and on-premises.

In this post, you will get to know how to store database credentials for a RDS database using AWS Secrets Manager. Here I have used a WORD PRESS application server that requires database credentials to access the MySQL database.

#Prerequisites
You’ll need an Amazon EC2 Server for this post. [Getting started with amazon EC2](https://aws.amazon.com/ec2/getting-started/) provides instructions on how to launch an EC2 Server.

You’ll also need [AWS Command Line Interface](https://docs.aws.amazon.com/cli/latest/userguide/installing.html) (AWS CLI) installed and configured on your machine. For this blog, I assume that the default AWS CLI region is set to N. Virginia (us-east-1) and that you have access to the AWS services described in this post. If you use other regions, you should check the [availability](https://aws.amazon.com/about-aws/global-infrastructure/regional-product-services/) of AWS services in those regions.

#Architecture Overview
![Architecture Overview](https://dev-to-uploads.s3.amazonaws.com/uploads/articles/vviywjus4wl6dfa2bd17.png)
The architecture diagram shows the overall deployment architecture with data flow, application server, Mysql DB instance, AWS CLI and AWS secrets manager.

#Solution overview
The blog post consists of the following phases:
1. Store a secret in Secrets Manager
2. Update an application to retrieve secret from Secrets Manager
3. Enable Rotation for your secret

##Phase 1: Store a secret in Secrets Manager
1. Open the Secrets Manager Console and select Store a new secret.
![Secrets Manager Console](https://dev-to-uploads.s3.amazonaws.com/uploads/articles/mzcek5drt12feaouboqw.png)
2. Select Credentials for RDS database and Give Username and password of RDS which will make a secret and choose the default encryption key.
![Select Credentials](https://dev-to-uploads.s3.amazonaws.com/uploads/articles/okei74whxe659op0o7dl.png)
3. Select the DB instance mysql-rds-database, and then select Next.
![Select the DB instance](https://dev-to-uploads.s3.amazonaws.com/uploads/articles/f8bf2fdjybaz2rgmkckk.png)
4. Give Secret name and description.
![Give Secret name and description](https://dev-to-uploads.s3.amazonaws.com/uploads/articles/4vdq6r82ehxedwnna5rn.png)
5. Choose default disable automatic rotation option.
![Choose default disable automatic rotation option](https://dev-to-uploads.s3.amazonaws.com/uploads/articles/jz8pd4i9scve2i9zzwi2.png)
6. Review all configurations and can change if you want.
![Review all configurations](https://dev-to-uploads.s3.amazonaws.com/uploads/articles/wrotsiiis1tm8mxiarh3.png)
7. Secret application successfully created.
![Secret application successfully created](https://dev-to-uploads.s3.amazonaws.com/uploads/articles/0arz0zpbgfwffvtf8rm9.png)
8. Can check the auto-generated sample code with different languages.
![check the auto-generated sample code](https://dev-to-uploads.s3.amazonaws.com/uploads/articles/jqbg5zv2cltmpfj6lo7w.png)

##Phase 2: Update an application to retrieve secret from Secrets Manager
Update the application to retrieve the database credential from Secrets Manager
1. Connect to EC2 instance.

2. Add this code to the application to retrieve credentials.
// Use the code snippet provided by Secrets Manager. 
import boto3
from botocore.exceptions import ClientError
def get_secret():
// Define the secret you want to retrieve
secret_name = “Applications/MyApp/MySQL-RDS-Database”
// Define the Secrets mManager end-point your code should use.
endpoint_url = “https://secretsmanager.us-east-1.amazonaws.com"
region_name = “us-east-1”
// Setup the client
session = boto3.session.Session()
client = session.client(
service_name=’secretsmanager’,
region_name=region_name,
endpoint_url=endpoint_url
)
// Use the client to retrieve the secret
try:
get_secret_value_response = client.get_secret_value(
SecretId=secret_name
)
// Error handling to make it easier for your code to tolerate faults
except ClientError as e:
if e.response[‘Error’][‘Code’] == ‘ResourceNotFoundException’:
print(“The requested secret “ + secret_name + “ was not found”)
elif e.response[‘Error’][‘Code’] == ‘InvalidRequestException’:
print(“The request was invalid due to:”, e)
elif e.response[‘Error’][‘Code’] == ‘InvalidParameterException’:
print(“The request had invalid params:”, e)
else:
// Decrypted secret using the associated KMS CMK
// Depending on whether the secret was a string or binary, one of these fields will be populated
if ‘SecretString’ in get_secret_value_response:
secret = get_secret_value_response[‘SecretString’]
else:
binary_secret_data = get_secret_value_response[‘SecretBinary’]
// Your code goes here.

3. Attach an IAM role to an EC2 instance.
{
“Version”: “2012–10–17”,
“Statement”: {
“Sid”: “RetrieveDbCredentialFromSecretsManager”,
“Effect”: “Allow”,
“Action”: “secretsmanager:GetSecretValue”,
“Resource”: “arn:aws:secretsmanager:::secretApplications/MyApp/MySQL-RDS-Database”
}
}

##Phase 3: Enable Rotation for Your Secret
1. To enable rotation option, goto rotation configuration edit option.
![enable rotation option](https://dev-to-uploads.s3.amazonaws.com/uploads/articles/ivewtbad8pf87le4kv6p.png)
2. Set enable automatic rotation option and choose rotation interval.
![Set enable automatic rotation](https://dev-to-uploads.s3.amazonaws.com/uploads/articles/q7uqarefhp26qjaa6ti8.png)
3. Choose to create a lambda function to perform rotation options.
![Choose to create a lambda function](https://dev-to-uploads.s3.amazonaws.com/uploads/articles/wqul2uaqjl7jjsyip01b.png)
4. Select Secret which was stored previously.
![Select Secret which was stored previously](https://dev-to-uploads.s3.amazonaws.com/uploads/articles/9c8298fvn2ldwp01uf3p.png)
5. Rotation is being created.
![Rotation is being created](https://dev-to-uploads.s3.amazonaws.com/uploads/articles/fcuaupvio0x2fnazxuby.png)
6. Rotation Enabled for selected days.
![Rotation Enabled](https://dev-to-uploads.s3.amazonaws.com/uploads/articles/3yl3jrp7og513st4urw6.png)

##WordPress application server with MYSQL RDS database to store credentials in a secret Manager —
###Step 1) Launched WordPress application server
![Launched WordPress application server](https://dev-to-uploads.s3.amazonaws.com/uploads/articles/9w5ugbosy7dse8xykgkg.png)
###Step 2) Created MYSQL RDS Database
![Created MYSQL RDS Database](https://dev-to-uploads.s3.amazonaws.com/uploads/articles/795tnenxuvirbsg8dur6.png)
###Step 3) Store a secret key of RDS in secret manager
![Store a secret key](https://dev-to-uploads.s3.amazonaws.com/uploads/articles/j7512068yk0yj80ij5id.png)
###Step 4) Enable key rotation option with defined details
![Enable key rotation option](https://dev-to-uploads.s3.amazonaws.com/uploads/articles/i1ui00ioxw8ivfe4o22k.png)
###Step 5) Check configurations in secret manager using AWS CLI for wordpress application. Enabled rotation here for 30 days.
![Check configurations in secret manager](https://dev-to-uploads.s3.amazonaws.com/uploads/articles/tadv2r3mfurg4us50fgw.png)
###Step 6) Enabled rotation here for 60 days
![Enabled rotation here for 60 days](https://dev-to-uploads.s3.amazonaws.com/uploads/articles/1uf668i43s0na0mc9x9g.png)
###Step 7) Get database credentials via AWS Command Line stored on AWS secret manager
![Get database credentials](https://dev-to-uploads.s3.amazonaws.com/uploads/articles/iz3d2mxiv7fum2a3q6r7.png)

#Clean-up
Terminate EC2 Server.
Delete AWS Secret Manager.
Delete RDS Database.

#Pricing
I review the pricing and estimated cost of this example. AWS Secrets Manager offers a 30-day trial period that starts when you store your first secret. Storage of each secret costs $0.40 per secret per month. For secrets that are stored for less than a month, the price is prorated based on the number of hours. There is an additional cost of $0.05 per 10,000 API calls. You can learn more by visiting the [AWS Secrets Manager pricing](https://aws.amazon.com/secrets-manager/pricing/) service details page.

Cost of EC2 = $0.012 per hour = $0.024(2 hours).

Cost of RDS = $14.75 per month = $0.04(2 hours).

Cost of AWS Secrets Manager = 2 hours x ($0.40 per secret per month / 30 days / 24 hours + $0.05 per 10,000 API calls).

#Summary

In this post, I had shown you how to store and rotate database credentials using AWS Secret Manager.
For more details on secrets management, Checkout Get started managing secrets, open the [Secrets Manager console](https://console.aws.amazon.com/secretsmanager/home?region=us-east-1#/home). To learn more, read the [Secrets Manager documentation](https://aws.amazon.com/documentation/secretsmanager/).

Thanks for reading!

Connect with me: [Linkedin](https://www.linkedin.com/in/gargee-bhatnagar-6b7223114)