Skip to content

Commit

Permalink
expression: support collation for REGEXP function (#17255) (#17581)
Browse files Browse the repository at this point in the history
  • Loading branch information
sre-bot authored Jun 2, 2020
1 parent dec49a1 commit 23b94af
Show file tree
Hide file tree
Showing 2 changed files with 42 additions and 10 deletions.
11 changes: 8 additions & 3 deletions expression/builtin_like.go
Original file line number Diff line number Diff line change
Expand Up @@ -17,6 +17,7 @@ import (
"regexp"
"sync"

"github.com/pingcap/parser/charset"
"github.com/pingcap/tidb/sessionctx"
"github.com/pingcap/tidb/types"
"github.com/pingcap/tidb/util/chunk"
Expand Down Expand Up @@ -121,7 +122,7 @@ func (c *regexpFunctionClass) getFunction(ctx sessionctx.Context, args []Express
}
bf.tp.Flen = 1
var sig builtinFunc
if types.IsBinaryStr(args[0].GetType()) || types.IsBinaryStr(args[1].GetType()) {
if bf.collation == charset.CollationBin {
sig = newBuiltinRegexpSig(bf)
sig.setPbCode(tipb.ScalarFuncSig_RegexpSig)
} else {
Expand Down Expand Up @@ -189,8 +190,12 @@ type builtinRegexpUTF8Sig struct {

func newBuiltinRegexpUTF8Sig(bf baseBuiltinFunc) *builtinRegexpUTF8Sig {
shared := builtinRegexpSharedSig{baseBuiltinFunc: bf}
shared.compile = func(pat string) (*regexp.Regexp, error) {
return regexp.Compile("(?i)" + pat)
if collate.IsCICollation(bf.collation) {
shared.compile = func(pat string) (*regexp.Regexp, error) {
return regexp.Compile("(?i)" + pat)
}
} else {
shared.compile = regexp.Compile
}
return &builtinRegexpUTF8Sig{builtinRegexpSharedSig: shared}
}
Expand Down
41 changes: 34 additions & 7 deletions expression/integration_test.go
Original file line number Diff line number Diff line change
Expand Up @@ -938,7 +938,7 @@ func (s *testIntegrationSuite2) TestStringBuiltin(c *C) {
tk.MustQuery(`select quote(null) REGEXP binary 'null'`).Check(testkit.Rows(`0`))
tk.MustQuery(`select quote(null) REGEXP binary 'NULL'`).Check(testkit.Rows(`1`))
tk.MustQuery(`select quote(null) REGEXP 'NULL'`).Check(testkit.Rows(`1`))
tk.MustQuery(`select quote(null) REGEXP 'null'`).Check(testkit.Rows(`1`))
tk.MustQuery(`select quote(null) REGEXP 'null'`).Check(testkit.Rows(`0`))

// for convert
result = tk.MustQuery(`select convert("123" using "binary"), convert("中文" using "binary"), convert("中文" using "utf8"), convert("中文" using "utf8mb4"), convert(cast("中文" as binary) using "utf8");`)
Expand Down Expand Up @@ -2783,28 +2783,28 @@ func (s *testIntegrationSuite2) TestBuiltin(c *C) {
tk.MustExec(`drop table if exists t;`)
tk.MustExec(`create table t (a char(10), b varchar(10), c binary(10), d varbinary(10));`)
tk.MustExec(`insert into t values ('text','text','text','text');`)
result = tk.MustQuery(`select a regexp 'Xt' from t;`)
result = tk.MustQuery(`select a regexp 'xt' from t;`)
result.Check(testkit.Rows("1"))
result = tk.MustQuery(`select b regexp 'Xt' from t;`)
result = tk.MustQuery(`select b regexp 'xt' from t;`)
result.Check(testkit.Rows("1"))
result = tk.MustQuery(`select b regexp binary 'Xt' from t;`)
result.Check(testkit.Rows("0"))
result = tk.MustQuery(`select c regexp 'Xt' from t;`)
result.Check(testkit.Rows("0"))
result = tk.MustQuery(`select d regexp 'Xt' from t;`)
result.Check(testkit.Rows("0"))
result = tk.MustQuery(`select a rlike 'Xt' from t;`)
result = tk.MustQuery(`select a rlike 'xt' from t;`)
result.Check(testkit.Rows("1"))
result = tk.MustQuery(`select a rlike binary 'Xt' from t;`)
result.Check(testkit.Rows("0"))
result = tk.MustQuery(`select b rlike 'Xt' from t;`)
result = tk.MustQuery(`select b rlike 'xt' from t;`)
result.Check(testkit.Rows("1"))
result = tk.MustQuery(`select c rlike 'Xt' from t;`)
result.Check(testkit.Rows("0"))
result = tk.MustQuery(`select d rlike 'Xt' from t;`)
result.Check(testkit.Rows("0"))
result = tk.MustQuery(`select 'a' regexp 'A', 'a' regexp binary 'A'`)
result.Check(testkit.Rows("1 0"))
result.Check(testkit.Rows("0 0"))

// testCase is for like and regexp
type testCase struct {
Expand Down Expand Up @@ -6142,7 +6142,7 @@ func (s *testIntegrationSerialSuite) TestCollateStringFunction(c *C) {
tk.MustQuery("select INSTR(p4,n4) from t1;").Check(testkit.Rows("1"))

tk.MustExec("truncate table t1;")
tk.MustExec("insert into t1 (a,p1,p2,p3,p4,n1,n2,n3,n4) values (2,'0aA1!测试テストמבחן ','0aA1!测试テストמבחן ','0aA1!测试テストמבחן ','0aA1!测试テストמבחן ','0Aa1!测试テストמבחן','0Aa1!测试テストמבחן','0Aa1!测试テストמבחן','0Aa1!测试テストמבחן');")
tk.MustExec("insert into t1 (a,p1,p2,p3,p4,n1,n2,n3,n4) values (1,'0aA1!测试テストמבחן ','0aA1!测试テストמבחן ','0aA1!测试テストמבחן ','0aA1!测试テストמבחן ','0Aa1!测试テストמבחן','0Aa1!测试テストמבחן','0Aa1!测试テストמבחן','0Aa1!测试テストמבחן');")
tk.MustExec("insert into t1 (a,p1,p2,p3,p4,n1,n2,n3,n4) values (2,'0aA1!测试テストמבחן','0aA1!测试テストמבחן','0aA1!测试テストמבחן','0aA1!测试テストמבחן','0Aa1!测试テストמבחן','0Aa1!测试テストמבחן','0Aa1!测试テストמבחן','0Aa1!测试テストמבחן');")
tk.MustExec("insert into t1 (a,p1,p2,p3,p4,n1,n2,n3,n4) values (3,'0aA1!测试テストמבחן','0aA1!测试テストמבחן','0aA1!测试テストמבחן','0aA1!测试テストמבחן','0Aa1!测试テストמבחן ','0Aa1!测试テストמבחן ','0Aa1!测试テストמבחן ','0Aa1!测试テストמבחן ');")

Expand All @@ -6163,6 +6163,33 @@ func (s *testIntegrationSerialSuite) TestCollateStringFunction(c *C) {
tk.MustQuery("select LOCATE(p4,n3) from t1;").Check(testkit.Rows("0", "0", "0"))
tk.MustQuery("select LOCATE(p4,n4) from t1;").Check(testkit.Rows("0", "1", "1"))

tk.MustExec("truncate table t1;")
tk.MustExec("insert into t1 (a) values (1);")
tk.MustExec("insert into t1 (a,p1,p2,p3,p4,n1,n2,n3,n4) values (2,'0aA1!测试テストמבחן ','0aA1!测试テストמבחן ','0aA1!测试テストמבחן ','0aA1!测试テストמבחן ','0Aa1!测试テストמבחן','0Aa1!测试テストמבחן','0Aa1!测试テストמבחן','0Aa1!测试テストמבחן');")
tk.MustExec("insert into t1 (a,p1,p2,p3,p4,n1,n2,n3,n4) values (3,'0aA1!测试テストמבחן','0aA1!测试テストמבחן','0aA1!测试テストמבחן','0aA1!测试テストמבחן','0Aa1!测试テストמבחן','0Aa1!测试テストמבחן','0Aa1!测试テストמבחן','0Aa1!测试テストמבחן');")
tk.MustExec("insert into t1 (a,p1,p2,p3,p4,n1,n2,n3,n4) values (4,'0aA1!测试テストמבחן','0aA1!测试テストמבחן','0aA1!测试テストמבחן','0aA1!测试テストמבחן','0Aa1!测试テストמבחן ','0Aa1!测试テストמבחן ','0Aa1!测试テストמבחן ','0Aa1!测试テストמבחן ');")
tk.MustExec("insert into t1 (a,p1,p2,p3,p4,n1,n2,n3,n4) values (5,'0aA1!测试テストמבחן0aA1!测试','0aA1!测试テストמבחן0aA1!测试','0aA1!测试テストמבחן0aA1!测试','0aA1!测试テストמבחן0aA1!测试','0Aa1!测试','0Aa1!测试','0Aa1!测试','0Aa1!测试');")
tk.MustExec("insert into t1 (a,p1,p2,p3,p4,n1,n2,n3,n4) values (6,'0aA1!测试テストמבחן0aA1!测试','0aA1!测试テストמבחן0aA1!测试','0aA1!测试テストמבחן0aA1!测试','0aA1!测试テストמבחן0aA1!测试','0aA1!测试','0aA1!测试','0aA1!测试','0aA1!测试');")
tk.MustExec("insert into t1 (a,p1,p2,p3,p4,n1,n2,n3,n4) values (7,'0aA1!测试テストמבחן ','0aA1!测试テストמבחן ','0aA1!测试テストמבחן ','0aA1!测试テストמבחן ','0aA1!测试テストמבחן','0aA1!测试テストמבחן','0aA1!测试テストמבחן','0aA1!测试テストמבחן');")
tk.MustExec("insert into t1 (a,p1,p2,p3,p4,n1,n2,n3,n4) values (8,'0aA1!测试テストמבחן','0aA1!测试テストמבחן','0aA1!测试テストמבחן','0aA1!测试テストמבחן','0aA1!测试テストמבחן ','0aA1!测试テストמבחן ','0aA1!测试テストמבחן ','0aA1!测试テストמבחן ');")

tk.MustQuery("select p1 REGEXP n1 from t1;").Check(testkit.Rows("<nil>", "0", "0", "0", "0", "1", "1", "0"))
tk.MustQuery("select p1 REGEXP n2 from t1;").Check(testkit.Rows("<nil>", "0", "0", "0", "0", "1", "1", "0"))
tk.MustQuery("select p1 REGEXP n3 from t1;").Check(testkit.Rows("<nil>", "0", "0", "0", "0", "1", "1", "0"))
tk.MustQuery("select p1 REGEXP n4 from t1;").Check(testkit.Rows("<nil>", "1", "1", "0", "1", "1", "1", "0"))
tk.MustQuery("select p2 REGEXP n1 from t1;").Check(testkit.Rows("<nil>", "0", "0", "0", "0", "1", "1", "0"))
tk.MustQuery("select p2 REGEXP n2 from t1;").Check(testkit.Rows("<nil>", "1", "1", "0", "1", "1", "1", "0"))
tk.MustQuery("select p2 REGEXP n3 from t1;").Check(testkit.Rows("<nil>", "0", "0", "0", "0", "1", "1", "0"))
tk.MustQuery("select p2 REGEXP n4 from t1;").Check(testkit.Rows("<nil>", "1", "1", "0", "1", "1", "1", "0"))
tk.MustQuery("select p3 REGEXP n1 from t1;").Check(testkit.Rows("<nil>", "0", "0", "0", "0", "1", "1", "0"))
tk.MustQuery("select p3 REGEXP n2 from t1;").Check(testkit.Rows("<nil>", "0", "0", "0", "0", "1", "1", "0"))
tk.MustQuery("select p3 REGEXP n3 from t1;").Check(testkit.Rows("<nil>", "0", "0", "0", "0", "1", "1", "0"))
tk.MustQuery("select p3 REGEXP n4 from t1;").Check(testkit.Rows("<nil>", "0", "0", "0", "0", "1", "1", "0"))
tk.MustQuery("select p4 REGEXP n1 from t1;").Check(testkit.Rows("<nil>", "1", "1", "0", "1", "1", "1", "0"))
tk.MustQuery("select p4 REGEXP n2 from t1;").Check(testkit.Rows("<nil>", "1", "1", "0", "1", "1", "1", "0"))
tk.MustQuery("select p4 REGEXP n3 from t1;").Check(testkit.Rows("<nil>", "0", "0", "0", "0", "1", "1", "0"))
tk.MustQuery("select p4 REGEXP n4 from t1;").Check(testkit.Rows("<nil>", "1", "1", "0", "1", "1", "1", "0"))

tk.MustExec("drop table t1;")
}

Expand Down

0 comments on commit 23b94af

Please sign in to comment.