apache/beam · error · TypeError
DoFn {self!r} yields element from both process and process_b
Error message
DoFn {self!r} yields element from both process and process_batch, but they have mismatched output typehints:
process: {process_type_hints.output_types}
process_batch: {process_batch_type_hints.output_types} What it means
When a DoFn defines both `process` and `process_batch` and both declare output type hints, Beam requires them to agree (core.py:814). Mismatched output typehints make the pipeline's inferred output type ambiguous, so default_type_hints raises this TypeError.
Source
Thrown at sdks/python/apache_beam/transforms/core.py:814
# process() produces batches, don't use it's output typehint
process_type_hints = process_type_hints.with_output_types_from(
typehints.decorators.IOTypeHints.empty())
if self._process_batch_yields_elements:
# process_batch() produces elements, *do* use it's output typehint
# First access the typehint
process_batch_type_hints = typehints.decorators.IOTypeHints.from_callable(
self.process_batch) or typehints.decorators.IOTypeHints.empty()
# Then we deconflict with the typehint from process, if it exists
if (process_batch_type_hints.output_types
!= typehints.decorators.IOTypeHints.empty().output_types):
if (process_type_hints.output_types
!= typehints.decorators.IOTypeHints.empty().output_types and
process_batch_type_hints.output_types
!= process_type_hints.output_types):
raise TypeError(
f"DoFn {self!r} yields element from both process and "
"process_batch, but they have mismatched output typehints:\n"
f" process: {process_type_hints.output_types}\n"
f" process_batch: {process_batch_type_hints.output_types}")
process_type_hints = process_type_hints.with_output_types_from(
process_batch_type_hints)
try:
process_type_hints = process_type_hints.strip_iterable()
except ValueError as e:
raise ValueError('Return value not iterable: %s: %s' % (self, e))
process_type_hints = process_type_hints.extract_tagged_outputs()
# Prefer class decorator type hints for backwards compatibility.
return get_type_hints(self.__class__).with_defaults(process_type_hints)
# TODO(sourabhbajaj): Do we want to remove the responsibility of these fromView on GitHub (pinned to 12126d8942)
Solutions
- Make the output type hints of `process` and `process_batch` consistent (same inner element type).
- Delete the now-redundant `process` method if you only use `process_batch`.
- Remove explicit output hints from one of the methods so only one source of truth exists.
Example fix
# before
class MyDoFn(DoFn):
def process(self, x) -> Iterable[str]: ...
def process_batch(self, batch) -> Iterator[List[int]]: ...
# after
class MyDoFn(DoFn):
def process(self, x) -> Iterator[str]: ...
def process_batch(self, batch) -> Iterator[List[str]]: ... Defensive patterns
Strategy: validation
Validate before calling
import inspect
from typing import get_type_hints
def check_matching_output_hints(dofn_cls):
if hasattr(dofn_cls, 'process') and hasattr(dofn_cls, 'process_batch'):
p = get_type_hints(dofn_cls.process).get('return')
pb = get_type_hints(dofn_cls.process_batch).get('return')
if p is not None and pb is not None and p != pb:
raise TypeError(f'process ({p}) and process_batch ({pb}) output hints differ') Type guard
def has_consistent_hints(cls) -> bool:
if not (hasattr(cls, 'process') and hasattr(cls, 'process_batch')):
return True
from typing import get_type_hints
return get_type_hints(cls.process).get('return') in (None, get_type_hints(cls.process_batch).get('return')) Try / catch
try:
hints = dofn.default_type_hints()
except TypeError as e:
if 'mismatched output typehints' in str(e):
logger.error('Align process/process_batch output hints: %s', e)
raise Prevention
- Keep only one of process/process_batch per DoFn when possible
- When migrating to batched processing, delete old process methods and their hints
- Write a smoke test that instantiates the DoFn and reads default_type_hints()
When it happens
Trigger: A DoFn subclass where `process` has e.g. @with_output_types(Iterable[str]) while `process_batch` is annotated/typed as returning batches of ints, and both output hint sets are non-empty and unequal.
Common situations: Migrating a DoFn from element-wise `process` to batched `process_batch` while leaving old type hints on `process`; annotations added incrementally by different contributors.
Understand the failure class
Background: Type mismatch errors: IllegalArgumentException, TypeError and type guards across 150 open-source libraries — this error's family across 150 libraries.
Related errors
- DoFn {self!r} yields batches from both process and process_b
- Unable to deterministically encode '%s' of type '%s', please
- text_splitter must be a LangChain TextSplitter
- Pipeline type checking is enabled, however no output type-hi
- A context manager constructor (not a fully constructed conte
AI-assisted analysis of apache/beam@12126d8942 (2026-09-13).
Data as JSON: /api/errors/c8a0d9a6b153e9fc.
Report an issue: GitHub.