DynamoDB enum conversion version 2

6k Views Asked by At

I am migration to AWS java sdk to version 2 to improve cold starts for infrequently used lambdas.

In version 1.x i used @DynamoDBTypeConvertedEnum to annotate enums and @DynamoDBDocument to store nested objects. how could i achieve the same, i don't want to change data stored in tables.

https://docs.aws.amazon.com/sdk-for-java/v2/developer-guide/client-configuration-starttime.html

<dependency>
    <groupId>software.amazon.awssdk</groupId>
    <artifactId>dynamodb</artifactId>
 </dependency>
 <dependency>
    <groupId>software.amazon.awssdk</groupId>
    <artifactId>dynamodb-enhanced</artifactId>
 </dependency>
2

There are 2 best solutions below

0
On

The enum can be converted with the following annotation.

@DynamoDbConvertedBy(EnumAttributeConverter.class)    
private JobType jobType;
0
On

Currently, you can write custom converters for any data type using the official dynamodb-enhanced client which contains DynamoDbConvertedBy annotation. There you can specify a converter class that implements the AttributeConverter interface for your data type.

Below is just my example of converter implementation for Map<EnumClass, String> type (the same way you can write it for any POJO):

@DynamoDbConvertedBy(EnumMapAttributeConverter.class) for the entity field's getter.

Class itself:

public class EnumMapAttributeConverter
    implements AttributeConverter<Map<EnumClass, String>> {

  @Override
  public AttributeValue transformFrom(final Map<EnumClass, String> input) {
    Map<String, AttributeValue> attributeValueMap =
        input.entrySet().stream()
            .collect(
                Collectors.toMap(
                    k -> k.getKey().getValue(),
                    v -> AttributeValue.builder().s(v.getValue()).build()));
    return AttributeValue.builder().m(attributeValueMap).build();
  }

  @Override
  public Map<EnumClass, String> transformTo(final AttributeValue input) {
    return input.m().entrySet().stream()
        .collect(
            Collectors.toMap(
                k -> getEnumClassKeyByString(k.getKey()), v -> v.getValue().s()));
  }

  private EnumClass getEnumClassKeyByString(final String key) {
    EnumClass enumClass = EnumClass.getByValue(key);
    return enumClass != null ? enumClass : EnumClass.NOT_FOUND;
  }

  @Override
  public EnhancedType<Map<EnumClass, String>> type() {
    return EnhancedType.mapOf(EnumClass.class, String.class);
  }

  @Override
  public AttributeValueType attributeValueType() {
    return AttributeValueType.M;
  }
}