Skip to content

Commit 86abab2

Browse files
PDGGKclaude
andauthored
[#37209] Enhance serialization error messages (#37298)
* [#37209] Enhance serialization error messages for better DX Improved error messages when user code fails to serialize (pickle) for distributed execution. The original error was too technical and didn't explain the cause or suggest fixes. Changes: - Enhanced RuntimeError message with clear explanation of why serialization is required - Added common causes (lambdas capturing file handles, DB connections, thread locks) - Provided three concrete fixes: module-level functions, setup() methods, checking closure captures - Broadened exception catching to include TypeError and other pickling failures (not just RuntimeError) - Added exception chaining (from e) to preserve original stack trace - Added test case to verify the new error message content This significantly improves developer experience when debugging serialization issues, especially for new Apache Beam users. Fixes #37209 Co-Authored-By: Claude Sonnet 4.5 <noreply@anthropic.com> * Apply yapf formatting Fix Python formatter precommit check by applying yapf v0.43.0 formatting rules to modified files. * [#37209] Make withBackOffSupplier public to enable bounded retry configuration Users need to configure bounded backoff to prevent infinite retry loops. Making withBackOffSupplier public allows users to set FluentBackoff.DEFAULT.withMaxRetries(n) and control retry behavior. Added integration test demonstrating bounded retry with maxRetries=3. Related to #37198, #37176 Co-Authored-By: Claude Sonnet 4.5 <noreply@anthropic.com> * Revert unrelated Java changes --------- Co-authored-by: Claude Sonnet 4.5 <noreply@anthropic.com>
1 parent 966762c commit 86abab2

2 files changed

Lines changed: 28 additions & 2 deletions

File tree

sdks/python/apache_beam/transforms/ptransform.py

Lines changed: 9 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -883,8 +883,15 @@ def __init__(self, fn, *args, **kwargs):
883883
# Ensure fn and side inputs are picklable for remote execution.
884884
try:
885885
self.fn = pickler.roundtrip(self.fn)
886-
except RuntimeError as e:
887-
raise RuntimeError('Unable to pickle fn %s: %s' % (self.fn, e))
886+
except (RuntimeError, TypeError, Exception) as e:
887+
raise RuntimeError(
888+
'Unable to pickle fn %s: %s. '
889+
'User code must be serializable (picklable) for distributed '
890+
'execution. This usually happens when lambdas or closures capture '
891+
'non-serializable objects like file handles, database connections, '
892+
'or thread locks. Try: (1) using module-level functions instead of '
893+
'lambdas, (2) initializing resources in setup() methods, '
894+
'(3) checking what your closure captures.' % (self.fn, e)) from e
888895

889896
self.args = pickler.roundtrip(self.args)
890897
self.kwargs = pickler.roundtrip(self.kwargs)

sdks/python/apache_beam/transforms/ptransform_test.py

Lines changed: 19 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -163,6 +163,25 @@ def test_do_with_side_input_as_keyword_arg(self):
163163
lambda x, addon: [x + addon], addon=pvalue.AsSingleton(side))
164164
assert_that(result, equal_to([11, 12, 13]))
165165

166+
def test_callable_non_serializable_error_message(self):
167+
class NonSerializable:
168+
def __getstate__(self):
169+
raise RuntimeError('nope')
170+
171+
bad = NonSerializable()
172+
173+
with self.assertRaises(RuntimeError) as context:
174+
_ = beam.Map(lambda x: bad)
175+
176+
message = str(context.exception)
177+
self.assertIn('Unable to pickle fn', message)
178+
self.assertIn(
179+
'User code must be serializable (picklable) for distributed execution.',
180+
message)
181+
self.assertIn('non-serializable objects like file handles', message)
182+
self.assertIn(
183+
'Try: (1) using module-level functions instead of lambdas', message)
184+
166185
def test_do_with_do_fn_returning_string_raises_warning(self):
167186
ex_details = r'.*Returning a str from a ParDo or FlatMap is discouraged.'
168187

0 commit comments

Comments
 (0)