Author: jacopoc
Date: Tue Oct 9 08:47:23 2007 New Revision: 583200 URL: http://svn.apache.org/viewvc?rev=583200&view=rev Log: Implemented service that computes the actual/real production run routing task's costs. Modified: ofbiz/trunk/applications/manufacturing/servicedef/services_production_run.xml ofbiz/trunk/applications/manufacturing/src/org/ofbiz/manufacturing/jobshopmgt/ProductionRunServices.java Modified: ofbiz/trunk/applications/manufacturing/servicedef/services_production_run.xml URL: http://svn.apache.org/viewvc/ofbiz/trunk/applications/manufacturing/servicedef/services_production_run.xml?rev=583200&r1=583199&r2=583200&view=diff ============================================================================== --- ofbiz/trunk/applications/manufacturing/servicedef/services_production_run.xml (original) +++ ofbiz/trunk/applications/manufacturing/servicedef/services_production_run.xml Tue Oct 9 08:47:23 2007 @@ -329,4 +329,9 @@ <attribute mode="IN" name="workEffortId" optional="false" type="String"/> <attribute mode="OUT" name="totalCost" optional="false" type="BigDecimal"/> </service> + <service name="createProductionRunTaskCosts" engine="java" + location="org.ofbiz.manufacturing.jobshopmgt.ProductionRunServices" invoke="createProductionRunTaskCosts" auth="true"> + <description>Compute the actual costs for the production run task.</description> + <attribute mode="IN" name="productionRunTaskId" optional="false" type="String"/> + </service> </services> Modified: ofbiz/trunk/applications/manufacturing/src/org/ofbiz/manufacturing/jobshopmgt/ProductionRunServices.java URL: http://svn.apache.org/viewvc/ofbiz/trunk/applications/manufacturing/src/org/ofbiz/manufacturing/jobshopmgt/ProductionRunServices.java?rev=583200&r1=583199&r2=583200&view=diff ============================================================================== --- ofbiz/trunk/applications/manufacturing/src/org/ofbiz/manufacturing/jobshopmgt/ProductionRunServices.java (original) +++ ofbiz/trunk/applications/manufacturing/src/org/ofbiz/manufacturing/jobshopmgt/ProductionRunServices.java Tue Oct 9 08:47:23 2007 @@ -857,6 +857,18 @@ return ServiceUtil.returnError(UtilProperties.getMessage(resource, "ManufacturingProductionRunStatusNotChanged", locale)); } } + // Calculate and store the production run task actual costs + serviceContext.clear(); + serviceContext.put("productionRunTaskId", taskId); + serviceContext.put("userLogin", userLogin); + resultService = null; + try { + resultService = dispatcher.runSync("createProductionRunTaskCosts", serviceContext); + } catch (GenericServiceException e) { + Debug.logError(e, "Problem calling the createProductionRunTaskCosts service", module); + return ServiceUtil.returnError(UtilProperties.getMessage(resource, "ManufacturingProductionRunStatusNotChanged", locale)); + } + result.put("oldStatusId", oldStatusId); result.put("newStatusId", "PRUN_COMPLETED"); result.put(ModelService.SUCCESS_MESSAGE, UtilProperties.getMessage(resource, "ManufacturingProductionRunStatusChanged",UtilMisc.toMap("newStatusId", "PRUN_DOC_PRINTED"), locale)); @@ -925,6 +937,118 @@ return result; } + public static Map createProductionRunTaskCosts(DispatchContext ctx, Map context) { + GenericDelegator delegator = ctx.getDelegator(); + LocalDispatcher dispatcher = ctx.getDispatcher(); + GenericValue userLogin = (GenericValue) context.get("userLogin"); + + // this is the id of the actual (real) production run task + String productionRunTaskId = (String)context.get("productionRunTaskId"); + try { + GenericValue workEffort = delegator.findByPrimaryKey("WorkEffort", UtilMisc.toMap("workEffortId", productionRunTaskId)); + if (UtilValidate.isEmpty(workEffort)) { + return ServiceUtil.returnError("Cannot find the production run task with id [" + productionRunTaskId + "]"); + } + double actualTotalMilliSeconds = 0.0; + Double actualSetupMillis = workEffort.getDouble("actualSetupMillis"); + Double actualMilliSeconds = workEffort.getDouble("actualMilliSeconds"); + if (actualSetupMillis != null) { + actualTotalMilliSeconds += actualSetupMillis.doubleValue(); + } + if (actualMilliSeconds != null) { + actualTotalMilliSeconds += actualMilliSeconds.doubleValue(); + } + // Get the template (aka routing task) of the work effort + List routingTasks = EntityUtil.filterByDate(delegator.findByAnd("WorkEffortAssoc", + UtilMisc.toMap("workEffortIdTo", productionRunTaskId, + "workEffortAssocTypeId", "WORK_EFF_TEMPLATE"))); + GenericValue routingTask = EntityUtil.getFirst(routingTasks); + List workEffortCostCalcs = null; + if (UtilValidate.isEmpty(routingTask)) { + // there is no template, try to get the cost entries for the actual production run task, if any + workEffortCostCalcs = delegator.findByAnd("WorkEffortCostCalc", UtilMisc.toMap("workEffortId", productionRunTaskId)); + } else { + workEffortCostCalcs = delegator.findByAnd("WorkEffortCostCalc", UtilMisc.toMap("workEffortId", routingTask.getString("workEffortIdFrom"))); + } + // Get all the valid CostComponentCalc entries + workEffortCostCalcs = EntityUtil.filterByDate(workEffortCostCalcs); + Iterator workEffortCostCalcsIt = workEffortCostCalcs.iterator(); + while (workEffortCostCalcsIt.hasNext()) { + GenericValue workEffortCostCalc = (GenericValue)workEffortCostCalcsIt.next(); + GenericValue costComponentCalc = workEffortCostCalc.getRelatedOne("CostComponentCalc"); + GenericValue customMethod = costComponentCalc.getRelatedOne("CustomMethod"); + if (UtilValidate.isEmpty(customMethod) || UtilValidate.isEmpty(customMethod.getString("customMethodName"))) { + // compute the total time + double totalTime = actualTotalMilliSeconds; + if (costComponentCalc.get("perMilliSecond") != null) { + long perMilliSecond = costComponentCalc.getLong("perMilliSecond").longValue(); + if (perMilliSecond != 0) { + totalTime = totalTime / perMilliSecond; + } + } + // compute the cost + BigDecimal fixedCost = costComponentCalc.getBigDecimal("fixedCost"); + BigDecimal variableCost = costComponentCalc.getBigDecimal("variableCost"); + if (fixedCost == null) { + fixedCost = BigDecimal.ZERO; + } + if (variableCost == null) { + variableCost = BigDecimal.ZERO; + } + BigDecimal totalCost = fixedCost.add(variableCost.multiply(BigDecimal.valueOf(totalTime))).setScale(decimals, rounding); + // store the cost + Map inMap = UtilMisc.toMap("userLogin", userLogin, "workEffortId", productionRunTaskId); + inMap.put("costComponentTypeId", "ACTUAL_" + workEffortCostCalc.getString("costComponentTypeId")); + inMap.put("costComponentCalcId", costComponentCalc.getString("costComponentCalcId")); + inMap.put("costUomId", costComponentCalc.getString("currencyUomId")); + inMap.put("cost", new Double(totalCost.doubleValue())); + dispatcher.runSync("createCostComponent", inMap); + } else { + // use the custom method (aka formula) to compute the costs + Map inMap = UtilMisc.toMap("userLogin", userLogin, "workEffort", workEffort); + inMap.put("workEffortCostCalc", workEffortCostCalc); + inMap.put("costComponentCalc", costComponentCalc); + dispatcher.runSync(customMethod.getString("customMethodName"), inMap); + } + } + } catch(Exception e) { + return ServiceUtil.returnError("Unable to create routing costs for the production run task [" + productionRunTaskId + "]: " + e.getMessage()); + } + // materials costs: these are the costs derived from the materials used by the production run task + try { + Iterator inventoryAssignIt = delegator.findByAnd("WorkEffortAndInventoryAssign", UtilMisc.toMap("workEffortId", productionRunTaskId)).iterator(); + Map materialsCostByCurrency = FastMap.newInstance(); + while (inventoryAssignIt.hasNext()) { + GenericValue inventoryConsumed = (GenericValue)inventoryAssignIt.next(); + BigDecimal quantity = inventoryConsumed.getBigDecimal("quantity"); + BigDecimal unitCost = inventoryConsumed.getBigDecimal("unitCost"); + if (UtilValidate.isEmpty(unitCost) || UtilValidate.isEmpty(quantity)) { + continue; + } + String currencyUomId = inventoryConsumed.getString("currencyUomId"); + if (!materialsCostByCurrency.containsKey(currencyUomId)) { + materialsCostByCurrency.put(currencyUomId, BigDecimal.ZERO); + } + BigDecimal materialsCost = (BigDecimal)materialsCostByCurrency.get(currencyUomId); + materialsCost = materialsCost.add(unitCost.multiply(quantity)).setScale(decimals, rounding); + materialsCostByCurrency.put(currencyUomId, materialsCost); + } + Iterator currencyIt = materialsCostByCurrency.keySet().iterator(); + while (currencyIt.hasNext()) { + String currencyUomId = (String)currencyIt.next(); + BigDecimal materialsCost = (BigDecimal)materialsCostByCurrency.get(currencyUomId); + Map inMap = UtilMisc.toMap("userLogin", userLogin, "workEffortId", productionRunTaskId); + inMap.put("costComponentTypeId", "ACTUAL_MAT_COST"); + inMap.put("costUomId", currencyUomId); + inMap.put("cost", new Double(materialsCost.doubleValue())); + dispatcher.runSync("createCostComponent", inMap); + } + } catch(Exception e) { + return ServiceUtil.returnError("Unable to create materials costs for the production run task [" + productionRunTaskId + "]: " + e.getMessage()); + } + return ServiceUtil.returnSuccess(); + } + /** * check if field for routingTask update are correct and if need recalculated data in Production Run. * Check<ul> @@ -1397,7 +1521,7 @@ Map outputMap = dispatcher.runSync("getProductionRunCost", UtilMisc.toMap("userLogin", userLogin, "workEffortId", productionRunId)); BigDecimal totalCost = (BigDecimal)outputMap.get("totalCost"); // FIXME - unitCost = totalCost.divide(new BigDecimal(quantity.doubleValue()), decimals, rounding); + unitCost = totalCost.divide(BigDecimal.valueOf(quantity.doubleValue()), decimals, rounding); } catch (GenericServiceException e) { Debug.logWarning(e.getMessage(), module); return ServiceUtil.returnError(e.getMessage()); |
Free forum by Nabble | Edit this page |