Skip to content

Commit

Permalink
Test-DbaLastBackup - Test MaxSize before CopyFile (#7784)
Browse files Browse the repository at this point in the history
  • Loading branch information
andreasjordan authored Sep 18, 2021
1 parent 0a74cce commit 59df5f5
Showing 1 changed file with 121 additions and 112 deletions.
233 changes: 121 additions & 112 deletions functions/Test-DbaLastBackup.ps1
Original file line number Diff line number Diff line change
Expand Up @@ -336,11 +336,30 @@ function Test-DbaLastBackup {

if (-not $lastbackup) {
Write-Message -Level Verbose -Message "No backups exist for this database."
$lastbackup = @{
Path = "No backups exist for this database"
# This code should never be executed as there is already a test for databases without backup in line 241.
continue
}

$totalSizeMB = ($lastbackup.TotalSize.Megabyte | Measure-Object -Sum).Sum
if ($MaxSize -and $MaxSize -lt $totalSizeMB) {
[pscustomobject]@{
SourceServer = $source
TestServer = $destination
Database = $db.name
FileExists = $null
Size = [dbasize](($lastbackup.TotalSize | Measure-Object -Sum).Sum)
RestoreResult = "The backup size for $dbName ($totalSizeMB MB) exceeds the specified maximum size ($MaxSize MB)."
DbccResult = "Skipped"
RestoreStart = $null
RestoreEnd = $null
RestoreElapsed = $null
DbccMaxDop = $null
DbccStart = $null
DbccEnd = $null
DbccElapsed = $null
BackupDates = [String[]]($lastbackup.Start)
BackupFiles = $lastbackup.FullName
}
$fileexists = $false
$success = $restoreresult = $dbccresult = "Skipped"
continue
}

Expand Down Expand Up @@ -413,139 +432,129 @@ function Test-DbaLastBackup {

$fileexists = $true
$ogdbname = $dbName
$restorelist = Read-DbaBackupHeader -SqlInstance $destserver -Path $lastbackup[0].Path -AzureCredential $AzureCredential
$dbccElapsed = $restoreElapsed = $startRestore = $endRestore = $startDbcc = $endDbcc = $null
$dbName = "$prefix$dbName"
$destdb = $destserver.databases[$dbName]

$totalsize = ($restorelist.BackupSize.Megabyte | Measure-Object -Sum ).Sum

if ($MaxSize -and $MaxSize -lt $totalsize) {
$success = "The backup size for $dbName ($totalsize MB) exceeds the specified maximum size ($MaxSize MB)."
$dbccresult = "Skipped"
} else {
$dbccElapsed = $restoreElapsed = $startRestore = $endRestore = $startDbcc = $endDbcc = $null

$dbName = "$prefix$dbName"
$destdb = $destserver.databases[$dbName]

if ($destdb) {
Stop-Function -Message "$dbName already exists on $destination - skipping." -Continue
}

if ($Pscmdlet.ShouldProcess($destination, "Restoring $ogdbname as $dbName.")) {
Write-Message -Level Verbose -Message "Performing restore."
$startRestore = Get-Date
try {
if ($ReuseSourceFolderStructure) {
$restoreSplat = @{
SqlInstance = $destserver
RestoredDatabaseNamePrefix = $prefix
DestinationFilePrefix = $Prefix
IgnoreLogBackup = $IgnoreLogBackup
AzureCredential = $AzureCredential
TrustDbBackupHistory = $true
ReuseSourceFolderStructure = $true
EnableException = $true
}
} else {
$restoreSplat = @{
SqlInstance = $destserver
RestoredDatabaseNamePrefix = $prefix
DestinationFilePrefix = $Prefix
DestinationDataDirectory = $datadirectory
DestinationLogDirectory = $logdirectory
IgnoreLogBackup = $IgnoreLogBackup
AzureCredential = $AzureCredential
TrustDbBackupHistory = $true
EnableException = $true
}
}
if ($destdb) {
Stop-Function -Message "$dbName already exists on $destination - skipping." -Continue
}

if (Test-Bound "MaxTransferSize") {
$restoreSplat.Add('MaxTransferSize', $MaxTransferSize)
}
if (Test-Bound "BufferCount") {
$restoreSplat.Add('BufferCount', $BufferCount)
if ($Pscmdlet.ShouldProcess($destination, "Restoring $ogdbname as $dbName.")) {
Write-Message -Level Verbose -Message "Performing restore."
$startRestore = Get-Date
try {
if ($ReuseSourceFolderStructure) {
$restoreSplat = @{
SqlInstance = $destserver
RestoredDatabaseNamePrefix = $prefix
DestinationFilePrefix = $Prefix
IgnoreLogBackup = $IgnoreLogBackup
AzureCredential = $AzureCredential
TrustDbBackupHistory = $true
ReuseSourceFolderStructure = $true
EnableException = $true
}

if ($verifyonly) {
$restoreresult = $lastbackup | Restore-DbaDatabase @restoreSplat -VerifyOnly:$VerifyOnly
} else {
$restoreresult = $lastbackup | Restore-DbaDatabase @restoreSplat
Write-Message -Level Verbose -Message " Restore-DbaDatabase -SqlInstance $destserver -RestoredDatabaseNamePrefix $prefix -DestinationFilePrefix $Prefix -DestinationDataDirectory $datadirectory -DestinationLogDirectory $logdirectory -IgnoreLogBackup:$IgnoreLogBackup -AzureCredential $AzureCredential -TrustDbBackupHistory"
} else {
$restoreSplat = @{
SqlInstance = $destserver
RestoredDatabaseNamePrefix = $prefix
DestinationFilePrefix = $Prefix
DestinationDataDirectory = $datadirectory
DestinationLogDirectory = $logdirectory
IgnoreLogBackup = $IgnoreLogBackup
AzureCredential = $AzureCredential
TrustDbBackupHistory = $true
EnableException = $true
}
} catch {
$errormsg = Get-ErrorMessage -Record $_
}

$endRestore = Get-Date
$restorets = New-TimeSpan -Start $startRestore -End $endRestore
$ts = [timespan]::fromseconds($restorets.TotalSeconds)
$restoreElapsed = "{0:HH:mm:ss}" -f ([datetime]$ts.Ticks)
if (Test-Bound "MaxTransferSize") {
$restoreSplat.Add('MaxTransferSize', $MaxTransferSize)
}
if (Test-Bound "BufferCount") {
$restoreSplat.Add('BufferCount', $BufferCount)
}

if ($restoreresult.RestoreComplete -eq $true) {
$success = "Success"
if ($verifyonly) {
$restoreresult = $lastbackup | Restore-DbaDatabase @restoreSplat -VerifyOnly:$VerifyOnly
} else {
if ($errormsg) {
$success = $errormsg
} else {
$success = "Failure"
}
$restoreresult = $lastbackup | Restore-DbaDatabase @restoreSplat
Write-Message -Level Verbose -Message " Restore-DbaDatabase -SqlInstance $destserver -RestoredDatabaseNamePrefix $prefix -DestinationFilePrefix $Prefix -DestinationDataDirectory $datadirectory -DestinationLogDirectory $logdirectory -IgnoreLogBackup:$IgnoreLogBackup -AzureCredential $AzureCredential -TrustDbBackupHistory"
}
} catch {
$errormsg = Get-ErrorMessage -Record $_
}

$destserver = Connect-DbaInstance -SqlInstance $Destination -SqlCredential $DestinationCredential
$endRestore = Get-Date
$restorets = New-TimeSpan -Start $startRestore -End $endRestore
$ts = [timespan]::fromseconds($restorets.TotalSeconds)
$restoreElapsed = "{0:HH:mm:ss}" -f ([datetime]$ts.Ticks)

if (-not $NoCheck -and -not $VerifyOnly) {
# shouldprocess is taken care of in Start-DbccCheck
if ($ogdbname -eq "master") {
$dbccresult =
"DBCC CHECKDB skipped for restored master ($dbName) database. `
The master database cannot be copied off of a server and have a successful DBCC CHECKDB. `
See https://www.itprotoday.com/my-master-database-really-corrupt for more information."
if ($restoreresult.RestoreComplete -eq $true) {
$success = "Success"
} else {
if ($errormsg) {
$success = $errormsg
} else {
if ($success -eq "Success") {
Write-Message -Level Verbose -Message "Starting DBCC."
$success = "Failure"
}
}
}

$startDbcc = Get-Date
$dbccresult = Start-DbccCheck -Server $destserver -DbName $dbName -MaxDop $MaxDop 3>$null
$endDbcc = Get-Date
$destserver = Connect-DbaInstance -SqlInstance $Destination -SqlCredential $DestinationCredential

$dbccts = New-TimeSpan -Start $startDbcc -End $endDbcc
$ts = [timespan]::fromseconds($dbccts.TotalSeconds)
$dbccElapsed = "{0:HH:mm:ss}" -f ([datetime]$ts.Ticks)
} else {
$dbccresult = "Skipped"
}
if (-not $NoCheck -and -not $VerifyOnly) {
# shouldprocess is taken care of in Start-DbccCheck
if ($ogdbname -eq "master") {
$dbccresult =
"DBCC CHECKDB skipped for restored master ($dbName) database. `
The master database cannot be copied off of a server and have a successful DBCC CHECKDB. `
See https://www.itprotoday.com/my-master-database-really-corrupt for more information."
} else {
if ($success -eq "Success") {
Write-Message -Level Verbose -Message "Starting DBCC."

$startDbcc = Get-Date
$dbccresult = Start-DbccCheck -Server $destserver -DbName $dbName -MaxDop $MaxDop 3>$null
$endDbcc = Get-Date

$dbccts = New-TimeSpan -Start $startDbcc -End $endDbcc
$ts = [timespan]::fromseconds($dbccts.TotalSeconds)
$dbccElapsed = "{0:HH:mm:ss}" -f ([datetime]$ts.Ticks)
} else {
$dbccresult = "Skipped"
}
}
}

if ($VerifyOnly) {
$dbccresult = "Skipped"
}
if ($VerifyOnly) {
$dbccresult = "Skipped"
}

if (-not $NoDrop -and $null -ne $destserver.databases[$dbName]) {
if ($Pscmdlet.ShouldProcess($dbName, "Dropping Database $dbName on $destination")) {
Write-Message -Level Verbose -Message "Dropping database."
if (-not $NoDrop -and $null -ne $destserver.databases[$dbName]) {
if ($Pscmdlet.ShouldProcess($dbName, "Dropping Database $dbName on $destination")) {
Write-Message -Level Verbose -Message "Dropping database."

## Drop the database
try {
#Variable $removeresult marked as unused by PSScriptAnalyzer replace with $null to catch output
$null = Remove-DbaDatabase -SqlInstance $destserver -Database $dbName -Confirm:$false
Write-Message -Level Verbose -Message "Dropped $dbName Database on $destination."
} catch {
$destserver.Databases.Refresh()
if ($destserver.databases[$dbName]) {
Write-Message -Level Warning -Message "Failed to Drop database $dbName on $destination."
}
## Drop the database
try {
#Variable $removeresult marked as unused by PSScriptAnalyzer replace with $null to catch output
$null = Remove-DbaDatabase -SqlInstance $destserver -Database $dbName -Confirm:$false
Write-Message -Level Verbose -Message "Dropped $dbName Database on $destination."
} catch {
$destserver.Databases.Refresh()
if ($destserver.databases[$dbName]) {
Write-Message -Level Warning -Message "Failed to Drop database $dbName on $destination."
}
}
}
}

#Cleanup BackupFiles if -CopyFile and backup was moved to destination
#Cleanup BackupFiles if -CopyFile and backup was moved to destination

$destserver.Databases.Refresh()
if ($destserver.Databases[$dbName] -and -not $NoDrop) {
Write-Message -Level Warning -Message "$dbName was not dropped."
}
$destserver.Databases.Refresh()
if ($destserver.Databases[$dbName] -and -not $NoDrop) {
Write-Message -Level Warning -Message "$dbName was not dropped."
}

if ($CopyFile) {
Expand Down

0 comments on commit 59df5f5

Please sign in to comment.