aws / aws/aws-sdk-java-v2

DynamoDB enhanced client silently fails when necessary extensions are not installed + exposes no list of installed extensions

Open
#6,227 4 comments 5 reactions 0 assignees View on GitHub
bug dynamodb-enhanced needs-review
Dominant language
Java
Stars
2.6k
Forks
1k
Avg merge
2d 9h
Merged PRs (30d)
51

Description

### Describe the bug

I learned the hard way that if the `VersionedRecordExtension` is not installed on my instance of `DynamoDbEnhancedClient`, the client silently ignores `DynamoDbVersionAttribute` annotations, stops performing optimistic locking, and writes null versions to the database. There is no compile time or run time check for missing extensions.

### Regression Issue

- [ ] Select this option if this issue appears to be a regression.

### Expected Behavior

I expected the client to provide a fast-fail mechanism of some kind if necessary extensions are not installed to support the annotations used in a `DynamoDbBean` entity definition. At the very least, it would be ideal if the `DynamoDbEnhancedClient` instances exposed a list of installed extensions so callers could implement their own fast-fail logic.

### Current Behavior

The `DynamoDbEnhancedClient` quietly ignores annotations that are not supported by its list of installed extensions.

### Reproduction Steps

The following code snippets can be used to write a record to Dynamo that should have a version field populated with the value `1`. Instead, it will have no value for this field.

Entity definition (Kotlin)

```kotlin
@DynamoDbBean
data class MyEntity(
@get:DynamoDbPartitionKey
@get:DynamoDbAttribute("pk")
var pk: String = "",
// Sort Key, should always be "LOAN" unless we introduce new types of records,
// which would probably be represented by different classes.
@get:DynamoDbSortKey
@get:DynamoDbAttribute("sk")
var recordType: String = "",

@get:DynamoDbVersionAttribute
@get:DynamoDbAttribute("version")
var version: Int? = null,
)
```

Client setup (Java):

```java
var client = DynamoDbEnhancedClient.builder()
.dynamoDbClient(DynamoDbClient.builder().build())
.extensions(List.of()) // Some list of extensions that causes record versioning extension not to be installed
.build();
```

Usage of table (Kotlin):

```kotlin
val table = client.table("my-table", TableSchema.fromBean(MyEntity::class.java))
val record = MyEntity(
pk = "some-pk",
sk = "some-sk"
)
table.putItem(PutItemEnhancedRequest.builder(MyEntity::class.java)
.item(record)
.build())
```

### Possible Solution

At a minimum, if the enhanced client object could provide a public list of extensions installed, callers could add start-up logic in their applications to assert that expected extensions are there.

### Additional Information/Context

_No response_

### AWS Java SDK version used

2.31.54

### JDK version used

21.0.4

### Operating System and version

MacBook Pro, Apple M2 Max, Sequoia 15.5

Contributor guide

Open the contributing guide

Assessment

This issue has not been assessed yet.

Get new issues in your inbox

A short digest of beginner-friendly GitHub issues.