我们如何根据年龄删除所有数据库。
如果我使用今天的日期并保留 2 个月,则列表将带有以下查询,现在我想删除所有带有查询输出的数据库。
SELECT name as [database] , database_id, create_date
FROM sys.databases where create_date <= '20190726' AND name NOT IN ('Master','Model','MSDB','tempdb')
Run Code Online (Sandbox Code Playgroud)
以下脚本无法处理错误:
DROP DATABASE VM_P
消息 2812,级别 16,状态 62,第 15 行
找不到存储过程“DROP DATABASE VM_P。
DECLARE @DBName VARCHAR (64)
DECLARE @SQL VARCHAR (255)
DECLARE DROPDB CURSOR FOR
SELECT name FROM sys.databases
WHERE create_date <= '20190726'
AND name NOT IN ('master','model','msdb','tempdb','distribution','ReportServer','ReportServerTempDB')
OPEN DROPDB
FETCH next FROM DROPDB INTO @DBName
WHILE @@FETCH_STATUS = 0
BEGIN
SET @SQL = 'DROP DATABASE ' + @DBName
PRINT @SQL
EXEC @SQL
FETCH next FROM DROPDB INTO @DBName
END
CLOSE DROPDB
DEALLOCATE DROPDB
Run Code Online (Sandbox Code Playgroud)
您的代码非常非常接近工作。
文档中没有明确说明,但示例确实显示了这一点。
在存储过程中使用EXEC
(或EXECUTE
) 时,直接在语句之后写入对象名称(下面的示例 1),但是在调用 T-SQL 字符串时,您必须包含括号(下面的示例 2)
示例 1
EXEC dbo.Procedure
Run Code Online (Sandbox Code Playgroud)
示例 2
EXEC ('SELECT * FROM dbo.SomeTable')
Run Code Online (Sandbox Code Playgroud)
因此,您的解决方案应如下所示(注意替换静态日期GETDATE()
以满足您根据数据库的年龄删除的原始条件):
--For internal objects, always use NVARCHAR - this is what the engine uses internally in most places
DECLARE @DBName NVARCHAR (64)
DECLARE @SQL NVARCHAR (255)
DECLARE DROPDB CURSOR FOR
SELECT name FROM sys.databases
--Use GETDATE() with DATEADD for -60 days to get the threshold for deletion
WHERE create_date <= DATEADD(DD,-60,GETDATE())
AND name NOT IN ('master','model','msdb','tempdb','distribution','ReportServer','ReportServerTempDB')
OPEN DROPDB
FETCH next FROM DROPDB INTO @DBName
WHILE @@FETCH_STATUS = 0
BEGIN
SET @SQL = 'DROP DATABASE ' + QUOTENAME(@DBName)
PRINT @SQL
EXEC (@SQL)
FETCH next FROM DROPDB INTO @DBName
END
CLOSE DROPDB
DEALLOCATE DROPDB
Run Code Online (Sandbox Code Playgroud)
顺便说一句,鉴于这是一个具有潜在破坏性的脚本,我将删除EXEC
并简单地将打印的语句复制到新查询中以运行它们。这将避免任何不可预见的事故,因为它使您有机会在运行脚本之前对其进行审核。
归档时间: |
|
查看次数: |
164 次 |
最近记录: |