{"record":{"id":"a23f0271a992b8bc","repo":"apache/beam","slug":"invalid-status-for-pardo-v-v-want-up","errorCode":null,"errorMessage":"invalid status for pardo %v: %v, want Up","messagePattern":"invalid status for pardo (.+?): (.+?), want Up","errorType":"error_code","errorClass":null,"httpStatus":null,"severity":"error","filePath":"sdks/go/pkg/beam/core/runtime/exec/pardo.go","lineNumber":124,"sourceCode":"\t\treturn n.fail(err)\n\t}\n\n\temitters, err := makeEmitters(n.Fn.ProcessElementFn(), n.Out)\n\tif err != nil {\n\t\treturn n.fail(err)\n\t}\n\tn.emitters = emitters\n\treturn nil\n}\n\nfunc (n *ParDo) AttachFinalizer(bf *bundleFinalizer) {\n\tn.bf = bf\n}\n\n// StartBundle does pre-bundle processing operation for the DoFn.\nfunc (n *ParDo) StartBundle(ctx context.Context, id string, data DataContext) error {\n\tif n.status != Up {\n\t\treturn errors.Errorf(\"invalid status for pardo %v: %v, want Up\", n.UID, n.status)\n\t}\n\tn.status = Active\n\tn.reader = data.State\n\tn.timerManager = data.Data\n\t// Allocating contexts all the time is expensive, but we seldom re-write them,\n\t// and never accept modified contexts from users, so we will cache them per-bundle\n\t// per-unit, to avoid the constant allocation overhead.\n\tn.ctx = metrics.SetPTransformID(ctx, n.PID)\n\n\tn.states.Set(n.ctx, metrics.StartBundle)\n\n\tif err := MultiStartBundle(n.ctx, id, data, n.Out...); err != nil {\n\t\treturn n.fail(err)\n\t}\n\n\t// TODO(BEAM-3303): what to set for StartBundle/FinishBundle window and emitter timestamp?\n\n\tif _, err := n.invokeDataFn(n.ctx, typex.NoFiringPane(), window.SingleGlobalWindow, mtime.ZeroTimestamp, n.Fn.StartBundleFn(), nil); err != nil {","sourceCodeStart":106,"sourceCodeEnd":142,"githubUrl":"https://github.com/apache/beam/blob/12126d8942aaf848030c478b4c6a28c6af861c66/sdks/go/pkg/beam/core/runtime/exec/pardo.go#L106-L142","documentation":"ParDo.StartBundle() transitions the unit from Up to Active and requires status == Up. The library throws this error when StartBundle is invoked on a ParDo that has not been Up'd (status still Initializing) or that is already Active/Broken, because bundle-level state (reader, timer manager) can only be installed between Up and Active.","triggerScenarios":"Calling StartBundle before Up, calling StartBundle twice for the same bundle, or calling StartBundle after FinishBundle transitioned status back but the unit was actually Broken.","commonSituations":"Custom runners or test harnesses driving the exec plan lifecycle manually out of order; reusing a plan across bundles when a previous bundle failed mid-way leaving status Broken.","solutions":["Always execute the full lifecycle via Plan.Execute (Up -> StartBundle -> Process -> FinishBundle) instead of calling unit methods directly.","Verify that StartBundle is called after Up and after FinishBundle returns the unit to Up status.","Rebuild the plan if a previous bundle execution failed and set status to Broken."],"exampleFix":"// before\nfor _, root := range plan.roots {\n    root.StartBundle(ctx, id, data) // skipped Up\n}\n// after\nif err := plan.Execute(ctx, id, data); err != nil {\n    return err // Execute performs Up then StartBundle in order\n}","handlingStrategy":"validation","validationCode":"if pardo.status != exec.Up {\n    return fmt.Errorf(\"pardo %v not ready for bundle (status %v)\", pardo.UID, pardo.status)\n}\nerr := pardo.StartBundle(ctx, id, data)","typeGuard":null,"tryCatchPattern":"if err := plan.Execute(ctx, id, mgr); err != nil {\n    if strings.Contains(err.Error(), \"want Up\") {\n        plan, err = constructAndExecutePlanWithContext(ctx, id, units, mgr)\n    }\n}","preventionTips":["Execute the full lifecycle via Plan.Execute, never unit methods in isolation.","Never reuse a plan object across bundles.","After any Execute error, treat the plan as Broken and construct a new one."],"tags":["go","apache-beam","lifecycle","state-machine"],"backgroundTag":"invalid-state-transition","analyzedSha":"12126d8942aaf848030c478b4c6a28c6af861c66","analyzedAt":"2026-09-13T01:50:10.254Z","contentChangedAt":"2026-09-13T01:50:10.254Z","schemaVersion":2},"datasetVersion":"2026-09-14T16:17:12.679Z"}