Trigger skipping entering 1st row on Insert

  • I have an insert trigger that will always skip the first row of the inserted table. There is a function in the trigger dbo.fnParseString that is taking a varchar field(123456-111111) and splitting it in into individual records. so now there is a record for 123456 and 111111 and associating it with another field. For some reason what ever the first Id is it is always missing from the new table. I know this sounds confusing so if you need more info please let me know. My trigger is below.

    create TRIGGER dbo.TR_BUY_Insert_ProductChoiceItemProductInventory

    ON dbo.bvc_ProductInventory

    AFTER Insert

    NOT FOR Replication

    /*

    USAGE:

    Procedure Name: TR_BUY_Insert_ProductChoiceItemProductInventoryoryKey

    Created By: Pam Ozer

    Create Date: August 18, 2009

    RevisionNo: 0

    Modified By:

    CREATE PURPOSE: Inserts the dbo.Buy_ProductChoiceItemProductInventory table with the new Choice Item IDs based on the InventoryKey

    MODIFICATION Details:

    */

    AS

    SET NOCOUNT ON

    SET TRANSACTION ISOLATION LEVEL READ UNCOMMITTED

    BEGIN TRY

    Declare @Inventorykey Nvarchar(50)

    Set @inventorykey=(Select Inventorykey from Inserted)

    If @inventorykey='0'

    Return

    BEGIN TRANSACTION

    INSERT INTO dbo.Buy_ProductInventoryProductChoiceItem

    ( ProductInventoryID, ProductChoiceItemID )

    SELECT .ID, dbo.fnparsestring(1,'-',I.inventorykey)

    FROM Inserted (nolock)

    where dbo.fnparsestring(1,'-',I.inventorykey) is not null

    Union all

    SELECT .ID, dbo.fnparsestring(2,'-',I.inventorykey)

    FROM Inserted (nolock)

    where dbo.fnparsestring(2,'-',I.inventorykey) is not null

    Union all

    SELECT .ID, dbo.fnparsestring(3,'-',I.inventorykey)

    FROM Inserted (nolock)

    where dbo.fnparsestring(3,'-',I.inventorykey) is not null

    Union all

    SELECT .ID, dbo.fnparsestring(4,'-',I.inventorykey)

    FROM Inserted (nolock)

    where dbo.fnparsestring(4,'-',I.inventorykey) is not null

    Union all

    SELECT .ID, dbo.fnparsestring(5,'-',I.inventorykey)

    FROM Inserted (nolock)

    where dbo.fnparsestring(5,'-',I.inventorykey) is not null

    COMMIT TRANSACTION

    --RETURN 0

    END TRY

    BEGIN CATCH

    IF Xact_State() = -1

    ROLLBACK TRANSACTION

    IF Xact_State() = 1

    COMMIT TRANSACTION

    --RETURN @@Error

    END CATCH

    SET TRANSACTION ISOLATION LEVEL READ COMMITTED

    SET NOCOUNT OFF

    GO

    GO

  • Hi,

    I don't see anything odd in your code, can you provide the source code for this function : dbo.fnparsestring().

    Maybe you need to send the parameter (0) to it, to get the first number? Just a guess.

    Cheers,

    J-F

  • While waiting on the parsestring function to be posted, I will also ask if you have considered rewriting it as a parse to produce a derived table to feed the INSERT, instead of using a bunch of UNION ALL queries.

    declare @sampleIn varchar(8000)

    declare @sampleOut table (data char(5))

    set @sampleIn = '12345-67890-23456-78901-34567'

    set @sampleIn = '-'+@sampleIn+'-'

    ;with tally (N) as (select ROW_NUMBER() over(order by id) from master..syscolumns)

    ,parseCTE AS

    (select substring(@sampleIn,N+1,charindex('-',@sampleIn,N+1)-(N+1)) as element

    from tally

    where substring(@sampleIn,N,1) = '-'

    and N < len(@sampleIn)

    )

    insert into @sampleOut

    select * from parseCTE

    select * from @sampleOut

    __________________________________________________

    Against stupidity the gods themselves contend in vain. -- Friedrich Schiller
    Stop, children, what's that sound? Everybody look what's going down. -- Stephen Stills

  • Here is a copy of the function. I did try using a 0 but that didn't work. It is looking at the sections before and after the - so that's why that wouldn't work. And No I hadn't thought of the derived table. I will have to see if that will work. Thanks for all your help. Any other help would be greatly appreciated

    SET ANSI_NULLS ON

    GO

    SET QUOTED_IDENTIFIER ON

    GO

    ALTER FUNCTION [dbo].[fnParseString]

    (

    @Section SMALLINT,

    @Delimiter CHAR,

    @Text VARCHAR(8000)

    )

    RETURNS VARCHAR(8000)

    AS

    BEGIN

    DECLARE

    @NextPos SMALLINT,

    @LastPos SMALLINT,

    @Found SMALLINT

    SELECT

    @NextPos = 0,

    @Found = 0

    IF @Section > 0

    SELECT @Text = REVERSE(@Text)

    WHILE @NextPos <= DATALENGTH(@Text) AND @Found < ABS(@Section)

    SELECT @LastPos = @NextPos,

    @NextPos = CASE

    WHEN CHARINDEX(@Delimiter, @Text, @LastPos + 1) = 0 THEN DATALENGTH(@Text) + 1

    ELSE CHARINDEX(@Delimiter, @Text, @LastPos + 1)

    END,

    @Found = @Found + 1

    IF @Found ABS(@Section) OR @Found = 0 OR @Section = 0

    SELECT @Text = NULL

    ELSE

    SELECT @Text = SUBSTRING(@Text, @LastPos + 1, @NextPos - @LastPos - 1)

    RETURN CASE WHEN @Section < 0 THEN @Text ELSE REVERSE(@Text) END

    END

  • Still don't see why what you have isn't working. But I do see that you are using a while loop in your parse function. Take a look in SSC at the various threads and articles about parsing using a tally table instead of a while loop. You stand to gain a bit of performance just rewriting that function.

    __________________________________________________

    Against stupidity the gods themselves contend in vain. -- Friedrich Schiller
    Stop, children, what's that sound? Everybody look what's going down. -- Stephen Stills

Viewing 5 posts - 1 through 4 (of 4 total)

You must be logged in to reply to this topic. Login to reply