Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

how to dynamically set table name in dynamodb using serverless and DynamoDBContext?

We need to be able to set table name based on build environment. Consider the following class:

[DynamoDBTable("movies")]
public class Movie
{
    [DynamoDBHashKey]
    public string Title { get; set; }

    [DynamoDBRangeKey(AttributeName = "Released")]
    public DateTime ReleaseDate { get; set; }

    public List<string> Genres { get; set; }
}

In serverless.yml, can the table name be set like this:

functions:
    update-movies:
        environment:
            tableName: movies-prod

Then in the code we can load the table name dynamically based on the table name in the tableName variable. We prefer to use DynamoDBContext rather than DynamoDBv2.DocumentModel (which already has a solution here How do I dynamically change dynamodb tablename in c# using object persistence model)

Something like this in Java: https://medium.com/@onclouds/aws-lambda-use-different-dynamodb-tables-for-different-stages-5eda9f5378b2

like image 203
Tung Nguyen Avatar asked Sep 20 '18 07:09

Tung Nguyen


People also ask

Do DynamoDB table names have to be globally unique?

In an AWS account, table names must be unique within each Region. That is, you can have two tables with same name if you create the tables in different Regions. CreateTable is an asynchronous operation. Upon receiving a CreateTable request, DynamoDB immediately returns a response with a TableStatus of CREATING .

Is Amazon DynamoDB serverless?

Amazon DynamoDB is a fully managed, serverless NoSQL database. In this post, you learn about the different DynamoDB patterns used in serverless applications, and use the recently launched Serverless Patterns Collection to configure DynamoDB as an event source for AWS Lambda.


1 Answers

Found a solution by passing a table name prefix:

DynamoDBContextConfig config = new DynamoDBContextConfig()
{
    TableNamePrefix = "prod-"
};

_dynamoDBContext = new DynamoDBContext(new AmazonDynamoDBClient(), config);

You still have to name your table movies though:

[DynamoDBTable("movies")]
public class Movie

DynamoDBContext will add the prefix to the table name when loading the context. So it will try to load prod-movies, stag-movies.

Here is where the table prefix is used in AWS SDK internally

if (!string.IsNullOrEmpty(flatConfig.TableNamePrefix))
    tableName = flatConfig.TableNamePrefix + tableName;

(https://github.com/aws/aws-sdk-net/blob/b691e46e57a3e24477e6a5fa2e849da44db7002f/sdk/src/Services/DynamoDBv2/Custom/DataModel/ContextInternal.cs)

Some references that helped me find the solution:

https://aws.amazon.com/blogs/developer/enhancements-to-the-dynamodb-sdk/

https://github.com/aws/aws-sdk-net/blob/b691e46e57a3e24477e6a5fa2e849da44db7002f/sdk/test/Services/DynamoDBv2/UnitTests/Custom/DynamoDBTests.cs

like image 70
Tung Nguyen Avatar answered Nov 14 '22 22:11

Tung Nguyen