如何检查,如果有约束存在Sql服务器?
-
21-09-2019 - |
题
我有这个sql:
ALTER TABLE dbo.ChannelPlayerSkins
DROP CONSTRAINT FK_ChannelPlayerSkins_Channels
但很显然,在一些其他数据库,我们的使用,制约具有不同的名称。我如何检查,如果有一个约束的名字 FK_ChannelPlayerSkins_Channels
.
解决方案
试试这个:
SELECT
*
FROM INFORMATION_SCHEMA.REFERENTIAL_CONSTRAINTS
WHERE CONSTRAINT_NAME ='FK_ChannelPlayerSkins_Channels'
-编辑--
当我最初回答了这个问题,我在想,"外交钥匙",因为原来的问题找到"FK_ChannelPlayerSkins_Channels".从那时起,许多人评论上寻找其它的"限制"这里有一些其他问题:
--Returns one row for each CHECK, UNIQUE, PRIMARY KEY, and/or FOREIGN KEY
SELECT *
FROM INFORMATION_SCHEMA.TABLE_CONSTRAINTS
WHERE CONSTRAINT_NAME='XYZ'
--Returns one row for each FOREIGN KEY constrain
SELECT *
FROM INFORMATION_SCHEMA.REFERENTIAL_CONSTRAINTS
WHERE CONSTRAINT_NAME='XYZ'
--Returns one row for each CHECK constraint
SELECT *
FROM INFORMATION_SCHEMA.CHECK_CONSTRAINTS
WHERE CONSTRAINT_NAME='XYZ'
这是一种替代方法
--Returns 1 row for each CHECK, UNIQUE, PRIMARY KEY, FOREIGN KEY, and/or DEFAULT
SELECT
OBJECT_NAME(OBJECT_ID) AS NameofConstraint
,SCHEMA_NAME(schema_id) AS SchemaName
,OBJECT_NAME(parent_object_id) AS TableName
,type_desc AS ConstraintType
FROM sys.objects
WHERE type_desc LIKE '%CONSTRAINT'
AND OBJECT_NAME(OBJECT_ID)='XYZ'
如果你需要更多的约束信息,看看里面的系统存储的过程 master.sys.sp_helpconstraint
看到如何获得某些信息。查看源代码的使用SQL服务器的管理工作室获得进入"的对象Explorer".从那里,你展开"主人"数据库,然后扩大"可编程性",那么"存储程序",然后"的系统存储程序"。然后你可以找到"sys.sp_helpconstraint"右击和选择"修改".只要小心来不保存任何更改。此外,您可以使用这个系统存储程序上的任何表通过使用这样 EXEC sp_helpconstraint YourTableNameHere
.
其他提示
最简单的方法以检查是否存在的约束(然后做一些事例如下降,如果它存在的话)是使用OBJECT_ID()function...
IF OBJECT_ID('dbo.[CK_ConstraintName]', 'C') IS NOT NULL
ALTER TABLE dbo.[tablename] DROP CONSTRAINT CK_ConstraintName
OBJECT_ID可以使用没有第二个参数('C'进行检查的制约是唯一的),也可以工作,但是如果你的约束的姓名名称匹配的其他目的在该数据库可以得到意想不到的结果。
IF OBJECT_ID('dbo.[CK_ConstraintName]') IS NOT NULL
ALTER TABLE dbo.[tablename] DROP CONSTRAINT CK_ConstraintName
OBJECT_ID也可用于与其它的"限制",如外国主要制约因素或主要的关键制约因素,等等。为了最好的结果,总是包括适当的对象类型作为第二个参数的OBJECT_ID功能:
约束对象的种类型:
- C=检查约束
- D=DEFAULT(约束或独立)
- F=外国主要制约因素
- PK=的主要关键制约因素
- R=规则(旧风格的、独立的)
- 昆士兰大学=独特的约束
还注意到,架构往往是必需的。该模式的制约通常采用的模式的父母表。
故障把你的约束(或者任何你都检查)在方括号中,当使用这种方法也可能会导致一种虚假的负面-如果你的对象采用不同寻常的人物(例如一个.), 括号是必需的。
如果你正在寻找其他类型的约束,例如默认值,你应该使用不同的查询 (从如何找到一个默认约束使用INFORMATION_SCHEMA?通过 devio 的回答)。使用:
SELECT * FROM sys.objects WHERE type = 'D' AND name = @name
按名称查找默认约束。
我已经把不同的“IF NOT EXISTS”在我的岗位检查 “的 DDL“IF不存在 “条件,使SQL脚本重新可运行”
IF (OBJECT_ID('FK_ChannelPlayerSkins_Channels') IS NOT NULL)
您在寻找这样的事情,下面是在SQL Server 2005
测试SELECT * FROM sys.check_constraints WHERE
object_id = OBJECT_ID(N'[dbo].[CK_accounts]') AND
parent_object_id = OBJECT_ID(N'[dbo]. [accounts]')
只是要看。..
在SQL服务器2008年R2短程,"脚本的约束作->下降和创建"的命令产生的T-SQL像下面
USE [MyDatabase]
GO
IF EXISTS (SELECT * FROM dbo.sysobjects WHERE id = OBJECT_ID(N'[DEF_Detail_IsDeleted]') AND type = 'D')
BEGIN
ALTER TABLE [Patient].[Detail] DROP CONSTRAINT [DEF_Detail_IsDeleted]
END
GO
USE [MyDatabase]
GO
ALTER TABLE [Patient].[Detail] ADD CONSTRAINT [DEF_Detail_IsDeleted] DEFAULT ((0)) FOR [IsDeleted]
GO
开箱,这个脚本没有下降的约束,因为选择返回0行。(见后 Microsoft连接).
名称的默认约束是错误的,但是我收集它也有一些与OBJECT_ID功能,因为改变名称不能解决问题。
为了解决这个问题,我删除了使用情况的OBJECT_ID和使用的默认约束的名称。
(SELECT * FROM dbo.sysobjects WHERE [name] = (N'DEF_Detail_IsDeleted') AND type = 'D')
我使用下面的查询来检查现有约束之前,我创建它。
IF (NOT EXISTS(SELECT 1 FROM sysconstraints WHERE OBJECT_NAME(constid) = 'UX_CONSTRAINT_NAME' AND OBJECT_NAME(id) = 'TABLE_NAME')) BEGIN
...
END
此查询按名称靶向给定的表名的约束。希望这有助于。
IF EXISTS(SELECT 1 FROM sys.foreign_keys WHERE parent_object_id = OBJECT_ID(N'dbo.TableName'))
BEGIN
ALTER TABLE TableName DROP CONSTRAINT CONSTRAINTNAME
END
IF EXISTS(SELECT TOP 1 1 FROM sys.default_constraints WHERE parent_object_id = OBJECT_ID(N'[dbo].[ChannelPlayerSkins]') AND name = 'FK_ChannelPlayerSkins_Channels')
BEGIN
DROP CONSTRAINT FK_ChannelPlayerSkins_Channels
END
GO
INFORMATION_SCHEMA
是你的朋友。它有各种视图,它显示各种模式的信息。检查你的系统的意见。你会发现你有处理约束三个视图,一个是CHECK_CONSTRAINTS
。
我使用它来检查在柱上,远程约束。它应该有你需要的一切。
DECLARE
@ps_TableName VARCHAR(300)
, @ps_ColumnName VARCHAR(300)
SET @ps_TableName = 'mytable'
SET @ps_ColumnName = 'mycolumn'
DECLARE c_ConsList CURSOR LOCAL STATIC FORWARD_ONLY FOR
SELECT
'ALTER TABLE ' + RTRIM(tb.name) + ' drop constraint ' + sco.name AS csql
FROM
sys.Objects tb
INNER JOIN sys.Columns tc on (tb.Object_id = tc.object_id)
INNER JOIN sys.sysconstraints sc ON (tc.Object_ID = sc.id and tc.column_id = sc.colid)
INNER JOIN sys.objects sco ON (sc.Constid = sco.object_id)
where
tb.name=@ps_TableName
AND tc.name=@ps_ColumnName
OPEN c_ConsList
FETCH c_ConsList INTO @ls_SQL
WHILE (@@FETCH_STATUS = 0) BEGIN
IF RTRIM(ISNULL(@ls_SQL, '')) <> '' BEGIN
EXECUTE(@ls_SQL)
END
FETCH c_ConsList INTO @ls_SQL
END
CLOSE c_ConsList
DEALLOCATE c_ConsList
SELECT tabla.name as Tabla,
restriccion.name as Restriccion,
restriccion.type as Tipo,
restriccion.type_desc as Tipo_Desc
FROM {DATABASE_NAME}.sys.objects tabla
INNER JOIN {DATABASE_NAME}.sys.objects restriccion
ON tabla.object_id = restriccion.parent_object_id
WHERE tabla.type = 'U' - Solo tablas creadas por el usuario.
AND restriccion.type = 'UQ' --Tipo de Restriccion UNIQUE
ORDER BY tabla.name, restriccion.type_desc
可以使用一个以上有一点需要注意:
IF EXISTS(
SELECT 1 FROM sys.foreign_keys
WHERE parent_object_id = OBJECT_ID(N'dbo.TableName')
AND name = 'CONSTRAINTNAME'
)
BEGIN
ALTER TABLE TableName DROP CONSTRAINT CONSTRAINTNAME
END
需要使用name = [Constraint name]
由于表可以具有多个外键和仍然没有被检查的外键为