Sqlserver
 sql >> Base de données >  >> RDS >> Sqlserver

Suppression de 1 million de lignes dans SQL Server

Voici une structure pour une suppression par lots comme suggéré ci-dessus. N'essayez pas 1M à la fois...

La taille du lot et le délai d'attente sont évidemment assez variables et dépendent des capacités de vos serveurs, ainsi que de votre besoin d'atténuer les conflits. Vous devrez peut-être supprimer manuellement certaines lignes, mesurer le temps qu'elles prennent et ajuster la taille de votre lot à quelque chose que votre serveur peut gérer. Comme mentionné ci-dessus, tout ce qui dépasse 5000 peut provoquer un blocage (ce dont je n'étais pas au courant).

Il serait préférable de le faire après des heures... mais 1 million de lignes, ce n'est vraiment pas beaucoup à gérer pour SQL. Si vous regardez vos messages dans SSMS, cela peut prendre un certain temps pour que la sortie imprimée s'affiche, mais elle le sera après plusieurs lots, sachez simplement qu'elle ne sera pas mise à jour en temps réel.

Edit :Ajout d'une heure d'arrêt @MAXRUNTIME &@BSTOPATMAXTIME . Si vous définissez @BSTOPATMAXTIME à 1, le script s'arrêtera tout seul à l'heure souhaitée, disons 8h00. De cette façon, vous pouvez le programmer tous les soirs pour qu'il commence à minuit, par exemple, et il s'arrêtera avant la production à 8h00.

Edit :la réponse est assez populaire, j'ai donc ajouté le RAISERROR au lieu de PRINT par commentaires.

DECLARE @BATCHSIZE INT, @WAITFORVAL VARCHAR(8), @ITERATION INT, @TOTALROWS INT, @MAXRUNTIME VARCHAR(8), @BSTOPATMAXTIME BIT, @MSG VARCHAR(500)
SET DEADLOCK_PRIORITY LOW;
SET @BATCHSIZE = 4000
SET @WAITFORVAL = '00:00:10'
SET @MAXRUNTIME = '08:00:00' -- 8AM
SET @BSTOPATMAXTIME = 1 -- ENFORCE 8AM STOP TIME
SET @ITERATION = 0 -- LEAVE THIS
SET @TOTALROWS = 0 -- LEAVE THIS

WHILE @BATCHSIZE>0
BEGIN
    -- IF @BSTOPATMAXTIME = 1, THEN WE'LL STOP THE WHOLE JOB AT A SET TIME...
    IF CONVERT(VARCHAR(8),GETDATE(),108) >= @MAXRUNTIME AND @BSTOPATMAXTIME=1
    BEGIN
        RETURN
    END

    DELETE TOP(@BATCHSIZE)
    FROM SOMETABLE
    WHERE 1=2

    SET @[email protected]@ROWCOUNT
    SET @[email protected]+1
    SET @[email protected][email protected]
    SET @MSG = 'Iteration: ' + CAST(@ITERATION AS VARCHAR) + ' Total deletes:' + CAST(@TOTALROWS AS VARCHAR)
    RAISERROR (@MSG, 0, 1) WITH NOWAIT
    WAITFOR DELAY @WAITFORVAL 
END