如何使用TRANSACTION将CREATE TRIGGER放入TRY-CATCH块?

问题描述 投票:0回答:1

我不是SQL的高级程序员,也许我的问题很愚蠢,但我还没有在谷歌找到答案。我们有一些用于实现更改包的SQL构造:

...
BEGIN TRY
    BEGIN TRANSACTION;
    <User Code Is Here>
    ...
    COMMIT TRANSACTION;
END TRY
BEGIN CATCH
    ...
END CATCH;
...

如何在没有错误的情况下放置CREATE TRIGGER块链而不是<User Code Is Here>

-- Table1
CREATE TRIGGER trTable1_Dates ON dbo.Table1
AFTER INSERT, UPDATE
AS
BEGIN
   SET NOCOUNT ON;
   ...
   SET NOCOUNT OFF;
END
GO
...
-- TableN
CREATE TRIGGER trTableN_Dates ON dbo.TableN
AFTER INSERT, UPDATE
AS
BEGIN
   SET NOCOUNT ON;
   ...
   SET NOCOUNT OFF;
END
GO

目的是创建所有触发器或什么都没有,如果失败则在CATCH代码块中打印消息。

编辑

错误是:

  1. 在第一个触发器的BEGIN:SQL80001:'BEGIN'附近的语法不正确。期待外在。
  2. 在第一次触发后,在GO上:SQL80001:'GO'附近的语法不正确。
  3. END TRY:SQL80001:'TRY'附近的语法不正确。期待对话。
  4. END CATCH:SQL80001:'CATCH'附近的语法不正确。期待对话。
sql-server tsql transactions try-catch database-trigger
1个回答
3
投票

您需要在单独的范围/批处理中运行每个create table语句(因为它必须是批处理中的第一个语句)。因此,您还必须转义触发器定义中的任何引号:

BEGIN TRY
    BEGIN TRANSACTION;
    exec sp_executesql N'CREATE TRIGGER trTable1_Dates ON dbo.Table1
    AFTER INSERT, UPDATE
    AS
    BEGIN
       SET NOCOUNT ON;
       //An empty string in here has to be '''' to escape the quotes
       SET NOCOUNT OFF;
    END'

    exec sp_executesql N'CREATE TRIGGER trTableN_Dates ON dbo.TableN
    AFTER INSERT, UPDATE
    AS
    BEGIN
       SET NOCOUNT ON;
       ...
       SET NOCOUNT OFF;
    END'
    COMMIT TRANSACTION;
END TRY
BEGIN CATCH
    ...
END CATCH;

事务与批处理和嵌套作用域正交,因此事务也涵盖了每个EXEC中发生的所有活动。

© www.soinside.com 2019 - 2024. All rights reserved.