1

I am working on rewriting a Stored procedure in SQL Server 2008 that is used in POS billing process. First step is to get Bill Number which is an auto-rotate sequence number with added prefix.

As the number of concurrent terminal grows ~10-30, we have faced number of issues like duplicate number, dead lock. Optimization that I am currently working on derived from here, which improved to an extend (no duplicates). But when I tried to test with SQLQueryStress based on this suggestion using 10 iteration and 10 concurrent thread, I see dead lock in few tests and consistent failure getting the prefix from the same table for the first(few iterations)

Procudure has these currently

  1. SET TRANSACTION ISOLATION LEVEL SERIALIZABLE
  2. get the prefix from the same table with (nolock) where type=@type and terminalid=@terminalid
  3. Begin Tran
  4. UPDATE Numbering with (serializable) SET @nextval=nextnumber, nextnumber = nextnumber + 1
  5. if @@rowcount = 0 insert
  6. Commit tran
  7. output Format prefix + @nextval

Note, This code snippet will not be Ideal as, I was going back and forth restructuring this. This is only a section of code of an if else, where the else has the same block repeating with different where condition(for four different scenarios).

ALTER PROCEDURE [dbo].[GetnextNumberTest] 
        @transType varchar(50), -- 
        @terminalaname varchar(50)='',  --will be empty if it is not terminal wise
        @nextvalue varchar(10) output
AS
BEGIN

SET TRANSACTION ISOLATION LEVEL SERIALIZABLE;

declare @ResetBasedOn int =0
        ,@Prefix varchar(50)=''
        ,@nextvalint int=0


select  @ResetBasedOn=RestartOn,
        @Prefix=((SELECT Prefix FROM TerminalMaster(nolock) WHERE TerminalName=@terminalaname)+'/'+ prefix)
                        from NumberingSchemeTest (nolock)
    where  TRSType= @transType 
        and (TerminalName=@terminalaname or TerminalName='') and active=1


if(@ResetBasedOn=0) --daily
begin

    Begin Tran
        UPDATE Numberingschemetest with (serializable)      
            SET @nextvalint=nextnumber,
            -- 
                nextnumber = nextnumber + 1

        WHERE TRSType= @transType 
            and (TerminalName=@terminalaname or TerminalName='') 
            and yearlydate =convert(varchar, GETDATE()) 
            and active=1 

       if @@rowcount = 0
       begin
            UPDATE Numberingschemetest with (serializable)  
                set active=0
            where  TRSType= @transType 
                and (TerminalName=@terminalaname or TerminalName='') 
                and yearlydate =convert(varchar, GETDATE() -1) 
                and active=1

            insert into  Numberingschemetest (
                TRSType,  
                Prefix,    
                TPrefix,   
                TerminalName,  
                RestartOn, 
                YearlyDate,  
                StartingFrom, 
                NextNumber, 
                active,PreparedBy
                )
            (select top 1  
                TRSType,  
                Prefix,    
                TPrefix,   
                TerminalName,  
                RestartOn,   
                convert(varchar, GETDATE()),  
                StartingFrom, 
                StartingFrom+1, 
                1  ,@terminalaname
            from Numberingschemetest 
                where TRSType= @transType 
                    and (TerminalName=@terminalaname or TerminalName='') 
                    and active=0 )

        End
    Commit Tran
    if(@nextvalint=0)
        set  @nextvalue=@Prefix+'0001' 
    else
    set @nextvalue =@Prefix+RIGHT('000'+ CAST(@nextvalint AS VARCHAR(50)),Case when LEN(@nextvalint)>4 then LEN(@nextvalint) else 4 end)
End

All these based on several similar question from this site. At this stage, I could only think of two things. One is split the prefix to a separate table and the other is to try a different tool to do the load testing.

I can understand that there will be some trade off, but want to know the best route forward.

Apsar
  • 19
  • 1
  • 1
  • 5
  • can you post the proc code? – S3S Feb 10 '19 at 10:23
  • @scsimon, any suggestions? Anything to move forward is fine, even if is rethinking on the Architecture. Thanks – Apsar Feb 17 '19 at 22:44
  • I just noticed you post a private code I will look at this tomorrow – S3S Feb 17 '19 at 22:53
  • I think it'd benefit you to check out [Kendra's poster](https://littlekendra.com/sqlserverposters/) on lock hints and [this answer](https://stackoverflow.com/a/7845331/6167855) – S3S Feb 18 '19 at 14:17

0 Answers0