Как откатить все (t-sql), если восстановление БД не удалось? - PullRequest
0 голосов
/ 30 августа 2011

Я вставляю новую запись в таблицу Project, после чего я восстанавливаю БД и вставляю в эту БД некоторую строку.Я хочу следующее:

  1. Если запись была вставлена ​​в таблицу Project, но восстановление БД (с помощью хранимой процедуры CreateDB ниже) не выполнено, поэтому я хочу откатить все
  2. При вставкезапись не удалась Я также хочу откатить все

Для этого я использую транзакцию, но получаю следующую ошибку RESTORE DATABASE is terminating abnormally.

Ниже приведены сценарии, которые я использую для этой цели.

В чем проблема и как ее исправить?


CreateProject

ALTER PROCEDURE CreateProject 
    @name nvarchar(50)      
AS
SET XACT_ABORT, NOCOUNT ON    
DECLARE @starttrancount int

BEGIN TRY
    SELECT @starttrancount = @@TRANCOUNT

    IF @starttrancount = 0
        BEGIN TRANSACTION                                       
        DECLARE @sql nvarchar(MAX)   

    DECLARE @projId int
    DECLARE @dbName nvarchar(128)

    -- ======================================================================
    --  Create new project
    -- ======================================================================
    INSERT INTO Project(Name)
    VALUES(@name)
    -- ======================================================================
    --  Generate dbname that will be used to restore db with that name
    -- ======================================================================
    SET @projId = SCOPE_IDENTITY()
    SET @dbName = 'Site' + CONVERT(nvarchar(20), @projId)
    -- ======================================================================
    --  Create db with @dbname
    -- ======================================================================
    EXEC CreateDB @dbName


    --Insert some records to tables in created DB
            ...
            ...

    IF @starttrancount = 0 
        COMMIT TRANSACTION
END TRY
BEGIN CATCH 
    DECLARE @ErrorMessage NVARCHAR(4000)
    DECLARE @ErrorState INT
    DECLARE @ErrorSeverity INT

    IF XACT_STATE() <> 0 AND @starttrancount = 0     
        ROLLBACK TRANSACTION    

    SELECT 
        @ErrorMessage = 'Source:CopyPage\r\t' + ERROR_MESSAGE(),
        @ErrorSeverity = ERROR_SEVERITY(),
        @ErrorState = ERROR_STATE();

        RAISERROR (@ErrorMessage,
                   @ErrorSeverity,
                   @ErrorState);
END CATCH   

CreateDB

ALTER PROCEDURE CreateDB
    @newDbname nvarchar(128),   
    @restoreFrom nvarchar(MAX) = 'C:\Program Files\Microsoft SQL Server\MSSQL10_50.MSSQLSERVER\MSSQL\Backup\Site.bak'
AS
SET XACT_ABORT, NOCOUNT ON


BEGIN TRY

    DECLARE @newMdfPath nvarchar(MAX) = 'C:\Program Files\Microsoft SQL Server\MSSQL10_50.MSSQLSERVER\MSSQL\DATA\' + @newDbname + '.mdf'
    DECLARE @newLdfPath nvarchar(MAX) = 'C:\Program Files\Microsoft SQL Server\MSSQL10_50.MSSQLSERVER\MSSQL\DATA\' + @newDbname + '_log.ldf'

    RESTORE DATABASE @newDbname FROM DISK=@restoreFrom
    WITH RECOVERY,
    MOVE 'Site'  TO @newMdfPath,
    MOVE 'Site_log' TO @newLdfPath      

END TRY
BEGIN CATCH 
    DECLARE @ErrorMessage NVARCHAR(4000)
    DECLARE @ErrorState INT
    DECLARE @ErrorSeverity INT

    SELECT 
        @ErrorMessage = 'Source:PrepareNewSite\r\t' + ERROR_MESSAGE(),
        @ErrorSeverity = ERROR_SEVERITY(),
        @ErrorState = ERROR_STATE();

        RAISERROR (@ErrorMessage,
                   @ErrorSeverity,
                   @ErrorState);
END CATCH

Ответы [ 2 ]

0 голосов
/ 30 августа 2011

Вы не можете "откатить" восстановление базы данных, это не операция ATOMic.

Вам придется перехватить ошибку и отменить ее вручную.

0 голосов
/ 30 августа 2011

Вы хотите откатить только текущий переход?

begin tran

  -- perform.......

  if @@error>0

     rollback tran

commit tran
Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...