This is an example of items I want to add in DynamoDB:
Item 1:
user :{'Id': '123456789', 'Name': 'user2', 'Keys': [{'KeyId': '987654321', 'keyStatus': 'Active'}]}
Item 2:
user :{'Id': '59940303', 'Name': 'user2', 'Keys': [{'KeyId': '987654321', 'keyStatus': 'Active'},{'KeyId': '6382920434', 'keyStatus': 'Active'}]}
As you can see the Keys section contains a list of dicts. Item1
contains one dict, item2
contains two dicts.
How can I add this in DynamoDB?
This works (without the list of dicts):
table = dynamodb_resource.Table("name")
table.update_item(
TableName=table_name,
Key={"Id": user["Id"]},
UpdateExpression="set Name=:n",
ExpressionAttributeValues={
":n": user["Name"]
},
ReturnValues="UPDATED_NEW"
But How should I update this for a list of dicts?
CodePudding user response:
Updates work fine for me as follows:
table.update_item(
Key={"id": user["Id"]},
UpdateExpression="set #n=:n, #k=:k",
ExpressionAttributeValues={":n": user["Name"], ":k": user["Keys"]},
ExpressionAttributeNames={"#n": "Name", "#k": "Keys"},
ReturnValues="UPDATED_NEW",
)
CodePudding user response:
Here's a working example:
from boto3.dynamodb.conditions import Key
users = [
{"Id": "A123456789", "Name": "user1", "Keys": [{"KeyId": "A987654321", "keyStatus": "Active"}],},
{ "Id": "B123456789", "Name": "user2", "Keys": [{"KeyId": "Z987654321", "keyStatus": "Active"},{"KeyId": "C6382920434", "keyStatus": "Active"},],},
]
# create the two records
for user in users:
tbl.update_item(
Key={
"Id": user["Id"],
},
UpdateExpression="set #name=:n, #keys=:k",
ExpressionAttributeValues={
":n": user["Name"],
":k": user["Keys"],
},
ExpressionAttributeNames={"#name": "Name", "#keys": "Keys"}, # fields are reserved keywords! we must use substitution
ReturnValues="UPDATED_NEW",
)
# query a record
res = tbl.query(KeyConditionExpression=Key('Id').eq('B123456789'))
print(res["Items"][0])
# {'Id': 'B123456789', 'Keys': [{'keyStatus': 'Active', 'KeyId': 'Z987654321'}, {'keyStatus': 'Active', 'KeyId': 'C6382920434'}],}
# update a nested attribute - set the first key status to inactive
tbl.update_item(
Key={"Id": "B123456789"},
UpdateExpression="set #keys[0].#status=:s",
ExpressionAttributeValues={
":s": "Inactive",
},
ExpressionAttributeNames={"#keys": "Keys", "#status": "keyStatus"},
ReturnValues="UPDATED_NEW",
)
# query the updated record again
res = tbl.query(KeyConditionExpression=Key('Id').eq('B123456789'))
print(res["Items"][0])
# {'Id': 'B123456789', 'Keys': [{'KeyId': 'Z987654321', 'keyStatus': 'Inactive'}, {'keyStatus': 'Active', 'KeyId': 'C6382920434'}], 'Name': 'user2'}