Comment obtenir le résultat de sp_executesql dans une variable?
-
03-07-2019 - |
Question
J'ai un morceau de SQL dynamique à exécuter, puis à stocker le résultat dans une variable.
Je sais que je peux utiliser sp_executesql
, mais je ne trouve pas d'exemples clairs expliquant comment procéder.
La solution
Si vous avez des paramètres de sortie, vous pouvez le faire
DECLARE @retval int
DECLARE @sSQL nvarchar(500);
DECLARE @ParmDefinition nvarchar(500);
DECLARE @tablename nvarchar(50)
SELECT @tablename = N'products'
SELECT @sSQL = N'SELECT @retvalOUT = MAX(ID) FROM ' + @tablename;
SET @ParmDefinition = N'@retvalOUT int OUTPUT';
EXEC sp_executesql @sSQL, @ParmDefinition, @retvalOUT=@retval OUTPUT;
SELECT @retval;
Mais si vous ne le faites pas et ne pouvez pas modifier le SP:
-- Assuming that your SP return 1 value
create table #temptable (ID int null)
insert into #temptable exec mysp 'Value1', 'Value2'
select * from #temptable
Pas joli, mais ça marche.
Autres conseils
DECLARE @tab AS TABLE (col VARCHAR(10), colu2 varchar(10))
INSERT into @tab EXECUTE sp_executesql N'SELECT 1 as col1, 2 as col2 union all SELECT 1 as col1, 2 as col2 union all SELECT 1 as col1, 2 as col2'
SELECT * FROM @tab
DECLARE @vi INT
DECLARE @vQuery NVARCHAR(1000)
SET @vQuery = N'SELECT @vi= COUNT(*) FROM <TableName>'
EXEC SP_EXECUTESQL
@Query = @vQuery
, @Params = N'@vi INT OUTPUT'
, @vi = @vi OUTPUT
SELECT @vi
Déclarez une @ variable variable
Exec @ variable = nom_proc
Les valeurs renvoyées ne sont généralement pas utilisées pour "retourner". un résultat mais pour retourner succès (0) ou un numéro d'erreur (1-65K). Tout cela semble indiquer que sp_executesql ne renvoie pas de valeur, ce qui n’est pas correct. sp_executesql renverra 0 en cas de succès et tout autre nombre en cas d'échec.
Dans la liste ci-dessous, @i renverra 2727
DECLARE @s NVARCHAR(500)
DECLARE @i INT;
SET @s = 'USE [Blah]; UPDATE STATISTICS [dbo].[TableName] [NonExistantStatisticsName];';
EXEC @i = sys.sp_executesql @s
SELECT @i AS 'Blah'
SSMS le montrera Msg 2727, Niveau 11, Etat 1, Ligne 1 Impossible de trouver l'index 'NonExistantStaticsName'.
DECLARE @ValueTable TABLE ( Valeur VARCHAR (100) )
SELECT @sql = N'SELECT SRS_SizeSetDetails.'+@COLUMN_NAME+' FROM SRS_SizeSetDetails WHERE FSizeID = '''+@FSizeID+''' AND SRS_SizeSetID = '''+@SRS_SizeSetID+'''';
INSERT INTO @ValueTable
EXEC sp_executesql @sql;
SET @Value='';
SET @Value = (SELECT TOP 1 Value FROM @ValueTable)
DELETE FROM @ValueTable
Si vous souhaitez renvoyer plus d'une valeur, utilisez ceci:
DECLARE @sqlstatement2 NVARCHAR(MAX);
DECLARE @retText NVARCHAR(MAX);
DECLARE @ParmDefinition NVARCHAR(MAX);
DECLARE @retIndex INT = 0;
SELECT @sqlstatement = 'SELECT @retIndexOUT=column1 @retTextOUT=column2 FROM XXX WHERE bla bla';
SET @ParmDefinition = N'@retIndexOUT INT OUTPUT, @retTextOUT NVARCHAR(MAX) OUTPUT';
exec sp_executesql @sqlstatement, @ParmDefinition, @retIndexOUT=@retIndex OUTPUT, @retTextOUT=@retText OUTPUT;
les valeurs renvoyées sont dans @retIndex et @retText
C'était il y a longtemps, donc vous ne savez pas si cela est toujours nécessaire, mais vous pouvez utiliser la variable @@ ROWCOUNT pour voir combien de lignes ont été affectées par la précédente instruction SQL.
Ceci est utile lorsque, par exemple, vous construisez une instruction Update dynamique et que vous l'exécutez avec exec. @@ ROWCOUNT indiquerait le nombre de lignes mises à jour.
Cela a fonctionné pour moi:
DECLARE @SQL NVARCHAR(4000)
DECLARE @tbl Table (
Id int,
Account varchar(50),
Amount int
)
-- Lots of code to Create my dynamic sql statement
insert into @tbl EXEC sp_executesql @SQL
select * from @tbl