You signed in with another tab or window. Reload to refresh your session.You signed out in another tab or window. Reload to refresh your session.You switched accounts on another tab or window. Reload to refresh your session.Dismiss alert
execute_range_query_pipeline's dual-population handling (added in #582, fixing #580) fetches and merges keys_query once, anchored at the range's end, and reuses that single snapshot for every output timestamp in the range. If the key set changes partway through the queried interval — a label combination first appears, or stops appearing — every step still uses the final snapshot: keys get phantom samples before they existed, or keep appearing after they stopped, instead of reflecting the key set as it actually was at each step's time.
Please also check other parts of the codebase for the same class of bug: any code path that fetches/merges a value or key set once and then reuses it across multiple output points in a time series, where the underlying set can legitimately change over that span. handle_binary_expr_range_promql's per-arm range context (build_arm_range_context, which calls the same finish_range_context/keys-snapshot logic per arm) is one likely candidate worth checking specifically.
Related: keys_query window scoping is instant-anchored, not range-aware
finish_range_context widens values_query to [start-lookback, end] for a range query, but clones keys_query unchanged — its window is still computed from a single instant (create_keys_query_params, using only end_timestamp), which is wrong for both key aggregation types, in opposite directions:
SetAggregator ("latest window only"): keys window is [end-window_size, end] — just the range's last window. Since the range loop iterates merged_keys (not all_data), a label with real values earlier in the range but absent from that final window's key snapshot never gets iterated at all — its whole history silently disappears from the output, with no error.
DeltaSetAggregator ("all keys since start"): keys window is [0, end]. This is actually necessary, not excessive — reconstructing the current key set requires replaying every delta bucket back to the initial full-snapshot window, and merge_with does reconcile add/remove deltas correctly. (A separate, unrelated bug in this accumulator's get_keys() is tracked on PR fix(query-engine): range queries expand keys_query and merge same-timestamp buckets #582's review thread, not here.)
Fixing this properly likely means fetching/merging keys per output step, scoped consistently with each step's own window, rather than once at the range's end — which would fix both this scoping mismatch and the snapshot-staleness problem above as the same fix.
execute_range_query_pipeline's dual-population handling (added in #582, fixing #580) fetches and mergeskeys_queryonce, anchored at the range'send, and reuses that single snapshot for every output timestamp in the range. If the key set changes partway through the queried interval — a label combination first appears, or stops appearing — every step still uses the final snapshot: keys get phantom samples before they existed, or keep appearing after they stopped, instead of reflecting the key set as it actually was at each step's time.Please also check other parts of the codebase for the same class of bug: any code path that fetches/merges a value or key set once and then reuses it across multiple output points in a time series, where the underlying set can legitimately change over that span.
handle_binary_expr_range_promql's per-arm range context (build_arm_range_context, which calls the samefinish_range_context/keys-snapshot logic per arm) is one likely candidate worth checking specifically.Related: keys_query window scoping is instant-anchored, not range-aware
finish_range_contextwidensvalues_queryto[start-lookback, end]for a range query, but cloneskeys_queryunchanged — its window is still computed from a single instant (create_keys_query_params, using onlyend_timestamp), which is wrong for both key aggregation types, in opposite directions:SetAggregator("latest window only"): keys window is[end-window_size, end]— just the range's last window. Since the range loop iteratesmerged_keys(notall_data), a label with real values earlier in the range but absent from that final window's key snapshot never gets iterated at all — its whole history silently disappears from the output, with no error.DeltaSetAggregator("all keys since start"): keys window is[0, end]. This is actually necessary, not excessive — reconstructing the current key set requires replaying every delta bucket back to the initial full-snapshot window, andmerge_withdoes reconcile add/remove deltas correctly. (A separate, unrelated bug in this accumulator'sget_keys()is tracked on PR fix(query-engine): range queries expand keys_query and merge same-timestamp buckets #582's review thread, not here.)Fixing this properly likely means fetching/merging keys per output step, scoped consistently with each step's own window, rather than once at the range's
end— which would fix both this scoping mismatch and the snapshot-staleness problem above as the same fix.