Reputation: 2563
I have a DynamoDB table with a schema similar to the below. I want to essentially run an "upsert" function on the jobs
attribute that will either add the jobs attribute or append to the list.
When executing my code, I am getting an error message:
An error occurred (ValidationException) when calling the UpdateItem operation: Invalid UpdateExpression: Incorrect operand type for operator or function; operator or function: list_append, operand type: M
Schema:
{
"jobs": [
{
"event_id": "event_id",
"job_map": [
{
"key1": "val1",
"key2": "val2"
}
],
"job_start": "time_stamp"
}
],
"p_key": "some_id"
}
Example/documentation:
Sample code:
p_key_string = 'some_id'
event_id = '123'
job_start = 'timestamp_string'
task_map = []
for item in items:
task_map.append({
"M": {
'key1': {"S": item.get('val1')},
'key2': {"S": item.get('val2')}
}
})
args = {
'Key': {
'p_key': p_key_string
},
'UpdateExpression': "SET p_key = :p_key, #ri = list_append(#ri, :vals)",
'ConditionExpression': "attribute_not_exists(p_key) OR p_key = :p_key",
'ExpressionAttributeNames': {
"#ri": "jobs"
},
'ExpressionAttributeValues': {
':p_key': p_key_string,
':vals': {
"L": [{
"M": {
"event_id": { "S": event_id},
"job_start": { "S": job_start},
'job_map': { "L": task_map}
}
}]
}
}
}
dynamo_client.update_item(**args)
Based on the error I tried a simpler query, but actually got the same error.
...
':vals': {
"L": [
{ "S": event_id},
{ "S": job_start}
]
}
...
So really not sure what I am missing.
Upvotes: 1
Views: 2829
Reputation: 141
If you are using the Document Client then you don't need to use type operands. You can write the objects in native JS. I was running into a similar issue and followed @getglad's advice to remove the type declarations and the transactions worked.
Upvotes: 0
Reputation: 4616
Is dynamodb_client
actually a Table
object and not the regular dynamodb client?
The Table
object will automatically convert the dynamodb data format into native data types while the regular DynamoDB client does not.
Upvotes: 0
Reputation: 2563
I'm not entirely sure I understand why, but by removing the data type declarations, I was able to move past the error. The code above had some additional errors, but the below changes appear to be working for me.
...
task_map.append({
'key1': 'val1',
'key2': 'val2'
})
...
...
args = {
'Key': {
'p_key': p_key_string
},
'UpdateExpression': "SET jobs = list_append(if_not_exists(jobs, :empty_list), :vals)",
'ExpressionAttributeValues': {
':vals': [{
"event_id": event_id,
"job_start": job_start,
"job_map": task_map
}],
":empty_list": []
}
}
...
Upvotes: 1