-
Notifications
You must be signed in to change notification settings - Fork 2.1k
New issue
Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.
By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.
Already on GitHub? Sign in to your account
Online DDL: ensure high lock_wait_timeout
in Vreplication cut-over
#16601
Changes from 1 commit
5afea9a
406d278
6f746f4
610908a
99da022
3d19e74
File filter
Filter by extension
Conversations
Jump to
Diff view
Diff view
There are no files selected for viewing
Original file line number | Diff line number | Diff line change |
---|---|---|
|
@@ -979,7 +979,16 @@ func (e *Executor) cutOverVReplMigration(ctx context.Context, s *VReplStream, sh | |
if err != nil { | ||
return err | ||
} | ||
// Set large enough `@@lock_wait_timeout` so that it does not interfere with the cut-over operation. | ||
// The code will ensure everything that needs to be terminated by `migrationCutOverThreshold` will be terminated. | ||
// Setting `lock_wait_timeout` here is done to just ensure MySQL does not interrupt prematurely. It is not | ||
// done by means of ensuring cleanup/termination of operations. | ||
lockConnRestoreLockWaitTimeout, err := e.initConnectionLockWaitTimeout(ctx, lockConn.Conn, 5*migrationCutOverThreshold) | ||
if err != nil { | ||
return err | ||
} | ||
defer lockConn.Recycle() | ||
defer lockConnRestoreLockWaitTimeout() | ||
defer lockConn.Conn.Exec(ctx, sqlUnlockTables, 1, false) | ||
|
||
renameCompleteChan := make(chan error) | ||
|
@@ -988,6 +997,14 @@ func (e *Executor) cutOverVReplMigration(ctx context.Context, s *VReplStream, sh | |
if err != nil { | ||
return err | ||
} | ||
// Set large enough `@@lock_wait_timeout` so that it does not interfere with the cut-over operation. | ||
// The code will ensure everything that needs to be terminated by `migrationCutOverThreshold` will be terminated. | ||
// Setting `lock_wait_timeout` here is done to just ensure MySQL does not interrupt prematurely. It is not | ||
// done by means of ensuring cleanup/termination of operations. | ||
There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. I'm not sure what the There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. I was trying to explain that There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. You can probably remove that whole sentence. The comment already says "The code will ensure ...", which is sufficient explanation. There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. Removed. |
||
renameConnRestoreLockWaitTimeout, err := e.initConnectionLockWaitTimeout(ctx, renameConn.Conn, 5*migrationCutOverThreshold*4) | ||
if err != nil { | ||
return err | ||
} | ||
defer renameConn.Recycle() | ||
defer func() { | ||
if !renameWasSuccessful { | ||
|
@@ -997,6 +1014,8 @@ func (e *Executor) cutOverVReplMigration(ctx context.Context, s *VReplStream, sh | |
} | ||
} | ||
}() | ||
defer renameConnRestoreLockWaitTimeout() | ||
|
||
// See if backend MySQL server supports 'rename_table_preserve_foreign_key' variable | ||
preserveFKSupported, err := e.isPreserveForeignKeySupported(ctx) | ||
if err != nil { | ||
|
@@ -1260,6 +1279,25 @@ func (e *Executor) initMigrationSQLMode(ctx context.Context, onlineDDL *schema.O | |
return deferFunc, nil | ||
} | ||
|
||
// initConnectionLockWaitTimeout sets the given locak_wait_timeout for the given connection, with a deferred value restoration function | ||
There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. lock is spelt wrong here (locak) |
||
func (e *Executor) initConnectionLockWaitTimeout(ctx context.Context, conn *connpool.Conn, lockWaitTimeout time.Duration) (deferFunc func(), err error) { | ||
deferFunc = func() {} | ||
mattlord marked this conversation as resolved.
Show resolved
Hide resolved
|
||
|
||
if _, err := conn.Exec(ctx, `set @lock_wait_timeout=@@lock_wait_timeout`, 0, false); err != nil { | ||
There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. Nit, but IMO slightly clearer to always use the return var. i.e. not use There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. IMO it would add clarity and intention to specify global here and a comment for those not super famiilar:
Similar for the defer:
(we are using There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more.
My take is the opposite, I always find it more comfortable to be explicit. There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. Now using explicit |
||
return deferFunc, vterrors.Errorf(vtrpcpb.Code_UNKNOWN, "could not read lock_wait_timeout: %v", err) | ||
} | ||
timeoutSeconds := int64(lockWaitTimeout.Seconds()) | ||
setQuery := fmt.Sprintf("set @@session.lock_wait_timeout=%d", timeoutSeconds) | ||
_, err = conn.Exec(ctx, setQuery, 0, false) | ||
if err != nil { | ||
return deferFunc, err | ||
} | ||
deferFunc = func() { | ||
conn.Exec(ctx, "SET lock_wait_timeout=@lock_wait_timeout", 0, false) | ||
} | ||
return deferFunc, nil | ||
} | ||
|
||
// newConstraintName generates a new, unique name for a constraint. Our problem is that a MySQL | ||
// constraint's name is unique in the schema (!). And so as we duplicate the original table, we must | ||
// create completely new names for all constraints. | ||
|
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Where does this
100000
value come from?There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Just some high value. Let me change that into something more official. One sec.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
now setting to actual original
lock_wait_timeout
.