Kindly help me to optimize this code, or let me know if I can do this in a better way.
Req: I'm updating Product
table which will have product info.
- The idea is to fetch some columns from other tables through join. (curTaxonomy is doing that.)
- And then update the fetched records to
Product
table. - But before that I need to check if the columns which I'm updating in the
product
table are NULL or have dissimilar value (different value than what is coming from join). - If these conditions match then only update the columns.
This I'm using cursors to fetch records and creating dynamic update query which will update the records.
CODE:
CREATE PROCEDURE [dbo].[UpdateProdCatalog]
AS
BEGIN
DECLARE @Tier_1_Tbl NVARCHAR(100) = NULL
DECLARE @Tier_2_Tbl NVARCHAR(100) = NULL
DECLARE @Flag_Tbl NVARCHAR(100) = NULL
DECLARE @Tier_1 NVARCHAR(100) = NULL
DECLARE @Tier_2 NVARCHAR(100) = NULL
DECLARE @Flag NVARCHAR(100) = NULL
DECLARE CurTaxonomy CURSOR FOR
SELECT CFR.T1,
CFR.T2,
CFR.Flag
FROM ProductCatalogue MPC
JOIN ControlFlow1 CF ON MPC.Product_Code = CF.Product_Code
JOIN ControlFlow2 CFR ON CF.MajorFamily = CFR.Product_Family
WHERE MPC.Manufacturer_Name = 'DELL';
OPEN CurTaxonomy
IF @@CURSOR_ROWS > 0
FETCH NEXT FROM CurTaxonomy INTO @Tier_1,@Tier_2,@Flag
WHILE @@Fetch_status = 0
BEGIN
--print @Tier_1 + ' : '+ @Tier_2 + ' : '+ @Flag
DECLARE CurProd CURSOR FOR
SELECT MPC.Tier_1,
MPC.Tier_2,
MPC.Flag
FROM ProductCatalogue MPC
WHERE MPC.Manufacturer_Name = 'DELL'
OPEN CurProd
IF @@CURSOR_ROWS > 0
FETCH NEXT FROM CurProd INTO @Tier_1_Tbl,@Tier_2_Tbl,@Flag_Tbl
WHILE @@Fetch_status = 0
BEGIN
--print @Tier_1_Tbl + ' : '+ @Tier_2_Tbl + ' : '+ @Flag_Tbl
DECLARE @sqlCommand VARCHAR(8000)
DECLARE @Starter VARCHAR(100)
--Generating dynamic update Query
SET @Starter = 'SET '
SET @sqlCommand = 'UPDATE ProductCatalogue '
BEGIN
IF ( @Tier_1 IS NOT NULL) AND (@Tier_1_Tbl IS NULL or @Tier_1_Tbl <> @Tier_1)
BEGIN SET @sqlCommand = @sqlCommand + @Starter + 'Tier_1 = ''' + @Tier_1 + '''' SET @Starter = ', ' END
IF ( @Tier_2 IS NOT NULL) AND (@Tier_2_Tbl IS NULL or @Tier_2_Tbl <> @Tier_2)
BEGIN SET @sqlCommand = @sqlCommand + @Starter + 'Tier_2 = ''' + @Tier_2 + '''' SET @Starter = ', ' END
IF ( @Flag IS NOT NULL) AND (@Flag_Tbl IS NULL or @Flag_Tbl <> @Flag)
BEGIN SET @sqlCommand = @sqlCommand + @Starter + 'Flag = ''' + @Flag + '''' SET @Starter = ', ' END
END
IF (@Starter = ', ')
BEGIN
SET @sqlCommand = @sqlCommand + @Starter + ' Last_Modify_Date = ''' + CONVERT(VARCHAR(22),SYSDATETIME(),121) + ''''
SET @sqlCommand = @sqlCommand + ' FROM ProductCatalogue MPC
JOIN ControlFlow1 CF ON MPC.Product_Code = CF.Product_Code
JOIN ControlFlow2 CFR ON CF.MajorFamily = CFR.Product_Family
WHERE MPC.Manufacturer_Name = ''' + 'DELL' + ''''
EXEC (@sqlCommand)
END
FETCH NEXT FROM CurProd INTO @Tier_1_Tbl,@Tier_2_Tbl,@Flag_Tbl
END
CLOSE CurProd
DEALLOCATE CurProd
FETCH NEXT FROM CurTaxonomy INTO @Tier_1,@Tier_2,@Flag
END
CLOSE CurTaxonomy
DEALLOCATE CurTaxonomy
END
Here my concern is that the two cursors will run some n x m times and it is also updating the same value to all of the records. I even tried this which works fine.
update ProductCatalogue
set Tier_1 = CFR.T1,
Tier_2 = CFR.T2,
Flag=CFR.Flag,
Last_Modify_Date = SYSDATETIME()
from ProductCatalogue MPC
join ControlFlow1 CF on MPC.Product_Code = CF.Product_Code
join ControlFlow2 CFR on CF.MajorFamily = CFR.Product_Family;
But I also need to check existing records in product
table and fulfill the requirements as mentioned above .If there is any better way to do the same that'll be much appreciated.