Skip to content
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

sql: introduce preliminary support for savepoints #43051

Closed
wants to merge 2 commits into from
Closed
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
41 changes: 31 additions & 10 deletions pkg/sql/conn_executor.go
Original file line number Diff line number Diff line change
Expand Up @@ -919,6 +919,10 @@ type connExecutor struct {
// stateOpen.
autoRetryCounter int

// numDDL keeps track of how many DDL statements have been
// executed so far.
numDDL int

// txnRewindPos is the position within stmtBuf to which we'll rewind when
// performing automatic retries. This is more or less the position where the
// current transaction started.
Expand Down Expand Up @@ -2298,11 +2302,12 @@ type StatementCounters struct {
TxnCommitCount telemetry.CounterWithMetric
TxnRollbackCount telemetry.CounterWithMetric

// Savepoint operations. SavepointCount is for real SQL savepoints
// (which we don't yet support; this is just a placeholder for
// telemetry); the RestartSavepoint variants are for the
// Savepoint operations. SavepointCount is for real SQL savepoints;
// the RestartSavepoint variants are for the
// cockroach-specific client-side retry protocol.
SavepointCount telemetry.CounterWithMetric
ReleaseSavepointCount telemetry.CounterWithMetric
RollbackToSavepointCount telemetry.CounterWithMetric
RestartSavepointCount telemetry.CounterWithMetric
ReleaseRestartSavepointCount telemetry.CounterWithMetric
RollbackToRestartSavepointCount telemetry.CounterWithMetric
Expand All @@ -2322,14 +2327,18 @@ func makeStartedStatementCounters(internal bool) StatementCounters {
getMetricMeta(MetaTxnCommitStarted, internal)),
TxnRollbackCount: telemetry.NewCounterWithMetric(
getMetricMeta(MetaTxnRollbackStarted, internal)),
SavepointCount: telemetry.NewCounterWithMetric(
getMetricMeta(MetaSavepointStarted, internal)),
RestartSavepointCount: telemetry.NewCounterWithMetric(
getMetricMeta(MetaRestartSavepointStarted, internal)),
ReleaseRestartSavepointCount: telemetry.NewCounterWithMetric(
getMetricMeta(MetaReleaseRestartSavepointStarted, internal)),
RollbackToRestartSavepointCount: telemetry.NewCounterWithMetric(
getMetricMeta(MetaRollbackToRestartSavepointStarted, internal)),
SavepointCount: telemetry.NewCounterWithMetric(
getMetricMeta(MetaSavepointStarted, internal)),
ReleaseSavepointCount: telemetry.NewCounterWithMetric(
getMetricMeta(MetaReleaseSavepointStarted, internal)),
RollbackToSavepointCount: telemetry.NewCounterWithMetric(
getMetricMeta(MetaRollbackToSavepointStarted, internal)),
SelectCount: telemetry.NewCounterWithMetric(
getMetricMeta(MetaSelectStarted, internal)),
UpdateCount: telemetry.NewCounterWithMetric(
Expand All @@ -2355,14 +2364,18 @@ func makeExecutedStatementCounters(internal bool) StatementCounters {
getMetricMeta(MetaTxnCommitExecuted, internal)),
TxnRollbackCount: telemetry.NewCounterWithMetric(
getMetricMeta(MetaTxnRollbackExecuted, internal)),
SavepointCount: telemetry.NewCounterWithMetric(
getMetricMeta(MetaSavepointExecuted, internal)),
RestartSavepointCount: telemetry.NewCounterWithMetric(
getMetricMeta(MetaRestartSavepointExecuted, internal)),
ReleaseRestartSavepointCount: telemetry.NewCounterWithMetric(
getMetricMeta(MetaReleaseRestartSavepointExecuted, internal)),
RollbackToRestartSavepointCount: telemetry.NewCounterWithMetric(
getMetricMeta(MetaRollbackToRestartSavepointExecuted, internal)),
SavepointCount: telemetry.NewCounterWithMetric(
getMetricMeta(MetaSavepointExecuted, internal)),
ReleaseSavepointCount: telemetry.NewCounterWithMetric(
getMetricMeta(MetaReleaseSavepointExecuted, internal)),
RollbackToSavepointCount: telemetry.NewCounterWithMetric(
getMetricMeta(MetaRollbackToSavepointExecuted, internal)),
SelectCount: telemetry.NewCounterWithMetric(
getMetricMeta(MetaSelectExecuted, internal)),
UpdateCount: telemetry.NewCounterWithMetric(
Expand Down Expand Up @@ -2398,15 +2411,23 @@ func (sc *StatementCounters) incrementCount(ex *connExecutor, stmt tree.Statemen
case *tree.RollbackTransaction:
sc.TxnRollbackCount.Inc()
case *tree.Savepoint:
if err := ex.validateSavepointName(t.Name); err == nil {
if ex.isRestartSavepoint(t.Name) {
sc.RestartSavepointCount.Inc()
} else {
sc.SavepointCount.Inc()
}
case *tree.ReleaseSavepoint:
sc.ReleaseRestartSavepointCount.Inc()
if ex.isRestartSavepoint(t.Savepoint) {
sc.ReleaseRestartSavepointCount.Inc()
} else {
sc.ReleaseSavepointCount.Inc()
}
case *tree.RollbackToSavepoint:
sc.RollbackToRestartSavepointCount.Inc()
if ex.isRestartSavepoint(t.Savepoint) {
sc.RollbackToRestartSavepointCount.Inc()
} else {
sc.RollbackToSavepointCount.Inc()
}
default:
if tree.CanModifySchema(stmt) {
sc.DdlCount.Inc()
Expand Down
18 changes: 18 additions & 0 deletions pkg/sql/conn_executor_exec.go
Original file line number Diff line number Diff line change
Expand Up @@ -573,6 +573,15 @@ func (ex *connExecutor) commitSQLTransactionInternal(
) (ev fsm.Event, payload fsm.EventPayload, ok bool) {
ex.clearSavepoints()

return ex.finalizeCommitTransactionInternal(ctx, stmt)
}

// finalizeCommitTrransaction is like commitSQLTransactionInternal but
// preserves the savepoint structure. Used by ROLLBACK TO SAVEPOINT
// cockroach_restart.
func (ex *connExecutor) finalizeCommitTransactionInternal(
ctx context.Context, stmt tree.Statement,
) (ev fsm.Event, payload fsm.EventPayload, ok bool) {
if err := ex.checkTableTwoVersionInvariant(ctx); err != nil {
ev, payload = ex.makeErrEvent(err, stmt)
return ev, payload, false
Expand Down Expand Up @@ -743,6 +752,13 @@ func (ex *connExecutor) makeExecPlan(ctx context.Context, planner *planner) erro
log.VEventf(ctx, 1, "optimizer plan failed: %v", err)
return err
}

// TODO(knz): Remove this accounting if/when savepoint rollbacks
// support rolling back over DDL.
if planner.curPlan.flags.IsSet(planFlagIsDDL) {
ex.extraTxnState.numDDL++
}

return nil
}

Expand Down Expand Up @@ -1018,6 +1034,8 @@ func (ex *connExecutor) runObserverStatement(
switch sqlStmt := stmt.AST.(type) {
case *tree.ShowTransactionStatus:
return ex.runShowTransactionState(ctx, res)
case *tree.ShowSavepointStatus:
return ex.runShowSavepointState(ctx, res)
case *tree.ShowSyntax:
return ex.runShowSyntax(ctx, sqlStmt.Statement, res)
case *tree.SetTracing:
Expand Down
Loading