aws / aws-sdk-java-v2

The official AWS SDK for Java - Version 2
Apache License 2.0
2.16k stars 840 forks source link

[DDB Enhanced Client] BigDecimal has different behavior between top level and nested value on handling trailing zeros #5529

Closed khiemns54 closed 2 weeks ago

khiemns54 commented 1 month ago

Describe the bug

BigDecimal has different behavior between top level and nested value on handling trailing zeros

value at top level is trailing-zeros-striped, but not for nested value

Expected Behavior

BigDecimal should have the same behavior regardless the property level(top, flatten, nested,...)

Current Behavior

value at top level is trailing-zeros-striped, but not for nested value

Reproduction Steps

Sample code. (Sorry for using kotlin, but I believe it should be similar in Java)

class BigDecimalConverterTest(
    private val dynamoDbClient: DynamoDbClient,
    private val dynamoDbEnhancedClient: DynamoDbEnhancedClient,
) {

    @DynamoDbBean
    data class TestTable(
        @get:DynamoDbPartitionKey
        var id: String = "",
        var topLvValue: BigDecimal = BigDecimal.ZERO,
        var nested : NestedObject = NestedObject(),
    )

    @DynamoDbBean
    data class NestedObject(
        var nestedValue: BigDecimal = BigDecimal.ZERO,
    )

    private val schema by lazy { TableSchema.fromBean(TestTable::class.java) }
    private val table by lazy { dynamoDbEnhancedClient.table("test_table", schema) }

    @BeforeEach
    fun setup() {
        try {
            table.deleteTable()
        } catch (_: Exception) {
        }
        table.createTable()
    }

    @Test
    fun testSave() {
        val item = TestTable(
            id = "id",
            topLvValue = BigDecimal("1234.4670000"),
            nested = NestedObject(
                nestedValue = BigDecimal("1234.4670000")
            )
        )

        table.putItem(item)

        val saved = table.getItem(Key.builder().partitionValue("id").build())
        Assertions.assertEquals(item, saved)
    }
}

Output

org.opentest4j.AssertionFailedError: 
Expected :TestTable(id=id, topLvValue=1234.4670000, nested=NestedObject(nestedValue=1234.4670000))
Actual   :TestTable(id=id, topLvValue=1234.467, nested=NestedObject(nestedValue=1234.4670000))

Possible Solution

No response

Additional Information/Context

No response

AWS Java SDK version used

2.25.36

JDK version used

openjdk 21.0.2 2024-01-16 LTS OpenJDK Runtime Environment Corretto-21.0.2.13.1 (build 21.0.2+13-LTS) OpenJDK 64-Bit Server VM Corretto-21.0.2.13.1 (build 21.0.2+13-LTS, mixed mode, sharing)

Operating System and version

macOS Sônma 14.6.1

debora-ito commented 1 month ago

Hi @khiemns54 I can't reproduce the issue, both top-level and nested big decimal returns "1234.467" in my case.

What's the attribute type in the DynamoDB table, is it Number for both? For reference, here's the JSON view of my local tests after I added to the table:

{
 "id": 111,
 "firstName": "Tom",
 "topValue": 1234.467,
 "mainAddress": {
      "city": "Los Angeles",
      "state": "CA",
      "value": 1234.467
 }
}

Can you generate the verbose wirelogs of the putItem and getItem requests? Make sure to redact any sensitive info (like access keys). Instructions can be found in our Developer Guide: https://docs.aws.amazon.com/sdk-for-java/latest/developer-guide/logging-slf4j.html#sdk-java-logging-verbose

github-actions[bot] commented 3 weeks ago

It looks like this issue has not been active for more than five days. In the absence of more information, we will be closing this issue soon. If you find that this is still a problem, please add a comment to prevent automatic closure, or if the issue is already closed please feel free to reopen it.

khiemns54 commented 1 week ago

@debora-ito Sorry, I completely forgot this, let me check it later but it looks like it's a problem of dynamodb local tool, I can see that the actual ddb truncating all trailing zeros