apache/beam · error · TypeError
Chain at {identify_object(spec)} missing transforms property
Error message
Chain at {identify_object(spec)} missing transforms property. What it means
A 'chain' transform in Beam YAML is sugar for a composite whose transforms pass outputs to inputs implicitly. chain_as_composite raises this TypeError when the chain spec lacks the required 'transforms' property, since there is nothing to chain.
Source
Thrown at sdks/python/apache_beam/yaml/yaml_transform.py:926
scope.root) | scope.unique_name(spec, None) >> transform
def expand_chain_transform(spec, scope):
return expand_composite_transform(chain_as_composite(spec), scope)
def chain_as_composite(spec):
def is_not_output_of_last_transform(new_transforms, value):
return (
('name' in new_transforms[-1] and
value != new_transforms[-1]['name']) or
('type' in new_transforms[-1] and value != new_transforms[-1]['type']))
# A chain is simply a composite transform where all inputs and outputs
# are implicit.
spec = normalize_source_sink(spec)
if 'transforms' not in spec:
raise TypeError(
f"Chain at {identify_object(spec)} missing transforms property.")
has_explicit_outputs = 'output' in spec
composite_spec = dict(normalize_inputs_outputs(tag_explicit_inputs(spec)))
new_transforms = []
for ix, transform in enumerate(composite_spec['transforms']):
transform = dict(transform)
if any(io in transform for io in ('input', 'output')):
if (ix == 0 and 'input' in transform and 'output' not in transform and
is_explicitly_empty(transform['input'])):
# This is OK as source clause sets an explicitly empty input.
pass
else:
raise ValueError(
f'Transform {identify_object(transform)} is part of a chain. '
'Cannot define explicit inputs on chain pipeline')
if ix == 0:
if is_explicitly_empty(transform.get('input', None)):
passView on GitHub (pinned to 12126d8942)
Solutions
- Add a 'transforms' list with at least one transform to the chain spec.
- Fix YAML indentation so 'transforms:' is nested inside the chain transform block.
- If the transform is not actually a chain, change its 'type' to 'composite' or a leaf type.
- Validate the spec against the Beam YAML schema before running.
Example fix
// before
- name: MyPipeline
type: chain
input: source
// after
- name: MyPipeline
type: chain
input: source
transforms:
- type: MapToFields
config:
id: element.id Defensive patterns
Strategy: validation
Validate before calling
def check_chain_spec(spec):
if spec.get('type') == 'chain' and 'transforms' not in spec:
raise ValueError('Chain spec must include a transforms list') Type guard
def is_complete_chain(spec) -> bool:
return isinstance(spec, dict) and spec.get('type') == 'chain' and isinstance(spec.get('transforms'), list) Try / catch
try:
expand_transform(spec, scope)
except TypeError as e:
if 'missing transforms property' in str(e):
print('Add transforms list to the chain spec')
else:
raise Prevention
- Always include 'transforms:' in chain specs, even for single-step chains.
- Check YAML indentation so transforms nests inside the chain block.
- Use composite instead of chain when explicit io wiring is needed.
When it happens
Trigger: A spec like {type: chain, name: MyChain, input: ...} with no 'transforms:' list — typically from YAML indentation issues or building chain specs programmatically without the transforms key.
Common situations: YAML where 'transforms:' is mis-indented so it lands outside the chain mapping; hand-editing a pipeline and deleting the transforms list; generating specs in tooling that omits transforms for empty chains.
Understand the failure class
Background: "is required", "must be set", "missing required field": configuration validation errors across open-source libraries — this error's family across 36 libraries.
Related errors
- Unknown enrichment source: {enrichment_handler}
- f'Unknown parameters {spec.keys()}'
- "Cannot specify 'callable' with 'path' and 'name' for functi
- Missing type parameter for transform at {identify_object(spe
- error_handling config is not supported directly in the outpu
AI-assisted analysis of apache/beam@12126d8942 (2026-09-13).
Data as JSON: /api/errors/80242422f56395bc.
Report an issue: GitHub.