From dd6900b6cce1629996b5be8ef43c492b83b89732 Mon Sep 17 00:00:00 2001 From: Jason Mo Date: Wed, 28 Aug 2024 17:43:37 +0800 Subject: [PATCH] for test --- pkg/expression/builtin_cast.go | 29 ++++++++++++++++++++----- pkg/expression/util.go | 2 +- pkg/planner/core/expression_rewriter.go | 2 +- 3 files changed, 26 insertions(+), 7 deletions(-) diff --git a/pkg/expression/builtin_cast.go b/pkg/expression/builtin_cast.go index fbdbba5d26033..3666bd3855c4a 100644 --- a/pkg/expression/builtin_cast.go +++ b/pkg/expression/builtin_cast.go @@ -38,6 +38,7 @@ import ( "github.com/pingcap/tidb/pkg/sessionctx/stmtctx" "github.com/pingcap/tidb/pkg/types" "github.com/pingcap/tidb/pkg/util/chunk" + "github.com/pingcap/tidb/pkg/util/collate" "github.com/pingcap/tipb/go-tipb" ) @@ -288,7 +289,8 @@ func (c *castAsDecimalFunctionClass) getFunction(ctx BuildContext, args []Expres type castAsStringFunctionClass struct { baseFunctionClass - tp *types.FieldType + tp *types.FieldType + isExplicitCharSet bool } func (c *castAsStringFunctionClass) getFunction(ctx BuildContext, args []Expression) (sig builtinFunc, err error) { @@ -299,6 +301,16 @@ func (c *castAsStringFunctionClass) getFunction(ctx BuildContext, args []Express if err != nil { return nil, err } + if c.isExplicitCharSet { + bf.SetCharsetAndCollation(c.tp.GetCharset(), c.tp.GetCollate()) + bf.setCollator(collate.GetCollator(c.tp.GetCollate())) + bf.SetCoercibility(CoercibilityExplicit) + if c.tp.GetCharset() == charset.CharsetASCII { + bf.SetRepertoire(ASCII) + } else { + bf.SetRepertoire(UNICODE) + } + } if args[0].GetType(ctx.GetEvalCtx()).Hybrid() { sig = &builtinCastStringAsStringSig{bf} sig.setPbCode(tipb.ScalarFuncSig_CastStringAsString) @@ -2265,7 +2277,7 @@ func CanImplicitEvalReal(expr Expression) bool { // BuildCastFunction4Union build a implicitly CAST ScalarFunction from the Union // Expression. func BuildCastFunction4Union(ctx BuildContext, expr Expression, tp *types.FieldType) (res Expression) { - res, err := BuildCastFunctionWithCheck(ctx, expr, tp, true) + res, err := BuildCastFunctionWithCheck(ctx, expr, tp, true, false) terror.Log(err) return } @@ -2302,13 +2314,20 @@ func BuildCastCollationFunction(ctx BuildContext, expr Expression, ec *ExprColla // BuildCastFunction builds a CAST ScalarFunction from the Expression. func BuildCastFunction(ctx BuildContext, expr Expression, tp *types.FieldType) (res Expression) { - res, err := BuildCastFunctionWithCheck(ctx, expr, tp, false) + res, err := BuildCastFunctionWithCheck(ctx, expr, tp, false, false) + terror.Log(err) + return +} + +// BuildCastFunctionExplicitCharset builds a CAST ScalarFunction from the Expression. +func BuildCastFunctionExplicitCharset(ctx BuildContext, expr Expression, tp *types.FieldType) (res Expression) { + res, err := BuildCastFunctionWithCheck(ctx, expr, tp, false, true) terror.Log(err) return } // BuildCastFunctionWithCheck builds a CAST ScalarFunction from the Expression and return error if any. -func BuildCastFunctionWithCheck(ctx BuildContext, expr Expression, tp *types.FieldType, inUnion bool) (res Expression, err error) { +func BuildCastFunctionWithCheck(ctx BuildContext, expr Expression, tp *types.FieldType, inUnion bool, isExplicitCharSet bool) (res Expression, err error) { argType := expr.GetType(ctx.GetEvalCtx()) // If source argument's nullable, then target type should be nullable if !mysql.HasNotNullFlag(argType.GetFlag()) { @@ -2336,7 +2355,7 @@ func BuildCastFunctionWithCheck(ctx BuildContext, expr Expression, tp *types.Fie case types.ETVectorFloat32: fc = &castAsVectorFloat32FunctionClass{baseFunctionClass{ast.Cast, 1, 1}, tp} case types.ETString: - fc = &castAsStringFunctionClass{baseFunctionClass{ast.Cast, 1, 1}, tp} + fc = &castAsStringFunctionClass{baseFunctionClass{ast.Cast, 1, 1}, tp, isExplicitCharSet} if expr.GetType(ctx.GetEvalCtx()).GetType() == mysql.TypeBit { tp.SetFlen((expr.GetType(ctx.GetEvalCtx()).GetFlen() + 7) / 8) } diff --git a/pkg/expression/util.go b/pkg/expression/util.go index 2af5c19d324f9..60797a9af7b52 100644 --- a/pkg/expression/util.go +++ b/pkg/expression/util.go @@ -455,7 +455,7 @@ func ColumnSubstituteImpl(ctx BuildContext, expr Expression, schema *Schema, new flag := v.RetType.GetFlag() var e Expression if v.FuncName.L == ast.Cast { - e = BuildCastFunction(ctx, newArg, v.RetType) + e = BuildCastFunctionExplicitCharset(ctx, newArg, v.RetType) } else { // for grouping function recreation, use clone (meta included) instead of newFunction e = v.Clone() diff --git a/pkg/planner/core/expression_rewriter.go b/pkg/planner/core/expression_rewriter.go index 7c47717e0a773..acaadb3b05cb1 100644 --- a/pkg/planner/core/expression_rewriter.go +++ b/pkg/planner/core/expression_rewriter.go @@ -1504,7 +1504,7 @@ func (er *expressionRewriter) Leave(originInNode ast.Node) (retNode ast.Node, ok return retNode, false } - castFunction, err := expression.BuildCastFunctionWithCheck(er.sctx, arg, v.Tp, false) + castFunction, err := expression.BuildCastFunctionWithCheck(er.sctx, arg, v.Tp, false, v.ExplicitCharSet) if err != nil { er.err = err return retNode, false