2015-02-11 99 views
0

我有一个存储过程,输入变量是类型uniqueidentifier。当我执行这个存储过程时,如果我得到表中正确的值,那么存储过程将返回记录,但是如果我给出的值错误,那么存储过程不应返回任何内容。从字符串转换为uniqueidentifier时转换失败。在SQL中

我得到这个错误:

Conversion failed when converting from a character string to uniqueidentifier.

这是我的存储过程:

ALTER PROCEDURE [dbo].[Get_Authorization_Token] 
    @Auth_Token uniqueidentifier 
AS 
BEGIN 
    SET NOCOUNT ON; 

    SELECT 
     Customer_ID, Auth_Token, Token_Expiration 
    FROM 
     Authorization_Token 
    WHERE 
     Auth_Token = @Auth_Token 
     AND GETDATE() < Token_Expiration 
END 

我不知道为什么我的冻结后!

我已经试过了CAST这样的:

CAST(Auth_Token as uniqueidentifier) 

,但我得到同样的错误。

+0

您忘记指出'auth_token'列的数据类型,这是此问题的关键。 – 2016-11-19 09:59:01

回答

1

我打算在这里出去走一走,说你表中的auth_token列是一个varchar(或nvarchar),并且那里的一个值不是有效的guid。因此,当您执行搜索时,它试图(和失败)将该列中的值转换为guid。

您可以将您的传入guid转换为字符串,以便它匹配列的数据类型,知道cousre,它永远不会匹配那些无效的字符串。

这里是发生了什么事情

if object_id('tempdb.dbo.#test') is not null drop table #test 
create table #test 
(
    AuthToken char(36) 
) 

insert into #Test 
select cast(newid() as varchar(36)) union all --this is fine 
select 'Not a guid' --this is not 

declare @authtoken uniqueidentifier = newid() 

select * 
from #test 
where AuthToken = @authtoken 

要解决此问题的说明,您可以重构select语句投@authtoken像这样的字符串:

select * 
from #test 
where AuthToken = cast(@authtoken as char(36)) 

如果你有SQL Server 2012,你也可以在列上使用try_convert

select * 
from #test 
where try_convert(uniqueidentifier, AuthToken) = @authtoken 

编辑:这里有人我写了一小段代码来测试字符串是否为GUID。我probalby不会在生产系统中使用它,但它可以帮助您找出无效的字符串。

declare @testGUID char(36) = newid(), 
@guidPattern varchar(1000) = 
    replicate('[0-9A-Fa-f]', 8) 
    + '-' 
    + replicate('[0-9A-Fa-f]', 4) 
    + '-' 
    + replicate('[0-9A-Fa-f]', 4) 
    + '-' 
    + replicate('[0-9A-Fa-f]', 4) 
    + '-' 
    + replicate('[0-9A-Fa-f]', 12) 


if @testGUID like @guidPattern 
    select 'ITS A GUID!' 
else 
    select 'OH NOES' 
相关问题