【问题标题】:DROP Constraint without knowing the name不知道名称的 DROP 约束
【发布时间】:2021-08-18 00:06:01
【问题描述】:

我知道我要提到的内容有很多参考资料。

我宁愿分享一些我认为应该非常有用的东西,并将其整合在一个地方 - Q&A-style。我之前一直在努力为不同时间的不同限制找到这一点。

常用的约束如下:

  • 主键约束
  • 外键约束
  • 唯一约束
  • 非空约束
  • 默认约束
  • 检查约束

如果您知道名称,那么很容易 DROP 约束 -

ALTER TABLE {table_name} DROP CONSTRAINT {constraint_name};

但大多数时候我们使用在创建表时定义约束并且没有名称。一段时间后,如果我们决定放弃任何约束,这并不是那么简单,我们确实需要编写一些相对复杂的查询。

那么,我们该怎么做呢?

【问题讨论】:

    标签: sql sql-server constraints


    【解决方案1】:
    -- Table T1
    IF OBJECT_ID('dbo.T1') IS NOT NULL
        DROP TABLE T1
    
    CREATE TABLE T1 (COL1 INT PRIMARY KEY)
    
    -- Table T2
    IF OBJECT_ID('dbo.T2') IS NOT NULL
        DROP TABLE T2
    
    CREATE TABLE T2 (
        COL1 INT FOREIGN KEY REFERENCES T1(COL1)
        ,COL2 VARCHAR(2) UNIQUE
        ,COL3 INT NOT NULL DEFAULT(0)
        ,CHECK (
            COL3 IN (
                0
                ,1
                ,2
                )
            )
        )
    GO
    
    -- *** Foreign key constraint ***
    
    DECLARE @Table NVARCHAR(256) = N'T2'
    DECLARE @Column NVARCHAR(256) = N'COL1'
    DECLARE @Command NVARCHAR(1000)
    
    SELECT @Command = 'ALTER TABLE ' + '[' + @Table + '] DROP CONSTRAINT ' + CONSTRAINT_NAME
    FROM INFORMATION_SCHEMA.KEY_COLUMN_USAGE
    WHERE TABLE_NAME = @Table
        AND COLUMN_NAME = @Column
    
    --PRINT (@Command)  -- ALTER TABLE [T2] DROP CONSTRAINT FK__T2__COL1__058EC7FB
    EXECUTE (@Command)
    
    GO
    
    -- *** Primary key constraint ***
    
    DECLARE @Table NVARCHAR(256) = N'T1'
    DECLARE @Command NVARCHAR(1000)
    
    SELECT @Command = 'ALTER TABLE ' + '[' + @Table + '] DROP CONSTRAINT ' + [name]
    FROM sys.key_constraints
    WHERE [type] = 'PK'
        AND [parent_object_id] = OBJECT_ID(@table);
    
    --PRINT (@Command)  -- ALTER TABLE [T1] DROP CONSTRAINT PK__T1__AA1D004EBAE57D94
    EXECUTE (@Command)
    
    GO
    
    -- *** Unique key constraint ***
    
    DECLARE @Table NVARCHAR(256) = N'T2'
    DECLARE @Column NVARCHAR(256) = N'COL2'
    DECLARE @Command NVARCHAR(1000)
    
    SELECT @Command = 'ALTER TABLE [' + @Table + '] DROP CONSTRAINT ' + d.name
    FROM sys.tables t
    JOIN sys.indexes d ON d.object_id = t.object_id
        AND d.type = 2
        AND d.is_unique = 1
    JOIN sys.index_columns ic ON d.index_id = ic.index_id
        AND ic.object_id = t.object_id
    JOIN sys.columns c ON ic.column_id = c.column_id
        AND c.object_id = t.object_id
    WHERE t.name = @Table
        AND c.name = @Column
    
    --PRINT (@Command)  -- ALTER TABLE [T2] DROP CONSTRAINT UQ__T2__AA1D0040A435D4E0
    EXECUTE (@Command)
    
    GO
    
    -- *** Not Null constraint ***
    
    -- ALTER TABLE T2 ALTER COLUMN COL3 INT NULL
    
    -- GO
    
    DECLARE @Table NVARCHAR(256) = N'T2'
    DECLARE @Column NVARCHAR(256) = N'COL3'
    DECLARE @Command NVARCHAR(1000)
    
    SELECT @Command = 'ALTER TABLE ' + '[' + @Table + '] DROP CONSTRAINT ' + d.name
    FROM sys.tables t
    JOIN sys.default_constraints d ON d.parent_object_id = t.object_id
    JOIN sys.columns c ON c.object_id = t.object_id
        AND c.column_id = d.parent_column_id
    WHERE t.name = @Table
        AND c.name = @Column
    
    --PRINT (@Command)  -- ALTER TABLE [T2] DROP CONSTRAINT DF__T2__COL3__0682EC34
    EXECUTE (@Command)
    
    GO
    
    -- *** Check constraint ***
    
    DECLARE @Table NVARCHAR(256) = N'T2'
    DECLARE @Column NVARCHAR(256) = N'COL3'
    DECLARE @Command NVARCHAR(1000)
    
    SELECT @Command = 'ALTER TABLE ' + '[' + @Table + '] DROP CONSTRAINT ' + d.name
    FROM sys.tables t
    JOIN sys.check_constraints d ON d.parent_object_id = t.object_id
    JOIN sys.columns c ON c.object_id = t.object_id
        AND c.column_id = d.parent_column_id
    WHERE t.name = @Table
        AND c.name = @Column
    
    --PRINT (@Command)  -- ALTER TABLE [T2] DROP CONSTRAINT CK__T2__COL3__0777106D
    EXECUTE (@Command)
    

    一些查询来自我的本地存储库,一些来自不同来源的引用:

    Finding a Primary Key Constraint on the fly in SQL Server 2005

    Drop Foreign Key without knowing the name of the constraint?

    How to drop a unique constraint from table column?

    【讨论】:

    • 这个脚本中的“not null”约束实际上是一个默认约束。尽管有名称,但默认约束不约束值(包括可空性);只是为了方便在未指定列时赋值。 NOT NULL“约束”在 SQL Server 中被正确地实现为列而不是对象,应该从您的问题中删除。就个人而言,我建议始终明确命名约束以避免动态 SQL 丑陋。
    • @DanGuzman 有道理,我会把它注释掉,保留在那里作为注释供参考。甚至我也支持显式命名的约束,但在实践中,我们确实多次遇到这个问题,也许是在处理其他人的作品时。
    猜你喜欢
    • 2011-04-06
    • 1970-01-01
    • 2023-03-10
    • 2011-02-02
    • 2011-04-26
    • 2012-02-18
    • 2012-09-05
    • 2017-04-18
    • 2010-11-28
    相关资源
    最近更新 更多