diff --git a/executor/write_test.go b/executor/write_test.go index 3315a73097fbf..ae61dba931d2d 100644 --- a/executor/write_test.go +++ b/executor/write_test.go @@ -1995,6 +1995,24 @@ func TestIssue34358(t *testing.T) { }, ld, t, tk, ctx, "select * from load_data_test", "delete from load_data_test") } +func TestIssue33298(t *testing.T) { + store, clean := testkit.CreateMockStore(t) + defer clean() + tk := testkit.NewTestKit(t, store) + ctx := tk.Session().(sessionctx.Context) + defer ctx.SetValue(executor.LoadDataVarKey, nil) + + tk.MustExec("use test") + tk.MustExec("drop table if exists load_data_test") + tk.MustExec("create table load_data_test (a varchar(10), b varchar(10))") + + // According to https://dev.mysql.com/doc/refman/8.0/en/load-data.html , fixed-row format should be used when fields + // terminated by '' and enclosed by ''. However, tidb doesn't support it yet and empty terminator leads to infinite + // loop in `indexOfTerminator` (see https://github.com/pingcap/tidb/issues/33298). + require.Error(t, tk.ExecToErr("load data local infile '/tmp/nonexistence.csv' into table load_data_test fields terminated by ''")) + require.Error(t, tk.ExecToErr("load data local infile '/tmp/nonexistence.csv' into table load_data_test fields terminated by '' enclosed by ''")) +} + func TestLoadData(t *testing.T) { trivialMsg := "Records: 1 Deleted: 0 Skipped: 0 Warnings: 0" store, clean := testkit.CreateMockStore(t) diff --git a/planner/core/planbuilder.go b/planner/core/planbuilder.go index e758bcbea3293..aab670ad79612 100644 --- a/planner/core/planbuilder.go +++ b/planner/core/planbuilder.go @@ -3891,6 +3891,10 @@ func (b *PlanBuilder) buildSelectPlanOfInsert(ctx context.Context, insert *ast.I } func (b *PlanBuilder) buildLoadData(ctx context.Context, ld *ast.LoadDataStmt) (Plan, error) { + // quick fix for https://github.com/pingcap/tidb/issues/33298 + if ld.FieldsInfo != nil && len(ld.FieldsInfo.Terminated) == 0 { + return nil, ErrNotSupportedYet.GenWithStackByArgs("load data with empty field terminator") + } p := LoadData{ IsLocal: ld.IsLocal, OnDuplicate: ld.OnDuplicate,