{"record":{"id":"294462911b2117ad","repo":"apache/beam","slug":"bad-pair-v","errorCode":null,"errorMessage":"bad pair: %+v","messagePattern":"bad pair: %\\+v","errorType":"exception","errorClass":null,"httpStatus":null,"severity":"error","filePath":"sdks/go/pkg/beam/core/runtime/graphx/dataflow.go","lineNumber":252,"sourceCode":"\tswitch c.Type {\n\tcase bytesType:\n\t\treturn coder.NewBytes(), nil\n\n\tcase boolType:\n\t\treturn coder.NewBool(), nil\n\n\tcase varIntType:\n\t\treturn coder.NewVarInt(), nil\n\n\tcase doubleType:\n\t\treturn coder.NewDouble(), nil\n\n\tcase stringType:\n\t\treturn coder.NewString(), nil\n\n\tcase pairType:\n\t\tif len(c.Components) != 2 {\n\t\t\treturn nil, errors.Errorf(\"bad pair: %+v\", c)\n\t\t}\n\n\t\tkey, err := DecodeCoderRef(c.Components[0])\n\t\tif err != nil {\n\t\t\treturn nil, err\n\t\t}\n\n\t\telm := c.Components[1]\n\t\tif elm.Type == streamType {\n\t\t\t// TODO(https://github.com/apache/beam/issues/18032): If CoGBK with > 1 input, handle as special GBK. We expect\n\t\t\t// it to be encoded as CoGBK<K,LP<Union<V,W,..>>. Remove this handling once\n\t\t\t// CoGBK has a first-class representation.\n\n\t\t\tif refs, ok := isCoGBKList(elm.Components[0]); ok {\n\t\t\t\tvalues, err := DecodeCoderRefs(refs)\n\t\t\t\tif err != nil {\n\t\t\t\t\treturn nil, err\n\t\t\t\t}","sourceCodeStart":234,"sourceCodeEnd":270,"githubUrl":"https://github.com/apache/beam/blob/12126d8942aaf848030c478b4c6a28c6af861c66/sdks/go/pkg/beam/core/runtime/graphx/dataflow.go#L234-L270","documentation":"DecodeCoderRef converts an encoded CoderRef back into a usable coder. A pair-type ref must have exactly two components (key and value); any other count means the encoded form is corrupt or was produced by an incompatible encoder, so decoding fails with the full ref in the message.","triggerScenarios":"Decoding a CoderRef with Type pairType whose Components slice has length != 2 — e.g. during pipeline deserialization of a model/Job message whose coder graph was corrupted, truncated, or produced by a different Beam version.","commonSituations":"Loading a pipeline artifact or model-pipeline.proto edited by hand; cross-version decode (SDK encodes pair differently then another version decodes); corrupted service responses for the Dataflow pipeline graph; custom tooling that rewrites CoderRef components.","solutions":["Inspect the printed CoderRef and confirm the pipeline graph source; regenerate it from the original pipeline rather than reusing a stale artifact.","Ensure the SDK version decoding the pipeline matches the version that encoded it.","If using custom graph-rewriting tools, verify they preserve pair-coder component count.","Re-export/rebuild the pipeline so the coder graph is re-encoded from valid in-memory coders."],"exampleFix":"// before (corrupt ref)\nref := &graphx.CoderRef{Type: graphx.Pair, Components: []*graphx.CoderRef{key}}\nc, err := graphx.DecodeCoderRef(ref)\n\n// after\nref := &graphx.CoderRef{Type: graphx.Pair, Components: []*graphx.CoderRef{key, value}}\nc, err := graphx.DecodeCoderRef(ref)","handlingStrategy":"try-catch","validationCode":"func validPairRef(r *graphx.CoderRef) bool {\n\treturn r != nil && r.Type == graphx.Pair && len(r.Components) == 2\n}","typeGuard":"func isPairRef(r *graphx.CoderRef) bool { return r != nil && r.Type == graphx.Pair && len(r.Components) == 2 }","tryCatchPattern":"c, err := graphx.DecodeCoderRef(ref)\nif err != nil {\n\tif strings.Contains(err.Error(), \"bad pair\") {\n\t\treturn nil, fmt.Errorf(\"corrupt pair coder ref %v: regenerate the pipeline artifact: %w\", ref, err)\n\t}\n\treturn nil, err\n}","preventionTips":["Never hand-edit encoded pipeline graphs","Validate decoded graphs against the same SDK version that encoded them","Checksum pipeline artifacts in CI before reuse"],"tags":["go","beam","coder-deserialization","dataflow"],"backgroundTag":"unexpected-response-shape","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"}