I'm calling the SQLDMO 8.0 COM library from VB.NET (using a PIA I generated with tlbimp) in order to backup a database with percentage completion notification:
Dim server As SQLDMO.SQLServer = Nothing
Dim backup As SQLDMO.Backup = Nothing
Dim restore As SQLDMO.Restore = Nothing
Dim backupAbortable As Boolean
Dim restoreAbortable As Boolean
Try
server = New SQLDMO.SQLServer
server.LoginSecure = True
server.Connect(serverName)
backup = New SQLDMO.Backup
backup.Action = SQLDMO.SQLDMO_BACKUP_TYPE.SQLDMOBackup_Database
backup.BackupSetDescription = "test"
backup.BackupSetName = "test"
backup.Database = databaseName
backup.Files = TransactSqlName.Delimit(fileName)
backup.TruncateLog = SQLDMO.SQLDMO_BACKUP_LOG_TYPE.SQLDMOBackup_Log_Truncate
backup.PercentCompleteNotification = 1
AddHandler backup.PercentComplete, AddressOf OnOperationPercentComplete
AddHandler backup.NextMedia, AddressOf OnOperationNextMedia
AddHandler backup.Complete, AddressOf OnOperationComplete
backupAbortable = True
backup.SQLBackup(server)
backupAbortable = False
restore = New SQLDMO.Restore
restore.Files = backup.Files
AddHandler restore.PercentComplete, AddressOf OnOperationPercentComplete
AddHandler restore.NextMedia, AddressOf OnOperationNextMedia
AddHandler restore.Complete, AddressOf OnOperationComplete
restoreAbortable = True
restore.SQLVerify(server)
restoreAbortable = False
server.DisConnect()
Catch ex As AbortException
If backupAbortable Then
backup.Abort()
End If
If restoreAbortable Then
restore.Abort()
End If
Finally
If restore IsNot Nothing Then
RemoveHandler restore.PercentComplete, AddressOf OnOperationPercentComplete
RemoveHandler restore.NextMedia, AddressOf OnOperationNextMedia
RemoveHandler restore.Complete, AddressOf OnOperationComplete
Marshal.FinalReleaseComObject(restore)
restore = Nothing
End If
If backup IsNot Nothing Then
RemoveHandler backup.PercentComplete, AddressOf OnOperationPercentComplete
RemoveHandler backup.NextMedia, AddressOf OnOperationNextMedia
RemoveHandler backup.Complete, AddressOf OnOperationComplete
Marshal.FinalReleaseComObject(backup)
backup = Nothing
End If
If server IsNot Nothing Then
Marshal.FinalReleaseComObject(server)
server = Nothing
End If
End Try
This works fine apart from the event handlers - only the first one wired up actually executes. I can't say for sure about the NextMedia event because it only fires for tape backups, but as for the other two, I either get the Complete event or the PercentComplete event firing depending on the order of the AddHandler statements, never both at the same time.
Possibilities:
- I'm doing it all wrong (suggestions welcome!)
- There's a bug in SQLDMO 8.0, and it's genuinely only firing one of the events.
- There's a bug in the RCW or the VB.NET compiler that affects COM interop events.
Any ideas?