c# - SQL Server SMO - 备份 - 如何确定失败/成功?

标签 c# .net sql-server backup smo

如果您使用 SMO 执行备份,成功完成后,我测试 SqlError 是否为 null,考虑到备份已完成且没有错误:

enter image description here

但是,如您所见,它实际上返回了 0 类编号 3014 的错误,表示成功。

那么问题是:

Q: How can I find out if backup completed successfully or not, and how should I handle these messages and statuses cleanly?

恐怕这里有多个“陷阱”,我不想稍后在这段代码投入生产时咬我的屁股:)

最佳答案

我同意存在多个“问题”,我个人认为 Microsoft SMO 事件实现不当,因为 ServerMessageEventArgs 包含一个属性错误,它并不总是提供有关错误的信息,而是提供有关成功操作的消息!!

举个例子: 代码为 4035 的“错误”是一条信息消息。不是错误。 代码为 3014 的“错误”是成功完成时发生的信息消息。不是错误

另请注意,信息事件并不总是在发生错误时发生。每当 SQL Server 发送一条消息,该消息可能是有关已成功完成的操作的信息时,它实际上就会发生

我还担心没有正确处理错误/成功,但是将 sqlError 检查为 Null 是一个坏主意,因为它永远不会为 null,并且它总是包含一些关于成功操作或一个错误。并且假设在出现错误时发生信息事件也是一个坏主意

我建议通过 SqlError.Number 处理错误,并根据触发的 SMO 事件进行处理。

我编写了以下代码来创建数据库备份。它在 VB.NET 中,但在 C# 中类似。它接收必要的参数,包括调用事件的委托(delegate)(将在 GUI 上处理)、报告百分比的进度和错误处理,具体取决于触发的事件和提到的 SqlError.Number

Public Sub BackupDatabase(databaseName As String, backupFileFullPath As String, optionsBackup As OptionsBackupDatabase, operationProgress As IProgress(Of Integer),
                          operationResult As Action(Of OperationResult)) Implements IDatabaseManager.BackupDatabase
    Dim sqlBackup As New Smo.Backup()
    sqlBackup.Action = Smo.BackupActionType.Database
    sqlBackup.BackupSetName = databaseName & " Backup"
    sqlBackup.BackupSetDescription = "Full Backup of " & databaseName
    sqlBackup.Database = databaseName
    Dim bkDevice As New Smo.BackupDeviceItem(backupFileFullPath, Smo.DeviceType.File)
    sqlBackup.Devices.Add(bkDevice)
    sqlBackup.Initialize = optionsBackup.Overwrite
    sqlBackup.Initialize = True
    sqlBackup.PercentCompleteNotification = 5

    AddHandler sqlBackup.PercentComplete, Sub(sender As Object, e As PercentCompleteEventArgs)
                                              operationProgress.Report(e.Percent)
                                          End Sub
    AddHandler sqlBackup.Complete, Sub(sender As Object, e As ServerMessageEventArgs)
                                       Dim sqlMessage As SqlClient.SqlError = e.Error
                                       Dim opResult As New OperationResult()
                                       Select Case sqlMessage.Number
                                           Case 3014
                                               opResult.operationResultType = OperationResultType.SmoSuccess
                                               opResult.message = "Backup successfully created at " & backupFileFullPath & ". " & sqlMessage.Number & ": " & sqlMessage.Message
                                           Case Else
                                               opResult.operationResultType = OperationResultType.SmoError
                                               opResult.message = "ERROR CODE " & sqlMessage.Number & ": " & sqlMessage.Message
                                       End Select
                                       operationResult.Invoke(opResult)
                                   End Sub

    AddHandler sqlBackup.NextMedia, Sub(sender As Object, e As ServerMessageEventArgs)
                                        Dim sqlMessage As SqlClient.SqlError = e.Error
                                        Dim opResult As New OperationResult()
                                        opResult.operationResultType = OperationResultType.SmoError
                                        opResult.message = "ERROR CODE:  " & sqlMessage.Number & ": " & sqlMessage.Message
                                        operationResult.Invoke(opResult)
                                    End Sub

    AddHandler sqlBackup.Information, Sub(sender As Object, e As ServerMessageEventArgs)
                                          Dim sqlMessage As SqlClient.SqlError = e.Error
                                          Dim opResult As New OperationResult()
                                          Select Case sqlMessage.Number
                                              Case 4035
                                                  opResult.operationResultType = OperationResultType.SmoInformation
                                                  opResult.message = sqlMessage.Number & ": " & sqlMessage.Message
                                              Case Else
                                                  opResult.operationResultType = OperationResultType.SmoError
                                                  opResult.message = "ERROR CODE " & sqlMessage.Number & ": " & sqlMessage.Message
                                          End Select
                                          operationResult.Invoke(opResult)
                                      End Sub
    Try
        sqlBackup.SqlBackupAsync(smoServer)
    Catch ex As Exception
        Throw New BackupManagerException("Error backing up database " & databaseName, ex)
    End Try
End Sub

关于c# - SQL Server SMO - 备份 - 如何确定失败/成功?,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/9358576/

相关文章:

c# - 如何检查值序列是否正确排序?

sql-server - SQL Server 对象的命名约定是什么?

php - Mysql DELETE 查询在 PMA 中有效,但在我的 PHP 脚本中无效

c# - 内存重新排序会导致 C# 访问未分配的内存吗?

c# - Entity Framework Core : Is it safe to delete Migration. Designer.cs 如果我们永远不会恢复迁移?

c# - .NET Framework 是否提供解析 HTML 字符串的方法?

c# - 为什么要创建一个新的委托(delegate)对象

c# - FxCop 中的自定义规则仅适用于特定类型的方法调用的方法

C# 建立从笔记本电脑内部蓝牙 4.0 到低功耗蓝牙 (BLE) 外围设备的流

sql - SQL 表值函数中的排序依据