Skip to content

Commit

Permalink
Merge pull request #42733 from pbardea/backport19.2-42005
Browse files Browse the repository at this point in the history
release-19.2: backupccl: allow restoration of empty db
  • Loading branch information
pbardea authored Dec 3, 2019
2 parents bf93c8a + 382ddd5 commit 2037648
Show file tree
Hide file tree
Showing 2 changed files with 35 additions and 23 deletions.
30 changes: 22 additions & 8 deletions pkg/ccl/backupccl/backup_test.go
Original file line number Diff line number Diff line change
Expand Up @@ -1579,15 +1579,14 @@ func TestBackupRestoreCrossTableReferences(t *testing.T) {

// Test cases where, after filtering out views that can't be restored, there are no other tables to restore

db.ExpectErr(t, `no tables to restore: DATABASE storestats`,
`RESTORE DATABASE storestats from $1 WITH OPTIONS ('skip_missing_views')`, localFoo)
db.Exec(t, `RESTORE DATABASE storestats from $1 WITH OPTIONS ('skip_missing_views')`, localFoo)
db.Exec(t, `RESTORE storestats.ordercounts from $1 WITH OPTIONS ('skip_missing_views')`, localFoo)
// Ensure that the views were not restored since they are missing the tables they reference.
db.CheckQueryResults(t, `USE storestats; SHOW TABLES;`, [][]string{})

db.ExpectErr(t, `no tables to restore: TABLE storestats.ordercounts`,
`RESTORE storestats.ordercounts from $1 WITH OPTIONS ('skip_missing_views')`, localFoo)

// referencing_early_customers depends only on early_customers, which can't be restored
db.ExpectErr(t, `no tables to restore: TABLE store.early_customers, store.referencing_early_customers`,
`RESTORE store.early_customers, store.referencing_early_customers from $1 WITH OPTIONS ('skip_missing_views')`, localFoo)
db.Exec(t, `RESTORE store.early_customers, store.referencing_early_customers from $1 WITH OPTIONS ('skip_missing_views')`, localFoo)
// Ensure that the views were not restored since they are missing the tables they reference.
db.CheckQueryResults(t, `SHOW TABLES;`, [][]string{})

// Test that views with valid dependencies are restored

Expand Down Expand Up @@ -3084,6 +3083,21 @@ func TestBackupCreatedStats(t *testing.T) {
})
}

// Ensure that backing up and restoring an empty database succeeds.
func TestBackupRestoreEmptyDB(t *testing.T) {
defer leaktest.AfterTest(t)()

const numAccounts = 1
_, _, sqlDB, _, cleanupFn := backupRestoreTestSetup(t, singleNode, numAccounts, initNone)
defer cleanupFn()

sqlDB.Exec(t, `CREATE DATABASE empty`)
sqlDB.Exec(t, `BACKUP DATABASE empty TO $1`, localFoo)
sqlDB.Exec(t, `DROP DATABASE empty`)
sqlDB.Exec(t, `RESTORE DATABASE empty FROM $1`, localFoo)
sqlDB.CheckQueryResults(t, `USE empty; SHOW TABLES;`, [][]string{})
}

func TestBackupRestoreSubsetCreatedStats(t *testing.T) {
defer leaktest.AfterTest(t)()

Expand Down
28 changes: 13 additions & 15 deletions pkg/ccl/backupccl/restore.go
Original file line number Diff line number Diff line change
Expand Up @@ -214,15 +214,8 @@ func selectTargets(
return nil, nil, err
}

seenTable := false
for _, desc := range matched.descs {
if desc.Table(hlc.Timestamp{}) != nil {
seenTable = true
break
}
}
if !seenTable {
return nil, nil, errors.Errorf("no tables found: %s", tree.ErrString(&targets))
if len(matched.descs) == 0 {
return nil, nil, errors.Errorf("no tables or databases matched the given targets: %s", tree.ErrString(&targets))
}

if lastBackupDesc.FormatVersion >= BackupFormatDescriptorTrackingVersion {
Expand Down Expand Up @@ -1546,9 +1539,6 @@ func doRestorePlan(
if err != nil {
return err
}
if len(filteredTablesByID) == 0 {
return errors.Errorf("no tables to restore: %s", tree.ErrString(&restoreStmt.Targets))
}
tableRewrites, err := allocateTableRewrites(ctx, p, databasesByID, filteredTablesByID, restoreDBs, opts)
if err != nil {
return err
Expand Down Expand Up @@ -1761,6 +1751,17 @@ func (r *restoreResumer) Resume(
}
r.tables = tables
r.databases = databases
r.exec = p.ExecCfg().InternalExecutor
r.statsRefresher = p.ExecCfg().StatsRefresher
r.latestStats = remapRelevantStatistics(latestBackupDesc, details.TableRewrites)

if len(r.tables) == 0 {
// We have no tables to restore (we are restoring an empty DB).
// Since we have already created any new databases that we needed,
// we can return without importing any data.
log.Warning(ctx, "no tables to restore")
return nil
}

res, err := restore(
ctx,
Expand All @@ -1776,9 +1777,6 @@ func (r *restoreResumer) Resume(
r.job,
)
r.res = res
r.exec = p.ExecCfg().InternalExecutor
r.statsRefresher = p.ExecCfg().StatsRefresher
r.latestStats = remapRelevantStatistics(latestBackupDesc, details.TableRewrites)
return err
}

Expand Down

0 comments on commit 2037648

Please sign in to comment.