Conversion failed when converting from a character string to uniqueidentifier - sql

Created a stored procedure in SQL 9 (2005) and have since upgraded to SQL 10 (2008). Since then, the following stored procedure has stopped working and thrown up the above error:
ALTER PROCEDURE [dbo].[GetModifiedPages]
#vPortalUID nvarchar(32) = ''
AS
BEGIN
-- Convert GUID to UI
DECLARE #nPortalUID AS uniqueidentifier
SET #nPortalUID = CAST(#vPortalUID AS uniqueidentifier)
The passed in param #vPortalUID contains: 2A66057D-F4E5-4E2B-B2F1-38C51A96D385. I execute the stored proc like this:
EXEC GetModifiedPages '2A66057D-F4E5-4E2B-B2F1-38C51A96D385'
It falls over. I have tried Convert aswell. Still no joy. Have also had the value going in with { } around it. I removed these programatically and manually as above.
If you are interested I am running the SP from an ASP Classic page, although that should not affect this as the above code was run using SSMS.
Thanks in advance for your help.
James

this fails:
DECLARE #vPortalUID NVARCHAR(32)
SET #vPortalUID='2A66057D-F4E5-4E2B-B2F1-38C51A96D385'
DECLARE #nPortalUID AS UNIQUEIDENTIFIER
SET #nPortalUID = CAST(#vPortalUID AS uniqueidentifier)
PRINT #nPortalUID
this works
DECLARE #vPortalUID NVARCHAR(36)
SET #vPortalUID='2A66057D-F4E5-4E2B-B2F1-38C51A96D385'
DECLARE #nPortalUID AS UNIQUEIDENTIFIER
SET #nPortalUID = CAST(#vPortalUID AS UNIQUEIDENTIFIER)
PRINT #nPortalUID
the difference is NVARCHAR(36), your input parameter is too small!

Related

Understanding scalar variables

