在SQL Server查询中强制转换

时间:2013-04-22 15:49:34

标签: sql-server-2008 stored-procedures casting

我遇到执行一个SQL查询的问题,下面是我的存储过程

查询

ALTER PROCEDURE ProcName
(
     @iID VARCHAR(50),
     @AccountID INT
)
AS
SET NOCOUNT ON

DECLARE @Sql VARCHAR(MAX)

SET @Sql = 'DELETE FROM ReferringPhysician WHERE iID IN(' + @iID + ') AND AccountID = '+ @AccountID + ''
EXEC (@Sql)

我正在尝试执行此查询,但它给了我错误,因为我正在使用exec(),这里在我的情况下我正在处理string,而在另一个条件我正在处理int,所以在第二种情况下我得到投射错误!我该如何解决这个问题?

任何帮助都会得到极大的赞赏!

由于

2 个答案:

答案 0 :(得分:4)

您的查询容易受到SQL注入的影响。

避免数据类型问题的一种方法是尽可能传递正确的数据类型,而不是使用EXEC()more details here):

DECLARE @sql NVARCHAR(MAX) = N'DELETE dbo.referringPhysician
    WHERE iID IN (' + @iID + ') AND AccountID = @AccountID;';

EXEC sp_executesql @sql, N'@AccountID INT', @AccountID;

您可以通过使用表值参数并使用适当的类型而不是逗号分隔的字符串传入DataTable或其他集合来完全保护SQL注入。 e.g:

CREATE TYPE dbo.iIDs TABLE(iID INT PRIMARY KEY);

现在,您的存储过程可以完全避免动态SQL:

ALTER PROCEDURE dbo.ProcName -- always use schema prefix!
  @iIDs dbo.iIDs READONLY,
  @AccountID INT
AS
BEGIN
  SET NOCOUNT ON;

  DELETE r
    FROM dbo.ReferringPhysician AS r
    INNER JOIN @iIDs AS i
    ON r.iID = i.iID
    WHERE r.AccountID = @AccountID;
END
GO

答案 1 :(得分:0)

试试这个:

ALTER PROCEDURE ProcName
(
     @iID VARCHAR(50),
     @AccountID INT
)
AS
SET NOCOUNT ON

DECLARE @Sql VARCHAR(MAX)

SET @Sql = 'DELETE FROM ReferringPhysician WHERE iID IN(' + CAST(@iID AS VARCHAR) + ') AND AccountID = '+ CAST(@AccountID AS VARCHAR) + ''
EXEC (@Sql)