Francesco
Francesco

Reputation: 977

How to remove an item from a StringSet in DynamoDB?

I have this table in DynamoDB:

{
  "lectures": {
    "L": [
      {
        "M": {
          "lecture_id": {
            "S": "CC0"
          },
          "students": {
            "SS": [
              "",
              "test"
            ]
          }
        }
      }
   ]
}

I want to remove "test" from the StringSet students.

Looking at the docs, I tried this code:

function removeLecture(event){
    const students = 'lectures[' + Number.parseInt(event.lecture_id) + '].students';
    console.log('test: ' + students);
    const params = {
        TableName: 'TableName',
        Key: {
            'Key': key
        },
        UpdateExpression: `DELETE ${students} :student`,
        ExpressionAttributeValues: {
            ':student' : {
                'SS': event.student
            }
        },
        ReturnValues : 'UPDATED_NEW'
    }
    
    return ddb.update(params).promise();
}

Anyway, I receive a ValidationException:

START RequestId: 3857a2c2-23a8-4c0c-b080-516669c6e615 Version: $LATEST
2021-08-18T10:21:39.078Z    3857a2c2-23a8-4c0c-b080-516669c6e615    INFO    test: lectures[0].students
2021-08-18T10:21:39.831Z    3857a2c2-23a8-4c0c-b080-516669c6e615    INFO    ValidationException: Invalid UpdateExpression: Incorrect operand type for operator or function; operator: DELETE, operand type: MAP, typeSet: ALLOWED_FOR_DELETE_OPERAND

I have also tried with ExpressionAttributeValues: {':student' : event.student}, but still I receive the same error with STRING instead of MAP.

How can I remove the String from the StringSet?

Upvotes: 2

Views: 1893

Answers (1)

Francesco
Francesco

Reputation: 977

After long trying, I discovered the function createSet() of the AWS.DynamoDB.DocumentClient class. I tried to use it, and it works. So the answer is: if you want to remove a String from a StringSet, you have to create another StringSet and remove the latter from the original.

Here is the code:

function removeLecture(event){
    const students = 'lectures[' + Number.parseInt(event.lecture_id) + '].students';
    console.log('test: ' + students);
    const params = {
        TableName: 'TableName',
        Key: {
            'Key': key
        },
        UpdateExpression: `DELETE ${students} :student`,
        ExpressionAttributeValues: {
            ':student' : ddb.createSet(event.student)
        },
        ReturnValues : 'UPDATED_NEW'
    }
    
    return ddb.update(params).promise();
}

Upvotes: 2

Related Questions