我有一个拥有超过1000个表的数据库。我正在创建新的空白设置。为此,我必须截断所有表,但我不希望截断一些表,所以我在表上创建并将名称存储在表中。
----------- Create hardcode table ----------------------
Create table TblHardCodeTableNotToTruncate(TableName varchar(100))
go
insert into TblHardCodeTableNotToTruncate
select 'TblHardCodeTableNotToTruncate'
go
---- insert the table names which dont wish to truncate ------------
Insert into TblHardCodeTableNotToTruncate
select 'TblAccount'
go
Insert into TblHardCodeTableNotToTruncate
select 'TblCity'
go
等,以下是我用来截断除了这些插入表之外的所有表的查询
------------------------- Truncate all the tables except the tables specified in the Hardcode table -------------------------
EXEC sp_MSForEachTable 'ALTER TABLE ? NOCHECK CONSTRAINT ALL'
GO
EXEC sp_MSForEachTable 'ALTER TABLE ? DISABLE TRIGGER ALL'
GO
DECLARE @TBLTEMP TABLE(TABLENAME VARCHAR(100))
insert into @TBLTEMP
select name from sysobjects where xtype = 'U'
delete from @TBLTEMP where tablename in (
select tablename from TblHardCodeTableNotToTruncate)
DECLARE @SQLQUERY VARCHAR(MAX) =''
DECLARE @INTCNT INT = 1
DECLARE @TABLENAME VARCHAR(100) =''
WHILE (SELECT COUNT(*) FROM @TBLTEMP) > 0
BEGIN
select top 1 @TABLENAME = TABLENAME from @TBLTEMP
SET @SQLQUERY = 'Truncate table ' + @TABLENAME
EXEC(@SQLQUERY)
PRINT @SQLQUERY
DELETE FROM @TBLTEMP WHERE TABLENAME = @TABLENAME
END
go
EXEC sp_MSForEachTable 'ALTER TABLE ? CHECK CONSTRAINT ALL'
GO
EXEC sp_MSForEachTable 'ALTER TABLE ? ENABLE TRIGGER ALL'
go
但我得到错误外键引用错误。我知道在做之前我需要放弃约束。但有没有办法做到这一点,因为我不能删除然后截断并再次添加这么多的表。我们可以在下面编写任何独特的脚本,如果存在则会删除约束,截断表并再次将删除的约束添加到表中。
答案 0 :(得分:3)
我担心没有限制就没有办法做到这一点, 你可以编写一个代码来提取表的约束并删除它们很简单。
创建一个临时表并使用此代码获取表约束,并注意sysconstraints.status必须为1或3才能获得外键和主键:
Select SysObjects.[Name] As "Constraint Name",
Tabls.[Name] as "Table Name",
Cols.[Name] As "Column Name"
From SysObjects Inner Join
(Select [Name],[ID] From SysObjects) As Tabls
On Tabls.[ID] = Sysobjects.[Parent_Obj]
Inner Join sysconstraints On sysconstraints.Constid = Sysobjects.[ID]
Inner Join SysColumns Cols On Cols.[ColID] = sysconstraints.[ColID]
And Cols.[ID] = Tabls.[ID]
where sysconstraints.status in (1, 3)
order by [Tabls].[Name]
你必须在截断后重新创建这些约束,这也很简单,但我不会做你所有的工作:)
答案 1 :(得分:0)
即使所有tabled都为空并禁用所有约束,截断也会因FK存在而失败。你真的必须放弃它。
您可以创建一个脚本来自动化它(截断所有删除和重新创建FK的表) 我在这里找到一个(谨慎使用) http://www.sqlservercentral.com/scripts/Development/62892/
此外,如果您只想创建一个“毯子”数据库,您可以导出脚本以创建所有对象,并只填充您需要的少数(域?)表。