ValidationException: Invalid UpdateExpression
TL;DR — Your UpdateExpression is malformed. Nine times out of ten it's a reserved keyword (like status, name, size) used directly — swap it for a #placeholder in ExpressionAttributeNames. The message names the exact token.
What it means
Typical messages:
ValidationException: Invalid UpdateExpression: Attribute name is a reserved keyword; reserved keyword: status
ValidationException: Invalid UpdateExpression: Syntax error; token: "=", near: "SET status ="
ValidationException: Invalid UpdateExpression: An expression attribute value used in expression is not defined; attribute value: :sDynamoDB parses the expression string and rejects anything that isn't valid grammar or references an undefined placeholder.
Why it happens
- Reserved keyword used raw. DynamoDB has hundreds of reserved words —
status,name,size,count,data,year. Used directly in an expression they cause a syntax error. The reserved words checker tests your attribute names against the full list and emits the alias map. - Missing
ExpressionAttributeNamesentry for a#nameyou referenced. - Missing
ExpressionAttributeValuesentry for a:valueyou referenced. - Wrong verb grammar — mixing clauses incorrectly (
SET,REMOVE,ADD,DELETEeach have their own syntax), or a stray=. - Attribute name with special characters (dots, dashes) used without a placeholder.
How to fix it
- Alias every attribute name through
ExpressionAttributeNames(#status) — it sidesteps the reserved-word list entirely, so aliasing everything is a safe habit. - Define every
:valueyou reference inExpressionAttributeValues. - Use the right clause.
SETto write/overwrite,REMOVEto delete an attribute,ADDfor atomic number/set increments,DELETEto remove from a set. - Run the reserved-word check before you ship. Paste your attribute names into the reserved words checker — it flags every name on the AWS list and prints the
#aliasmap you need. - Build the expression once, copy everywhere. A hand-edited string drifts; generate the full
UpdateExpressionplus both attribute maps from one source so placeholders stay paired.
Example
import {DynamoDBClient} from '@aws-sdk/client-dynamodb';
import {DynamoDBDocumentClient, UpdateCommand} from '@aws-sdk/lib-dynamodb';
const doc = DynamoDBDocumentClient.from(new DynamoDBClient({}));
await doc.send(
new UpdateCommand({
TableName: 'Orders',
Key: {pk: 'ORDER#1'},
// #status aliases the reserved word "status"
UpdateExpression: 'SET #status = :s, updatedAt = :t',
ExpressionAttributeNames: {'#status': 'status'},
ExpressionAttributeValues: {':s': 'SHIPPED', ':t': Date.now()}
})
);Check first in DynoTable
When an update fails in your app, reproduce it in DynoTable before you change production code. Open the table with ⌘K, select the item, and use the inline update editor — DynoTable aliases reserved attribute names automatically and shows the generated UpdateExpression with both attribute maps. Staging (⌘S) lets you preview the edit and catch syntax errors before commit.
For batch fixes, paste the failing expression into the Expression Builder and compare its output to what your SDK sends. Profile switching (⌘P) keeps test runs on the same account as the error; use Test Connection on Settings → Profiles to confirm the profile matches. See Connect to AWS and Install for profile setup. Cross-check attribute names in the reserved words checker when the error names a specific token like status or data. Aliasing every attribute name — not just reserved ones — is a safe habit that prevents this class of error entirely.
Sources
- Using update expressions in DynamoDB (verified 2026-07-13)
- Reserved words in DynamoDB (verified 2026-07-13)
Related errors
- ExpressionAttributeValues contains invalid value
- ValidationException (overview)
- Code example: UpdateItem in Node.js · in Python (boto3) — a valid UpdateExpression with #names and :values.
- Learn: Update expressions · Expression names & values
References
- Using update expressions in DynamoDB — Amazon DynamoDB Developer Guide
- Reserved words in DynamoDB — Amazon DynamoDB Developer Guide
- Expression attribute names (aliases) in DynamoDB — Amazon DynamoDB Developer Guide
Last verified 2026-07-13 against the official AWS documentation linked above.