CREATE PROC dbo.GEX_RESETQTY ( @PROD1 NVARCHAR(20), @PROD2 NVARCHAR(20), @RESETTYPE NCHAR(1), @DATE2 VARCHAR(10) ) /* Function : 進銷存數量重置主程式 Description: 目前的想法是將所有歷史重置的資料都統一寫到 FIVINVFINAL_HISTORY, 用 RESETDATE 區分不同時期的重置 風險是單一 Table 會有過大的疑慮, 但好處是固定的 Table 名稱, 管理及 SQL 語法都較方便處理 不含生管的數量重置作業, 可以支援單一產品或全產品重置 執行範例 EXEC GEX_RESETQTY '','ZZ','1','2099/12/31' RESETTYPE = 1 全重置 2 從頭到指定重置日 3 從前次重置日到指定重置日 4 從前次重置日到最後 9 期初期末存量表等報表要臨時使用的期初存量(取消) 1,4 寫到 FIVINVFINAL 2,3 寫到 FIVINVFINAL_HISTORY 目前只要使用1和2 即可, 期末數量和單據筆數關連不大 但是成本重置的 SP, 就要分段計算, 這是效能問題 Build Date : 2011/07/13 Modify History Item Who Date Modify Docs ==== ========== ========== ================================================ 1 Michael 2011/07/13 加入註解 2 Michael 2011/11/10 修正產品引數傳入星號(zz)的 SQL 問題 3 Michael 2013/03/18 將數量欄位為 null 更新為 0 */ AS --要先停掉 Trigger DISABLE TRIGGER DBO.TRI_INVSTKBILL1_CALCCOST ON dbo.INVSTKBILL1_D; DISABLE TRIGGER DBO.TRI_INVSTKBILL2_CALCCOST ON dbo.INVSTKBILL2_D; DISABLE TRIGGER DBO.TRI_INVSTKBILL3_CALCCOST ON dbo.INVSTKBILL3_D; IF @RESETTYPE = 1 OR @RESETTYPE = 4 BEGIN SET @DATE2 = '2199/12/31' END IF @RESETTYPE = '' OR @RESETTYPE = '*' BEGIN SET @RESETTYPE = '1' END IF @DATE2 = '' BEGIN SET @DATE2 = '2199/12/31' END --FOR 擴充機制使用 DECLARE @LOGINID VARCHAR(60) DECLARE @FUNCTAG VARCHAR(30) SELECT @LOGINID=GETDATE()+Round(RAND() * 10000, 0) SET @FUNCTAG = 'GEX_RESETQTY' --擴充機制 EXEC GEXRPT_INVRPT_EXTEND @PROD1,@PROD2,'','zz','1900/01/01',@DATE2,@FUNCTAG,'INV_INIT',@LOGINID,1 SELECT A.PRODUCTID, B.WAREID INTO #INVALL FROM BASPRODUCT A LEFT JOIN BASWAREHOUSE B ON 1 = 1 WHERE CASE WHEN @PROD1 = '*' THEN @PROD1 ELSE A.PRODUCTID END >= @PROD1 AND CASE WHEN @PROD2 = '*' THEN @PROD2 ELSE A.PRODUCTID END <= @PROD2 IF @RESETTYPE = 1 OR @RESETTYPE = 4 BEGIN DELETE FROM FIVINVFINAL WHERE NOT EXISTS ( SELECT * FROM BASPRODUCT WHERE PRODUCTID = FIVINVFINAL.PRODUCTID ) DELETE FROM FIV_LPS WHERE LOWPOINTSTOCK IS NULL INSERT INTO FIVINVFINAL (PRODUCTID,WAREID,LOWPOINTSTOCK,NOWQUANTITY,NOWCOST,BORROWOUTQTY,BORROWINQTY,RETURNINQTY,RETURNOUTQTY) SELECT A.PRODUCTID,A.WAREID,0,0,0,0,0,0,0 FROM #INVALL A LEFT JOIN FIVINVFINAL B ON A.PRODUCTID = B.PRODUCTID AND A.WAREID = B.WAREID WHERE B.NOWQUANTITY IS NULL AND CASE WHEN @PROD1 = '*' THEN @PROD1 ELSE A.PRODUCTID END >= @PROD1 AND CASE WHEN @PROD2 = '*' THEN @PROD2 ELSE A.PRODUCTID END <= @PROD2 --保留安全庫存設定 INSERT INTO FIV_LPS (PRODUCTID,WAREID,LOWPOINTSTOCK) SELECT A.PRODUCTID,A.WAREID,ISNULL(A.LOWPOINTSTOCK,0) FROM FIVINVFINAL A LEFT JOIN FIV_LPS B ON A.PRODUCTID = B.PRODUCTID AND A.WAREID = B.WAREID WHERE B.LOWPOINTSTOCK IS NULL AND CASE WHEN @PROD1 = '*' THEN @PROD1 ELSE A.PRODUCTID END >= @PROD1 AND CASE WHEN @PROD2 = '*' THEN @PROD2 ELSE A.PRODUCTID END <= @PROD2 UPDATE FIV_LPS SET LOWPOINTSTOCK = (SELECT LOWPOINTSTOCK FROM FIVINVFINAL WHERE FIV_LPS.PRODUCTID = FIVINVFINAL.PRODUCTID AND FIV_LPS.WAREID = FIVINVFINAL.WAREID) END ELSE IF @RESETTYPE = 2 OR @RESETTYPE = 3 BEGIN INSERT INTO FIVINVFINAL_HISTORY (RESETDATE,PRODUCTID,WAREID,LOWPOINTSTOCK,NOWQUANTITY,NOWCOST,BORROWOUTQTY,BORROWINQTY,RETURNINQTY,RETURNOUTQTY) SELECT @DATE2,A.PRODUCTID,A.WAREID,0,0,0,0,0,0,0 FROM #INVALL A LEFT JOIN FIVINVFINAL_HISTORY B ON A.PRODUCTID = B.PRODUCTID AND A.WAREID = B.WAREID AND RESETDATE = @DATE2 WHERE B.NOWQUANTITY IS NULL AND CASE WHEN @PROD1 = '*' THEN @PROD1 ELSE A.PRODUCTID END >= @PROD1 AND CASE WHEN @PROD2 = '*' THEN @PROD2 ELSE A.PRODUCTID END <= @PROD2 END; WITH INV1 AS ( SELECT A.PRODUCTID, A.WAREID, SUM(A.QUANTITY) AS QTY1 FROM INVSTKBILL1_D A LEFT JOIN INVSTKBILL1_M B ON A.BILLNO = B.BILLNO WHERE B.BILLDATE <= @DATE2 GROUP BY A.PRODUCTID, A.WAREID ), INV2 AS ( SELECT A.PRODUCTID, A.WAREID, SUM(A.QUANTITY) AS QTY2 FROM INVSTKBILL2_D A LEFT JOIN INVSTKBILL2_M B ON A.BILLNO = B.BILLNO WHERE B.BILLDATE <= @DATE2 GROUP BY A.PRODUCTID, A.WAREID ), INV3 AS ( SELECT A.PRODUCTID, A.WAREID, SUM(A.QUANTITY) AS QTY3 FROM INVSTKBILL3_D A LEFT JOIN INVSTKBILL3_M B ON A.BILLNO = B.BILLNO WHERE B.BILLDATE <= @DATE2 GROUP BY A.PRODUCTID, A.WAREID ), INV41 AS ( SELECT A.PRODUCTID, A.WAREINWAREHOUSE, SUM(A.QUANTITY) AS QTY41 FROM INVSTKBILL4_D A LEFT JOIN INVSTKBILL4_M B ON A.BILLNO = B.BILLNO WHERE B.BILLDATE <= @DATE2 GROUP BY A.PRODUCTID, A.WAREINWAREHOUSE ), INV42 AS ( SELECT A.PRODUCTID, A.WAREID, SUM(A.QUANTITY) AS QTY42 FROM INVSTKBILL4_D A LEFT JOIN INVSTKBILL4_M B ON A.BILLNO = B.BILLNO WHERE B.BILLDATE <= @DATE2 GROUP BY A.PRODUCTID, A.WAREID ), INV5 AS ( SELECT A.PRODUCTID, A.WAREID, SUM(A.QUANTITY) AS QTY5 FROM INVSTKBILL5_D A LEFT JOIN INVSTKBILL5_M B ON A.BILLNO = B.BILLNO WHERE B.BILLDATE <= @DATE2 GROUP BY A.PRODUCTID, A.WAREID ), INV6 AS ( SELECT A.PRODUCTID, A.WAREID, SUM(A.QUANTITY) AS QTY6 FROM INVSTKBILL6_D A LEFT JOIN INVSTKBILL6_M B ON A.BILLNO = B.BILLNO WHERE B.BILLDATE <= @DATE2 GROUP BY A.PRODUCTID, A.WAREID ), INV71 AS ( SELECT A.M_PRODID, A.WAREID, SUM(A.STANDARDBATCHQTY) AS QTY71 FROM INVSTKBILL7_M A WHERE A.BILLDATE <= @DATE2 GROUP BY A.M_PRODID, A.WAREID ), INV72 AS ( SELECT A.PRODUCTID, A.WAREID, SUM(A.QUANTITY) AS QTY72 FROM INVSTKBILL7_D A LEFT JOIN INVSTKBILL7_M B ON A.BILLNO = B.BILLNO WHERE B.BILLDATE <= @DATE2 GROUP BY A.PRODUCTID, A.WAREID ), INV77 AS ( --擴充機制 SELECT A.PRODUCTID, A.WAREID, SUM(A.QUANTITY) AS QTY77 FROM INVEXTEND_INIT A WHERE A.LOGINID = @LOGINID AND FUNCTAG = @FUNCTAG GROUP BY A.PRODUCTID, A.WAREID ), FINAL99 AS ( SELECT A.PRODUCTID, A.WAREID, ISNULL(B.QTY1,0) AS QTY1, ISNULL(C.QTY2,0) AS QTY2, ISNULL(D.QTY3,0) AS QTY3, ISNULL(E.QTY41,0) AS QTY41, ISNULL(F.QTY42,0) AS QTY42, ISNULL(G.QTY5,0) AS QTY5, ISNULL(H.QTY6,0) AS QTY6, ISNULL(I.QTY71,0) AS QTY71, ISNULL(J.QTY72,0) AS QTY72, ISNULL(K.QTY77,0) AS QTY77 FROM #INVALL A LEFT JOIN INV1 B ON A.PRODUCTID = B.PRODUCTID AND A.WAREID = B.WAREID LEFT JOIN INV2 C ON A.PRODUCTID = C.PRODUCTID AND A.WAREID = C.WAREID LEFT JOIN INV3 D ON A.PRODUCTID = D.PRODUCTID AND A.WAREID = D.WAREID LEFT JOIN INV41 E ON A.PRODUCTID = E.PRODUCTID AND A.WAREID = E.WAREINWAREHOUSE LEFT JOIN INV42 F ON A.PRODUCTID = F.PRODUCTID AND A.WAREID = F.WAREID LEFT JOIN INV5 G ON A.PRODUCTID = G.PRODUCTID AND A.WAREID = G.WAREID LEFT JOIN INV6 H ON A.PRODUCTID = H.PRODUCTID AND A.WAREID = H.WAREID LEFT JOIN INV71 I ON A.PRODUCTID = I.M_PRODID AND A.WAREID = I.WAREID LEFT JOIN INV72 J ON A.PRODUCTID = J.PRODUCTID AND A.WAREID = J.WAREID LEFT JOIN INV77 K ON A.PRODUCTID = K.PRODUCTID AND A.WAREID = K.WAREID ), FINALOK AS ( SELECT PRODUCTID, WAREID, (QTY1-QTY2+QTY3+QTY41-QTY42-QTY5+QTY6+QTY71-QTY72+QTY77) AS NOWQTY FROM FINAL99 ) --用 WITH 就一定要在下一句 SQL 使用, 只好先寫到 TempDB SELECT * INTO #FINALOK FROM FINALOK IF @RESETTYPE = 1 OR @RESETTYPE = 4 BEGIN UPDATE FIVINVFINAL SET NOWQUANTITY = B.NOWQTY FROM #FINALOK B WHERE B.PRODUCTID = FIVINVFINAL.PRODUCTID AND B.WAREID= FIVINVFINAL.WAREID UPDATE FIVINVFINAL SET LOWPOINTSTOCK = (SELECT LOWPOINTSTOCK FROM FIV_LPS WHERE FIV_LPS.PRODUCTID = FIVINVFINAL.PRODUCTID AND FIV_LPS.WAREID = FIVINVFINAL.WAREID) DELETE FROM FIVINVFINAL WHERE NOWQUANTITY = 0 AND LOWPOINTSTOCK = 0 AND BORROWOUTQTY = 0 AND BORROWINQTY = 0 AND RETURNINQTY = 0 AND RETURNOUTQTY = 0 END ELSE IF @RESETTYPE = 2 OR @RESETTYPE = 3 BEGIN UPDATE FIVINVFINAL_HISTORY SET NOWQUANTITY = B.NOWQTY FROM #FINALOK B WHERE B.PRODUCTID = FIVINVFINAL_HISTORY.PRODUCTID AND B.WAREID= FIVINVFINAL_HISTORY.WAREID AND FIVINVFINAL_HISTORY.RESETDATE = @DATE2 DELETE FROM FIVINVFINAL_HISTORY WHERE NOWQUANTITY = 0 AND LOWPOINTSTOCK = 0 AND BORROWOUTQTY = 0 AND BORROWINQTY = 0 AND RETURNINQTY = 0 AND RETURNOUTQTY = 0 END --刪除暫存內容 DELETE FROM INVEXTEND_INIT WHERE LOGINID = @LOGINID AND FUNCTAG = @FUNCTAG --重置借還貨數量 IF @RESETTYPE = 1 OR @RESETTYPE = 4 BEGIN EXEC GEX_RESET_BORRQTY @PROD1,@PROD2 END --將 NULL 重設為 0 UPDATE FIVINVFINAL SET LOWPOINTSTOCK = 0 WHERE LOWPOINTSTOCK IS NULL UPDATE FIVINVFINAL SET BORROWOUTQTY = 0 WHERE BORROWOUTQTY IS NULL UPDATE FIVINVFINAL SET BORROWINQTY = 0 WHERE BORROWINQTY IS NULL UPDATE FIVINVFINAL SET RETURNINQTY = 0 WHERE RETURNINQTY IS NULL UPDATE FIVINVFINAL SET RETURNOUTQTY = 0 WHERE RETURNOUTQTY IS NULL DROP TABLE #INVALL DROP TABLE #FINALOK; --重啟 Trigger ENABLE TRIGGER DBO.TRI_INVSTKBILL1_CALCCOST ON dbo.INVSTKBILL1_D; ENABLE TRIGGER DBO.TRI_INVSTKBILL2_CALCCOST ON dbo.INVSTKBILL2_D; ENABLE TRIGGER DBO.TRI_INVSTKBILL3_CALCCOST ON dbo.INVSTKBILL3_D;