Utilisez la clause "WHERE CURRENT OF" pour mettre à jour uniquement la ligne spécifique sur laquelle le CURSOR est positionné dans SQL

J'ai le slider suivant dans SQL:

DECLARE @Script varchar(max) DECLARE @getScript CURSOR SET @getScript = CURSOR FOR SELECT [Script] FROM ScriptTable OPEN @getScript FETCH NEXT FROM @getScript INTO @Script WHILE @@FETCH_STATUS = 0 BEGIN BEGIN TRY EXEC(@Script) --Working part. This executes the query stored in the Script column. --For example INSERT INTO zTest VALUES(VAL1, VAL2, etc etc..) UPDATE ScriptTable SET DateDone = GETDATE(), IsDone = 1, Err = NULL FETCH NEXT FROM @getScript INTO @Script END TRY BEGIN CATCH DECLARE @Err varchar(max) SET @Err = ERROR_MESSAGE() UPDATE ScriptTable SET DateDone = GETDATE(), Err = @Err END CATCH END CLOSE @getScript DEALLOCATE @getScript 

Q1: Actuellement, j'obtiens les valeurs insérées dans la table "zTest" spécifiée dans mes commentaires quand j'exécute EXEC (@Script).

Toutefois, la deuxième partie où se trouve la «mise à jour ScriptTable» met à jour toutes les lignes de ma table de script. Je sais que je dois spécifier l'ID de la ligne appropriée que le slider traverse. La question est, comment puis-je faire cela? Je ne voulais pas seulement mettre à jour la ligne appropriée, passer à la suivante puis mettre à jour celle-ci.

Q2: Ma prochaine question est, dans le bloc CATCH, je pense que je crée une boucle infinie dès qu'il y a une erreur dans l'une des requêtes dans la colonne Script de ScriptTable comme quand je regarde les résultats, ça continue et aller. Je ne veux pas rompre; la procédure car je veux écrire une erreur dans la colonne Err et continuer avec les lignes suivantes jusqu'à la fin de @Script, puis arrêtez.

IDENT_CURRENT, Scope_Identity etc ne fonctionne pas car je n'ai rien inséré dans la table Scripts.

S'il vous plaît aider.

En ce qui concerne Q1, vous devez avoir une key primaire pour utiliser le slider pour la mise à jour (bien qu'il existe des solutions de contournement).
En général, vous voudrez quelque chose comme:

 update ScriptTable SET DateDone = GETDATE(), IsDone = 1, Err = NULL where ID of @getScript 

En ce qui concerne Q2, il est logique que ce soit une boucle infinie. Lorsque vous utilisez les clauses TRY et CATCH et qu'il échoue, il n'exécute aucune syntaxe dans la "zone" TRY . Par conséquent, le FETCH NEXT est ignoré et la même erreur se produit dans la boucle suivante.
Essayez de vous assurer qu'il y a toujours un FETCH NEXT dans la boucle.

J'espère que cela vous aide un peu.

Voici mon code final si quelqu'un est intéressé:

 DECLARE @Script varchar(max) DECLARE @getScript CURSOR SET @getScript = CURSOR FOR SELECT [Script] FROM ScriptControl OPEN @getScript FETCH NEXT FROM @getScript INTO @Script DECLARE @Counter int = 1 WHILE @@FETCH_STATUS = 0 BEGIN BEGIN TRY EXEC(@Script) UPDATE ScriptControl SET DateDone = GETDATE(), IsDone = 1, Error = NULL WHERE ID = @Counter FETCH NEXT FROM @getScript INTO @Script SET @Counter = (@Counter + 1) END TRY BEGIN CATCH DECLARE @Err varchar(max) SET @Err = ERROR_MESSAGE() UPDATE ScriptControl SET CSC_EOD_DateDone = NULL, CSC_EOD_Err = @Err, CSC_EOD_IsDone = 0 WHERE CURRENT OF @getScript FETCH NEXT FROM @getScript INTO @Script SET @Counter = (@Counter + 1) END CATCH END CLOSE @getScript DEALLOCATE @getScript 

Ce:

 DECLARE @ScriptControlId INT, @Script VARCHAR(MAX) DECLARE @getScript CURSOR SET @getScript = CURSOR FOR SELECT [ID], [Script] FROM ScriptControl OPEN @getScript FETCH NEXT FROM @getScript INTO @ScriptControlId, @Script WHILE @@FETCH_STATUS = 0 BEGIN BEGIN TRY EXEC(@Script) UPDATE ScriptControl SET DateDone = GETDATE(), IsDone = 1, Error = NULL WHERE ID = @ScriptControlId FETCH NEXT FROM @getScript INTO @ScriptControlId, @Script END TRY BEGIN CATCH DECLARE @Err VARCHAR(MAX) = ERROR_MESSAGE() UPDATE ScriptControl SET DateDone = NULL, Error = @Err, IsDone = 0 WHERE CURRENT OF @getScript FETCH NEXT FROM @getScript INTO @ScriptControlId, @Script END CATCH END CLOSE @getScript DEALLOCATE @getScript 

Ou ca:

 DECLARE @Script VARCHAR(MAX) DECLARE @getScript CURSOR SET @getScript = CURSOR FOR SELECT [Script] FROM ScriptControl OPEN @getScript FETCH NEXT FROM @getScript INTO @Script WHILE @@FETCH_STATUS = 0 BEGIN BEGIN TRY EXEC(@Script) UPDATE ScriptControl SET DateDone = GETDATE(), IsDone = 1, Error = NULL WHERE CURRENT OF @getScript FETCH NEXT FROM @getScript INTO @Script END TRY BEGIN CATCH DECLARE @Err VARCHAR(MAX) = ERROR_MESSAGE() UPDATE ScriptControl SET DateDone = NULL, Error = @Err, IsDone = 0 WHERE CURRENT OF @getScript FETCH NEXT FROM @getScript INTO @Script END CATCH END CLOSE @getScript DEALLOCATE @getScript