如何检查 sp_rename 是否成功完成?

How to check if sp_rename is done successfully?

我是运行以下查询:

SELECT * INTO dbo.2015_10_2_cs FROM dbo.2015_10_2

IF NOT EXISTS 
(SELECT type FROM sys.indexes WHERE object_id = object_id('dbo.2015_10_2_cs') 
AND NAME ='cci' AND type = 5)
BEGIN
    CREATE CLUSTERED COLUMNSTORE INDEX cci
    ON dbo.2015_10_2_cs
    DROP TABLE dbo.2015_10_2
    EXEC sp_rename "dbo.2015_10_2_cs" , "dbo.2015_10_2"
END

并且我想确保将 table dbo.2015_10_2_cs 重命名为 dbo.2015_10_2 的部分已成功完成(不会丢失任何数据)。 循环内的步骤应该用 SQL 事务包围,以保持过程安全可靠(以防任何步骤失败)。 有人可以帮忙吗?提前致谢。

您可以使用 EXISTS 检查 table 名称和架构。

IF NOT EXISTS (SELECT 'table does not exist' FROM INFORMATION_SCHEMA.TABLES WHERE TABLE_NAME = N'2015_10_2'AND TABLE_SCHEMA = 'dbo')
BEGIN

    RAISERROR('The table doesn''t exist!!!!', 16, 1)

END

sp_rename 不会让您丢失 table 内容,它只会更改 table 引用名称并更新其所有约束和索引引用。如果要重命名的 table 不存在,它也会引发错误。也许您想要的是将您的流程包装在事务中,并在出现故障时回滚。

编辑:

对于基本的事务处理,您可以使用以下内容。请阅读 documentation 使用交易,可能需要一段时间才能知道它是如何正确工作的。

IF OBJECT_ID('tempdb..#Test') IS NOT NULL
    DROP TABLE #Test

CREATE TABLE #Test (Number INT)

SELECT AmountRecords = COUNT(1) FROM #Test -- AmountRecords = 0

BEGIN TRY

    BEGIN TRANSACTION

    -- Do your statements here

    INSERT INTO #Test (Number)
    VALUES (1)

    DECLARE @errorVariable INT = CONVERT(INT, 'NotAnInteger!!') -- Example of error: can't convert

    COMMIT

END TRY

BEGIN CATCH -- If something goes wrong

    IF @@TRANCOUNT > 0 -- ... and transaction is still open
        ROLLBACK -- Revert statements from the BEGIN TRANSACTION onwards

END CATCH


SELECT AmountRecords = COUNT(1) FROM #Test -- AmountRecords = 0 (the transaction was rolled back and the INSERT reverted)

基本上,您使用 BEGIN TRANSACTION 来启动一个还原点,以便在发生故障时返回。然后在您确定一切正常后使用 COMMIT(从那时起,其他用户将看到更改并且修改将被保留)。如果出现问题(您需要 TRY/CATCH 块来处理错误),您可以发出 ROLLBACK 来恢复您的更改。

EXEC sp_rename "dbo.2015_10_2_cs" , "dbo.2015_10_2"

这不会达到您的预期。如果您在新 table 名称中指定架构名称,则新 table 将被命名为 [dbo].[dbo.2015_10_2]。重命名的 table 隐含在现有 table 的模式中,因为必须使用 ALTER SCHEMA 而不是 sp_rename 在模式之间移动对象。

您的脚本还有许多其他问题。因为 table 名称以数字开头,所以它不符合 regular identifier naming rules 并且必须用方括号或双引号引起来。传递给 sp_rename 的文字参数应该是单引号。您还可以检查存储过程 return 代码以确定成功或失败。下面的示例在具有结构化错误处理的事务中执行这些任务。

DECLARE @rc int;
BEGIN TRY
    BEGIN TRAN;
    IF NOT EXISTS 
        (SELECT type FROM sys.indexes WHERE object_id = object_id(N'dbo.2015_10_2_cs') 
        AND NAME ='cci' AND type = 5)
    BEGIN
        CREATE CLUSTERED COLUMNSTORE INDEX cci
        ON dbo.[2015_10_2_cs];
        DROP TABLE dbo.[2015_10_2];
        EXEC @rc = sp_rename 'dbo.[2015_10_2_cs]' , '2015_10_2';
        IF @rc <> 0
        BEGIN
            RAISERROR('sp_rename returned return code %d',16,1);
        END;
    END;
    COMMIT;
END TRY
BEGIN CATCH
    IF @@TRANCOUNT > 0 ROLLBACK;
    THROW;
END CATCH;