2014-07-26 63 views
1

是否存在删除/删除没有表的数据库的查询(删除空数据库)?删除没有表的数据库

服务器是Microsoft SQL Server 2005的

+0

Sql Shell将是我的选择。 – stckl0ve

+0

请参阅http://dba.stackexchange.com/questions/47726/how-to-query-a-database-for-empty-tables。然后删除名称返回的表。 – scrayne

+1

@DanRitchie那真的不是OP要找的东西....我们正在谈论数据库,而不是表格。 –

回答

1

这应该做到这一点。 在实验室机器上进行测试,并使用0个用户表删除所有数据库。 但是请注意,表格不一定是数据库中唯一的东西。可能存在有人可能仍然需要的存储过程,函数等。

注意这是一个非常危险的操作,因为它丢弃数据库。自担风险使用。我对您造成的损害不承担任何责任。

USE [master]; 
DECLARE @name varchar(50); 
DECLARE @innerQuery varchar(max); 
DECLARE tableCursor CURSOR FOR SELECT name FROM sys.databases where owner_sid != 0x01; 
OPEN tableCursor; 

FETCH NEXT FROM tableCursor 
INTO @name 

WHILE @@FETCH_STATUS = 0 
BEGIN 
    SET @innerQuery = 'USE [' + @name + ']; IF (SELECT COUNT(*) FROM sys.objects WHERE type = ''U'') = 0 
    BEGIN 
     USE [master]; 
     DROP DATABASE [' + @name + '] 
    END' 
    EXEC(@innerQuery) 
    FETCH NEXT FROM tableCursor INTO @name 
END 

CLOSE tableCursor; 
DEALLOCATE tableCursor; 

另请注意,如果正在使用数据库,SQL Server将拒绝将其删除。所以,如果有其他连接到特定的数据库,它试图放弃,该命令将中止。

为了避免这个问题,您可以将有问题的数据库设置为单用户模式。

以下脚本与上述相同,但它也将目标数据库设置为单用户模式以终止活动连接。 更加小心,因为它本质上'S核选择:

use [master]; 
DECLARE @name varchar(50); 
DECLARE @innerQuery varchar(max); 
DECLARE tableCursor CURSOR FOR SELECT name FROM sys.databases where owner_sid != 0x01; 
OPEN tableCursor; 

FETCH NEXT FROM tableCursor 
INTO @name 

WHILE @@FETCH_STATUS = 0 
BEGIN 
    SET @innerQuery = 
    'USE [' + @name + ']; 
    IF (SELECT COUNT(*) FROM sys.objects WHERE type = ''U'') = 0 
    BEGIN 
     USE [master]; 
     ALTER DATABASE [' + @name + '] SET SINGLE_USER WITH ROLLBACK IMMEDIATE; 
     DROP DATABASE [' + @name + ']; 
    END' 
    EXEC(@innerQuery) 
    FETCH NEXT FROM tableCursor INTO @name 
END 

CLOSE tableCursor; 
DEALLOCATE tableCursor; 
0

我认为这是不可能的(至少不是一个TSQL的命令,可能是一个存储过程的地方)。您必须查询sysobjects并在发现任何情况下中止。 (并且您必须决定是否要忽略某些系统对象,如设计表)。

0

下面的脚本将生成所需的DROP DATABASE脚本。你可以调整它来执行语句(在主数据库上下文中),但我建议你先检查它以防万一。

EXEC sp_MSforeachdb N' 
    USE [?]; 
    IF N''?'' NOT IN(N''master'', N''model'', N''msdb'', N''tempdb'') 
    BEGIN 
     IF NOT EXISTS(
      SELECT * 
      FROM sys.tables 
      WHERE 
       OBJECTPROPERTYEX(object_id, ''IsMSShipped'') = 0 
      ) 
     BEGIN 
      PRINT ''DROP DATABASE [?];''; 
     END; 
    END;';