Sql 如何编写只截断特定模式的表的存储过程
我的数据库中有不同类型的模式。如果要删除具有暂存架构的表,如何修改此存储过程Sql 如何编写只截断特定模式的表的存储过程,sql,sql-server,tsql,Sql,Sql Server,Tsql,我的数据库中有不同类型的模式。如果要删除具有暂存架构的表,如何修改此存储过程 CREATE PROC sp_Truncate AS BEGIN EXEC sp_MSforeachtable @command1 = 'TRUNCATE TABLE ?' END GO 是否有任何方法可以为架构名称传递参数(键入varchar或nvarchar)使用不带where子句的Delete语句是安全的,而不是truncate,如果有引用约束,则可能会失败。请尝试此查询 Declare @sql Nv
CREATE PROC sp_Truncate
AS
BEGIN
EXEC sp_MSforeachtable @command1 = 'TRUNCATE TABLE ?'
END
GO
是否有任何方法可以为架构名称传递参数(键入
varchar
或nvarchar
)使用不带where
子句的Delete
语句是安全的,而不是truncate
,如果有引用约束,则可能会失败。请尝试此查询
Declare @sql Nvarchar(max)=''
SELECT @sql += ' delete from ' + s.NAME + '.' + t.NAME
+' Go DBCC CHECKIDENT ('''+s.NAME + '''.''' + t.NAME+''', RESEED, 0) GO '
FROM sys.tables t
JOIN sys.schemas s
ON t.[schema_id] = s.[schema_id]
WHERE t.type = 'U'
and s.name = 'schema_name' -- your schema name
Exec sp_executesql @sql
光标版本:
DECLARE @s_name VARCHAR(128)
DECLARE @t_name VARCHAR(128)
DECLARE db_cursor CURSOR FOR
SELECT s.NAME as Schema_Nam , t.NAME as Table_Name
FROM sys.tables t
JOIN sys.schemas s
ON t.[schema_id] = s.[schema_id]
WHERE t.type = 'U'
and s.name = 'schema_name'
OPEN db_cursor
FETCH NEXT FROM db_cursor INTO @s_name,@t_name
WHILE @@FETCH_STATUS = 0
BEGIN
set @sql += ' delete from ' + s.NAME + '.' + t.NAME
+' Go DBCC CHECKIDENT ('''+s.NAME + '''.''' + t.NAME+''', RESEED, 0) GO '
FETCH NEXT FROM db_cursor INTO @s_name,@t_name
END
CLOSE db_cursor
DEALLOCATE db_cursor
Exec sp_executesql @sql
可以安全地使用不带where
子句的Delete
语句,而不是truncate
,如果有引用约束,则该语句可能会失败。请尝试此查询
Declare @sql Nvarchar(max)=''
SELECT @sql += ' delete from ' + s.NAME + '.' + t.NAME
+' Go DBCC CHECKIDENT ('''+s.NAME + '''.''' + t.NAME+''', RESEED, 0) GO '
FROM sys.tables t
JOIN sys.schemas s
ON t.[schema_id] = s.[schema_id]
WHERE t.type = 'U'
and s.name = 'schema_name' -- your schema name
Exec sp_executesql @sql
光标版本:
DECLARE @s_name VARCHAR(128)
DECLARE @t_name VARCHAR(128)
DECLARE db_cursor CURSOR FOR
SELECT s.NAME as Schema_Nam , t.NAME as Table_Name
FROM sys.tables t
JOIN sys.schemas s
ON t.[schema_id] = s.[schema_id]
WHERE t.type = 'U'
and s.name = 'schema_name'
OPEN db_cursor
FETCH NEXT FROM db_cursor INTO @s_name,@t_name
WHILE @@FETCH_STATUS = 0
BEGIN
set @sql += ' delete from ' + s.NAME + '.' + t.NAME
+' Go DBCC CHECKIDENT ('''+s.NAME + '''.''' + t.NAME+''', RESEED, 0) GO '
FETCH NEXT FROM db_cursor INTO @s_name,@t_name
END
CLOSE db_cursor
DEALLOCATE db_cursor
Exec sp_executesql @sql
您可以使用(请记住,sp\msforeachtable
是未记录的存储过程):
sp\msforeachtable
参数:
@command1-是由执行的第一个命令
“sp_MSforeachtable”,定义为nvarchar(2000年)
@wherend-此参数可用于添加其他约束
帮助标识sysobjects表中将要删除的行
选中时,此参数也是nvarchar(2000)
警告:
我假设您的暂存区域表没有外键。否则它可能会失败
不要使用前缀sp_u
命名存储过程:
在SQL Server中,sp_uu前缀指定系统存储过程。如果
您可以在存储过程中使用该前缀,即
过程可能与系统存储过程的名称冲突
这将在未来创建。如果发生此类冲突,您的
如果应用程序引用该过程,则应用程序可能会中断
没有按架构限定引用。在这种情况下
名称将绑定到系统过程而不是您的过程
您可以使用(请记住,sp\msforeachtable
是未记录的存储过程):
sp\msforeachtable
参数:
@command1-是由执行的第一个命令
“sp_MSforeachtable”,定义为nvarchar(2000年)
@wherend-此参数可用于添加其他约束
帮助标识sysobjects表中将要删除的行
选中时,此参数也是nvarchar(2000)
警告:
我假设您的暂存区域表没有外键。否则它可能会失败
不要使用前缀sp_u
命名存储过程:
在SQL Server中,sp_uu前缀指定系统存储过程。如果
您可以在存储过程中使用该前缀,即
过程可能与系统存储过程的名称冲突
这将在未来创建。如果发生此类冲突,您的
如果应用程序引用该过程,则应用程序可能会中断
没有按架构限定引用。在这种情况下
名称将绑定到系统过程而不是您的过程
通常,您可以用模式名限定表名,因此,不要只给出简单的表名,而要包括模式名,例如“schema.table”sp_MSforeachtable
和sp_MSforeachdb
都因缺少表和数据库而臭名昭著。按照MM93
答案中的建议使用sys
目录视图。DELETE
、DROP
或TRUNCATE
:您真正想要的是哪一个?旁注:您不应该在存储过程中使用sp_
前缀。微软已经这样做了,而且你确实有可能在将来的某个时候发生名称冲突。最好只是简单地避免使用sp.
并使用其他东西作为前缀,或者根本不使用前缀!通常,您可以用模式名限定表名,因此,不要只给出简单的表名,而要包括模式名,例如“schema.table”sp_MSforeachtable
和sp_MSforeachdb
都因缺少表和数据库而臭名昭著。按照MM93
答案中的建议使用sys
目录视图。DELETE
、DROP
或TRUNCATE
:您真正想要的是哪一个?旁注:您不应该在存储过程中使用sp_
前缀。微软已经这样做了,而且你确实有可能在将来的某个时候发生名称冲突。最好只是简单地避免使用sp.
并使用其他东西作为前缀,或者根本不使用前缀!仍然可能是错误的,请参见:代码类似于从表中选择@Variable+=someField
依赖于物理实现和内部访问路径,我将坚持使用截断
而不是删除,日志记录更少,速度更快,但您的sys cataloge view方法优于sp_MSforeachtable
方法。此外,仅当该表未被任何其他表引用时,才能使用Truncate。@lad2025-是的,我知道。但对我来说,它从未失败过。我们可以使用游标instead@M.Ali-这就是我选择删除的原因。
@MM93太好了,还添加了截断重置标识列而不删除的选项。我没有更多的问题,仍然可能是错误的,请看:代码类似于SELECT@Variable+=someField
依赖于物理实现和内部访问路径,我将坚持使用截断
而不是删除,日志记录更少,速度更快,但您的sys cataloge view方法优于sp_MSforeachtable
方法。此外,仅当该表未被任何其他表引用时,才能使用Truncate。@lad2025-是的,我知道。但对我来说,它从未失败过。我们可以使用游标instead@M.Ali-这就是我选择删除的原因。
@MM93太好了,还添加了截断重置标识列而不删除的选项。我没有更多的问题了