{"record":{"id":"4aea8851124f321d","repo":"apache/beam","slug":"main-input-is-global-windowed-in-dofn-v-but-side-input-v-is","errorCode":null,"errorMessage":"main input is global windowed in DoFn %v but side input %v is not, cannot map windows correctly. Consider re-windowing the side input PCollection before use","messagePattern":"main input is global windowed in DoFn (.+?) but side input (.+?) is not, cannot map windows correctly\\. Consider re-windowing the side input PCollection before use","errorType":"validation","errorClass":null,"httpStatus":null,"severity":"error","filePath":"sdks/go/pkg/beam/pardo.go","lineNumber":66,"sourceCode":"\t\tdoFnOpt = graph.NumMainInputs(graph.MainKv)\n\t} else if typex.IsCoGBK(col.Type()) {\n\t\tdoFnOpt = graph.CoGBKMainInput(len(col.Type().Components()))\n\t}\n\tfn, err := graph.NewDoFn(dofn, doFnOpt)\n\tif err != nil {\n\t\treturn nil, addParDoCtx(err, s)\n\t}\n\n\tin := []*graph.Node{col.n}\n\tinWfn := col.n.WindowingStrategy().Fn\n\tfor i, s := range side {\n\t\tsideNode := s.Input.n\n\t\tsideWfn := sideNode.WindowingStrategy().Fn\n\t\tif sideWfn.Kind == window.Sessions {\n\t\t\treturn nil, fmt.Errorf(\"error with side input %d in DoFn %v: PCollections using merging WindowFns are not supported as side inputs. Consider re-windowing the side input PCollection before use\", i, fn)\n\t\t}\n\t\tif (inWfn.Kind == window.GlobalWindows) && (sideWfn.Kind != window.GlobalWindows) {\n\t\t\treturn nil, fmt.Errorf(\"main input is global windowed in DoFn %v but side input %v is not, cannot map windows correctly. Consider re-windowing the side input PCollection before use\", fn, i)\n\t\t}\n\t\tif (sideWfn.Kind == window.GlobalWindows) && !sideNode.Bounded() {\n\t\t\t// TODO(https://github.com/apache/beam/issues/21596): Replace this warning with an error return when proper streaming test functions have been added.\n\t\t\tlog.Warnf(context.Background(), \"side input %v is global windowed in DoFn %v but is unbounded, DoFn will block until end of Global Window. Consider windowing your unbounded side input PCollection before use. This will cause your pipeline to fail in a future release, see https://github.com/apache/beam/issues/21596 for details\", i, fn)\n\t\t}\n\t\tin = append(in, s.Input.n)\n\t}\n\n\tvar rc *coder.Coder\n\t// Sdfs will always encode restrictions as KV<restriction, watermark state | bool(false)>\n\tif fn.IsSplittable() {\n\t\tsdf := (*graph.SplittableDoFn)(fn)\n\t\trestT := typex.New(sdf.RestrictionT())\n\t\t// If no watermark estimator state, use boolean as a placeholder\n\t\tweT := typex.New(reflect.TypeOf(true))\n\t\tif sdf.IsStatefulWatermarkEstimating() {\n\t\t\tweT = typex.New(sdf.WatermarkEstimatorStateT())\n\t\t}","sourceCodeStart":48,"sourceCodeEnd":84,"githubUrl":"https://github.com/apache/beam/blob/12126d8942aaf848030c478b4c6a28c6af861c66/sdks/go/pkg/beam/pardo.go#L48-L84","documentation":"TryParDo requires that when the main input PCollection is in GlobalWindows, every side input is also in GlobalWindows; otherwise windows of side elements cannot be mapped to the main element's single global window. This validation error fires at graph construction when that combination is detected.","triggerScenarios":"beam.ParDo with a GlobalWindows main input and a side input PCollection windowed with FixedWindows/SlidingWindows/Sessions. Fails immediately during pipeline construction.","commonSituations":"Batch enrichment in streaming pipelines: the main collection defaults to global windows while the lookup table was windowed for freshness; mixing a bounded global-windowed input with a re-windowed static dataset.","solutions":["Re-window the side input into GlobalWindows (often with window.WindowInto(window.NewGlobalWindows()) after grouping).","Alternatively, window the main input to match the side input's windows so per-window lookups make sense.","If side-input freshness is the goal, use a non-merging windowing on both sides, or use state/timers instead of side inputs.","Group the side PCollection and view it as a single-element side input in global windows (e.g. via beam.Combine + AsMap patterns adapted to global window)."],"exampleFix":"// before\nside := s | beam.WindowInto(window.NewFixedWindows(time.Minute))\nout := globalMain | beam.ParDo(dofn, beam.SideInput{Input: side}) // error\n\n// after\nsideGlobal := side | beam.CombinePerKey(...) | beam.WindowInto(window.NewGlobalWindows())\nout := globalMain | beam.ParDo(dofn, beam.SideInput{Input: sideGlobal})","handlingStrategy":"validation","validationCode":"// Ensure global-window main inputs only receive global-window side inputs:\nif mainWfn.Kind == window.GlobalWindows {\n    side = side | beam.WindowInto(window.NewGlobalWindows())\n}","typeGuard":"func globalWindowed(n *graph.Node) bool {\n    return n.WindowingStrategy().Fn.Kind == window.GlobalWindows\n}","tryCatchPattern":null,"preventionTips":["When the main input is global-windowed, always re-window side inputs into GlobalWindows after grouping.","Document windowing requirements on DoFn constructors that accept side inputs.","Run graph construction (e.g. a small local pipeline test) in CI to catch these errors before deployment."],"tags":["beam-go","side-input","windowing","global-windows","graph-validation"],"backgroundTag":"invalid-argument-value","analyzedSha":"12126d8942aaf848030c478b4c6a28c6af861c66","analyzedAt":"2026-09-13T01:50:10.254Z","contentChangedAt":"2026-09-13T01:50:10.254Z","schemaVersion":2},"datasetVersion":"2026-09-20T03:17:13.778Z"}