Skip to content

Commit ed05984

Browse files
Add table name to error message for transactional operations (#835)
1 parent c7cbd47 commit ed05984

File tree

2 files changed

+21
-3
lines changed

2 files changed

+21
-3
lines changed

pynamodb/connection/base.py

Lines changed: 11 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -427,11 +427,19 @@ def _make_api_call(self, operation_name, operation_kwargs):
427427
'request_id': headers.get('x-amzn-RequestId')
428428
}
429429

430-
if 'RequestItems' in operation_kwargs:
430+
if REQUEST_ITEMS in operation_kwargs:
431431
# Batch operations can hit multiple tables, report them comma separated
432-
verbose_properties['table_name'] = ','.join(operation_kwargs['RequestItems'])
432+
verbose_properties['table_name'] = ','.join(operation_kwargs[REQUEST_ITEMS])
433+
elif TRANSACT_ITEMS in operation_kwargs:
434+
# Transactional operations can also hit multiple tables, or have multiple updates within
435+
# the same table
436+
table_names = []
437+
for item in operation_kwargs[TRANSACT_ITEMS]:
438+
for op in item.values():
439+
table_names.append(op[TABLE_NAME])
440+
verbose_properties['table_name'] = ','.join(table_names)
433441
else:
434-
verbose_properties['table_name'] = operation_kwargs.get('TableName')
442+
verbose_properties['table_name'] = operation_kwargs.get(TABLE_NAME)
435443

436444
try:
437445
raise VerboseClientError(botocore_expected_format, operation_name, verbose_properties)

tests/integration/test_transaction_integration.py

Lines changed: 10 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -124,6 +124,7 @@ def test_transact_write__error__idempotent_parameter_mismatch(connection):
124124
with TransactWrite(connection=connection, client_request_token=client_token) as transaction:
125125
transaction.save(User(3))
126126
assert get_error_code(exc_info.value) == IDEMPOTENT_PARAMETER_MISMATCH
127+
assert User.Meta.table_name in exc_info.value.cause.MSG_TEMPLATE
127128

128129
# ensure that the first request succeeded in creating new users
129130
assert User.get(1)
@@ -143,6 +144,9 @@ def test_transact_write__error__different_regions(connection):
143144
transact_write.save(BankStatement(1))
144145
transact_write.save(User(1))
145146
assert get_error_code(exc_info.value) == RESOURCE_NOT_FOUND
147+
assert DifferentRegion.Meta.table_name in exc_info.value.cause.MSG_TEMPLATE
148+
assert BankStatement.Meta.table_name in exc_info.value.cause.MSG_TEMPLATE
149+
assert User.Meta.table_name in exc_info.value.cause.MSG_TEMPLATE
146150

147151

148152
@pytest.mark.ddblocal
@@ -158,6 +162,8 @@ def test_transact_write__error__transaction_cancelled__condition_check_failure(c
158162
transaction.save(BankStatement(1), condition=(BankStatement.user_id.does_not_exist()))
159163
assert get_error_code(exc_info.value) == TRANSACTION_CANCELLED
160164
assert 'ConditionalCheckFailed' in get_error_message(exc_info.value)
165+
assert User.Meta.table_name in exc_info.value.cause.MSG_TEMPLATE
166+
assert BankStatement.Meta.table_name in exc_info.value.cause.MSG_TEMPLATE
161167

162168

163169
@pytest.mark.ddblocal
@@ -170,6 +176,7 @@ def test_transact_write__error__multiple_operations_on_same_record(connection):
170176
transaction.condition_check(BankStatement, 1, condition=(BankStatement.user_id.exists()))
171177
transaction.update(BankStatement(1), actions=[(BankStatement.balance.add(10))])
172178
assert get_error_code(exc_info.value) == VALIDATION_EXCEPTION
179+
assert BankStatement.Meta.table_name in exc_info.value.cause.MSG_TEMPLATE
173180

174181

175182
@pytest.mark.ddblocal
@@ -343,6 +350,7 @@ def test_transaction_write_with_version_attribute_condition_failure(connection):
343350
transaction.save(Foo(21))
344351
assert get_error_code(exc_info.value) == TRANSACTION_CANCELLED
345352
assert 'ConditionalCheckFailed' in get_error_message(exc_info.value)
353+
assert Foo.Meta.table_name in exc_info.value.cause.MSG_TEMPLATE
346354

347355
with pytest.raises(TransactWriteError) as exc_info:
348356
with TransactWrite(connection=connection) as transaction:
@@ -354,6 +362,7 @@ def test_transaction_write_with_version_attribute_condition_failure(connection):
354362
)
355363
assert get_error_code(exc_info.value) == TRANSACTION_CANCELLED
356364
assert 'ConditionalCheckFailed' in get_error_message(exc_info.value)
365+
assert Foo.Meta.table_name in exc_info.value.cause.MSG_TEMPLATE
357366
# Version attribute is not updated on failure.
358367
assert foo2.version is None
359368

@@ -362,3 +371,4 @@ def test_transaction_write_with_version_attribute_condition_failure(connection):
362371
transaction.delete(foo2)
363372
assert get_error_code(exc_info.value) == TRANSACTION_CANCELLED
364373
assert 'ConditionalCheckFailed' in get_error_message(exc_info.value)
374+
assert Foo.Meta.table_name in exc_info.value.cause.MSG_TEMPLATE

0 commit comments

Comments
 (0)