📄 bomnode.java
字号:
/* * * Copyright 2001-2006 The Apache Software Foundation * * Licensed under the Apache License, Version 2.0 (the "License"); you may not * use this file except in compliance with the License. You may obtain a copy of * the License at * * http://www.apache.org/licenses/LICENSE-2.0 * * Unless required by applicable law or agreed to in writing, software * distributed under the License is distributed on an "AS IS" BASIS, WITHOUT * WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. See the * License for the specific language governing permissions and limitations * under the License. */package org.ofbiz.manufacturing.bom;import java.sql.Timestamp;import java.util.ArrayList;import java.util.Date;import java.util.HashMap;import java.util.Iterator;import java.util.List;import java.util.Map;import org.ofbiz.base.util.Debug;import org.ofbiz.base.util.UtilDateTime;import org.ofbiz.base.util.UtilMisc;import org.ofbiz.entity.GenericDelegator;import org.ofbiz.entity.GenericEntityException;import org.ofbiz.entity.GenericValue;import org.ofbiz.entity.util.EntityUtil;import org.ofbiz.service.GenericServiceException;import org.ofbiz.service.LocalDispatcher;/** An ItemCoinfigurationNode represents a component in a bill of materials. * @author <a href="mailto:tiz@sastau.it">Jacopo Cappellato</a> */public class BOMNode { public static final String module = BOMNode.class.getName(); protected LocalDispatcher dispatcher = null; protected GenericDelegator delegator = null; protected GenericValue userLogin = null; private BOMTree tree; // the tree to which this node belongs private BOMNode parentNode; // the parent node (null if it's not present) private BOMNode substitutedNode; // The virtual node (if any) that this instance substitutes private GenericValue ruleApplied; // The rule (if any) that that has been applied to configure the current node private String productForRules; private GenericValue product; // the current product (from Product entity) private GenericValue productAssoc; // the product assoc record (from ProductAssoc entity) in which the current product is in productIdTo private ArrayList children; // current node's children (ProductAssocs) private ArrayList childrenNodes; // current node's children nodes (BOMNode) private double quantityMultiplier; // the necessary quantity as declared in the bom (from ProductAssocs or ProductManufacturingRule) private double scrapFactor; // the scrap factor as declared in the bom (from ProductAssocs) // Runtime fields private int depth; // the depth of this node in the current tree private double quantity; // the quantity of this node in the current tree private String bomTypeId; // the type of the current tree public BOMNode(GenericValue product, LocalDispatcher dispatcher, GenericValue userLogin) { this.product = product; this.delegator = product.getDelegator(); this.dispatcher = dispatcher; this.userLogin = userLogin; children = new ArrayList(); childrenNodes = new ArrayList(); parentNode = null; productForRules = null; bomTypeId = null; quantityMultiplier = 1; scrapFactor = 1; // Now we initialize the fields used in breakdowns depth = 0; quantity = 0; } public BOMNode(String productId, GenericDelegator delegator, LocalDispatcher dispatcher, GenericValue userLogin) throws GenericEntityException { this(delegator.findByPrimaryKey("Product", UtilMisc.toMap("productId", productId)), dispatcher, userLogin); } protected void loadChildren(String partBomTypeId, Date inDate, List productFeatures, int type) throws GenericEntityException { if (product == null) { throw new GenericEntityException("product is null"); } // If the date is null, set it to today. if (inDate == null) inDate = new Date(); bomTypeId = partBomTypeId;// GenericDelegator delegator = product.getDelegator(); List rows = delegator.findByAnd("ProductAssoc", UtilMisc.toMap("productId", product.get("productId"), "productAssocTypeId", partBomTypeId), UtilMisc.toList("sequenceNum")); rows = EntityUtil.filterByDate(rows, inDate); if ((rows == null || rows.size() == 0) && substitutedNode != null) { // If no child is found and this is a substituted node // we try to search for substituted node's children. rows = delegator.findByAnd("ProductAssoc", UtilMisc.toMap("productId", substitutedNode.getProduct().get("productId"), "productAssocTypeId", partBomTypeId), UtilMisc.toList("sequenceNum")); rows = EntityUtil.filterByDate(rows, inDate); } children = new ArrayList(rows); childrenNodes = new ArrayList(); Iterator childrenIterator = children.iterator(); GenericValue oneChild = null; BOMNode oneChildNode = null; while(childrenIterator.hasNext()) { oneChild = (GenericValue)childrenIterator.next(); // Configurator oneChildNode = configurator(oneChild, productFeatures, getRootNode().getProductForRules(), inDate); // If the node is null this means that the node has been discarded by the rules. if (oneChildNode != null) { oneChildNode.setParentNode(this); switch (type) { case BOMTree.EXPLOSION: oneChildNode.loadChildren(partBomTypeId, inDate, productFeatures, BOMTree.EXPLOSION); break; case BOMTree.EXPLOSION_MANUFACTURING: if (!oneChildNode.isWarehouseManaged()) { oneChildNode.loadChildren(partBomTypeId, inDate, productFeatures, type); } break; } } childrenNodes.add(oneChildNode); } } private BOMNode substituteNode(BOMNode oneChildNode, List productFeatures, List productPartRules) throws GenericEntityException { if (productPartRules != null) { GenericValue rule = null; for (int i = 0; i < productPartRules.size(); i++) { rule = (GenericValue)productPartRules.get(i); String ruleCondition = (String)rule.get("productFeature"); String ruleOperator = (String)rule.get("ruleOperator"); String newPart = (String)rule.get("productIdInSubst"); double ruleQuantity = 0; try { ruleQuantity = rule.getDouble("quantity").doubleValue(); } catch(Exception exc) { ruleQuantity = 0; } GenericValue feature = null; boolean ruleSatisfied = false; if (ruleCondition == null || ruleCondition.equals("")) { ruleSatisfied = true; } else { if (productFeatures != null) { for (int j = 0; j < productFeatures.size(); j++) { feature = (GenericValue)productFeatures.get(j); if (ruleCondition.equals((String)feature.get("productFeatureId"))) { ruleSatisfied = true; break; } } } } if (ruleSatisfied && ruleOperator.equals("OR")) { BOMNode tmpNode = oneChildNode; if (newPart == null || newPart.equals("")) { oneChildNode = null; } else { BOMNode origNode = oneChildNode; oneChildNode = new BOMNode(newPart, delegator, dispatcher, userLogin); oneChildNode.setTree(tree); oneChildNode.setSubstitutedNode(tmpNode); oneChildNode.setRuleApplied(rule); oneChildNode.setProductAssoc(origNode.getProductAssoc()); oneChildNode.setScrapFactor(origNode.getScrapFactor()); if (ruleQuantity > 0) { oneChildNode.setQuantityMultiplier(ruleQuantity); } else { oneChildNode.setQuantityMultiplier(origNode.getQuantityMultiplier()); } } break; } // FIXME: AND operator still not implemented } // end of for } return oneChildNode; } private BOMNode configurator(GenericValue node, List productFeatures, String productIdForRules, Date inDate) throws GenericEntityException { BOMNode oneChildNode = new BOMNode((String)node.get("productIdTo"), delegator, dispatcher, userLogin); oneChildNode.setTree(tree); oneChildNode.setProductAssoc(node); try { oneChildNode.setQuantityMultiplier(node.getDouble("quantity").doubleValue()); } catch(Exception nfe) { oneChildNode.setQuantityMultiplier(1); } try { double percScrapFactor = node.getDouble("scrapFactor").doubleValue(); if (percScrapFactor >= 0 && percScrapFactor < 100) { percScrapFactor = 1 + percScrapFactor / 100; } else { percScrapFactor = 1; } oneChildNode.setScrapFactor(percScrapFactor); } catch(Exception nfe) { oneChildNode.setScrapFactor(1); } BOMNode newNode = oneChildNode; // CONFIGURATOR if (oneChildNode.isVirtual()) { // If the part is VIRTUAL and // productFeatures and productPartRules are not null // we have to substitute the part with the right part's variant List productPartRules = delegator.findByAnd("ProductManufacturingRule", UtilMisc.toMap("productId", productIdForRules, "productIdFor", node.get("productId"), "productIdIn", node.get("productIdTo"))); if (substitutedNode != null) { productPartRules.addAll(delegator.findByAnd("ProductManufacturingRule", UtilMisc.toMap("productId", productIdForRules, "productIdFor", substitutedNode.getProduct().getString("productId"), "productIdIn", node.get("productIdTo")))); } productPartRules = EntityUtil.filterByDate(productPartRules, inDate); newNode = substituteNode(oneChildNode, productFeatures, productPartRules); if (newNode == oneChildNode) { // If no substitution has been done (no valid rule applied), // we try to search for a generic link-rule List genericLinkRules = delegator.findByAnd("ProductManufacturingRule", UtilMisc.toMap("productIdFor", node.get("productId"), "productIdIn", node.get("productIdTo"))); if (substitutedNode != null) { genericLinkRules.addAll(delegator.findByAnd("ProductManufacturingRule", UtilMisc.toMap("productIdFor", substitutedNode.getProduct().getString("productId"), "productIdIn", node.get("productIdTo")))); } genericLinkRules = EntityUtil.filterByDate(genericLinkRules, inDate); newNode = null; newNode = substituteNode(oneChildNode, productFeatures, genericLinkRules); if (newNode == oneChildNode) { // If no substitution has been done (no valid rule applied), // we try to search for a generic node-rule List genericNodeRules = delegator.findByAnd("ProductManufacturingRule", UtilMisc.toMap("productIdIn", node.get("productIdTo")), UtilMisc.toList("ruleSeqId")); genericNodeRules = EntityUtil.filterByDate(genericNodeRules, inDate); newNode = null; newNode = substituteNode(oneChildNode, productFeatures, genericNodeRules); if (newNode == oneChildNode) { // If no substitution has been done (no valid rule applied), // we try to set the default (first) node-substitution if (genericNodeRules != null && genericNodeRules.size() > 0) { // FIXME //... }
⌨️ 快捷键说明
复制代码
Ctrl + C
搜索代码
Ctrl + F
全屏模式
F11
切换主题
Ctrl + Shift + D
显示快捷键
?
增大字号
Ctrl + =
减小字号
Ctrl + -