github.com/whtcorpsinc/milevadb-prod@v0.0.0-20211104133533-f57f4be3b597/dbs/cmd/failtest/fail_db_test.go (about)

     1  // Copyright 2020 WHTCORPS INC
     2  //
     3  // Licensed under the Apache License, Version 2.0 (the "License");
     4  // you may not use this file except in compliance with the License.
     5  // You may obtain a copy of the License at
     6  //
     7  //     http://www.apache.org/licenses/LICENSE-2.0
     8  //
     9  // Unless required by applicable law or agreed to in writing, software
    10  // distributed under the License is distributed on an "AS IS" BASIS,
    11  // See the License for the specific language governing permissions and
    12  // limitations under the License.
    13  
    14  package dbs_test
    15  
    16  import (
    17  	"context"
    18  	"fmt"
    19  	"math/rand"
    20  	"os"
    21  	"sync/atomic"
    22  	"testing"
    23  	"time"
    24  
    25  	"github.com/whtcorpsinc/BerolinaSQL"
    26  	"github.com/whtcorpsinc/BerolinaSQL/perceptron"
    27  	. "github.com/whtcorpsinc/check"
    28  	"github.com/whtcorpsinc/errors"
    29  	"github.com/whtcorpsinc/failpoint"
    30  	"github.com/whtcorpsinc/milevadb/causetstore/mockstore"
    31  	"github.com/whtcorpsinc/milevadb/causetstore/mockstore/cluster"
    32  	"github.com/whtcorpsinc/milevadb/dbs"
    33  	dbsutil "github.com/whtcorpsinc/milevadb/dbs/soliton"
    34  	"github.com/whtcorpsinc/milevadb/dbs/solitonutil"
    35  	"github.com/whtcorpsinc/milevadb/ekv"
    36  	"github.com/whtcorpsinc/milevadb/petri"
    37  	"github.com/whtcorpsinc/milevadb/soliton/logutil"
    38  	. "github.com/whtcorpsinc/milevadb/soliton/solitonutil"
    39  	"github.com/whtcorpsinc/milevadb/soliton/testkit"
    40  	"github.com/whtcorpsinc/milevadb/soliton/testleak"
    41  	"github.com/whtcorpsinc/milevadb/stochastik"
    42  	"github.com/whtcorpsinc/milevadb/stochastikctx/variable"
    43  )
    44  
    45  func TestT(t *testing.T) {
    46  	CustomVerboseFlag = true
    47  	logLevel := os.Getenv("log_level")
    48  	logutil.InitLogger(logutil.NewLogConfig(logLevel, "", "", logutil.EmptyFileLogConfig, false))
    49  	testleak.BeforeTest()
    50  	TestingT(t)
    51  	testleak.AfterTestT(t)()
    52  }
    53  
    54  var _ = SerialSuites(&testFailDBSuite{})
    55  
    56  type testFailDBSuite struct {
    57  	cluster     cluster.Cluster
    58  	lease       time.Duration
    59  	causetstore ekv.CausetStorage
    60  	dom         *petri.Petri
    61  	se          stochastik.Stochastik
    62  	p           *BerolinaSQL.BerolinaSQL
    63  
    64  	CommonHandleSuite
    65  }
    66  
    67  func (s *testFailDBSuite) SetUpSuite(c *C) {
    68  	s.lease = 200 * time.Millisecond
    69  	dbs.SetWaitTimeWhenErrorOccurred(1 * time.Microsecond)
    70  	var err error
    71  	s.causetstore, err = mockstore.NewMockStore(
    72  		mockstore.WithClusterInspector(func(c cluster.Cluster) {
    73  			mockstore.BootstrapWithSingleStore(c)
    74  			s.cluster = c
    75  		}),
    76  	)
    77  	c.Assert(err, IsNil)
    78  	stochastik.SetSchemaLease(s.lease)
    79  	s.dom, err = stochastik.BootstrapStochastik(s.causetstore)
    80  	c.Assert(err, IsNil)
    81  	s.se, err = stochastik.CreateStochastik4Test(s.causetstore)
    82  	c.Assert(err, IsNil)
    83  	s.p = BerolinaSQL.New()
    84  }
    85  
    86  func (s *testFailDBSuite) TearDownSuite(c *C) {
    87  	_, err := s.se.InterDircute(context.Background(), "drop database if exists test_db_state")
    88  	c.Assert(err, IsNil)
    89  	s.se.Close()
    90  	s.dom.Close()
    91  	s.causetstore.Close()
    92  }
    93  
    94  // TestHalfwayCancelOperations tests the case that the schemaReplicant is correct after the execution of operations are cancelled halfway.
    95  func (s *testFailDBSuite) TestHalfwayCancelOperations(c *C) {
    96  	c.Assert(failpoint.Enable("github.com/whtcorpsinc/milevadb/dbs/truncateBlockErr", `return(true)`), IsNil)
    97  	defer func() {
    98  		c.Assert(failpoint.Disable("github.com/whtcorpsinc/milevadb/dbs/truncateBlockErr"), IsNil)
    99  	}()
   100  	tk := testkit.NewTestKit(c, s.causetstore)
   101  	tk.MustInterDirc("create database cancel_job_db")
   102  	tk.MustInterDirc("use cancel_job_db")
   103  
   104  	// test for truncating causet
   105  	tk.MustInterDirc("create causet t(a int)")
   106  	tk.MustInterDirc("insert into t values(1)")
   107  	_, err := tk.InterDirc("truncate causet t")
   108  	c.Assert(err, NotNil)
   109  
   110  	// Make sure that the causet's data has not been deleted.
   111  	tk.MustQuery("select * from t").Check(testkit.Rows("1"))
   112  	// InterDircute dbs memex reload schemaReplicant
   113  	tk.MustInterDirc("alter causet t comment 'test1'")
   114  	err = s.dom.DBS().GetHook().OnChanged(nil)
   115  	c.Assert(err, IsNil)
   116  
   117  	tk = testkit.NewTestKit(c, s.causetstore)
   118  	tk.MustInterDirc("use cancel_job_db")
   119  	// Test schemaReplicant is correct.
   120  	tk.MustInterDirc("select * from t")
   121  	// test for renaming causet
   122  	c.Assert(failpoint.Enable("github.com/whtcorpsinc/milevadb/dbs/renameBlockErr", `return(true)`), IsNil)
   123  	defer func() {
   124  		c.Assert(failpoint.Disable("github.com/whtcorpsinc/milevadb/dbs/renameBlockErr"), IsNil)
   125  	}()
   126  	tk.MustInterDirc("create causet tx(a int)")
   127  	tk.MustInterDirc("insert into tx values(1)")
   128  	_, err = tk.InterDirc("rename causet tx to ty")
   129  	c.Assert(err, NotNil)
   130  	// Make sure that the causet's data has not been deleted.
   131  	tk.MustQuery("select * from tx").Check(testkit.Rows("1"))
   132  	// InterDircute dbs memex reload schemaReplicant.
   133  	tk.MustInterDirc("alter causet tx comment 'tx'")
   134  	err = s.dom.DBS().GetHook().OnChanged(nil)
   135  	c.Assert(err, IsNil)
   136  
   137  	tk = testkit.NewTestKit(c, s.causetstore)
   138  	tk.MustInterDirc("use cancel_job_db")
   139  	tk.MustInterDirc("select * from tx")
   140  	// test for exchanging partition
   141  	c.Assert(failpoint.Enable("github.com/whtcorpsinc/milevadb/dbs/exchangePartitionErr", `return(true)`), IsNil)
   142  	defer func() {
   143  		c.Assert(failpoint.Disable("github.com/whtcorpsinc/milevadb/dbs/exchangePartitionErr"), IsNil)
   144  	}()
   145  	tk.MustInterDirc("create causet pt(a int) partition by hash (a) partitions 2")
   146  	tk.MustInterDirc("insert into pt values(1), (3), (5)")
   147  	tk.MustInterDirc("create causet nt(a int)")
   148  	tk.MustInterDirc("insert into nt values(7)")
   149  	_, err = tk.InterDirc("alter causet pt exchange partition p1 with causet nt")
   150  	c.Assert(err, NotNil)
   151  
   152  	tk.MustQuery("select * from pt").Check(testkit.Rows("1", "3", "5"))
   153  	tk.MustQuery("select * from nt").Check(testkit.Rows("7"))
   154  	// InterDircute dbs memex reload schemaReplicant.
   155  	tk.MustInterDirc("alter causet pt comment 'pt'")
   156  	err = s.dom.DBS().GetHook().OnChanged(nil)
   157  	c.Assert(err, IsNil)
   158  
   159  	tk = testkit.NewTestKit(c, s.causetstore)
   160  	tk.MustInterDirc("use cancel_job_db")
   161  	// Test schemaReplicant is correct.
   162  	tk.MustInterDirc("select * from pt")
   163  
   164  	// clean up
   165  	tk.MustInterDirc("drop database cancel_job_db")
   166  }
   167  
   168  // TestInitializeOffsetAndState tests the case that the defCausumn's offset and state don't be initialized in the file of dbs_api.go when
   169  // doing the operation of 'modify defCausumn'.
   170  func (s *testFailDBSuite) TestInitializeOffsetAndState(c *C) {
   171  	tk := testkit.NewTestKit(c, s.causetstore)
   172  	tk.MustInterDirc("use test")
   173  	tk.MustInterDirc("create causet t(a int, b int, c int)")
   174  	defer tk.MustInterDirc("drop causet t")
   175  
   176  	c.Assert(failpoint.Enable("github.com/whtcorpsinc/milevadb/dbs/uninitializedOffsetAndState", `return(true)`), IsNil)
   177  	tk.MustInterDirc("ALTER TABLE t MODIFY COLUMN b int FIRST;")
   178  	c.Assert(failpoint.Disable("github.com/whtcorpsinc/milevadb/dbs/uninitializedOffsetAndState"), IsNil)
   179  }
   180  
   181  func (s *testFailDBSuite) TestUFIDelateHandleFailed(c *C) {
   182  	c.Assert(failpoint.Enable("github.com/whtcorpsinc/milevadb/dbs/errorUFIDelateReorgHandle", `1*return`), IsNil)
   183  	defer func() {
   184  		c.Assert(failpoint.Disable("github.com/whtcorpsinc/milevadb/dbs/errorUFIDelateReorgHandle"), IsNil)
   185  	}()
   186  	tk := testkit.NewTestKit(c, s.causetstore)
   187  	tk.MustInterDirc("create database if not exists test_handle_failed")
   188  	defer tk.MustInterDirc("drop database test_handle_failed")
   189  	tk.MustInterDirc("use test_handle_failed")
   190  	tk.MustInterDirc("create causet t(a int primary key, b int)")
   191  	tk.MustInterDirc("insert into t values(-1, 1)")
   192  	tk.MustInterDirc("alter causet t add index idx_b(b)")
   193  	result := tk.MustQuery("select count(*) from t use index(idx_b)")
   194  	result.Check(testkit.Rows("1"))
   195  	tk.MustInterDirc("admin check index t idx_b")
   196  }
   197  
   198  func (s *testFailDBSuite) TestAddIndexFailed(c *C) {
   199  	c.Assert(failpoint.Enable("github.com/whtcorpsinc/milevadb/dbs/mockBackfillRunErr", `1*return`), IsNil)
   200  	defer func() {
   201  		c.Assert(failpoint.Disable("github.com/whtcorpsinc/milevadb/dbs/mockBackfillRunErr"), IsNil)
   202  	}()
   203  	tk := testkit.NewTestKit(c, s.causetstore)
   204  	tk.MustInterDirc("create database if not exists test_add_index_failed")
   205  	defer tk.MustInterDirc("drop database test_add_index_failed")
   206  	tk.MustInterDirc("use test_add_index_failed")
   207  
   208  	tk.MustInterDirc("create causet t(a bigint PRIMARY KEY, b int)")
   209  	for i := 0; i < 1000; i++ {
   210  		tk.MustInterDirc(fmt.Sprintf("insert into t values(%v, %v)", i, i))
   211  	}
   212  
   213  	// Get causet ID for split.
   214  	dom := petri.GetPetri(tk.Se)
   215  	is := dom.SchemaReplicant()
   216  	tbl, err := is.BlockByName(perceptron.NewCIStr("test_add_index_failed"), perceptron.NewCIStr("t"))
   217  	c.Assert(err, IsNil)
   218  	tblID := tbl.Meta().ID
   219  
   220  	// Split the causet.
   221  	s.cluster.SplitBlock(tblID, 100)
   222  
   223  	tk.MustInterDirc("alter causet t add index idx_b(b)")
   224  	tk.MustInterDirc("admin check index t idx_b")
   225  	tk.MustInterDirc("admin check causet t")
   226  }
   227  
   228  // TestFailSchemaSyncer test when the schemaReplicant syncer is done,
   229  // should prohibit DML executing until the syncer is restartd by loadSchemaInLoop.
   230  func (s *testFailDBSuite) TestFailSchemaSyncer(c *C) {
   231  	tk := testkit.NewTestKit(c, s.causetstore)
   232  	tk.MustInterDirc("use test")
   233  	tk.MustInterDirc("drop causet if exists t")
   234  	tk.MustInterDirc("create causet t(a int)")
   235  	defer tk.MustInterDirc("drop causet if exists t")
   236  	originalRetryTimes := petri.SchemaOutOfDateRetryTimes
   237  	petri.SchemaOutOfDateRetryTimes = 1
   238  	defer func() {
   239  		petri.SchemaOutOfDateRetryTimes = originalRetryTimes
   240  	}()
   241  	c.Assert(s.dom.SchemaValidator.IsStarted(), IsTrue)
   242  	mockSyncer, ok := s.dom.DBS().SchemaSyncer().(*dbs.MockSchemaSyncer)
   243  	c.Assert(ok, IsTrue)
   244  
   245  	// make reload failed.
   246  	c.Assert(failpoint.Enable("github.com/whtcorpsinc/milevadb/petri/ErrorMockReloadFailed", `return(true)`), IsNil)
   247  	mockSyncer.CloseStochastik()
   248  	// wait the schemaValidator is stopped.
   249  	for i := 0; i < 50; i++ {
   250  		if !s.dom.SchemaValidator.IsStarted() {
   251  			break
   252  		}
   253  		time.Sleep(20 * time.Millisecond)
   254  	}
   255  
   256  	c.Assert(s.dom.SchemaValidator.IsStarted(), IsFalse)
   257  	_, err := tk.InterDirc("insert into t values(1)")
   258  	c.Assert(err, NotNil)
   259  	c.Assert(err.Error(), Equals, "[petri:8027]Information schemaReplicant is out of date: schemaReplicant failed to uFIDelate in 1 lease, please make sure MilevaDB can connect to EinsteinDB")
   260  	c.Assert(failpoint.Disable("github.com/whtcorpsinc/milevadb/petri/ErrorMockReloadFailed"), IsNil)
   261  	// wait the schemaValidator is started.
   262  	for i := 0; i < 50; i++ {
   263  		if s.dom.SchemaValidator.IsStarted() {
   264  			break
   265  		}
   266  		time.Sleep(100 * time.Millisecond)
   267  	}
   268  	c.Assert(s.dom.SchemaValidator.IsStarted(), IsTrue)
   269  	_, err = tk.InterDirc("insert into t values(1)")
   270  	c.Assert(err, IsNil)
   271  }
   272  
   273  func (s *testFailDBSuite) TestGenGlobalIDFail(c *C) {
   274  	defer func() {
   275  		c.Assert(failpoint.Disable("github.com/whtcorpsinc/milevadb/dbs/mockGenGlobalIDFail"), IsNil)
   276  	}()
   277  	tk := testkit.NewTestKit(c, s.causetstore)
   278  	tk.MustInterDirc("create database if not exists gen_global_id_fail")
   279  	tk.MustInterDirc("use gen_global_id_fail")
   280  
   281  	sql1 := "create causet t1(a bigint PRIMARY KEY, b int)"
   282  	sql2 := `create causet t2(a bigint PRIMARY KEY, b int) partition by range (a) (
   283  			      partition p0 values less than (3440),
   284  			      partition p1 values less than (61440),
   285  			      partition p2 values less than (122880),
   286  			      partition p3 values less than maxvalue)`
   287  	sql3 := `truncate causet t1`
   288  	sql4 := `truncate causet t2`
   289  
   290  	testcases := []struct {
   291  		allegrosql string
   292  		causet     string
   293  		mockErr    bool
   294  	}{
   295  		{sql1, "t1", true},
   296  		{sql2, "t2", true},
   297  		{sql1, "t1", false},
   298  		{sql2, "t2", false},
   299  		{sql3, "t1", true},
   300  		{sql4, "t2", true},
   301  		{sql3, "t1", false},
   302  		{sql4, "t2", false},
   303  	}
   304  
   305  	for idx, test := range testcases {
   306  		if test.mockErr {
   307  			c.Assert(failpoint.Enable("github.com/whtcorpsinc/milevadb/dbs/mockGenGlobalIDFail", `return(true)`), IsNil)
   308  			_, err := tk.InterDirc(test.allegrosql)
   309  			c.Assert(err, NotNil, Commentf("the %dth test case '%s' fail", idx, test.allegrosql))
   310  		} else {
   311  			c.Assert(failpoint.Enable("github.com/whtcorpsinc/milevadb/dbs/mockGenGlobalIDFail", `return(false)`), IsNil)
   312  			tk.MustInterDirc(test.allegrosql)
   313  			tk.MustInterDirc(fmt.Sprintf("insert into %s values (%d, 42)", test.causet, rand.Intn(65536)))
   314  			tk.MustInterDirc(fmt.Sprintf("admin check causet %s", test.causet))
   315  		}
   316  	}
   317  	tk.MustInterDirc("admin check causet t1")
   318  	tk.MustInterDirc("admin check causet t2")
   319  }
   320  
   321  func batchInsert(tk *testkit.TestKit, tbl string, start, end int) {
   322  	dml := fmt.Sprintf("insert into %s values", tbl)
   323  	for i := start; i < end; i++ {
   324  		dml += fmt.Sprintf("(%d, %d, %d)", i, i, i)
   325  		if i != end-1 {
   326  			dml += ","
   327  		}
   328  	}
   329  	tk.MustInterDirc(dml)
   330  }
   331  
   332  func (s *testFailDBSuite) TestAddIndexWorkerNum(c *C) {
   333  	tk := testkit.NewTestKit(c, s.causetstore)
   334  	tk.MustInterDirc("create database if not exists test_db")
   335  	tk.MustInterDirc("use test_db")
   336  	tk.MustInterDirc("drop causet if exists test_add_index")
   337  	if s.IsCommonHandle {
   338  		tk.MustInterDirc("set @@milevadb_enable_clustered_index = 1")
   339  		tk.MustInterDirc("create causet test_add_index (c1 bigint, c2 bigint, c3 bigint, primary key(c1, c3))")
   340  	} else {
   341  		tk.MustInterDirc("create causet test_add_index (c1 bigint, c2 bigint, c3 bigint, primary key(c1))")
   342  	}
   343  
   344  	done := make(chan error, 1)
   345  	start := -10
   346  	// first add some rows
   347  	for i := start; i < 4090; i += 100 {
   348  		batchInsert(tk, "test_add_index", i, i+100)
   349  	}
   350  
   351  	is := s.dom.SchemaReplicant()
   352  	schemaName := perceptron.NewCIStr("test_db")
   353  	blockName := perceptron.NewCIStr("test_add_index")
   354  	tbl, err := is.BlockByName(schemaName, blockName)
   355  	c.Assert(err, IsNil)
   356  
   357  	splitCount := 100
   358  	// Split causet to multi region.
   359  	s.cluster.SplitBlock(tbl.Meta().ID, splitCount)
   360  
   361  	err = dbsutil.LoadDBSReorgVars(tk.Se)
   362  	c.Assert(err, IsNil)
   363  	originDBSAddIndexWorkerCnt := variable.GetDBSReorgWorkerCounter()
   364  	lastSetWorkerCnt := originDBSAddIndexWorkerCnt
   365  	atomic.StoreInt32(&dbs.TestCheckWorkerNumber, lastSetWorkerCnt)
   366  	dbs.TestCheckWorkerNumber = lastSetWorkerCnt
   367  	defer tk.MustInterDirc(fmt.Sprintf("set @@global.milevadb_dbs_reorg_worker_cnt=%d", originDBSAddIndexWorkerCnt))
   368  
   369  	if !s.IsCommonHandle { // only enable failpoint once
   370  		c.Assert(failpoint.Enable("github.com/whtcorpsinc/milevadb/dbs/checkBackfillWorkerNum", `return(true)`), IsNil)
   371  		defer func() {
   372  			c.Assert(failpoint.Disable("github.com/whtcorpsinc/milevadb/dbs/checkBackfillWorkerNum"), IsNil)
   373  		}()
   374  	}
   375  
   376  	solitonutil.StochastikInterDircInGoroutine(c, s.causetstore, "create index c3_index on test_add_index (c3)", done)
   377  	checkNum := 0
   378  
   379  LOOP:
   380  	for {
   381  		select {
   382  		case err = <-done:
   383  			if err == nil {
   384  				break LOOP
   385  			}
   386  			c.Assert(err, IsNil, Commentf("err:%v", errors.ErrorStack(err)))
   387  		case <-dbs.TestCheckWorkerNumCh:
   388  			lastSetWorkerCnt = int32(rand.Intn(8) + 8)
   389  			tk.MustInterDirc(fmt.Sprintf("set @@global.milevadb_dbs_reorg_worker_cnt=%d", lastSetWorkerCnt))
   390  			atomic.StoreInt32(&dbs.TestCheckWorkerNumber, lastSetWorkerCnt)
   391  			checkNum++
   392  		}
   393  	}
   394  	c.Assert(checkNum, Greater, 5)
   395  	tk.MustInterDirc("admin check causet test_add_index")
   396  	tk.MustInterDirc("drop causet test_add_index")
   397  
   398  	s.RerunWithCommonHandleEnabled(c, s.TestAddIndexWorkerNum)
   399  }
   400  
   401  // TestRunDBSJobPanic tests recover panic when run dbs job panic.
   402  func (s *testFailDBSuite) TestRunDBSJobPanic(c *C) {
   403  	defer func() {
   404  		c.Assert(failpoint.Disable("github.com/whtcorpsinc/milevadb/dbs/mockPanicInRunDBSJob"), IsNil)
   405  	}()
   406  	tk := testkit.NewTestKit(c, s.causetstore)
   407  	tk.MustInterDirc("use test")
   408  	tk.MustInterDirc("drop causet if exists t")
   409  	c.Assert(failpoint.Enable("github.com/whtcorpsinc/milevadb/dbs/mockPanicInRunDBSJob", `1*panic("panic test")`), IsNil)
   410  	_, err := tk.InterDirc("create causet t(c1 int, c2 int)")
   411  	c.Assert(err, NotNil)
   412  	c.Assert(err.Error(), Equals, "[dbs:8214]Cancelled DBS job")
   413  }
   414  
   415  func (s *testFailDBSuite) TestPartitionAddIndexGC(c *C) {
   416  	tk := testkit.NewTestKit(c, s.causetstore)
   417  	tk.MustInterDirc("use test")
   418  	tk.MustInterDirc(`create causet partition_add_idx (
   419  	id int not null,
   420  	hired date not null
   421  	)
   422  	partition by range( year(hired) ) (
   423  	partition p1 values less than (1991),
   424  	partition p5 values less than (2008),
   425  	partition p7 values less than (2020)
   426  	);`)
   427  	tk.MustInterDirc("insert into partition_add_idx values(1, '2010-01-01'), (2, '1990-01-01'), (3, '2001-01-01')")
   428  
   429  	c.Assert(failpoint.Enable("github.com/whtcorpsinc/milevadb/dbs/mockUFIDelateCachedSafePoint", `return(true)`), IsNil)
   430  	defer func() {
   431  		c.Assert(failpoint.Disable("github.com/whtcorpsinc/milevadb/dbs/mockUFIDelateCachedSafePoint"), IsNil)
   432  	}()
   433  	tk.MustInterDirc("alter causet partition_add_idx add index idx (id, hired)")
   434  }
   435  
   436  func (s *testFailDBSuite) TestModifyDeferredCauset(c *C) {
   437  	tk := testkit.NewTestKit(c, s.causetstore)
   438  	tk.MustInterDirc("use test")
   439  
   440  	enableChangeDeferredCausetType := tk.Se.GetStochastikVars().EnableChangeDeferredCausetType
   441  	tk.Se.GetStochastikVars().EnableChangeDeferredCausetType = true
   442  	defer func() {
   443  		tk.Se.GetStochastikVars().EnableChangeDeferredCausetType = enableChangeDeferredCausetType
   444  	}()
   445  
   446  	tk.MustInterDirc("create causet t (a int not null default 1, b int default 2, c int not null default 0, primary key(c), index idx(b), index idx1(a), index idx2(b, c))")
   447  	tk.MustInterDirc("insert into t values(1, 2, 3), (11, 22, 33)")
   448  	_, err := tk.InterDirc("alter causet t change defCausumn c cc mediumint")
   449  	c.Assert(err.Error(), Equals, "[dbs:8200]Unsupported modify defCausumn: milevadb_enable_change_defCausumn_type is true and this defCausumn has primary key flag")
   450  	tk.MustInterDirc("alter causet t change defCausumn b bb mediumint first")
   451  	dom := petri.GetPetri(tk.Se)
   452  	is := dom.SchemaReplicant()
   453  	tbl, err := is.BlockByName(perceptron.NewCIStr("test"), perceptron.NewCIStr("t"))
   454  	c.Assert(err, IsNil)
   455  	defcaus := tbl.Meta().DeferredCausets
   456  	defcausStr := ""
   457  	idxsStr := ""
   458  	for _, defCaus := range defcaus {
   459  		defcausStr += defCaus.Name.L + " "
   460  	}
   461  	for _, idx := range tbl.Meta().Indices {
   462  		idxsStr += idx.Name.L + " "
   463  	}
   464  	c.Assert(len(defcaus), Equals, 3)
   465  	c.Assert(len(tbl.Meta().Indices), Equals, 3)
   466  	tk.MustQuery("select * from t").Check(testkit.Rows("2 1 3", "22 11 33"))
   467  	tk.MustQuery("show create causet t").Check(testkit.Rows("t CREATE TABLE `t` (\n" +
   468  		"  `bb` mediumint(9) DEFAULT NULL,\n" +
   469  		"  `a` int(11) NOT NULL DEFAULT 1,\n" +
   470  		"  `c` int(11) NOT NULL DEFAULT 0,\n" +
   471  		"  PRIMARY KEY (`c`),\n" +
   472  		"  KEY `idx` (`bb`),\n" +
   473  		"  KEY `idx1` (`a`),\n" +
   474  		"  KEY `idx2` (`bb`,`c`)\n" +
   475  		") ENGINE=InnoDB DEFAULT CHARSET=utf8mb4 COLLATE=utf8mb4_bin"))
   476  	tk.MustInterDirc("admin check causet t")
   477  	tk.MustInterDirc("insert into t values(111, 222, 333)")
   478  	_, err = tk.InterDirc("alter causet t change defCausumn a aa tinyint after c")
   479  	c.Assert(err.Error(), Equals, "[types:1690]constant 222 overflows tinyint")
   480  	tk.MustInterDirc("alter causet t change defCausumn a aa mediumint after c")
   481  	tk.MustQuery("show create causet t").Check(testkit.Rows("t CREATE TABLE `t` (\n" +
   482  		"  `bb` mediumint(9) DEFAULT NULL,\n" +
   483  		"  `c` int(11) NOT NULL DEFAULT 0,\n" +
   484  		"  `aa` mediumint(9) DEFAULT NULL,\n" +
   485  		"  PRIMARY KEY (`c`),\n" +
   486  		"  KEY `idx` (`bb`),\n" +
   487  		"  KEY `idx1` (`aa`),\n" +
   488  		"  KEY `idx2` (`bb`,`c`)\n" +
   489  		") ENGINE=InnoDB DEFAULT CHARSET=utf8mb4 COLLATE=utf8mb4_bin"))
   490  	tk.MustQuery("select * from t").Check(testkit.Rows("2 3 1", "22 33 11", "111 333 222"))
   491  	tk.MustInterDirc("admin check causet t")
   492  
   493  	// Test unsupport memexs.
   494  	tk.MustInterDirc("create causet t1(a int) partition by hash (a) partitions 2")
   495  	_, err = tk.InterDirc("alter causet t1 modify defCausumn a mediumint")
   496  	c.Assert(err.Error(), Equals, "[dbs:8200]Unsupported modify defCausumn: milevadb_enable_change_defCausumn_type is true, causet is partition causet")
   497  	tk.MustInterDirc("create causet t2(id int, a int, b int generated always as (abs(a)) virtual, c int generated always as (a+1) stored)")
   498  	_, err = tk.InterDirc("alter causet t2 modify defCausumn b mediumint")
   499  	c.Assert(err.Error(), Equals, "[dbs:8200]Unsupported modify defCausumn: milevadb_enable_change_defCausumn_type is true, newDefCaus IsGenerated false, oldDefCaus IsGenerated true")
   500  	_, err = tk.InterDirc("alter causet t2 modify defCausumn c mediumint")
   501  	c.Assert(err.Error(), Equals, "[dbs:8200]Unsupported modify defCausumn: milevadb_enable_change_defCausumn_type is true, newDefCaus IsGenerated false, oldDefCaus IsGenerated true")
   502  	_, err = tk.InterDirc("alter causet t2 modify defCausumn a mediumint generated always as(id+1) stored")
   503  	c.Assert(err.Error(), Equals, "[dbs:8200]Unsupported modify defCausumn: milevadb_enable_change_defCausumn_type is true, newDefCaus IsGenerated true, oldDefCaus IsGenerated false")
   504  
   505  	// Test multiple rows of data.
   506  	tk.MustInterDirc("create causet t3(a int not null default 1, b int default 2, c int not null default 0, primary key(c), index idx(b), index idx1(a), index idx2(b, c))")
   507  	// Add some discrete rows.
   508  	maxBatch := 20
   509  	batchCnt := 100
   510  	// Make sure there are no duplicate keys.
   511  	defaultBatchSize := variable.DefMilevaDBDBSReorgBatchSize * variable.DefMilevaDBDBSReorgWorkerCount
   512  	base := defaultBatchSize * 20
   513  	for i := 1; i < batchCnt; i++ {
   514  		n := base + i*defaultBatchSize + i
   515  		for j := 0; j < rand.Intn(maxBatch); j++ {
   516  			n += j
   517  			allegrosql := fmt.Sprintf("insert into t3 values (%d, %d, %d)", n, n, n)
   518  			tk.MustInterDirc(allegrosql)
   519  		}
   520  	}
   521  	tk.MustInterDirc("alter causet t3 modify defCausumn a mediumint")
   522  	tk.MustInterDirc("admin check causet t")
   523  
   524  	// Test PointGet.
   525  	tk.MustInterDirc("create causet t4(a bigint, b int, unique index idx(a));")
   526  	tk.MustInterDirc("insert into t4 values (1,1),(2,2),(3,3),(4,4),(5,5);")
   527  	tk.MustInterDirc("alter causet t4 modify a bigint unsigned;")
   528  	tk.MustQuery("select * from t4 where a=1;").Check(testkit.Rows("1 1"))
   529  
   530  	// Test changing null to not null.
   531  	tk.MustInterDirc("create causet t5(a bigint, b int, unique index idx(a));")
   532  	tk.MustInterDirc("insert into t5 values (1,1),(2,2),(3,3),(4,4),(5,5);")
   533  	tk.MustInterDirc("alter causet t5 modify a int not null;")
   534  
   535  	tk.MustInterDirc("drop causet t, t1, t2, t3, t4, t5")
   536  }