SQL Server - Assign value to variable inside Dynamic SQL - sql

I wanted to assign value to out variable inside a dynamic query.
SET #query = 'IF EXISTS(Condition)
BEGIN
--Some action goes here
SET #result= 1
END
ELSE
BEGIN
SET #result= 2
END'
EXEC(#query)
When am trying to execute this query, I am getting an error:
Must declare the scalar variable "#result".
How can I set value to variable inside dynamic query?
Thanks in advance.

Just try this:
DECLARE #result INT
,#query NVARCHAR(MAX);
SET #query = 'IF (1 = 0)
BEGIN
--Some action goes here
SET #result= 1
END
ELSE
BEGIN
SET #result= 2
END';
EXEC sp_executesql #query, N'#result INT OUTPUT',#result = #result OUTPUT
SELECT #result;
You can use sp_executesql in order to execute dynamic T-SQL statement and initialize SQL variables. In the sp_executesql you need to pass the parameter definition and then parameter mappings.

When you Execute a Query String, It is Considered as a separate session, so The variables that you have declared in the current windows won't be accessible whereas you can access the Temporary tables.
So you have to declare the variable inside the string. Your Query can be re-written as below
SET #query = '
DECLARE #result INT
IF EXISTS(Condition)
BEGIN
--Some action goes here
SET #result= 1
END
ELSE
BEGIN
SET #result= 2
END'
EXEC(#query)
Or Store the result in a table variable and access it from there
DECLARE #Tablevar TABLE
(
Result INT
)
SET #query = '
IF EXISTS(Condition)
BEGIN
--Some action goes here
select 1
END
ELSE
BEGIN
SELECT 2
END'
INSERT INTO #Tablevar
EXEC(#query)
select #Result = Result FROM #Tablevar

Related

Set parameter inside SQL server execute command

I want to assign the value to a parameter PRGMREFID inside the if-else condition using the execute commands. Each time I try to do that, it shows NULL value assigned to PRGMREFID parameter, and if I place its declare command inside SEt #C, I do not find the parameter PRGMREFID outside of if-else. How to do that pls help.
Below is the patch.
DECLARE #C VARCHAR(MAX)
DECLARE #PRGMREFID VARCHAR(10)
IF 1=1
SET #C = 'set '+ (#PRGMREFID) +' = ''X'' '
else
set #c = ''
EXECUTE(#C)
select #PRGMREFID
To do what you are trying to do you need to use sp_executesql and define the parameter as an output parameter in order to have the value returned to your session's local variable:
DECLARE #C NVARCHAR(MAX)
DECLARE #PRGMREFID VARCHAR(10)
if 1=1
set #C = 'set #PRGMREFID = ''X'' '
else
set #C = ''
exec sp_executesql #C, N'#PRGMREFID VARCHAR(10) output', #PRGMREFID output
select #PRGMREFID

sp_executesql return id on insert in stored procedure

I have created a dynamic stored procedure that updates,inserts and deletes from specific table:
CREATE PROCEDURE dbo.Pj_Change
#Action Varchar(20),
#TableName Varchar(20),
#InsertQuery Nvarchar(max),
#UpdateQuery Nvarchar(max),
#Where Varchar(50)
AS
BEGIN
DECLARE #SQLString nvarchar(max);
SET NOCOUNT ON
IF(#Action = 'UPDATE')
SET #SQLString = 'UPDATE '+#TableName+' SET '+#UpdateQuery+' WHERE ('+#Where+')';
ELSE IF(#Action = 'INSERT')
SET #SQLString = 'INSERT INTO '+#TableName+' '+#InsertQuery + ';
ELSE IF(#Action = 'DELETE')
SET #SQLString = 'DELETE FROM '+#TableName+' WHERE ('+#Where+')';
EXECUTE sys.sp_executesql #SQLString
END
The problem is, than I try to add to this code SELECT SCOPE_IDENTITY() to get an ID of new row on insert, I get -1 in output.
The change that I make is:
#SQLString = 'INSERT INTO '+#TableName+' '+#InsertQuery + '; SELECT SCOPE_IDENTITY()';
What do I need to change for this to work?
It's ok, you shouldn't be using scope_identity anyway. You have more modern constructs, like:
update ... set ... output updated.id where ... -- same for insert and delete
You can either output the results in a table (not needed for a single insert) or use the simple form like above and have the update statement act as select and return the value.

SQL "if exists..." dynamic query

Suppose I have a query stored in a variable like this (it's actually dynamically populated and more complex, but this is for demonstration purposes):
DECLARE #Query VARCHAR(1000) = 'SELECT * FROM dbo.MyTable'
Is there a way to check if the query would return any results? Something like this, but this doesn't work:
IF EXISTS (#Query)
BEGIN
-- do something
END
The only way that I can think of to do this is to put the results in a temp table and then query from that, but that is not ideal because the columns in the dynamic query can vary and I really don't need the temp table at all for any reason other than checking whether some rows would be returned. Is there a better way?
Try Executing the Dynamic query and use ##RowCount to find the existence of rows.
DECLARE #Query NVARCHAR(1000) = 'SELECT * FROM [dbo].[Mytable]',
#rowcnt INT
EXEC Sp_executesql #query
SELECT #rowcnt = ##ROWCOUNT
IF #rowcnt > 0
BEGIN
PRINT 'row present'
END
Try this:
DECLARE #Query NVARCHAR(1000) = 'SELECT #C = COUNT(*) FROM dbo.MyTable'
DECLARE #Count AS INT
EXEC sp_executesql #Query, N'#C INT OUTPUT', #C=#Count OUTPUT
IF (#Count > 0)
BEGIN
END
I know this answer is too late. but, I'm leaving this here to help someone else to use IF EXISTS with a dynamic query.
This is how you should do it with dynamic queries.
DECLARE #Query VARCHAR(MAX)
SET #Query = 'SELECT * FROM [dbo].[MyTable]'
SET #Query = 'IF EXISTS (' + #Query + ')
BEGIN
-- do something
print ''1''
END
ELSE
BEGIN
-- do something else
print ''0''
END
'
exec (#Query)
Hope this helped someone. Vote if it did :)
You can use EXEC to execute sql statement, then call ##ROWCOUNT which Returns the number of rows affected by the last statement, to check row exists in sql select stetement.
DECLARE #Query VARCHAR(1000) = 'SELECT * FROM dbo.MyTable',#hasRow int
EXEC (#Query)
SELECT #hasRow =##ROWCOUNT // Returns the number of rows affected by the last statement
PRINT #hasRow
IF #hasRow > 0
BEGIN
Print 1
END
BEGIN
Print 2
END
Hi I think that only way is to put IF EXISTS part into code of execution. My case is to stop execution in point when select affects at least one row, that is goal of IF EXISTS.
Little example that saves reading all records covering by condition to first occurence:
set nocount off;
drop table if exists #temp
go
create table #temp (idCol int identity(1,1),someText nvarchar(1))
go
insert into #temp values ('a')
go 25000
declare #query nvarchar(max)
,#resultFork bit
set #query = 'if exists (select * from #temp where idCol % 3 = 0)
set #resultFork=1
else
set #resultFork=0'
print #query
exec sp_executeSQL #query, N'#resultFork int output', #resultFork=#resultFork output
print #resultFork
/*Now U can use #resultFork in simple if condition...
if #resultFork = 1
begin
--
end
else
begin
--
end
*/

Using sp_executesql without returning row sets

In a store procedure I am building dynamic SQL statement which is executed using sp_executesql procedure.
The dynamic SQL statement can be a store procedure, that:
do not return row set
do return one row set
do return multiple row sets
The initial store procedure itself returns other row sets. I want to return only them, and to not return the row sets from the internal procedure.
Generally, I want to force the following statement to do not return anything:
DECLARE #DynamicSQLStatement NVARCHAR(MAX)
SET #DynamicSQLStatement = N'SELECT 1 SELECT 2 SELECT 3 SELECT 4 SELECT 5'
EXEC sp_executesql #DynamicSQLStatement
Is there a way to do this?
I guess you can tweak your Store Procedures by doing something like this .
CREATE PROCEDURE usp_StopMessageProc
#StopMsg bit = 0
AS
BEGIN
SET NOCOUNT ON;
DECLARE #Sql VARCHAR(MAX);
SET #Sql = '';
SET #Sql = 'SELECT Column1, Column2, Column3.... ';
IF #StopMsg = 1
SET #Sql = #Sql + 'INTO #TempDeleteMe';
SET #Sql = #Sql +
'FROM dbo.SomeTable ';
EXEC(#Sql);
END
GO
By defualt your proc will do whatever it does best but when #StopMsg is set to 1 it suppress the return messages/Result sets.

Assign db query value to t-sql variable in dynamic query

I have this requirement to be implemented in a stored procedure. Dynamically query the database to get the count of a table, store it in a t-sql variable and then take some decisions based on that.
This is the stored procedure that i am working on . This is throwing some errors as i don't think there is a simple way of assigning the result of a tsql dynamic query to a variable.
CREATE PROCEDURE test
AS
BEGIN
DECLARE #sql VARCHAR(255)
DECLARE #cnt int
SET #sql = 'SELECT COUNT(1) FROM myTable'
SET #cnt = EXEC(#sql)
IF (#cnt > 0)
PRINT 'A'
ELSE
PRINT 'B'
END
GO
Could someone tell me if there is a simpler way of achieving this using T-SQL ?
Thanks.
alternative:
declare #tablename varchar(512) = 'sometable'
declare #sql nvarchar(512) = 'set #count = (select count(*) from ' + #tablename + ')'
declare #count int
execute sp_executesql #sql, N'#count int output', #count=#count output
select case when #count > 0 then 'A' else 'B' end
Try this:
SET #sql = 'SELECT #cnt = COUNT(1) FROM myTable'
EXEC(#sql)