private I_M_Product getM_Product_ToUse() {
    if (_product != null) {
      return _product;
    }

    final IMRPContext mrpContext = getMRPContext();
    if (mrpContext != null) {
      return mrpContext.getM_Product();
    }
    return null;
  }
  private I_DD_OrderLine createDD_OrderLine(
      final IMRPContext mrpContext,
      final I_DD_Order order,
      final I_DD_NetworkDistributionLine networkLine,
      final I_M_Locator locatorFrom,
      final I_M_Locator locatorTo,
      final BigDecimal qtyToMove,
      final Timestamp supplyDateFinishSchedule,
      final IMRPCreateSupplyRequest request) {
    final I_M_Product product = mrpContext.getM_Product();
    final int bpartnerId = request.getMRPDemandBPartnerId();
    final int orderLineSOId = request.getMRPDemandOrderLineSOId();

    //
    // Create DD Order Line
    final I_DD_OrderLine ddOrderline =
        InterfaceWrapperHelper.newInstance(I_DD_OrderLine.class, order);
    ddOrderline.setAD_Org_ID(order.getAD_Org_ID());
    ddOrderline.setDD_Order(order);
    ddOrderline.setC_BPartner_ID(bpartnerId);
    ddOrderline.setC_OrderLineSO_ID(orderLineSOId);

    //
    // Locator From/To
    ddOrderline.setM_Locator(locatorFrom);
    ddOrderline.setM_LocatorTo(locatorTo);

    //
    // Product, UOM, Qty
    // NOTE: we assume qtyToMove is in "mrpContext.getC_UOM()" which shall be the Product's stocking
    // UOM
    ddOrderline.setM_Product(product);
    ddOrderline.setC_UOM(mrpContext.getC_UOM());
    ddOrderline.setQtyEntered(qtyToMove);
    ddOrderline.setQtyOrdered(qtyToMove);
    ddOrderline.setTargetQty(qtyToMove);

    //
    // Dates
    ddOrderline.setDateOrdered(order.getDateOrdered());
    ddOrderline.setDatePromised(order.getDatePromised());

    //
    // Other flags
    ddOrderline.setIsInvoiced(false);
    ddOrderline.setDD_AllowPush(networkLine.isDD_AllowPush());
    ddOrderline.setIsKeepTargetPlant(networkLine.isKeepTargetPlant());

    //
    // Save DD Order Line
    InterfaceWrapperHelper.save(ddOrderline);

    //
    // Create DD_OrderLine_Alternatives
    // NOTE: demand MRP line is available only in lot-for-lot order policy
    // TODO: i think we shall get all MRP demands, retrieve their alternatives, aggregate them and
    // create DD_OrderLine_Alternatives
    final I_PP_MRP parentMRPDemand = request.getMRPDemandRecordOrNull();
    if (parentMRPDemand != null) {
      final List<I_PP_MRP_Alternative> mrpAlternatives =
          mrpDAO.retrieveMRPAlternativesQuery(parentMRPDemand).create().list();
      for (final I_PP_MRP_Alternative mrpAlternative : mrpAlternatives) {
        createDD_OrderLine_Alternative(mrpContext, ddOrderline, mrpAlternative);
      }
    }

    //
    // Set Correct Planning Dates
    final int durationDays = calculateDurationDays(mrpContext, networkLine);
    final Timestamp supplyDateStartSchedule =
        TimeUtil.addDays(supplyDateFinishSchedule, 0 - durationDays);
    final List<I_PP_MRP> mrpList = mrpDAO.retrieveMRPRecords(ddOrderline);
    for (final I_PP_MRP mrp : mrpList) {
      mrp.setDateStartSchedule(supplyDateStartSchedule);
      mrp.setDateFinishSchedule(supplyDateFinishSchedule);
      InterfaceWrapperHelper.save(mrp);
    }

    return ddOrderline;
  }