金蝶K3 Wise—BOM批量多级展开

新手——刚开始研究BOM,不对之处还望各位博友不吝赐教

1、创建BOM父项表    ——FID,FItemID

create table HWbom
(
FId int identity(1,1),
FItemID int
)

2、创建BOM子项表    ——FID,FOrgID,FParentID,FLevel,FSN,FItemID,FQty,FBOMInterID,FEntryID

create table HWbomchild
(
	FID int identity(1,1),
	FOrgID int,
	FParentID int,
	FLevel int,
	FSN nvarchar(200),
	FItemID int,
	FQty decimal(28,19),
	FBOMInterID int,
	FEntryID int
)

3、将父项BOM对应的物料内码插入父项表(可带条件)

--t_ICItem——物料表
--t_item——基础资料主表
--icbom——BOM表
--ICBOMGROUP——BOM组别表

--物料表FErpClsID  物料属性(1-外购,2-自制,3-委外加工,5-虚拟件)
--基础资料主表	fdeleted   是否删除(0,未删除)  
--基础资料主表	FItemClassID	对应编码:
--1-客户
--2-部门
--3-职员
--4-商品
--5-仓位
--7-单位
--8-供应商
--基础资料主表	FDetail	是否明细(1,明细)

-- delete from HWbom                                                            

INSERT INTO HWbom ( FItemID ) SELECT
t.Fitemid 
FROM
	t_ICItem t --71615
	INNER JOIN t_item t5 ON t5.FItemID = t.Fitemid
	LEFT JOIN icbom t6 ON t6.fitemid= t.Fitemid
	LEFT JOIN ICBOMGROUP t7 ON t7.finterid= t6.fparentid 
WHERE
	t.FErpClsID IN ( 1, 2, 3, 5 ) --2代表自制件,3代表委外件,5代表虚拟件
	
	AND t5.FItemClassID= 4 
	AND t5.FDeleted= 0 
	AND t5.FDetail= 1 --类型是4(商品),未删除,明细是1 
	--and t5.fnumber in('物料编码1','物料编码2')	--可根据需要限定BOM范围
	
ORDER BY
	t.fnumber 

4、根据父项表数据,将数据插入子项表,为后续卷算做准备

	INSERT INTO HWbomchild ( FOrgID, FParentID, FSN, FItemID, FQty, FBOMInterID, FEntryID, FLevel ) SELECT
	FId,- 1 AS FParentID,
	'001',
	u1.FItemID,
	1 AS Fqty,
	t1.FInterID AS FBOMInterID,- 1 AS FEntryID,
	0 
FROM
	HWbom u1
	LEFT JOIN ICBOM t1 ON u1.FItemID= t1.FItemID 
	AND t1.FUseStatus= 1072 

5、BOM卷算

DECLARE
	@LEVEL INT 
	SET @LEVEL = 1

WHILE
		EXISTS ( 
            SELECT 1 FROM HWbomchild 
                WHERE FLevel = @LEVEL - 1 
                        AND FItemID 
                            IN ( SELECT Fitemid FROM icbom WHERE FUseStatus = 1072 ) 
                ) 
		AND @LEVEL < 20 

BEGIN
			INSERT INTO HWbomchild ( FOrgID, FParentID, FSN, FItemID, FQty, FBOMInterID, FEntryID, FLevel ) 
        SELECT
			u1.FOrgID,
			u1.FID,
			u1.FSN+ '.' + RIGHT ( '000' + CONVERT ( nvarchar ( 50 ), t2.Fentryid ), 3 ),
			t2.Fitemid,
			u1.FQty* ( t2.FQty/ t1.FQty ) / ( 1-t2.FScrap/ 100 ),
			t2.FInterID,
			t2.FEntryID,@LEVEL 
		FROM
			HWbomchild u1
			INNER JOIN icbom t1 ON u1.FItemID= t1.FItemID
			INNER JOIN ICBOMChild t2 ON t2.FInterID= t1.FInterID 
		WHERE
			u1.FLevel=@LEVEL - 1 
			AND t1.FUseStatus= 1072 
			
SET @LEVEL =@LEVEL + 1 

END 

6、最终BOM展开数据检索

