vitessio/vitess · error
err
Error message
err
What it means
This panic re-raises the first error returned by evalengine.TypeAggregator.Add while merging the types of the LHS/RHS expressions of a UNION column during createMergedUnion (go/vt/vtgate/planbuilder/operators/union_merging.go:301). When both sides' types are known, the planner aggregates rt then lt to compute the merged column type; Add fails when the two types cannot be aggregated (incompatible types/collations). The panic surfaces that type-resolution failure as an internal planning error.
Source
Thrown at go/vt/vtgate/planbuilder/operators/union_merging.go:301
if noDeps {
continue
}
deps := ctx.SemTable.RecursiveDeps(lae.Expr)
rae, ok := rhsExprs[idx].(*sqlparser.AliasedExpr)
if !ok {
noDeps = true
continue
}
deps = deps.Merge(ctx.SemTable.RecursiveDeps(rae.Expr))
rt, foundR := ctx.TypeForExpr(rae.Expr)
lt, foundL := ctx.TypeForExpr(lae.Expr)
if foundR && foundL {
collations := ctx.VSchema.Environment().CollationEnv()
var typer evalengine.TypeAggregator
if err := typer.Add(rt, collations); err != nil {
panic(err)
}
if err := typer.Add(lt, collations); err != nil {
panic(err)
}
ctx.SemTable.ExprTypes[col] = typer.Type()
}
ctx.SemTable.Recursive[col] = deps
}
exprs := [][]sqlparser.SelectExpr{lhsExprs, rhsExprs}
union := newUnion([]Operator{lhsRoute.Source, rhsRoute.Source}, exprs, cols, distinct)
selectExprs := unionSelects(lhsExprs)
return &Route{
unaryOperator: newUnaryOp(union),
MergedWith: []*Route{rhsRoute},
Routing: routing,View on GitHub (pinned to 01a25a7d17)
Solutions
- Make both UNION arms produce compatible types for the column, using explicit CAST/CONVERT in one arm
- Align charsets/collations of the columns on both sides (ALTER TABLE ... CONVERT TO CHARACTER SET) when arms come from differently configured tables
- If types look compatible, reproduce and file a Vitess issue with both arms' column definitions — the aggregator rejecting them may be a bug
Example fix
// before (incompatible types across arms) SELECT int_col FROM t1 UNION SELECT varchar_col FROM t2; // after SELECT CAST(int_col AS CHAR) FROM t1 UNION SELECT varchar_col FROM t2;
Defensive patterns
Strategy: validation
Validate before calling
// verify both arms' column types are aggregatable before issuing
lt, rt := columnTypes(arm1, arm2, idx)
if !evalengine.CanAggregate(rt, lt) { return fmt.Errorf("cast column %d to a common type", idx) } Try / catch
if err != nil && strings.Contains(err.Error(), "type") {
return executeWithCasts(ctx, addUnionCasts(query))
} Prevention
- CAST mismatched columns in one arm so both sides share a type
- Keep charsets/collations consistent across unioned tables
- Avoid unioning JSON/enum/set columns with unrelated types
When it happens
Trigger: createMergedUnion (called from mergeUnionInputs / tryMergeNoneUnion / tryMergeUnionShardedRouting) merges two routes into one UNION; for a column position, ctx.TypeForExpr succeeds on both sides (foundR && foundL) and the first typer.Add(rt, collations) call returns an error — e.g. an unsupported or invalid type pairing for the aggregation.
Common situations: UNION of columns with exotic or incompatible types (e.g. binary/collation conflicts between arms on different keyspaces with different charsets); JSON/enum/set columns unioned with other types; cross-keyspace merges where collation environments disagree.
Related errors
AI-assisted analysis of vitessio/vitess@01a25a7d17 (2026-09-01).
Data as JSON: /api/errors/27005b4174688ab2.
Report an issue: GitHub.