Skip to content

Commit 828b461

Browse files
authored
planner: make pattern match case-insensitive for some infoschema tables (#56378)
close #56377
1 parent e80059b commit 828b461

File tree

4 files changed

+51
-1
lines changed

4 files changed

+51
-1
lines changed

pkg/parser/mysql/charset.go

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -541,6 +541,7 @@ const (
541541
BinaryDefaultCollationID = 63
542542
UTF8MB4DefaultCollation = "utf8mb4_bin"
543543
DefaultCollationName = UTF8MB4DefaultCollation
544+
UTF8MB4GeneralCICollation = "utf8mb4_general_ci"
544545

545546
// MaxBytesOfCharacter, is the max bytes length of a character,
546547
// refer to RFC3629, in UTF-8, characters from the U+0000..U+10FFFF range

pkg/planner/core/memtable_infoschema_extractor.go

Lines changed: 33 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -198,9 +198,15 @@ func (e *InfoSchemaBaseExtractor) Extract(
198198
}
199199
var likePatterns []string
200200
remained, likePatterns = e.extractLikePatternCol(ctx, schema, names, remained, colName, true, false)
201+
if len(likePatterns) == 0 {
202+
continue
203+
}
201204
regexp := make([]collate.WildcardPattern, len(likePatterns))
202205
for i, pattern := range likePatterns {
203-
regexp[i] = collate.GetCollatorByID(collate.CollationName2ID(mysql.UTF8MB4DefaultCollation)).Pattern()
206+
// Because @@lower_case_table_names is always 2 in TiDB,
207+
// schema object names comparison should be case insensitive.
208+
ciCollateID := collate.CollationName2ID(mysql.UTF8MB4GeneralCICollation)
209+
regexp[i] = collate.GetCollatorByID(ciCollateID).Pattern()
204210
regexp[i].Compile(pattern, byte('\\'))
205211
}
206212
e.LikePatterns[colName] = likePatterns
@@ -249,6 +255,11 @@ func (e *InfoSchemaBaseExtractor) filter(colName string, val string) bool {
249255
if e.SkipRequest {
250256
return true
251257
}
258+
for _, re := range e.colsRegexp[colName] {
259+
if !re.DoMatch(val) {
260+
return true
261+
}
262+
}
252263
predVals, ok := e.ColPredicates[colName]
253264
if ok && len(predVals) > 0 {
254265
fn, ok := e.pushedDownFuncs[colName]
@@ -661,6 +672,15 @@ func findTableAndSchemaByName(
661672
schemaSlice = append(schemaSlice, st.schema)
662673
tableSlice = append(tableSlice, st.table)
663674
}
675+
sort.Slice(schemaSlice, func(i, j int) bool {
676+
iSchema, jSchema := schemaSlice[i].L, schemaSlice[j].L
677+
less := iSchema < jSchema ||
678+
(iSchema == jSchema && tableSlice[i].Name.L < tableSlice[j].Name.L)
679+
if less {
680+
tableSlice[i], tableSlice[j] = tableSlice[j], tableSlice[i]
681+
}
682+
return less
683+
})
664684
return schemaSlice, tableSlice, nil
665685
}
666686

@@ -687,6 +707,9 @@ func listTablesForEachSchema(
687707
return schemaSlice, tableSlice, nil
688708
}
689709

710+
// findSchemasForTables finds a schema for each tableInfo, and it
711+
// returns a schema slice and a table slice that has the same length.
712+
// Note that input arg "tableSlice" will be changed in place.
690713
func findSchemasForTables(
691714
ctx context.Context,
692715
is infoschema.InfoSchema,
@@ -721,6 +744,15 @@ func findSchemasForTables(
721744
remains = append(remains, tbl)
722745
}
723746
}
747+
sort.Slice(schemaSlice, func(i, j int) bool {
748+
iSchema, jSchema := schemaSlice[i].L, schemaSlice[j].L
749+
less := iSchema < jSchema ||
750+
(iSchema == jSchema && remains[i].Name.L < remains[j].Name.L)
751+
if less {
752+
remains[i], remains[j] = remains[j], remains[i]
753+
}
754+
return less
755+
})
724756
return schemaSlice, remains, nil
725757
}
726758

tests/integrationtest/r/infoschema/infoschema.result

Lines changed: 11 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -134,6 +134,16 @@ engine DATA_LENGTH
134134
InnoDB 8
135135
drop table infoschema__infoschema.t4;
136136
drop table infoschema__infoschema.t5;
137+
create table caseSensitive (a int);
138+
create table unrelatedTable (a int);
139+
select table_schema, table_name from information_schema.tables where table_schema = 'infoschema__infoschema' and table_name like '%aseSensitive';
140+
table_schema table_name
141+
infoschema__infoschema caseSensitive
142+
select table_schema, table_name, tidb_pk_type from information_schema.tables where table_schema = 'infoschema__infoschema' and table_name like '%aseSensitive';
143+
table_schema table_name tidb_pk_type
144+
infoschema__infoschema caseSensitive NONCLUSTERED
145+
drop table caseSensitive;
146+
drop table unrelatedTable;
137147
create table pt1(a int primary key, b int) partition by hash(a) partitions 4;
138148
create table pt2(a int primary key, b int) partition by hash(a) partitions 4;
139149
select TABLE_NAME, PARTITION_NAME from information_schema.partitions where table_schema = 'infoschema__infoschema';
@@ -477,5 +487,6 @@ Projection_4 10000.00 root Column#2, Column#3
477487
└─MemTableScan_5 10000.00 root table:SEQUENCES sequence_schema_pattern:[%db1%]
478488
select sequence_schema, sequence_name from information_schema.sequences where sequence_schema like '%db1%';
479489
sequence_schema sequence_name
490+
Db1 s1
480491
drop database db1;
481492
drop database db2;

tests/integrationtest/t/infoschema/infoschema.test

Lines changed: 6 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -60,6 +60,12 @@ explain select engine, DATA_LENGTH from information_schema.tables where table_na
6060
select engine, DATA_LENGTH from information_schema.tables where table_name ='t4' and upper(table_name) ='T4' and table_schema = 'infoschema__infoschema';
6161
drop table infoschema__infoschema.t4;
6262
drop table infoschema__infoschema.t5;
63+
create table caseSensitive (a int);
64+
create table unrelatedTable (a int);
65+
select table_schema, table_name from information_schema.tables where table_schema = 'infoschema__infoschema' and table_name like '%aseSensitive';
66+
select table_schema, table_name, tidb_pk_type from information_schema.tables where table_schema = 'infoschema__infoschema' and table_name like '%aseSensitive';
67+
drop table caseSensitive;
68+
drop table unrelatedTable;
6369

6470
# TestPartitionsColumn
6571
create table pt1(a int primary key, b int) partition by hash(a) partitions 4;

0 commit comments

Comments
 (0)