SELECT
	t2.FModel 专机号,
	t4.FBOMNumber BOM编号,
	t2.FNumber 产品代码,
	t2.FName 产品名称,
	t1.FSN 序号,
	t3.FNumber 材料代码,
	t3.FName 材料名称,
	t3.FModel 材料规格,
	t1.FQty 产品用量,
	yy.fname 材料属性,
	t5.FQty 单位用量,
	t5.FScrap 损耗率,
	t6.FName AS 是否跳层,
	t5.FNote 备注,
	t5.FPositionNo 位置号 
		FROM
			HWbom u1
			INNER JOIN HWbomchild t1 ON u1.FId= t1.FOrgID
			INNER JOIN t_icitem t2 ON t2.FItemID= u1.FItemID
			INNER JOIN t_ICItem t3 ON t3.FItemID= t1.FItemID
			LEFT JOIN ICBOM t4 ON t4.FInterID= t1.FBOMInterID
			LEFT JOIN ICBOMChild t5 ON t5.FInterID= t1.FBOMInterID 
			AND t5.FEntryID= t1.FEntryID
			LEFT JOIN t_SubMessage t6 ON t6.FInterID= t4.FBOMSkip
			INNER JOIN t_SubMessage yy ON yy.FInterID= t3.FErpClsID
where t2.FModel='EYY33/04/S.515'
AND T4.FUseStatus = 1072 
and t4.FBomType <> 3 --FBomType;0-普通,1-配置类,2-生产规划类,3-客户BOM,4-特征类
-- and t4.fitemid=t2.fitemid
-- and t4.FBOMNumber = 'BOM019979'
        
order by u1.FId,t1.FSN

7、最后清空父项表和子项表数据

TRUNCATE TABLE HWbom --清空附表数据
TRUNCATE TABLE HWbomchild --清空子表数据

8、如果不再使用,可以将这两个表删除

DROP TABLE HWbom --删除父表
DROP TABLE HWbomchild --删除子表

9、依据BOM号或规格型号查询某bom所有层级物料价格——注意这只能查询出BOM字表单层级的

在以上1-8以需求选取基础上创建一个定时任务每天实时同步BOM,其中的参数如下,注释的为依据BOM查询,第一条为规格型号查询

AND t2.FModel='ATD60L/19.300.E01'
-- and t4.fitemid=t2.fitemid
-- and t4.FBOMNumber = 'BOM019979'

with bb as( 
(
select
t2.FModel 专机号,
t4.FBOMNumber BOM编号,
t2.FNumber 产品代码,
t2.FName 产品名称,
t1.FSN 序号,
t3.FNumber 材料代码,
t3.FName 材料名称,t3.FModel 材料规格
,t1.FQty 产品用量,yy.fname 材料属性,
t5.FQty 单位用量,
t5.FScrap 损耗率,
t6.FName as 是否跳层,
t5.FNote 备注,
t5.FPositionNo 位置号
 from HWbom u1
inner join HWbomchild t1 on u1.FId=t1.FOrgID
inner join t_icitem t2 on t2.FItemID=u1.FItemID
inner join t_ICItem t3 on t3.FItemID=t1.FItemID
left join ICBOM t4 on t4.FInterID=t1.FBOMInterID
left join ICBOMChild t5 on t5.FInterID=t1.FBOMInterID and t5.FEntryID=t1.FEntryID
left join t_SubMessage t6 on t6.FInterID=t4.FBOMSkip
inner join t_SubMessage yy on yy.FInterID=t3.FErpClsID
--left join pp on pp.FNumber=t3.FNumber
where T4.FUseStatus = 1072 and t4.FBomType <> 3 --FBomType;0-普通,1-配置类,2-生产规划类,3-客户BOM,4-特征类
AND t2.FModel='ATD60L/19.300.E01'
-- and t4.fitemid=t2.fitemid
-- and t4.FBOMNumber = 'BOM019979'
))
select bb.*,pp.FName,pp.FPrice from bb
left join (
select zz.*
from(
SELECT v1.FNumber AS FSupplyNumber,t1.FModel,v1.FName,
u1.FPrice,
t1.FNumber AS FItemNumber,
u1.FLastModifiedDate,
t1.FName AS FItemName, row_number ( ) OVER ( partition BY t1.FNumber,v1.FNumber ORDER BY u1.FLastModifiedDate DESC ) Suquence 
FROM t_SupplyEntry u1 INNER JOIN t_Supplier v1 ON u1.FSupID=v1.FItemID
     INNER JOIN t_Supply u2 ON u1.FSupID = u2.FSupID AND u1.FItemID=u2.FItemID AND u1.FPType=u2.FPType
     INNER JOIN t_ICItem t1 ON u2.FItemID = t1.FItemID
     INNER JOIN t_MeasureUnit t2 ON u1.FUnitID = t2.FItemID
     INNER JOIN t_Currency t3 ON u1.FCyID = t3.FCurrencyID
     INNER JOIN t_Currency u3 ON u3.FCurrencyID = u2.FCurrencyID
     LEFT JOIN ICSupOperation t7 on u1.FEntryID=t7.FID
     LEFT JOIN t_item t5 ON t1.FParentID=t5.FItemID
     LEFT JOIN t_User U ON u1.FLastModifiedBy = U.FUserID
     LEFT JOIN t_SubMessage t8 ON t7.FOpID=t8.FInterID
     LEFT JOIN t_User uu ON uu.FUserID <> 0 AND u1.FCheckerID = uu.FUserID
 WHERE v1.FStatus<>1074  and u1.FPType = '1'
 )zz
  where zz.Suquence=1
)pp on bb.材料代码=pp.FItemNumber

