/****************************************************************************** * Product: Adempiere ERP & CRM Smart Business Solution * * Copyright (C) 1999-2006 ComPiere, Inc. All Rights Reserved. * * This program is free software; you can redistribute it and/or modify it * * under the terms version 2 of the GNU General Public License as published * * by the Free Software Foundation. This program is distributed in the hope * * that it will be useful, but WITHOUT ANY WARRANTY; without even the implied * * warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. * * See the GNU General Public License for more details. * * You should have received a copy of the GNU General Public License along * * with this program; if not, write to the Free Software Foundation, Inc., * * 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA. * * For the text or an alternative of this public license, you may reach us * * ComPiere, Inc., 2620 Augustine Dr. #245, Santa Clara, CA 95054, USA * * or via info@compiere.org or http://www.compiere.org/license.html * *****************************************************************************/ package org.compiere.acct; import java.math.BigDecimal; import java.sql.ResultSet; import java.util.ArrayList; import java.util.logging.Level; import org.compiere.model.MAccount; import org.compiere.model.MAcctSchema; import org.compiere.model.MBankAccount; import org.compiere.model.MBankStatement; import org.compiere.model.MBankStatementLine; import org.compiere.model.MDepositBatchLine; import org.compiere.model.MPayment; import org.compiere.util.Env; /** * Post {@link MBankStatement} Documents. *
 *  Table:              C_BankStatement (392)
 *  Document Types:     CMB
 *  
* @author Jorg Janke * @version $Id: Doc_Bank.java,v 1.3 2006/07/30 00:53:33 jjanke Exp $ *

* FR [ 1840016 ] Avoid usage of clearing accounts - subject to C_AcctSchema.IsPostIfClearingEqual.
* Avoid posting if both accounts BankAsset and BankInTransit are equal. * @author victor.perez@e-evolution.com, e-Evolution http://www.e-evolution.com *

  • FR [ 2520591 ] Support multiples calendar for Org * @see https://sourceforge.net/p/adempiere/feature-requests/631/ * */ public class Doc_BankStatement extends Doc { /** * Constructor * @param as accounting schema * @param rs record * @param trxName trx */ public Doc_BankStatement (MAcctSchema as, ResultSet rs, String trxName) { super (as, MBankStatement.class, rs, null, trxName); } // Doc_Bank /** Bank Account */ protected int m_C_BankAccount_ID = 0; /** * Load Specific Document Details * @return error message or null */ @Override protected String loadDocumentDetails () { MBankStatement bs = (MBankStatement)getPO(); setDateDoc(bs.getStatementDate()); setDateAcct(bs.getDateAcct()); m_C_BankAccount_ID = bs.getC_BankAccount_ID(); // Amounts setAmount(AMTTYPE_Gross, bs.getStatementDifference()); // Set Bank Account Info (Currency) MBankAccount ba = MBankAccount.get (getCtx(), m_C_BankAccount_ID); setC_Currency_ID (ba.getC_Currency_ID()); // Contained Objects p_lines = loadLines(bs); if (log.isLoggable(Level.FINE)) log.fine("Lines=" + p_lines.length); return null; } // loadDocumentDetails /** * Load bank statement lines. * @param bs bank statement *
    	 *  4 amounts
    	 *  AMTTYPE_Payment
    	 *  AMTTYPE_Statement2
    	 *  AMTTYPE_Charge
    	 *  AMTTYPE_Interest
    	 *  
    * @return DocLine Array */ protected DocLine[] loadLines(MBankStatement bs) { ArrayList list = new ArrayList(); MBankStatementLine[] lines = bs.getLines(false); for (int i = 0; i < lines.length; i++) { MBankStatementLine line = lines[i]; if(line.isActive()) { DocLine_Bank docLine = new DocLine_Bank(line, this); list.add(docLine); } } // Return Array DocLine[] dls = new DocLine[list.size()]; list.toArray(dls); return dls; } // loadLines /** * Get Source Currency Balance - subtracts line amounts from total - no rounding * @return positive amount, if total invoice is bigger than lines */ @Override public BigDecimal getBalance() { BigDecimal retValue = Env.ZERO; StringBuilder sb = new StringBuilder (" ["); // Total retValue = retValue.add(getAmount(Doc.AMTTYPE_Gross)); sb.append(getAmount(Doc.AMTTYPE_Gross)); // - Lines for (int i = 0; i < p_lines.length; i++) { BigDecimal lineBalance = ((DocLine_Bank)p_lines[i]).getStmtAmt(); retValue = retValue.subtract(lineBalance); sb.append("-").append(lineBalance); } sb.append("]"); // if (log.isLoggable(Level.FINE)) log.fine(toString() + " Balance=" + retValue + sb.toString()); return retValue; } // getBalance /** * Create Facts (the accounting logic) for * CMB. *
    	 *      BankAsset       DR      CR  (Statement)
    	 *      BankInTransit   DR      CR  (Payment)
    	 *      Charge          DR          (Charge)
    	 *      Interest        DR      CR  (Interest)
    	 *  
    * @param as accounting schema * @return Fact */ @Override public ArrayList createFacts (MAcctSchema as) { // create Fact Header Fact fact = new Fact(this, as, Fact.POST_Actual); // boolean isInterOrg = isInterOrg(as); // Header -- there may be different currency amounts FactLine fl = null; int AD_Org_ID = getBank_Org_ID(); // Bank Account Org // Lines for (int i = 0; i < p_lines.length; i++) { DocLine_Bank line = (DocLine_Bank)p_lines[i]; int C_BPartner_ID = line.getC_BPartner_ID(); // Avoid usage of clearing accounts // If both accounts BankAsset and BankInTransit are equal // then remove the posting MAccount acct_bank_asset = getAccount(Doc.ACCTTYPE_BankAsset, as); MAccount acct_bank_in_transit = getAccount(Doc.ACCTTYPE_BankInTransit, as); // don't validate interorg on banks for this - normally banks are balanced by orgs if ((!as.isPostIfClearingEqual()) && acct_bank_asset.equals(acct_bank_in_transit)) { // Not using clearing accounts // just post the difference (if any) BigDecimal amt_stmt_minus_trx = line.getStmtAmt().subtract(line.getTrxAmt()); if (amt_stmt_minus_trx.compareTo(Env.ZERO) != 0) { // BankAsset DR CR (Statement minus Payment) fl = fact.createLine(line, acct_bank_asset, line.getC_Currency_ID(), amt_stmt_minus_trx); if (fl != null && AD_Org_ID != 0) fl.setAD_Org_ID(AD_Org_ID); if (fl != null && C_BPartner_ID != 0) fl.setC_BPartner_ID(C_BPartner_ID); } } else { // Normal Adempiere behavior -- unchanged if using clearing accounts // BankAsset DR CR (Statement) fl = fact.createLine(line, acct_bank_asset, line.getC_Currency_ID(), line.getStmtAmt()); if (fl != null && AD_Org_ID != 0) fl.setAD_Org_ID(AD_Org_ID); if (fl != null && C_BPartner_ID != 0) fl.setC_BPartner_ID(C_BPartner_ID); // BankInTransit DR CR (Payment) MBankStatementLine statementLine = (MBankStatementLine) line.getPO(); if (statementLine.getC_DepositBatch_ID() != 0) { // All Deposit Line MDepositBatchLine[] depositBatchLines = statementLine.getC_DepositBatch().getLines(); for (MDepositBatchLine depositLine : depositBatchLines) { MPayment payment = depositLine.getC_Payment(); DocLine_DepositBatch docDepositLine = new DocLine_DepositBatch(payment, this, statementLine.isReversal()); fl = fact.createLine(docDepositLine, getAccount(Doc.ACCTTYPE_BankInTransit, as), payment.getC_Currency_ID(), payment.isReceipt() ? payment.getPayAmt().negate() : payment.getPayAmt()); // line id fl.setLine_ID(statementLine.get_ID()); if (fl != null) { if (C_BPartner_ID != 0) fl.setC_BPartner_ID(C_BPartner_ID); if (AD_Org_ID != 0) fl.setAD_Org_ID(AD_Org_ID); else fl.setAD_Org_ID(docDepositLine.getAD_Org_ID(true)); // from payment } } } else { fl = fact.createLine(line, getAccount(Doc.ACCTTYPE_BankInTransit, as), line.getC_Currency_ID(), line.getTrxAmt().negate()); if (fl != null) { if (C_BPartner_ID != 0) fl.setC_BPartner_ID(C_BPartner_ID); if (AD_Org_ID != 0) fl.setAD_Org_ID(AD_Org_ID); else fl.setAD_Org_ID(line.getAD_Org_ID(true)); // from payment } } } // End Avoid usage of clearing accounts // Charge DR (Charge) if (line.getChargeAmt().compareTo(Env.ZERO) > 0) { fl = fact.createLine(line, line.getChargeAccount(as, line.getChargeAmt().negate()), line.getC_Currency_ID(), null, line.getChargeAmt()); } else { fl = fact.createLine(line, line.getChargeAccount(as, line.getChargeAmt().negate()), line.getC_Currency_ID(), line.getChargeAmt().negate(), null); } if (fl != null && C_BPartner_ID != 0) fl.setC_BPartner_ID(C_BPartner_ID); // Interest DR CR (Interest) if (line.getInterestAmt().signum() < 0) fl = fact.createLine(line, getAccount(Doc.ACCTTYPE_InterestExp, as), getAccount(Doc.ACCTTYPE_InterestExp, as), line.getC_Currency_ID(), line.getInterestAmt().negate()); else fl = fact.createLine(line, getAccount(Doc.ACCTTYPE_InterestRev, as), getAccount(Doc.ACCTTYPE_InterestRev, as), line.getC_Currency_ID(), line.getInterestAmt().negate()); if (fl != null && C_BPartner_ID != 0) fl.setC_BPartner_ID(C_BPartner_ID); } // ArrayList facts = new ArrayList(); facts.add(fact); return facts; } // createFact /** * Get AD_Org_ID from Bank Account * @return AD_Org_ID or 0 */ protected int getBank_Org_ID () { if (m_C_BankAccount_ID == 0) return 0; // MBankAccount ba = MBankAccount.get(getCtx(), m_C_BankAccount_ID); return ba.getAD_Org_ID(); } // getBank_Org_ID } // Doc_Bank