T-SQL过程不起作用,与varchar到日期转换问题

时间:2014-09-05 17:39:24

标签: sql sql-server date sql-server-2012 date-parsing

当我运行此SP时,我得到:
消息241,级别16,状态1,过程PED_SP_PED_Updates,第22行 从字符串转换日期和/或时间时转换失败。

这是执行:

exec dbo.ped_sp_ped_updates
@CURRENTHICN='111111111A',
@DATERECEIVED = '20140904',
@FIELDTOBECHANGED='FIRST_NAME_MEMBER',
@CURRENTFIELDVALUE = 'MARY',
@NEWFIELDVALUE = 'MARYTEST',
@REQUESTEDBY = 'IPISORS',
@ID=156

我不知道为什么,我将varchar转换回比较日期 请注意,我没有问题被告知更好的方法,但是如果可以的话,它会(我认为)对我的学习更有帮助,至少也是' ,直接回答为什么我目前的处理工作不起作用。除了任何有用的想法,为什么它应该做不同,更好,等等等。

ALTER PROCEDURE [dbo].[PED_SP_PED_Updates]
    @CurrentHicn VARCHAR(500),
    @DateReceived VARCHAR(20),
    @FieldToBeChanged VARCHAR(500),
    @CurrentFieldValue VARCHAR(500),
    @NewFieldValue VARCHAR (500),
    @RequestedBy VARCHAR(10),
    @ID int

AS
BEGIN
    -- SET NOCOUNT ON added to prevent extra result sets from
    -- interfering with SELECT statements.
    SET NOCOUNT ON;

    -- Insert statements for procedure here
    DECLARE @CurrentDBNote VARCHAR(MAX)
    DECLARE @NewNote VARCHAR(MAX)
    DECLARE @CountofHicn INT

    SET @NEWNOTE = 'Isaac Pisors | ' + GetDate() + ' | ' 
            + 'Changing field: ' + @FieldToBeChanged + ' from ' + @CurrentFieldValue + ' to ' + @NewFieldValue
            + ', per ' + @RequestedBy + ' request.  Also changing any related DOCS/FAXES records to correspond'

    SET @CurrentDBNote=
        (SELECT NOTES_GENERAL FROM PED_APPLICATIONS WHERE HICN_MEDICARE_NUMBER=@CurrentHicn AND (Cast(ISNULL(DATE_RECEIVED,'1900-01-01') as DATE)=CAST(@DateReceived AS DATE)))

    --NOW ADD THE TWO:
    SET @NewNote = @CurrentDBNote + CHAR(13) + @CurrentDBNote

    --SEE IF THERE IS STILL A MATCHING RECORD
    SET @CountofHicn=
        (SELECT COUNT(*) FROM PED_APPLICATIONS WHERE HICN_MEDICARE_NUMBER=@CurrentHicn AND (CAST(ISNULL(DATE_RECEIVED,'1900-01-01') AS DATE)=CAST(@DateReceived AS DATE)))

    IF @CountofHicn=0  --THERE IS NO LONGER A MATCHING RECORD - INSERT THAT NOTE AND CALL IT A DAY
        BEGIN   
            UPDATE PED_PEDUPDATES SET COMPLETEDON=GetDate(), COMPLETEDBY='SSIS',
            EXCEPTIONNOTE='Could not locate any records where HICN is ' + @CurrentHicn + ' and Date Received is ' + CAST(@DateReceived AS VARCHAR)
            WHERE [ID]=@ID
        END
    ELSE                --GO AHEAD AND DO THE UPDATE
        BEGIN
            UPDATE PED_APPLICATIONS SET @FieldToBeChanged = @NewFieldValue
            WHERE HICN_MEDICARE_NUMBER=@CurrentHicn AND (CAST(ISNULL(DATE_RECEIVED,'1900-01-01') AS DATE)=CAST(@DateReceived AS DATE))
        END

    IF @FieldToBeChanged='HICN_MEDICARE_NUMBER' --THEN WE HAVE TO UPDATE DOCS TABLE, TOO
        BEGIN
            UPDATE PED_DOCS SET HICN_MEDICARE_NUMBER=@NewFieldValue
            WHERE
                (HICN_MEDICARE_NUMBER=@CurrentFieldValue AND (CAST(ISNULL(DATE_RECEIVED,'1900-01-01') AS DATE)=@DateReceived)) or
                (HICN_MEDICARE_NUMBER=@CurrentFieldValue AND DATE_RECEIVED IS NULL)
        END

    IF @FieldToBeChanged='HICN_MEDICARE_NUMBER'     --THEN OUR WHERE CLAUSE-HICN IS THE *NEW* HICN
        BEGIN
            UPDATE PED_APPLICATIONS SET NOTES_GENERAL=@NewNote
            WHERE HICN_MEDICARE_NUMBER=@NewFieldValue AND (CAST(ISNULL(DATE_RECEIVED,'1900-01-01') AS DATE)=CAST(@DateReceived AS DATE))
        END
    ELSE                                            --ELSE OUR WHERE CLAUSE-HICN IS THE *OLD* HICN
        BEGIN
            UPDATE PED_APPLICATIONS SET NOTES_GENERAL=@NewNote
            WHERE HICN_MEDICARE_NUMBER=@CurrentHicn AND (CAST(ISNULL(DATE_RECEIVED,'1900-01-01') AS DATE)=CAST(@DateReceived AS DATE))
        END

    --FINALLY, UPDATE RECORD AS COMPLETE:
    UPDATE PED_PEDUPDATES SET COMPLETEDON=GetDate(),COMPLETEDBY='SSIS' WHERE [ID]=@ID


END


GO

1 个答案:

答案 0 :(得分:3)

短期修复

  • 使用CAST(@DateReceived AS DATE)

    代替CONVERT(date, @DateReceived, 112)

    值112是您正在使用的yyyymmdd格式化varchar的样式代码。有关详细信息,请参阅cast and convert documentation

  • 此外,您应该验证表格DATE_RECEIVED列中的所有值格式是否正确。即使一个不可转换的值也会导致此错误。

正确修复

  • @DateReceived应作为date而不是varchar传递给该程序。

  • 您的表格中的DATE_RECEIVED字段应宣布date而不是varchar

通常,当存在用于此目的的本机类型时,请避免将日期或时间视为数据库中的字符串。