ddl: disallow changing the default value of the primary key column to null (#24417)

This commit is contained in:
Lynn
2021-05-06 21:01:52 +08:00
committed by GitHub
parent bc4a38c9b9
commit 5bd601bdae
2 changed files with 39 additions and 32 deletions

View File

@ -1702,6 +1702,20 @@ func (s *testColumnTypeChangeSuite) TestChangingAttributeOfColumnWithFK(c *C) {
tk.MustExec("drop table if exists orders, users")
}
func (s *testColumnTypeChangeSuite) TestAlterPrimaryKeyToNull(c *C) {
tk := testkit.NewTestKit(c, s.store)
tk.MustExec("use test")
tk.Se.GetSessionVars().EnableChangeColumnType = true
tk.MustExec("drop table if exists t, t1")
tk.MustExec("create table t(a int not null, b int not null, primary key(a, b));")
tk.MustGetErrCode("alter table t modify a bigint null;", mysql.ErrPrimaryCantHaveNull)
tk.MustGetErrCode("alter table t change column a a bigint null;", mysql.ErrPrimaryCantHaveNull)
tk.MustExec("create table t1(a int not null, b int not null, primary key(a));")
tk.MustGetErrCode("alter table t modify a bigint null;", mysql.ErrPrimaryCantHaveNull)
tk.MustGetErrCode("alter table t change column a a bigint null;", mysql.ErrPrimaryCantHaveNull)
}
// Close issue #23202
func (s *testColumnTypeChangeSuite) TestDDLExitWhenCancelMeetPanic(c *C) {
tk := testkit.NewTestKit(c, s.store)

View File

@ -690,24 +690,7 @@ func columnDefToCol(ctx sessionctx.Context, offset int, colDef *ast.ColumnDef, o
}
}
processDefaultValue(col, hasDefaultValue, setOnUpdateNow)
processColumnFlags(col)
err = checkPriKeyConstraint(col, hasDefaultValue, hasNullFlag, outPriKeyConstraint)
if err != nil {
return nil, nil, errors.Trace(err)
}
err = checkColumnValueConstraint(col, col.Collate)
if err != nil {
return nil, nil, errors.Trace(err)
}
err = checkDefaultValue(ctx, col, hasDefaultValue)
if err != nil {
return nil, nil, errors.Trace(err)
}
err = checkColumnFieldLength(col)
if err != nil {
if err = processAndCheckDefaultValueAndColumn(ctx, col, outPriKeyConstraint, hasDefaultValue, setOnUpdateNow, hasNullFlag); err != nil {
return nil, nil, errors.Trace(err)
}
return col, constraints, nil
@ -3675,6 +3658,7 @@ func processColumnOptions(ctx sessionctx.Context, col *table.Column, options []*
var hasDefaultValue, setOnUpdateNow bool
var err error
var hasNullFlag bool
for _, opt := range options {
switch opt.Tp {
case ast.ColumnOptionDefaultValue:
@ -3690,6 +3674,7 @@ func processColumnOptions(ctx sessionctx.Context, col *table.Column, options []*
case ast.ColumnOptionNotNull:
col.Flag |= mysql.NotNullFlag
case ast.ColumnOptionNull:
hasNullFlag = true
col.Flag &= ^mysql.NotNullFlag
case ast.ColumnOptionAutoIncrement:
col.Flag |= mysql.AutoIncrementFlag
@ -3734,17 +3719,33 @@ func processColumnOptions(ctx sessionctx.Context, col *table.Column, options []*
}
}
processDefaultValue(col, hasDefaultValue, setOnUpdateNow)
processColumnFlags(col)
if hasDefaultValue {
return errors.Trace(checkDefaultValue(ctx, col, true))
if err = processAndCheckDefaultValueAndColumn(ctx, col, nil, hasDefaultValue, setOnUpdateNow, hasNullFlag); err != nil {
return errors.Trace(err)
}
return nil
}
func processAndCheckDefaultValueAndColumn(ctx sessionctx.Context, col *table.Column, outPriKeyConstraint *ast.Constraint, hasDefaultValue, setOnUpdateNow, hasNullFlag bool) error {
processDefaultValue(col, hasDefaultValue, setOnUpdateNow)
processColumnFlags(col)
err := checkPriKeyConstraint(col, hasDefaultValue, hasNullFlag, outPriKeyConstraint)
if err != nil {
return errors.Trace(err)
}
if err = checkColumnValueConstraint(col, col.Collate); err != nil {
return errors.Trace(err)
}
if err = checkDefaultValue(ctx, col, hasDefaultValue); err != nil {
return errors.Trace(err)
}
if err = checkColumnFieldLength(col); err != nil {
return errors.Trace(err)
}
return nil
}
func (d *ddl) getModifiableColumnJob(ctx sessionctx.Context, ident ast.Ident, originalColName model.CIStr,
spec *ast.AlterTableSpec) (*model.Job, error) {
specNewColumn := spec.NewColumns[0]
@ -3854,10 +3855,6 @@ func (d *ddl) getModifiableColumnJob(ctx sessionctx.Context, ident ast.Ident, or
return nil, errors.Trace(err)
}
if err = checkColumnValueConstraint(newCol, newCol.Collate); err != nil {
return nil, errors.Trace(err)
}
if err = checkModifyTypes(ctx, &col.FieldType, &newCol.FieldType, isColumnWithIndex(col.Name.L, t.Meta().Indices)); err != nil {
if strings.Contains(err.Error(), "Unsupported modifying collation") {
colErrMsg := "Unsupported modifying collation of column '%s' from '%s' to '%s' when index is defined on it."
@ -3894,10 +3891,6 @@ func (d *ddl) getModifiableColumnJob(ctx sessionctx.Context, ident ast.Ident, or
modifyColumnTp = mysql.TypeNull
}
if err = checkColumnFieldLength(newCol); err != nil {
return nil, err
}
if err = checkColumnWithIndexConstraint(t.Meta(), col.ColumnInfo, newCol.ColumnInfo); err != nil {
return nil, err
}