I've inherited an SSRS report which I need some assistance in understanding how the scalar variable works as I just don't get it.
The stored procedure starts off as below and there is no issue running the stored procedure with the #FromPeriod and #ToPeriod.
CREATE PROCEDURE [dbo].[_SP_STOREDPROCEDURE]
(#FromPeriod int, #ToPeriod Int)
AS
set nocount on
declare #v_FromPeriod int
declare #v_ToPeriod int
declare #cnt int, #periods int
declare #v_periodbegindate datetime
declare #v_YearBegindate datetime
ETC. ETC.
Next, I then have the other script which is run on an adhoc basis and this is the part I need help on:
declare #Period int
declare #PriorPeriod int
select #period = cur_per from tbm_Parms
if right(#Period, 2) <> '01'
begin
set #PriorPeriod = #Period - 1
end
exec [_SP_STOREDPROCEDURE] #PriorPeriod, #PriorPeriod
How does this work?
My stored procedure has #FromPeriod and #ToPeriod defined, yet using the adhoc script it is passing #PriorPeriod instead. It works perfectly but I don't understand how/why it works.
Any pearls of wisdom would be appreciated.
Thanks
Your stored procedure "[dbo].[_SP_STOREDPROCEDURE]" simply applies the same value to both parameters.
Your parameters are:
#FromPeriod int, #ToPeriod Int
You invoke with:
exec [_SP_STOREDPROCEDURE] #PriorPeriod, #PriorPeriod
Assuming that #PriorPeriod = 5, that is just the same as:
exec [_SP_STOREDPROCEDURE] 5, 5.
Now #FromPeriod contains 5. And #ToPeriod /also/ contains 5.
But you haven't given us enough code from _SP_STOREDPROCEDURE to explain why, according to you, that works perfectly. But I'm guessing that the answer is in the WHERE clause in your stored procedure.

How do i convert variable name to string name?

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

Using the IN Clause With Stored Procedures

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?

Using varchar(max) in a Stored Proc. Why is the insert value truncated?

I am new to both SQL 2005 and Enterprise Library (version 4.) I'd like to call a Stored Proc and pass a string that is over 8000 chars. The column in the db is defined as varchar(max). I thought I'd start out by doing a little test first with calling the stored proc from T-SQL and I was surprised that the inserted string value was truncated, even for a short string.
CREATE TABLE [dbo].[ChadTest](
[TestParam] [varchar](max) NOT NULL
) ON [CMISII_DATA]
GO
ALTER PROCEDURE [dbo].[spr_ChadTest]
(
#TestParam varchar(max)
)
AS
BEGIN
INSERT INTO ChadTest
(TestParam) VALUES (#TestParam)
END
DECLARE #RC int
DECLARE #TestParam varchar
-- TODO: Set parameter values here.
SET #TestParam = '12345'
EXECUTE #RC = [CMISII].[dbo].[spr_ChadTest]
#TestParam
Select TestParam, len(TestParam) from chadtest
Output:
1 1
Once I get this simple example above to work, I will need to figure out how to pass a long string to the SP from VB.NET code using the Enterprise library . What would the data type of the param be? I see no overloaded version of the AddInParameter method that accepts a length nor do I see a "varchar(max)" enum as an available data type.
dbCmd = db.GetStoredProcCommand("spr_ChadTest")
db.AddInParameter(dbCmd, "TestParam", SqlDbType.VarChar, TestParam.ToString)
Thanks!
DECLARE #TestParam varchar
is the problem in your TSQL. You need to declare that as varchar(max) datatype to avoid truncation at 1 character length.
Your variable definition for TestParam is missing the (MAX) at the end of it. This will resolve your SQL query problem. The following code will add a paramter to a SqlCommand allowing the use of VARCHAR(MAX) from a VB .Net ASP application.
' Set up the output parameter to retrieve the summary.
Dim paramSummary As SqlParameter = New SqlParameter("#TestParam", SqlDbType.VarChar, -1)
command.Parameters.Add(paramSummary)
The following link displays more information

Is it possible to ignore an output param of a stored procedure?

How can I ignore an output parameter of a stored procedure? I'm calling the procedure from another procedure, e.g.:
DECLARE #param1 integer
EXEC mystoredprocedure
#in_param_1,
#in_param2_,
#param1 OUTPUT,
-- what do I type here to ignore the second output param??
I'm using T-SQL (MS SQL 2005).
You can just use NULL as the last parameter, and it should work fine - as long as that parameter isn't expected for input logic in the proc as well.
In your case, you'd call the proc as
exec mystoredproc #in_param_1, #in_param2_, #param1 OUTPUT, null
Here's another example that for the same scenario...
create proc MyTempProc
(#one int,
#two int out,
#three int out)
AS
begin
set #two = 2
set #three = 3
select #one as One
end
go
declare #p1 int,
#p2 int
set #p1 = 1
exec MyTempProc #p1, #p2 out, null
print #p1
print #p2
The output parameter has to have a default in order for you to not pass it. See below
create proc x (#in int = null, #out int = null OUTPUT)
as
Begin
Select #in
End
exec x 1
EDIT
To clarify a little, the error is being returned because the stored procedure that is being called has a parameter defined (in this case #param1), for which no default is defined. (i.e. #param1 int rather than #param int = -1) In the case where neither a parameter or default is specified for a defined parameter of a stored procedure when calling the stored procedure an error will occur. The same thing would happen if you tired to omit an input parameter that does not have a default specified.
You'll probably have to just ignore the OUTPUT param yourself by just not doing anything with the value. It's not like the overhead of that variable is an issue or anything. The only issue here is that your code will be a little bit uglier. So slap a comment on there explaining that the OUTPUT param isn't being used and everything should be alright.
If the SP you're calling expects a parameter to be passed, you have to have one there. Even if you disregard the output of it, it is part of the structure of the SP.
Think of parameters as a "Data Contract". If they're not defaulted, they're required. Even if the values are disregarded.
Forcing you to declare a dummy value you'll never read is the cost of calling that stored proc that may be used by something that DOES need to utilize the value of the output parameter.