Using IAM authentication for Amazon MemoryDB and ElastiCache

How to securely connect your Go applications using IAM authentication

Abhishek Gupta
Amazon Employee
Published Dec 7, 2023
Last Modified Jun 18, 2024
Amazon MemoryDB is a durable, in-memory database service. It has supported username/password based authentication using Access Control Lists since the very beginning. But using IAM based authentication allows you to associate IAM users and roles with MemoryDB users so that applications can use IAM credentials to authenticate to the MemoryDB cluster. With this authentication mode, you don't need to use a (long-lived) user password. Instead, you use an authentication token generated using AWS Signature Version 4.
There are many benefits to this approach. Instead of managing username and password based credentials, you can use IAM to centrally manage access to MemoryDB clusters. For client applications running on Amazon EC2, Amazon EKS, AWS Lambda, AWS App Runner etc., you can inject these credentials (depending on the platform e.g. profile credentials in EC2 and instance role in App Runner) - this provides greater security.
MemoryDB documentation has an example for a Java application with the Lettuce client. The process is similar for other languages, but you still need to implement it. So, let's learn how to do it for a Go application with the widely used go-redis client.
As a bonus, this is also applicable to ElastiCache for Redis, which also supports IAM authentication. There are minor differences which I will list at the end of the blog.
Let's get started....

1. Configure the MemoryDB cluster along with user and IAM role

Start by creating a MemoryDB user, Access Control list (ACL) and add the user to it. Make sure to use IAM as the authentication type.
create user
create user
Now, create the MemoryDB cluster. Make sure to choose version 7.0 or above and choose the ACL you created before.
choose version
choose version
While the cluster is being provisioned, you can create an IAM role. Use the following Trust Relationship to allow connectivity from an EC2 instance:
Use the following permissions - replace the MemoryDB cluster, IAM username, AWS account ID and region:

2. Configure AWS Cloud9 environment

Create an AWS Cloud9 environment to execute the client application that will connect to MemoryDB.
  • Make sure to use same VPC and subnet as the MemoryDB cluster
  • Update the MemoryDB subnet group to add inbound rule for the client application connectivity.
Refer to the Getting started with Redis on AWS - the easy way! blog post that already has this covered.

3. Run the client application

Once the MemoryDB cluster and Cloud9 instance are ready, go ahead and execute the client application.
Open the Cloud9 instance terminal, clone the following GitHub repository:
Update the run.sh file to enter the MemoryDB cluster endpoint, and username. For example:
To run the application:
Once the app is up and running, simply invoke it's HTTP endpoints to verify that it works with IAM authentication.
The application super simple. That's on purpose. Let's move on to the important bits, which is about the IAM authentication part.

IAM authentication logic - Behind the scenes

You can refer to the authentication code in the GitHub repository
1) We first create a HTTP GET request that contains the cluster name as part of the URL along with username, the action (connect) and token expiry (900 seconds) as query parameters:
2) The request is then signed using PresignHTTP:
3) The token generator is invoked in a CredentialsProvider during client creation:
That's it in terms of a quick overview. But wait, there is more...

This can also be used for ElastiCache!

The same approach applies - with a few changes. First, the IAM policy has to be updated to reflect ElastiCache resources (obviously!)
For example:
Before you run the application, update the SERVICE_NAME environment variable to elasticache as well as the endpoint URL, cluster name and IAM username for the ElastiCache instance.
This example assumes you are using a Redis Cluster connection mode (which is the only option in case of MemoryDB). But in case of ElastiCache be mindful of whether you are using cluster-mode enabled configuration. If not, you will have to tweak the code to use redis.NewClient (instead of redis.NewClusterClient). The CredentialsProvider option will be available nonetheless.

Conclusion

Using IAM authentication has its benefits. Instead of managing username and passwords in multiple locations/applications, delegate the heavy lifting to IAM. All you need is to provide configure appropriate permissions (following the principle of "least privilege").
But you also need to be aware of the limitations. For e.g. IAM authentication is not supported in MULTI EXEC commands. For a complete list, refer to the documentation.
Have you tried using IAM authentication with MemoryDB or ElastiCache for Redis in other programming languages? Let me know.
Happy building!
 

Any opinions in this post are those of the individual author and may not reflect the opinions of AWS.

Comments