In this blog, we will learn how to update items in DynamoDB using Python and boto3. We will also learn how to remove attributes on an item, add a new element to a list in an item, and also how to increment the value of an attribute of an item in the DynamoDB table.

Prerequisites

For this blog, I have created a `users` table with email as a primary key. You can learn about how to create a DynamoDB table using AWS CDK in this blog. You will also need to attach permission for this table to your IAM user. You can learn about IAM users and permissions in how to create an IAM user and attach a policy to this blog.

Update Item Attribute in DynamoDB Table

Before we learn how to update items in the DynamoDB table, let us look at the `users` table.

Initial Item in DynamoDB table
Original state of the DynamoDB table before the update

In the above table, we have one item with the email `[email protected]` and the name `test 1`. Let us say we want to change the user’s name to something more real, like `John Doe`.

import boto3
from pprint import pprint

boto3.setup_default_session(profile_name="ah")

table_name = "users"
dynamodb_resource = boto3.resource("dynamodb")
users_table = dynamodb_resource.Table(table_name)


def update_item_exiting_attribute():
    response = users_table.update_item(
        Key={"email": "[email protected]"},
        UpdateExpression="set #name = :n",
        ExpressionAttributeNames={
            "#name": "name",
        },
        ExpressionAttributeValues={
            ":n": "John Doe",
        },
        ReturnValues="UPDATED_NEW",
    )
    pprint(response["Attributes"])

    # output
    # 'Attributes': {'name': 'John Doe'}

In the above code,

  1. We have created a resource for the `users` table.
  2. We select which item we want to update by passing the item’s key to the `Key` parameter in the `update_item` function.
  3. In `UpdateExpression`, we pass attributes we want to update along with their values. Note that we are passing attribute names and values as expressions.
  4. `ExpressionAttributeNames` contains a map of attribute names and their values from `UpdateExpression`.
  5. `ExpressionAttributeValues` contains a new value we want to set up for the attribute.

When we run this function, we can see that name of our user has been updated in the DynamoDB table.

DynamoDB table item after attribute update
DynamoDB table item after attribute update

Add an Attribute to an Item in the DynamoDB table

We can use the same update function to add new attributes to an item in the DynamoDB table. Let us look at the example code below.

def update_item_adding_new_attribute():
    response = users_table.update_item(
        Key={"email": "[email protected]"},
        UpdateExpression="set phone_number = :n",
        ExpressionAttributeValues={
            ":n": 9876543210,
        },
        ReturnValues="UPDATED_NEW",
    )
    pprint(response["Attributes"])

    # output
    # 'Attributes': {'phone_number': Decimal('9876543210')

In the above code, we have added a new `phone_number` attribute to the user item in the DynamoDB table. We can also validate this on the AWS console.

DynamoDB table item after adding new attribute
DynamoDB table item after adding a new attribute

Adding Element to a List in DynamoDB table Item

DynamoDB supports `Lists` for attributes. In our example, we have an attribute `payment_method`, which is a list of payment methods added by the user. Let us assume the user wants to add another payment method. We can add a new item to lists in the DynamoDB table using the `list_append` function, as shown in the following code.

def update_item_add_item_to_list():
    new_payment_method = [{"type": "card", "card_number": 1234123412341234}]
    response = users_table.update_item(
        Key={"email": "[email protected]"},
        UpdateExpression="set payment_methods = list_append(payment_methods, :n)",
        ExpressionAttributeValues={
            ":n": new_payment_method,
        },
        ReturnValues="UPDATED_NEW",
    )

    pprint(response["Attributes"])

    # output
    # {'payment_methods': [{'card_number': Decimal('1212121212121212'),
    #                       'type': 'card'},
    #                      {'card_number': Decimal('1234123412341234'),
    #                       'type': 'card'}]}

In the above code, we are appending a new element to the `payment_methods` list using the `list_append` function and assigning this new list to the `payment_methods` attribute.

add new elemnt to list in DynamoDB item
Added new element to list in DynamoDB item

Increment Attribute Value of Item in DynamoDB Table

Consider that there is some attribute for an item, and you want to add or subtract some value from it. How can we do this? One way is we read that Item first, then get the attribute’s exiting value, perform our addition/subtraction operation and then write that item back to the DynamoDB table. Too many steps, especially when there is a better alternative available for such kind of operations.

I have added a new attribute, `total_orders,` to the user item we have worked with.

item with total_orders_attribute
DynamoDB item with total_orders attribute

Consider an example case that a user has placed a new order, and we need to add 1 to this total_order attribute. We can use `UpdateExpression` to add value to total_orders and set that value to total_orders as shown in the below code.

def update_item_increment_value():
    response = users_table.update_item(
        Key={"email": "[email protected]"},
        UpdateExpression="set total_orders = total_orders + :n",
        ExpressionAttributeValues={
            ":n": 1,
        },
        ReturnValues="UPDATED_NEW",
    )
    pprint(response["Attributes"])

    # output
    # {'total_orders': Decimal('11')}

In the output of the above code, we can see that total_orders have been changed to 11. This can also be verified on the DynamoDB console. In the above code, we are adding 1. But you can add/subtract any value.

item after incrementing total_orders
DynamoDB item after incrementing total_orders

Removing Attribute from DynamoDB Item

We can also use the `update_item` function to remove attributes from DynamoDB items. The below code shows removing the phone number attribute, but you can use it to drop multiple attributes in a single call.

def update_item_remove_attribute():
    response = users_table.update_item(
        Key={"email": "[email protected]"},
        UpdateExpression="remove phone_number",
        ReturnValues="ALL_NEW",
    )

    pprint(response["Attributes"])

    # output
    # {'address': {'city': 'New York'},
    #  'email': '[email protected]',
    #  'is_pro_user': False,
    #  'name': 'John Doe',
    #  'payment_methods': [{'card_number': Decimal('1212121212121212'),
    #                       'type': 'card'},
    #                      {'card_number': Decimal('1234123412341234'),
    #                       'type': 'card'}],
    #  'total_orders': Decimal('11')}
item after removing attribute
DynamoDB item after removing attribute

Conclusion

In this blog, we have learned how to update an item in the DynamoDB table. DynamoDB update item function is much more versatile, and I hope the above examples will help you understand the different ways in which we can use it. In the next blog, we will learn how to delete items in the DynamoDB table. See you there.

Similar Posts