10、若要实现多级展开需要捋顺BOM的层级逻辑关系

BOM主表与子表之间可能只是存储了一层的关联关系;通过BOM主子表关联出来这一层后,这一层中所包含的物料很可能是个组件对应的是另一个BOM需要对它进行再次的展开

通过关联关系将子表中对应的物料id查询出,可再通过关联关系查询出对应物料的用料信息,价格信息

因为每个物料对应的BOM很可能是不一致的所以多级展开无法使用BOM进行查询,此处我使用的是规格型号,可自己再往上加条件

with bb as(
select distinct cc.FItemID from HWbomchild cc 
inner join t_ICItem t3 on t3.FItemID=cc.FItemID
where cc.FBOMInterID in(
select
 distinct t1.FBOMInterID
 from HWbom u1
inner join HWbomchild t1 on u1.FId=t1.FOrgID
inner join t_icitem t2 on t2.FItemID=u1.FItemID
inner join t_ICItem t3 on t3.FItemID=t1.FItemID
left join ICBOM t4 on t4.FInterID=t1.FBOMInterID
left join ICBOMChild t5 on t5.FInterID=t1.FBOMInterID and t5.FEntryID=t1.FEntryID  --添加与BOM分组表关联
left join t_SubMessage t6 on t6.FInterID=t4.FBOMSkip
inner join t_SubMessage yy on yy.FInterID=t3.FErpClsID
--left join pp on pp.FNumber=t3.FNumber
where T4.FUseStatus = 1072 and t4.FBomType <> 3 --FBomType;0-普通,1-配置类,2-生产规划类,3-客户BOM,4-特征类
AND t2.FModel='ADW77K')
)
select aa.FItemID,aa.FModel,aa.FName,aa.FNumber,aa.FDeleted,aa.FErpClsID,FUnitID,FUseState,aa.FFullName from bb left join t_ICItem aa on aa.FItemID = bb.FItemID
left join (
select zz.*
from(
SELECT v1.FNumber AS FSupplyNumber,t1.FModel,v1.FName,
u1.FPrice,
t1.FNumber AS FItemNumber,
u1.FLastModifiedDate,
t1.FName AS FItemName, row_number ( ) OVER ( partition BY t1.FNumber,v1.FNumber ORDER BY u1.FLastModifiedDate DESC ) Suquence 
FROM t_SupplyEntry u1 INNER JOIN t_Supplier v1 ON u1.FSupID=v1.FItemID
     INNER JOIN t_Supply u2 ON u1.FSupID = u2.FSupID AND u1.FItemID=u2.FItemID AND u1.FPType=u2.FPType
     INNER JOIN t_ICItem t1 ON u2.FItemID = t1.FItemID
     INNER JOIN t_MeasureUnit t2 ON u1.FUnitID = t2.FItemID
     INNER JOIN t_Currency t3 ON u1.FCyID = t3.FCurrencyID
     INNER JOIN t_Currency u3 ON u3.FCurrencyID = u2.FCurrencyID
     LEFT JOIN ICSupOperation t7 on u1.FEntryID=t7.FID
     LEFT JOIN t_item t5 ON t1.FParentID=t5.FItemID
     LEFT JOIN t_User U ON u1.FLastModifiedBy = U.FUserID
     LEFT JOIN t_SubMessage t8 ON t7.FOpID=t8.FInterID
     LEFT JOIN t_User uu ON uu.FUserID <> 0 AND u1.FCheckerID = uu.FUserID
 WHERE v1.FStatus<>1074  and u1.FPType = '1'
 )zz
  where zz.Suquence=1
)pp on aa.FNumber=pp.FItemNumber

 

  • 3
    点赞
  • 6
    收藏
    觉得还不错? 一键收藏
  • 打赏
    打赏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包

打赏作者

维C°

你的鼓励将是我创作的最大动力

¥1 ¥2 ¥4 ¥6 ¥10 ¥20
扫码支付:¥1
获取中
扫码支付

您的余额不足,请更换扫码支付或充值

打赏作者

实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值