javaamazon-web-servicesaws-lambdaamazon-dynamodb

DeleteItem API throws error - The provided key element does not match the schema (DynamoDB)


I'm using the java v2 sdk and trying to delete an item from the table using below code

public static DeleteItemResponse deleteDynamoDBItem(String key, String keyVal) {

    Map<String, AttributeValue> keyToGet =
            new HashMap<>();

    keyToGet.put(key, AttributeValue.builder()
            .s(keyVal)
            .build());

    DeleteItemRequest deleteReq = DeleteItemRequest.builder()
            .tableName(TABLE_NAME)
            .key(keyToGet)
            .build();

    try {
        return DYNAMO_DB.deleteItem(deleteReq);
    } catch (DynamoDbException e) {
        System.err.println(e.getMessage());
        System.exit(1);
    }
    return null;
}

Error is thrown in the logs

"The provided key element does not match the schema (Service: DynamoDb, Status Code: 400, Request ID: VCTLMOSSUBMSHMCNOMN589ETPJVV4KQNSO5AEMVJF66Q9ASUAAJG)"

DeleteItemResponse response = DataService.deleteDynamoDBItem("userid", "abc");

Below is the table structure

enter image description here

enter image description here

I'm referring below url for example

https://github.com/awsdocs/aws-doc-sdk-examples/blob/main/javav2/example_code/dynamodb/src/main/java/com/example/dynamodb/DeleteItem.java


Solution

  • In DynamoDB, if a table has both a partition key and a sort key, any operation (like DeleteItem) must provide values for both keys to uniquely identify the item. so this is how your code should look like:

    public static DeleteItemResponse deleteDynamoDBItem(String partitionKey, String partitionKeyValue, String sortKey, int sortKeyValue) {
    
        Map<String, AttributeValue> keyToGet = new HashMap<>();
    
        keyToGet.put(partitionKey, AttributeValue.builder()
                .s(partitionKeyValue) // Partition key is a String
                .build());
        keyToGet.put(sortKey, AttributeValue.builder()
                .n(String.valueOf(sortKeyValue)) // Sort key is a Number, so convert int to String
                .build());
    
        DeleteItemRequest deleteReq = DeleteItemRequest.builder()
                .tableName(TABLE_NAME)
                .key(keyToGet)
                .build();
    
        try {
            return DYNAMO_DB.deleteItem(deleteReq);
        } catch (DynamoDbException e) {
            System.err.println(e.getMessage());
            System.exit(1);
        }
        return null;
    }
    

    and then you can easily call:

    DeleteItemResponse response = DataService.deleteDynamoDBItem("userid", "abc", "age", 89);