apache/beam · error · ValueError
No window for %s
Error message
No window for %s
What it means
MergingTriggerState.get_window looks up which window owns a given window_id by scanning window_ids and raises ValueError('No window for %s') when the id is not registered. This indicates the caller is using a stale or foreign window id that the state driver never assigned.
Source
Thrown at sdks/python/apache_beam/transforms/trigger.py:1191
def merge(self, to_be_merged, merge_result):
for window in to_be_merged:
if window != merge_result:
if window in self.window_ids:
if merge_result in self.window_ids:
merge_window_ids = self.window_ids[merge_result]
else:
merge_window_ids = self.window_ids[merge_result] = []
merge_window_ids.extend(self.window_ids.pop(window))
self._persist_window_ids()
def known_windows(self):
return list(self.window_ids)
def get_window(self, window_id):
for window, ids in self.window_ids.items():
if window_id in ids:
return window
raise ValueError('No window for %s' % window_id)
def _get_id(self, window):
if window in self.window_ids:
return self.window_ids[window][0]
window_id = self._get_next_counter()
self.window_ids[window] = [window_id]
self._persist_window_ids()
return window_id
def _get_ids(self, window):
return self.window_ids.get(window, [])
def _get_next_counter(self):
if not self.window_ids:
self.counter = 0
elif self.counter is None:
self.counter = max(k for ids in self.window_ids.values() for k in ids)View on GitHub (pinned to 12126d8942)
Solutions
- Obtain window ids only from the state driver (window_ids / _get_id) and never invent or cache them across cleanup.
- Clear any stored window ids when windows are output/garbage-collected; re-derive them for late data.
- Add a lookup guard before use: check the id exists in the driver's window_ids before calling APIs that resolve it.
Example fix
// before
state.get_state(window_id, tag) # window_id from an old firing
// after
if window_id in [i for ids in state.window_ids.values() for i in ids]:
state.get_state(window_id, tag) Defensive patterns
Strategy: validation
Validate before calling
known_ids = {i for ids in state.window_ids.values() for i in ids}
assert window_id in known_ids, f'stale window_id {window_id}' Type guard
def has_window_id(state, window_id):
return any(window_id in ids for ids in state.window_ids.values()) Try / catch
try:
window = state.get_window(window_id)
except ValueError:
window = None # window was cleaned up; skip stale callback Prevention
- Never cache window ids across pane firings or bundle retries.
- Clear stored ids when windows are output/garbage-collected.
- Resolve ids via the driver's own window_ids mapping only.
When it happens
Trigger: Calling get_state/clear_state or trigger callbacks with a window_id that was never created via _get_id, or one already removed when windows were cleaned up after being fired/garbage-collected.
Common situations: Custom trigger drivers holding window ids across pane firings after the state was cleaned; timers firing for windows already garbage-collected; retaining ids from a previous bundle/retry.
Understand the failure class
Background: 'Could not be found', 'does not exist', 'not found in database': the resource-not-found family when an ID, slug, key, or URI lookup comes back empty — this error's family across 20 libraries.
Related errors
- Merging requested for non-mergeable state tag: %r.
- Invalid tag.
- {module} is not registered for pickle by value
- PCollection not available, please run the pipeline.
- input is already set.
AI-assisted analysis of apache/beam@12126d8942 (2026-09-13).
Data as JSON: /api/errors/8827890613154533.
Report an issue: GitHub.