Skip to content

UpdateItem on Cassandra returns 500 when a secondary-index key is set to an empty value #410

Description

@LeeroyHannigan

UpdateItem on Cassandra returns 500 when a secondary-index key is set to an empty value

What happens

On the Cassandra backend, an UpdateItem that sets a global secondary index key attribute to an empty binary (or empty string) returns HTTP 500 InternalServerError. The service, the SQLite backend, and the PostgreSQL backend (after #409) return HTTP 400 ValidationException with:

One or more parameter values are not valid. The update expression attempted to update a secondary index key to a value that is not supported. The AttributeValue for a key attribute cannot contain an empty binary value. IndexName: <name>, IndexKey: <attr>

Why

Cassandra's PutItem path validates index-key types and emptiness on the item before writing (crates/storage-cassandra/src/data/put_get_item.rs, the validate_index_keys call). The standalone UpdateItem path (crates/storage-cassandra/src/data/update_item.rs, after apply_update_validated and the item-size check) and the transacted Update path (crates/storage-cassandra/src/data/transactions.rs) do not run that check on the post-update item. The empty-binary key then reaches the write and fails internally rather than being rejected up front.

Repro

With a Cassandra-backed server and a table carrying a GSI whose key is a binary attribute bidx:

UpdateItem { Key: {...}, UpdateExpression: "SET bidx = :empty", ExpressionAttributeValues: {":empty": {"B": ""}} }

Observed: HTTP 500 InternalServerError. Expected: HTTP 400 ValidationException with the message above.

tests/test_item_size_at_limit.py::TestEmptyBinaryIndexKeyOnUpdate::test_update_refuses_empty_binary_index_key asserts the service behaviour and is skipped on Cassandra today (and on MongoDB, which should be checked for the same gap); it covers this case once fixed.

Fix

Run the post-update item through the same index-key validation the Cassandra PutItem path already uses, on both the standalone UpdateItem path and the transacted Update path, after the update actions are applied. This mirrors what #409 did for the PostgreSQL standalone UpdateItem path, which reused validate_index_key_types and validate_index_key_not_empty (the UpdateExpression empty-value context). The wrong-type case should be confirmed against the service at the same time, since the put path checks both type and emptiness.

Severity

Wrong status class (500 instead of 400) and no validation message, so a client cannot tell a rejected request from a server fault. Data plane, Cassandra backend only.

Activity

  1. added a commit that references this issue on Oct 20, 2026
    701bf4a
  2. self-assigned this
    on Oct 22, 2026
  3. added a commit that references this issue on Oct 26, 2026
    3b41218
  4. added this to the 1.0 milestone on Oct 27, 2026
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Metadata

Metadata

Assignees

Labels

backend:cassandraRelated to the Cassandra backend specifically

Type

No type

Projects

No projects

    Relationships

    None yet

    Development

    No branches or pull requests

    Issue actions