I'm in need of your hands.
I have 2 windows forms in c#.net where 1st form contains checked list box , collecting the ids from that box passing the value to the second form where i have written a stored procedure like this
ALTER PROCEDURE [dbo].[sp_GDE_QA]
#oks_ids varchar(100),
#Operation varchar(50)
AS BEGIN
declare #Execute as varchar(100)
set #Execute = 'select oks_id, path from tb_gde_qc where status=''QC Completed'' and oks_id in '''+#oks_ids+'''';
exec(#Execute)
END
Now I want to pass the value for the parameter #oks_ids. For example
select oks_id, path
from tb_gde_qc
where status=''QC Completed''
and oks_id in ('GD_01358', 'GD_01361', 'GD_01363')
Can anyone help me? Will be thankful to all
Try this
ALTER PROCEDURE [dbo].[sp_GDE_QA]
#oks_ids varchar(100),
#Operation varchar(50)
AS BEGIN
declare #Execute as varchar(100)
set #Execute = 'select oks_id, path from tb_gde_qc where status=''QC Completed'' and oks_id in '''+#oks_ids+'''';
sp_ExecuteSQL #Execute
END
sp_ExecuteSQL should be able to handle the passing of the string within the parameter.
Can I ask where does #Operation come into play?
Related
I want to use the value from variables that is passed into the stored proc. Is that allow?
For example, I want to pass CID=5,SID=4 Into an Update Stored Proc
and it looks like this:
CREATE PROCEDURE Update #CID nvarchar(4),#SID nvarchar(4)
AS
DELETE FROM [User"+#CID+#SID+"]
GO;
In which is like "DELETE FROM [User54]"
But I want to dynamically done given the parameter
Can it be done and how is it done?
Thanks
You must use dynamic SQL. To do it safely, ensure the created object name is properly delimited using the quotename function.
Like this:
CREATE OR ALTER PROCEDURE UpdateSomeTable #CID nvarchar(4), #SID nvarchar(4)
AS
begin
declare #tableName nvarchar(500) = quotename(concat('User',#CID,#SID));
declare #sql nvarchar(max) = concat('DELETE FROM ',#tableName);
--print #sql
exec sp_executesql #sql
end
Assume I have the following SQL snippet in SQL Server 2012:
DECLARE #fname varchar(20), #strVarName varchar(50)
SET #fname = 'cronus'
SET #strVarName = COVERT_VARIABLE_TO_STRING_NAME ( #fname)
--this should return '#fname'. this is not a value conversion this is converting a variable name to a string name
SELECT #strVarName
How do I do this?
SQL Server does not support reflection. You may be able to retrieve column or table names from its catalog views but with variables you're out of luck. Maybe you'll find another way to solve this issue with dynamic SQL.
Use dynamic sql query
DECLARE #fname varchar(20), #sql varchar(MAX)
SET #fname = 'cronus'
SET #sql = 'SELECT ' + #fname
EXEC (#sql)
There are following Character data types used to store character strings:
char,
varchar,
nvarchar,
text,
If u already used variable as String then why need to convert as a string
DECLARE #fname varchar(20), #strVarName varchar(50)
SET #fname = 'cronus'
SET #strVarName = #fname
SELECT #strVarName
if needed use CAST and CONVERT function
This is such a bizarre question, sounds like something I'd try to do.
Hmm, SQL is not supposed to do this but I guess, it doesn't mean you can't make it.
I think you would effectively have to write your own process to pull this off, something along the lines of:
Create dbo.sProcInserts stored procedure to insert values into a table:
Takes VariableName, Value and possibly table name to insert into as parameters
Create dbo.sProcExec stored procedure to execute stored procedure:
Before execute, read stored procedure into a variable
Find all variables that are SET (i.e. they have a SET #Var = OR SELECT #Var =)
After each variable set, add to your string a line that calls dbo.sProcInserts with the name of the variable and a select #Variable
Execute your newly written stored procedure
That way you don't have to actually make any modifications to your sProcs and it should catch the flow of variables and their changes through your procedure
However the requirement itself is a bit strange for me, but here is a way that could be a good start point for you:
declare #var1 int
Set #var1= 1
--some code here
declare #var2 nvarchar(max)
set #var2 = 10
--some other code here
declare #var3 bit
print ##VERSION
print 'this is fake #value inside a string'
--$ This is a Hint to help me find the Query that should parsed
declare #sql varbinary(max)
select #sql=sql_handle
from sys.sysprocesses
where spid=56
declare #q nvarchar(max)
select #q= substring(text,1,charindex('$',text)-3) from sys.dm_exec_sql_text(#sql)
Select distinct rtrim(ltrim(substring(Name,1,charindex(' ',Name)))) as Name from(
Select substring(replace(Name,'=',' '),8, Len(Name)) as Name from dbo.SplitString(#q,'declare ')
) as K
where Name like '#[^#]%'
By running the above query you will get the variables name.
Output:
#var1
#var2
#var3
You can find the source code for SplitString function Here
Note: If you are using SQL Server 2016 and your database's compatibility level is equal or greater than 130, you can also use SPLIT_STRING introduced by Microsoft it self. Learn more Here
Given a stored procedure like the one shown below:
CREATE PROCEDURE [dbo].[GetBusinessUnitSysNameAndGroupNames]
#ModelAfter varchar(100),
#BusinessUnitSystemName varchar(100) OUT,
#GroupsName varchar(4000) OUT
AS
BEGIN
if (#ModelAfter = 'Corporate')
BEGIN
SET #GroupsName = 'Admins'
SET #BusinessUnitSystemName = 'AcmeOutdoors'
END
else if (#ModelAfter = 'Retailers')
BEGIN
SET #GroupsName = 'Sellers'
SET #BusinessUnitSystemName = 'AcmeShoppers'
END
END
When I run from the SQL Studio command line:
EXEC [dbo].[GetBusinessUnitSysNameAndGroupNames] '~ModelAfter~', 'acmeoutdoors', 'admins'
I just get a result in the message panel like Command(s) completed successfully. But what I would like to see the actual result, not just a success message. Something like shown below(which doesn't work, just my idea).
DECLARE #Result varchar(max)
SET #Result = EXEC [dbo].[GetBusinessUnitSysNameAndGroupNames] '~ModelAfter~', 'acmeoutdoors', 'admins'
PRINT #Result
Returning Data by Using OUTPUT Parameters
If you specify the OUTPUT keyword for a parameter in the procedure
definition, the stored procedure can return the current value of the
parameter to the calling program when the stored procedure exits. To
save the value of the parameter in a variable that can be used in the
calling program, the calling program must use the OUTPUT keyword when
executing the stored procedure.
DECLARE #Result1 varchar(max), #Result2, varchar(max)
EXEC [dbo].[GetBusinessUnitSysNameAndGroupNames] 'Corporate', #Result1 OUT, #Result2 OUT
PRINT #Result1
PRINT #Result2
I am writing a stored procedure which will compare two similar tables under two different database. Here I am using the keyword USE [dbname].
DECLARE
--INPUT
#BASE_DATABASE_NAME NVARCHAR(50),
#TARGET_DATABASE_NAME NVARCHAR(50),
#TARGET_PRODUCT_ID NVARCHAR(50),
#TARGET_PRODUCT_CODE NVARCHAR(50)
SET #BASE_DATABASE_NAME='USE [DB1]'
SET #TARGET_DATABASE_NAME='USE [DB2]'
SET #TARGET_PRODUCT_ID=4194
SET #TARGET_PRODUCT_CODE = #BASE_DATABASE_NAME ( SELECT PRODUCT_CODE FROM T_PRODUCT_MST WHERE PROD_ID = #TARGET_PRODUCT_ID)
print #TARGET_PRODUCT_CODE.
Error--
It's not working...
Can anybody help me out with this? I need to pass the database name dynamically to the sql query.
Thanks in advance..
You cannot use USE this way. USE sets the database against which all the statements are executed and cannot be used inside another query.
You can use dynamic SQL though to specify your query:
DECLARE
--INPUT
#BASE_DATABASE_NAME NVARCHAR(50),
#TARGET_PRODUCT_ID INT,
#TARGET_PRODUCT_CODE NVARCHAR(50)
SET #BASE_DATABASE_NAME='[DB1]'
SET #TARGET_PRODUCT_ID=1
DECLARE #SQL NVARCHAR(MAX) = N'SELECT #TARGET_PRODUCT_CODE = PRODUCT_CODE FROM '
+ #BASE_DATABASE_NAME
+ N'..T_PRODUCT_MST WHERE PROD_ID = #TARGET_PRODUCT_ID'
exec sp_executesql #SQL, N'#TARGET_PRODUCT_ID INT, #TARGET_PRODUCT_CODE NVARCHAR(50) OUTPUT',
#TARGET_PRODUCT_ID, #TARGET_PRODUCT_CODE OUTPUT
print #TARGET_PRODUCT_CODE
Another option to Szymon's answer is to use synonyms. First create your synonyms in the DB:
CREATE SYNONYM [dbo].[TargetProductCode] FOR [DB2].[dbo].[T_Product_MST]
And then your sql syntax becomes:
SET #TARGET_PRODUCT_CODE = SELECT PRODUCT_CODE
FROM dbo.TargetProductCod WHERE PROD_ID = #TARGET_PRODUCT_ID
If this doesn't need to be dynamic, this can be a good solution, and can also make for easier testing, if for some reason you need to point a test DB to a different target (can just update the synonym).
here is an interesting problem in Sql Server; I have a stored procedure, that returns the following error when executed:
The type 'MyTable' already exists, or you do not have permission to
create it.
I think the type MyTable wasn't properly created, and I base this guess upon the fact other types (nvarchar, for example) are all coloured in blue, whereas when I hover the mouse above #T declaration (DECLARE #T AS MyTable), it says #T has an invalid data type.
Here is a version of the sproc :
CREATE PROCEDURE SPXXX
AS
BEGIN
DECLARE #calc numeric(18,2)
DECLARE #sql nvarchar(1500), #column_name nvarchar(50), #table_name nvarchar(50), #prmDef nvarchar(1500)
DECLARE #v1 nvarchar(50), #v2 nvarchar(50)
DECLARE #T AS MyTable
Set #column_name = 'EID'
Set #table_name = 'CTRY_S'
Set #sql = N'Select #calcOUT = SUM(datalength(#v1))/2 from #T';
Set #prmDef = '#v1 nvarchar(50), #calcOUT numeric(18,2) OUTPUT';
EXECUTE sp_executesql #sql, #prmDef, #v1=#column_name, #T=#table_name, #calcOUT=#calc OUTPUT;
END
GO
You have a bunch of syntax errors in the example code. I am assuming that happened when you shortened the example, so I am not going to talk about them.
Your main problem is, that the CREATE TYPE MyTable TABLE(..) command creates an object in the database. This type is not local to the procedure and stays in the database after the procedure finishes. The next time the procedure executes, you will get the error you have seen because the type indeed already exists.
Just remove the create type statement and you should be fine.
As for intellisense, you can never really trust it. Only execution tells if your statement is correct or not. You can use alternatives that are sold by other companies. They tend to be better, but non that I have come across is perfect.