78

I'm trying to update an Item in my Dynamodb Table +Users+. I have tried many different ways but I always received the same error message:

The provided key element does not match the schema

The creation of an Item works, as well as a query but not the update. When I check on DynamoDB the user is well created:

{
  "email": "[email protected]",
  "password": "123",
  "registration": 1460136902241,
  "verified": false
}

Here is the table information:

  • Table name: Users
  • Primary partition key: email (String)
  • Primary sort key: registration (Number)

Here is the code (called from lambda):

exports.handler = function(event, context)
{
    var AWS = require("aws-sdk");


    var docClient = new AWS.DynamoDB.DocumentClient();

    var params = {
        TableName: "Users",
        Item:{
            email: "[email protected]",
            password: "123",
            verified: false,
            registration: (new Date()).getTime(),
        }
    };

    // Create the user.

    docClient.put(params, function(err, data)
    {
        if (err)
        {
            context.fail("Put failed...");
            return;
        }

        var params = {
            TableName: "Users",
            Key: { email : "[email protected]" },
            AttributeUpdates: {
                verified: {
                    Action: "PUT",
                    Value: true
                }
            }
        };

        // Update the user.
        docClient.update(params, function(err, data)
        {
            if (err)
            {
                console.log(JSON.stringify(err));
                context.fail(JSON.stringify(err));
                return;
            }
            context.succeed("User successfully updated.");
        });


    });

};

Do you have any idea of what could be wrong in my code?

7 Answers 7

145

You are only providing half of your primary key. Your primary key is a combination of the partition key and range key. You need to include the range key in your Key attribute in the update parameters.

Sign up to request clarification or add additional context in comments.

9 Comments

It works, thank you! But is it possible to have only the email address as primary key ?
Yes it is possible to have only email address as primary key. docs.aws.amazon.com/amazondynamodb/latest/developerguide/…
Maybe typos in key name, it happened for me
If you still want to query by PK only, you have to use 'query', not 'get' method. In this case you can provide KeyConditionExpression: 'PK = xxx' only.
I don't have a range key in my table, and I am providing the partition key, but getting this error when I'm calling deleteItem. Are there any other cases that may cause this error?
|
26

For others who have faced the same challenge and the issue is not fixed by above answers, it is always better to double check the data type of the value being updated, in my case the primary key was expecting a Number and I was trying to update with a string. Silly me

1 Comment

I also had a silly issue. My table was created with a composite key (i.e. a primary key AND a sort key). When in reality, I only wanted a primary key experience. Lesson learned--plan ahead!
7

My issue was with the Node SDK for deletes, where the documentation says to provide in format:

... {Key: {'id': {S: '123'}}} ...

Which does not appear to work with the aws-sdk ^2.1077.0. This seems to work:

... {Key: {'id': '123'}} ...

2 Comments

You saved me from another day of debugging thank you!
Same issue here -- thanks! Perhaps worth mentioning this is specifically for the BatchWriteItem api.
2

For the error,

The provided key element does not match the schema

There could be two possible problems here:

  1. You are only providing half of your primary key. For the primary key, you must provide all of the attributes. For example, with a simple primary key, you only need to provide a value for the partition key. For a composite primary key, you must provide values for both the partition key and the sort key.
  2. Field's value should have a proper data type as per the table. It is always better to double-check the data type of the value being passed. Maybe, you have defined the primary key as a Number and you are passing a string value in the getItem call.

Hope it helps.

Please add more if there could be other possible reasons.

Comments

1

My checklist when facing this issue:

  1. Check that the name and type of your key correspond to what you have in the database.
  2. Use corresponding attributes to make it explicit. E.g. use @DynamoDBHashKey(attributeName = "userId") in Java to indicate the partition key named userId.
  3. Ensure that only one field or getter marked as partition key in your class.

Please, add more if you know in the comments.

Comments

1

I was doing BatchGetItem, then streamed it to BatchWriteItem (Delete). DeleteItem didn't like it got all attributes from the object instead of only partition and sort key.

Gathering all answers:

  • mismatch in an attribute name
  • mismatch in attribute type
  • half key provided
  • unnecessary additional keys

Comments

1
  • assuming you are using "@aws-sdk/client-dynamodb" in NodeJS

  • if you have both sort key(ex. post_id) and range key(ex. user_id) in your table(ex. UserPostTable), and if you are updating this table with other attribute(for example image_url) then.

  • you need to specify both sort key and range key as well

      const updateParams = {
    TableName: process.env.TABLE_NAME,
    Key: {
      post_id: { S: post_id },
      user_id: { S: user_id },
    },
    UpdateExpression: "SET image_url = :url",
    ExpressionAttributeValues: { ":url": { S: image_url } },};const updateCommand = new UpdateItemCommand(updateParams);
    

Comments

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service and acknowledge you have read our privacy policy.

Start asking to get answers

Find the answer to your question by asking.

Ask question

Explore related questions

See similar questions with these tags.