Comment puis-je spécifier "fermer les connexions existantes" dans le script sql

je fais du développement actif sur mon schéma dans SQL Server 2008 et je veux souvent relire mon script de base de données drop/create. Quand je cours

USE [master]
GO

IF  EXISTS (SELECT name FROM sys.databases WHERE name = N'MyDatabase')
DROP DATABASE [MyDatabase]
GO

je reçois souvent cette erreur

Msg 3702, Level 16, State 4, Line 3
Cannot drop database "MyDatabase" because it is currently in use.

si vous faites un clic droit sur la base de données dans le volet de l'Explorateur d'objets et que vous sélectionnez la tâche Supprimer dans le menu contextuel, il y a une case à cocher pour "fermer les connexions existantes"

est-il possible de spécifier cette option dans mon script?

129
demandé sur nick 2009-11-11 01:56:12

5 réponses

vous pouvez déconnecter tout le monde et annuler leurs transactions avec:

alter database [MyDatbase] set single_user with rollback immediate

après cela, vous pouvez laisser tomber en toute sécurité la base de données:)

206
répondu Andomar 2009-11-10 22:58:53

allez à management studio et faites tout ce que vous décrivez, seulement au lieu de cliquer OK, cliquez sur Script. Il affichera le code qu'il lancera et que vous pourrez ensuite incorporer dans vos scripts.

dans ce cas, vous voulez:

ALTER DATABASE [MyDatabase] SET SINGLE_USER WITH ROLLBACK IMMEDIATE
GO
31
répondu hgmnz 2009-11-11 14:57:18

selon la documentation ALTER DATABASE SET , il est encore possible qu'après avoir paramétré une base de données en mode SINGLE_USER vous ne puissiez pas accéder à cette base de données:

avant de définir la base de données à SINGLE_USER, vérifiez que L'option AUTO_UPDATE_STATISTICS_ASYNC est définie à OFF. Lorsque défini à ON, le thread de fond utilisé pour mettre à jour les statistiques prend une connexion dans la base de données, et vous ne pourrez pas accéder à la base de données en mode mono-utilisateur.

ainsi, un script complet pour supprimer la base de données avec des connexions existantes peut ressembler à ceci:

DECLARE @dbId int
DECLARE @isStatAsyncOn bit
DECLARE @jobId int
DECLARE @sqlString nvarchar(500)

SELECT @dbId = database_id,
       @isStatAsyncOn = is_auto_update_stats_async_on
FROM sys.databases
WHERE name = 'db_name'

IF @isStatAsyncOn = 1
BEGIN
    ALTER DATABASE [db_name] SET  AUTO_UPDATE_STATISTICS_ASYNC OFF

    -- kill running jobs
    DECLARE jobsCursor CURSOR FOR
    SELECT job_id
    FROM sys.dm_exec_background_job_queue
    WHERE database_id = @dbId

    OPEN jobsCursor

    FETCH NEXT FROM jobsCursor INTO @jobId
    WHILE @@FETCH_STATUS = 0
    BEGIN
        set @sqlString = 'KILL STATS JOB ' + STR(@jobId)
        EXECUTE sp_executesql @sqlString
        FETCH NEXT FROM jobsCursor INTO @jobId
    END

    CLOSE jobsCursor
    DEALLOCATE jobsCursor
END

ALTER DATABASE [db_name] SET  SINGLE_USER WITH ROLLBACK IMMEDIATE

DROP DATABASE [db_name]
14
répondu AlexD 2013-05-06 11:43:53

j'ai essayé ce que hgmnz saids sur SQL Server 2012.

Gestion créé à moi:

EXEC msdb.dbo.sp_delete_database_backuphistory @database_name = N'MyDataBase'
GO
USE [master]
GO
/****** Object:  Database [MyDataBase]    Script Date: 09/09/2014 15:58:46 ******/
DROP DATABASE [MyDataBase]
GO
1
répondu Deiwys 2014-09-09 19:24:25

je sais qu'il est trop tard, mais peut-être qu'il peut aider quelqu'un. en utilisant ce prendre votre base de données hors ligne

ALTER DATABASE dbname SET OFFLINE
0
répondu Abhishek Upadhyay 2017-06-03 10:39:16