You are viewing a plain text version of this content. The canonical link for it is here.
Posted to commits@ofbiz.apache.org by ja...@apache.org on 2007/03/27 06:47:02 UTC
svn commit: r522749 -
/ofbiz/trunk/applications/accounting/src/org/ofbiz/accounting/finaccount/FinAccountPaymentServices.java
Author: jaz
Date: Mon Mar 26 21:47:01 2007
New Revision: 522749
URL: http://svn.apache.org/viewvc?view=rev&rev=522749
Log:
partially working payment services for financial accounts; implements payment processor interfaces and generic deposit/withdraw services
Added:
ofbiz/trunk/applications/accounting/src/org/ofbiz/accounting/finaccount/FinAccountPaymentServices.java (with props)
Added: ofbiz/trunk/applications/accounting/src/org/ofbiz/accounting/finaccount/FinAccountPaymentServices.java
URL: http://svn.apache.org/viewvc/ofbiz/trunk/applications/accounting/src/org/ofbiz/accounting/finaccount/FinAccountPaymentServices.java?view=auto&rev=522749
==============================================================================
--- ofbiz/trunk/applications/accounting/src/org/ofbiz/accounting/finaccount/FinAccountPaymentServices.java (added)
+++ ofbiz/trunk/applications/accounting/src/org/ofbiz/accounting/finaccount/FinAccountPaymentServices.java Mon Mar 26 21:47:01 2007
@@ -0,0 +1,787 @@
+/*
+ Licensed to the Apache Software Foundation (ASF) under one
+ or more contributor license agreements. See the NOTICE file
+ distributed with this work for additional information
+ regarding copyright ownership. The ASF licenses this file
+ to you 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.accounting.finaccount;
+
+import org.ofbiz.service.DispatchContext;
+import org.ofbiz.service.LocalDispatcher;
+import org.ofbiz.service.ServiceUtil;
+import org.ofbiz.service.GenericServiceException;
+import org.ofbiz.entity.GenericDelegator;
+import org.ofbiz.entity.GenericValue;
+import org.ofbiz.entity.GenericEntityException;
+import org.ofbiz.entity.util.EntityUtil;
+import org.ofbiz.base.util.*;
+import org.ofbiz.order.order.OrderReadHelper;
+import org.ofbiz.order.finaccount.FinAccountHelper;
+import org.ofbiz.accounting.payment.PaymentGatewayServices;
+import org.ofbiz.product.store.ProductStoreWorker;
+
+import java.util.Map;
+import java.util.List;
+import java.math.BigDecimal;
+import java.sql.Timestamp;
+
+import javolution.util.FastMap;
+
+/**
+ * FinAccountPaymentServices - Financial account used as payment method
+ */
+public class FinAccountPaymentServices {
+
+ public static final String module = FinAccountPaymentServices.class.getName();
+
+ // base payment intergration services
+ public static Map finAccountPreAuth(DispatchContext dctx, Map context) {
+ LocalDispatcher dispatcher = dctx.getDispatcher();
+ GenericDelegator delegator = dctx.getDelegator();
+ GenericValue userLogin = (GenericValue) context.get("userLogin");
+
+ GenericValue paymentPref = (GenericValue) context.get("orderPaymentPreference");
+ String finAccountCode = (String) context.get("finAccountCode");
+ String finAccountPin = (String) context.get("finAccountPin");
+ String finAccountId = (String) context.get("finAccountId");
+
+ String currency = (String) context.get("currency");
+ String orderId = (String) context.get("orderId");
+ Double amount = (Double) context.get("processAmount");
+
+ // make sure we have a currency
+ if (currency == null) {
+ currency = UtilProperties.getPropertyValue("general.properties", "currency.uom.id.default", "USD");
+ }
+
+ // check for an existing auth trans and cancel it
+ GenericValue authTrans = PaymentGatewayServices.getAuthTransaction(paymentPref);
+ if (authTrans != null) {
+ Map input = UtilMisc.toMap("userLogin", userLogin, "finAccountAuthId", authTrans.get("referenceNum"));
+ try {
+ dispatcher.runSync("expireFinAccountAuth", input);
+ } catch (GenericServiceException e) {
+ Debug.logError(e, module);
+ return ServiceUtil.returnError(e.getMessage());
+ }
+ }
+
+ // obtain the order information
+ OrderReadHelper orh = new OrderReadHelper(delegator, orderId);
+ String productStoreId = orh.getProductStoreId();
+
+ // get the financial account
+ GenericValue finAccount;
+ if (finAccountId != null) {
+ try {
+ finAccount = delegator.findByPrimaryKey("FinAccount", UtilMisc.toMap("finAccountId", finAccountId));
+ } catch (GenericEntityException e) {
+ Debug.logError(e, module);
+ return ServiceUtil.returnError(e.getMessage());
+ }
+ } else {
+ if (finAccountCode != null) {
+ try {
+ finAccount = FinAccountHelper.getFinAccountFromCode(finAccountCode, delegator);
+ } catch (GenericEntityException e) {
+ Debug.logError(e, module);
+ return ServiceUtil.returnError("Unable to locate financial account from account code");
+ }
+ } else {
+ return ServiceUtil.returnError("Both finAccountId and finAccountCode cannot be null; at least one is required");
+ }
+ }
+ if (finAccount == null) {
+ return ServiceUtil.returnError("Invalid financial account; cannot locate account");
+ }
+
+ String finAccountTypeId = finAccount.getString("finAccountTypeId");
+ finAccountId = finAccount.getString("finAccountId");
+
+ try {
+ // fin the store requires a pin number; validate the PIN with the code
+ GenericValue finAccountSettings = delegator.findByPrimaryKeyCache("ProductStoreFinActSetting",
+ UtilMisc.toMap("productStoreId", productStoreId, "finAccountTypeId", finAccountTypeId));
+ String allowAuthToNegative = "N";
+
+ if (finAccountSettings != null) {
+ allowAuthToNegative = finAccountSettings.getString("allowAuthToNegative");
+
+ // validate the PIN if the store requires it
+ if ("Y".equals(finAccountSettings.getString("requirePinCode"))) {
+ if (!FinAccountHelper.validatePin(delegator, finAccountCode, finAccountPin)) {
+ return ServiceUtil.returnError("Financial account PIN/CODE combination not found");
+ }
+ }
+ }
+
+ // check for account being frozen
+ String isFrozen = finAccount.getString("isFrozen");
+ if (isFrozen != null && "Y".equals(isFrozen)) {
+ return ServiceUtil.returnError("Financial account is currently frozen");
+ }
+
+ // check for expiration date
+ if ((finAccount.getTimestamp("thruDate") != null) && (finAccount.getTimestamp("thruDate").before(UtilDateTime.nowTimestamp()))) {
+ return ServiceUtil.returnError("Financial account has expired as of " + finAccount.getTimestamp("thruDate"));
+ }
+
+ // check the amount to authorize against the available balance of fin account, which includes active authorizations as well as transactions
+ BigDecimal availableBalance = FinAccountHelper.getAvailableBalance(finAccountId, currency, delegator);
+ Map result = ServiceUtil.returnSuccess();
+ Boolean processResult;
+ String refNum;
+
+ // turn amount into a big decimal, making sure to round and scale it to the same as availableBalance
+ BigDecimal amountBd = (new BigDecimal(amount.doubleValue())).setScale(FinAccountHelper.decimals, FinAccountHelper.rounding);
+
+ Debug.log("Allow auth to negative: " + allowAuthToNegative + " :: available: " + availableBalance + " comp: " + FinAccountHelper.ZERO + " = " + availableBalance.compareTo(FinAccountHelper.ZERO) + " :: req: " + amountBd, module);
+ // check the available balance to see if we can auth this tx
+ if (("Y".equals(allowAuthToNegative) && availableBalance.compareTo(FinAccountHelper.ZERO) > -1)
+ || (availableBalance.compareTo(amountBd) > -1)) {
+ Timestamp thruDate;
+
+ if (finAccountSettings != null && finAccountSettings.getLong("authValidDays") != null) {
+ thruDate = UtilDateTime.getDayEnd(UtilDateTime.nowTimestamp(), finAccountSettings.getLong("authValidDays").intValue());
+ } else {
+ thruDate = UtilDateTime.getDayEnd(UtilDateTime.nowTimestamp(), 30); // default 30 days for an auth
+ }
+
+ Map tmpResult = dispatcher.runSync("createFinAccountAuth", UtilMisc.toMap("finAccountId", finAccountId,
+ "amount", amount, "currencyUomId", currency, "thruDate", thruDate, "userLogin", userLogin));
+
+ if (ServiceUtil.isError(tmpResult)) {
+ return tmpResult;
+ } else {
+ refNum = (String) tmpResult.get("finAccountAuthId");
+ processResult = Boolean.TRUE;
+ }
+
+ // mark the account as frozen if we have gone negative
+ BigDecimal newBalance = FinAccountHelper.getAvailableBalance(finAccountId, currency, delegator);
+ if (newBalance.compareTo(FinAccountHelper.ZERO) == -1) {
+ finAccount.set("isFrozen", "Y");
+ try {
+ finAccount.store();
+ } catch (GenericEntityException e) {
+ Debug.logError(e, module);
+ return ServiceUtil.returnError(e.getMessage());
+ }
+ }
+
+ } else {
+ Debug.logError("Attempted to authorize [" + amount + "] against a balance of only [" + availableBalance + "]", module);
+ refNum = "0"; // a refNum is always required from authorization
+ processResult = Boolean.FALSE;
+ }
+
+ result.put("processAmount", amount);
+ result.put("authResult", processResult);
+ result.put("processAmount", amount);
+ result.put("authFlag", "1");
+ result.put("authCode", "A");
+ result.put("authRefNum", refNum);
+
+ return result;
+ } catch (GenericEntityException ex) {
+ Debug.logError(ex, "Cannot authorize financial account", module);
+ return ServiceUtil.returnError("Cannot authorize financial account due to " + ex.getMessage());
+ } catch (GenericServiceException ex) {
+ Debug.logError(ex, "Cannot authorize gift certificate", module);
+ return ServiceUtil.returnError("Cannot authorize financial account due to " + ex.getMessage());
+ }
+ }
+
+ public static Map finAccountReleaseAuth(DispatchContext dctx, Map context) {
+ LocalDispatcher dispatcher = dctx.getDispatcher();
+ GenericValue userLogin = (GenericValue) context.get("userLogin");
+
+ GenericValue paymentPref = (GenericValue) context.get("orderPaymentPreference");
+
+ String err = "Unable to expire financial account authorization: ";
+ try {
+
+ // expire the related financial authorization transaction
+ GenericValue authTransaction = PaymentGatewayServices.getAuthTransaction(paymentPref);
+ if (authTransaction == null) {
+ return ServiceUtil.returnError(err + " Could not find authorization transaction.");
+ }
+
+ Map input = UtilMisc.toMap("userLogin", userLogin, "finAccountAuthId", authTransaction.get("referenceNum"));
+ Map serviceResults = dispatcher.runSync("expireFinAccountAuth", input);
+
+ Map result = ServiceUtil.returnSuccess();
+ result.put("releaseRefNum", authTransaction.getString("referenceNum"));
+ result.put("releaseAmount", authTransaction.getDouble("amount"));
+ result.put("releaseResult", Boolean.TRUE);
+
+ // if there's an error, don't release
+ if (ServiceUtil.isError(serviceResults)) {
+ return ServiceUtil.returnError(err + ServiceUtil.getErrorMessage(serviceResults));
+ }
+
+ return result;
+ } catch (GenericServiceException e) {
+ Debug.logError(e, e.getMessage(), module);
+ return ServiceUtil.returnError(err + e.getMessage());
+ }
+ }
+
+ public static Map finAccountCapture(DispatchContext dctx, Map context) {
+ LocalDispatcher dispatcher = dctx.getDispatcher();
+ GenericDelegator delegator = dctx.getDelegator();
+
+ GenericValue orderPaymentPreference = (GenericValue) context.get("orderPaymentPreference");
+ GenericValue userLogin = (GenericValue) context.get("userLogin");
+ GenericValue authTrans = (GenericValue) context.get("authTrans");
+ Double amount = (Double) context.get("captureAmount");
+ String currency = (String) context.get("currency");
+
+ // get the authorization transaction
+ if (authTrans == null){
+ authTrans = PaymentGatewayServices.getAuthTransaction(orderPaymentPreference);
+ }
+ if (authTrans == null) {
+ return ServiceUtil.returnError("No authorization transaction found for the OrderPaymentPreference; cannot capture");
+ }
+
+ // get the auth record
+ String finAccountAuthId = authTrans.getString("referenceNum");
+ GenericValue finAccountAuth;
+ try {
+ finAccountAuth = delegator.findByPrimaryKey("FinAccountAuth", UtilMisc.toMap("finAccountAuthId", finAccountAuthId));
+ } catch (GenericEntityException e) {
+ Debug.logError(e, module);
+ return ServiceUtil.returnError(e.getMessage());
+ }
+
+ // get the financial account
+ GenericValue finAccount;
+ try {
+ finAccount = finAccountAuth.getRelatedOne("FinAccount");
+ } catch (GenericEntityException e) {
+ Debug.logError(e, module);
+ return ServiceUtil.returnError(e.getMessage());
+ }
+
+ // make sure authorization has not expired
+ Timestamp authExpiration = finAccountAuth.getTimestamp("thruDate");
+ if ((authExpiration != null) && (authExpiration.before(UtilDateTime.nowTimestamp()))) {
+ return ServiceUtil.returnError("Authorization transaction [" + authTrans.getString("paymentGatewayResponseId") + "] has expired as of " + authExpiration);
+ }
+
+ // make sure the fin account itself has not expired
+ if ((finAccount.getTimestamp("thruDate") != null) && (finAccount.getTimestamp("thruDate").before(UtilDateTime.nowTimestamp()))) {
+ return ServiceUtil.returnError("Financial account has expired as of " + finAccount.getTimestamp("thruDate"));
+ }
+ String finAccountId = finAccount.getString("finAccountId");
+
+ // need the product store ID & party ID
+ String orderId = orderPaymentPreference.getString("orderId");
+ String productStoreId = null;
+ String partyId = null;
+ if (orderId != null) {
+ OrderReadHelper orh = new OrderReadHelper(delegator, orderId);
+ productStoreId = orh.getProductStoreId();
+
+ GenericValue billToParty = orh.getBillToParty();
+ if (billToParty != null) {
+ partyId = billToParty.getString("partyId");
+ }
+ }
+
+ // build the withdraw context
+ Map withdrawCtx = FastMap.newInstance();
+ withdrawCtx.put("finAccountId", finAccountId);
+ withdrawCtx.put("productStoreId", productStoreId);
+ withdrawCtx.put("currency", currency);
+ withdrawCtx.put("partyId", partyId);
+ withdrawCtx.put("amount", amount);
+ withdrawCtx.put("userLogin", userLogin);
+
+ // call the withdraw service
+ Map withdrawResp;
+ try {
+ withdrawResp = dispatcher.runSync("finAccountWithdraw", withdrawCtx);
+ } catch (GenericServiceException e) {
+ Debug.logError(e, module);
+ return ServiceUtil.returnError(e.getMessage());
+ }
+ if (ServiceUtil.isError(withdrawResp)) {
+ return withdrawResp;
+ }
+
+ // cancel the authorization
+ Map releaseResult;
+ try {
+ releaseResult = dispatcher.runSync("expireFinAccountAuth", UtilMisc.toMap("userLogin", userLogin, "finAccountAuthId", finAccountAuthId));
+ } catch (GenericServiceException e) {
+ Debug.logError(e, module);
+ return ServiceUtil.returnError(e.getMessage());
+ }
+ if (ServiceUtil.isError(releaseResult)) {
+ return releaseResult;
+ }
+
+ // create the capture response
+ Map result = ServiceUtil.returnSuccess();
+ Boolean processResult = (Boolean) withdrawResp.get("processResult");
+ Double withdrawAmount = (Double) withdrawResp.get("amount");
+ String referenceNum = (String) withdrawResp.get("referenceNum");
+ result.put("captureResult", processResult);
+ result.put("captureRefNum", referenceNum);
+ result.put("captureCode", "C");
+ result.put("captureFlag", "1");
+ result.put("captureAmount", withdrawAmount);
+
+ return result;
+ }
+
+ public static Map finAccountRefund(DispatchContext dctx, Map context) {
+ LocalDispatcher dispatcher = dctx.getDispatcher();
+ GenericDelegator delegator = dctx.getDelegator();
+
+ GenericValue orderPaymentPreference = (GenericValue) context.get("orderPaymentPreference");
+ GenericValue userLogin = (GenericValue) context.get("userLogin");
+ Double amount = (Double) context.get("refundAmount");
+ String currency = (String) context.get("currency");
+ String finAccountId = (String) context.get("finAccountId");
+
+ String productStoreId = null;
+ String partyId = null;
+
+ if (orderPaymentPreference != null) {
+ String orderId = orderPaymentPreference.getString("orderId");
+ if (orderId != null) {
+ OrderReadHelper orh = new OrderReadHelper(delegator, orderId);
+ productStoreId = orh.getProductStoreId();
+
+ GenericValue billToParty = orh.getBillToParty();
+ if (billToParty != null) {
+ partyId = billToParty.getString("partyId");
+ }
+ }
+ }
+
+ // call the deposit service
+ Map depositCtx = FastMap.newInstance();
+ depositCtx.put("finAccountId", finAccountId);
+ depositCtx.put("productStoreId", productStoreId);
+ depositCtx.put("isRefund", Boolean.TRUE);
+ depositCtx.put("currency", currency);
+ depositCtx.put("partyId", partyId);
+ depositCtx.put("amount", amount);
+ depositCtx.put("userLogin", userLogin);
+
+ Map depositResp;
+ try {
+ depositResp = dispatcher.runSync("finAccountDeposit", depositCtx);
+ } catch (GenericServiceException e) {
+ Debug.logError(e, module);
+ return ServiceUtil.returnError(e.getMessage());
+ }
+ if (ServiceUtil.isError(depositResp)) {
+ return depositResp;
+ }
+
+ // create the refund response
+ Map result = ServiceUtil.returnSuccess();
+ Boolean processResult = (Boolean) depositResp.get("processResult");
+ Double depositAmount = (Double) depositResp.get("amount");
+ String referenceNum = (String) depositResp.get("referenceNum");
+ result.put("refundResult", processResult);
+ result.put("refundRefNum", referenceNum);
+ result.put("refundCode", "R");
+ result.put("refundFlag", "1");
+ result.put("refundAmount", depositAmount);
+
+ return result;
+ }
+
+ // base account transaction services
+ public static Map finAccountWithdraw(DispatchContext dctx, Map context) {
+ LocalDispatcher dispatcher = dctx.getDispatcher();
+ GenericDelegator delegator = dctx.getDelegator();
+
+ GenericValue userLogin = (GenericValue) context.get("userLogin");
+ String productStoreId = (String) context.get("productStoreId");
+ String finAccountId = (String) context.get("finAccountId");
+ Double amount = (Double) context.get("amount");
+
+ final String WITHDRAWAL = "WITHDRAWAL";
+
+ String partyId = (String) context.get("partyId");
+ if (UtilValidate.isEmpty(partyId)) {
+ partyId = "_NA_";
+ }
+ String currencyUom = (String) context.get("currency");
+ if (UtilValidate.isEmpty(currencyUom)) {
+ currencyUom = UtilProperties.getPropertyValue("general.properties", "currency.uom.id.default", "USD");
+ }
+
+ // validate the amount
+ if (amount.doubleValue() < 0.00) {
+ return ServiceUtil.returnError("Amount should be a positive number.");
+ }
+
+ GenericValue finAccount;
+ try {
+ finAccount = delegator.findByPrimaryKey("FinAccount", UtilMisc.toMap("finAccountId", finAccountId));
+ } catch (GenericEntityException e) {
+ Debug.logError(e, module);
+ return ServiceUtil.returnError(e.getMessage());
+ }
+
+ // verify we have a financial account
+ if (finAccount == null) {
+ return ServiceUtil.returnError("Unable to find Financial account for this transaction");
+ }
+
+ // make sure the fin account itself has not expired
+ if ((finAccount.getTimestamp("thruDate") != null) && (finAccount.getTimestamp("thruDate").before(UtilDateTime.nowTimestamp()))) {
+ return ServiceUtil.returnError("Financial account has expired as of " + finAccount.getTimestamp("thruDate"));
+ }
+
+ // check the actual balance (excluding authorized amounts) and create the transaction if it is sufficient
+ BigDecimal previousBalance;
+ try {
+ previousBalance = FinAccountHelper.getBalance(finAccountId, currencyUom, delegator);
+ } catch (GeneralException e) {
+ Debug.logError(e, module);
+ return ServiceUtil.returnError(e.getMessage());
+ }
+
+ BigDecimal balance;
+ String refNum;
+ Boolean procResult;
+ if (previousBalance.doubleValue() >= amount.doubleValue()) {
+ try {
+ refNum = FinAccountPaymentServices.createFinAcctPaymentTransaction(delegator, dispatcher, userLogin, amount,
+ productStoreId, partyId, currencyUom, WITHDRAWAL, finAccountId);
+ balance = FinAccountHelper.getAvailableBalance(finAccountId, currencyUom, delegator);
+ procResult = Boolean.TRUE;
+ } catch (GeneralException e) {
+ Debug.logError(e, module);
+ return ServiceUtil.returnError(e.getMessage());
+ }
+ } else {
+ procResult = Boolean.FALSE;
+ balance = previousBalance;
+ refNum = "N/A";
+ }
+
+ Map result = ServiceUtil.returnSuccess();
+ result.put("previousBalance", new Double(previousBalance.doubleValue()));
+ result.put("balance", new Double(balance.doubleValue()));
+ result.put("amount", amount);
+ result.put("processResult", procResult);
+ result.put("referenceNum", refNum);
+ return result;
+ }
+
+ // base deposit service
+ public static Map finAccountDeposit(DispatchContext dctx, Map context) {
+ LocalDispatcher dispatcher = dctx.getDispatcher();
+ GenericDelegator delegator = dctx.getDelegator();
+
+ GenericValue userLogin = (GenericValue) context.get("userLogin");
+ String productStoreId = (String) context.get("productStoreId");
+ String finAccountId = (String) context.get("finAccountId");
+ Boolean isRefund = (Boolean) context.get("isRefund");
+ Double amount = (Double) context.get("amount");
+
+ final String DEPOSIT = isRefund == null || !isRefund.booleanValue() ? "DEPOSIT" : "ADJUSTMENT";
+
+ String partyId = (String) context.get("partyId");
+ if (UtilValidate.isEmpty(partyId)) {
+ partyId = "_NA_";
+ }
+ String currencyUom = (String) context.get("currency");
+ if (UtilValidate.isEmpty(currencyUom)) {
+ currencyUom = UtilProperties.getPropertyValue("general.properties", "currency.uom.id.default", "USD");
+ }
+
+ GenericValue finAccount;
+ try {
+ finAccount = delegator.findByPrimaryKey("FinAccount", UtilMisc.toMap("finAccountId", finAccountId));
+ } catch (GenericEntityException e) {
+ Debug.logError(e, module);
+ return ServiceUtil.returnError(e.getMessage());
+ }
+
+ // verify we have a financial account
+ if (finAccount == null) {
+ return ServiceUtil.returnError("Unable to find Financial account for this transaction");
+ }
+
+ // make sure the fin account itself has not expired
+ if ((finAccount.getTimestamp("thruDate") != null) && (finAccount.getTimestamp("thruDate").before(UtilDateTime.nowTimestamp()))) {
+ return ServiceUtil.returnError("Financial account has expired as of " + finAccount.getTimestamp("thruDate"));
+ }
+ Debug.log("Deposit into financial account #" + finAccountId + " [" + amount + "]", module);
+
+ // get the previous balance
+ BigDecimal previousBalance;
+ try {
+ previousBalance = FinAccountHelper.getAvailableBalance(finAccountId, currencyUom, delegator);
+ } catch (GeneralException e) {
+ Debug.logError(e, module);
+ return ServiceUtil.returnError(e.getMessage());
+ }
+
+ // create the transaction
+ BigDecimal balance;
+ String refNum;
+ try {
+ refNum = FinAccountPaymentServices.createFinAcctPaymentTransaction(delegator, dispatcher, userLogin, amount,
+ productStoreId, partyId, currencyUom, DEPOSIT, finAccountId);
+ balance = FinAccountHelper.getAvailableBalance(finAccountId, currencyUom, delegator);
+ } catch (GeneralException e) {
+ Debug.logError(e, module);
+ return ServiceUtil.returnError(e.getMessage());
+ }
+
+ Map result = ServiceUtil.returnSuccess();
+ result.put("previousBalance", new Double(previousBalance.doubleValue()));
+ result.put("balance", new Double(balance.doubleValue()));
+ result.put("amount", amount);
+ result.put("processResult", Boolean.TRUE);
+ result.put("referenceNum", refNum);
+ return result;
+ }
+
+ // auto-replenish service (deposit)
+ public static Map finAccountReplenish(DispatchContext dctx, Map context) {
+ LocalDispatcher dispatcher = dctx.getDispatcher();
+ GenericDelegator delegator = dctx.getDelegator();
+
+ GenericValue userLogin = (GenericValue) context.get("userLogin");
+ String productStoreId = (String) context.get("productStoreId");
+ String finAccountId = (String) context.get("finAccountId");
+
+ // lookup the FinAccount
+ GenericValue finAccount;
+ try {
+ finAccount = delegator.findByPrimaryKey("FinAccount", UtilMisc.toMap("finAccountId", finAccountId));
+ } catch (GenericEntityException e) {
+ Debug.logError(e, module);
+ return ServiceUtil.returnError(e.getMessage());
+ }
+ if (finAccount == null) {
+ return ServiceUtil.returnError("Invalid financial account [" + finAccountId + "]");
+ }
+ String currency = finAccount.getString("currencyUomId");
+
+ // look up the type -- determine auto-replenish is active
+ GenericValue finAccountType;
+ try {
+ finAccountType = finAccount.getRelatedOne("FinAccountType");
+ } catch (GenericEntityException e) {
+ Debug.logError(e, module);
+ return ServiceUtil.returnError(e.getMessage());
+ }
+ String replenishEnumId = finAccountType.getString("replenishEnumId");
+ if (!"FARP_AUTOMATIC".equals(replenishEnumId)) {
+ // type does not support auto-replenish
+ return ServiceUtil.returnSuccess();
+ }
+
+ BigDecimal replenishLevel = finAccount.getBigDecimal("replenishLevel");
+ if (replenishLevel == null) {
+ // no replenish level set; this account goes not support auto-replenish
+ return ServiceUtil.returnSuccess();
+ }
+
+ // get the current balance
+ BigDecimal balance;
+ try {
+ balance = FinAccountHelper.getBalance(finAccountId, currency, delegator);
+ } catch (GenericEntityException e) {
+ Debug.logError(e, module);
+ return ServiceUtil.returnError(e.getMessage());
+ }
+
+ // the deposit is level - balance (500 - (-10) = 510 || 500 - (10) = 490)
+ BigDecimal depositAmount = replenishLevel.subtract(balance);
+
+ // find the owner party
+ List finAcctOwners;
+ try {
+ finAcctOwners = delegator.findByAnd("FinAccountRole", UtilMisc.toMap("finAccountId", finAccountId, "roleTypeId", "OWNER"), UtilMisc.toList("-fromDate"));
+ } catch (GenericEntityException e) {
+ Debug.logError(e, module);
+ return ServiceUtil.returnError(e.getMessage());
+ }
+ finAcctOwners = EntityUtil.filterByDate(finAcctOwners);
+ GenericValue finAccountOwner = EntityUtil.getFirst(finAcctOwners);
+ if (finAccountOwner == null) {
+ // no owner cannot replenish; (not fatal, just not supported by this account)
+ Debug.logWarning("No owner attached to financial account [" + finAccountId + "] cannot auto-replenish", module);
+ return ServiceUtil.returnSuccess();
+ }
+ String partyId = finAccountOwner.getString("partyId");
+
+ // determine the payment method to use to replenish
+ List paymentMethods;
+ try {
+ paymentMethods = delegator.findByAnd("PaymentMethod", UtilMisc.toMap("partyId", partyId), UtilMisc.toList("-fromDate"));
+ } catch (GenericEntityException e) {
+ Debug.logError(e, module);
+ return ServiceUtil.returnError(e.getMessage());
+ }
+ paymentMethods = EntityUtil.filterByDate(paymentMethods);
+ GenericValue paymentMethod = EntityUtil.getFirst(paymentMethods);
+ if (paymentMethod == null) {
+ // no payment methods on file; cannot replenish
+ Debug.logWarning("No payment methods attached to party [" + partyId + "] cannot auto-replenish", module);
+ return ServiceUtil.returnSuccess();
+ }
+
+ // clear out the frozen flag
+ finAccount.set("isFrozen", "N");
+ try {
+ finAccount.store();
+ } catch (GenericEntityException e) {
+ Debug.logError(e, module);
+ return ServiceUtil.returnError(e.getMessage());
+ }
+
+ // hit the payment method for the amount to replenish
+ Map orderItemMap = UtilMisc.toMap("Auto-Replenishment", new Double(depositAmount.doubleValue()));
+ Map replOrderCtx = FastMap.newInstance();
+ replOrderCtx.put("productStoreId", productStoreId);
+ replOrderCtx.put("paymentMethodId", paymentMethod.getString("paymentMethodId"));
+ replOrderCtx.put("currency", currency);
+ replOrderCtx.put("partyId", partyId);
+ replOrderCtx.put("itemMap", orderItemMap);
+ replOrderCtx.put("userLogin", userLogin);
+ Map replResp;
+ try {
+ replResp = dispatcher.runSync("createSimpleNonProductSalesOrder", replOrderCtx);
+ } catch (GenericServiceException e) {
+ Debug.logError(e, module);
+ return ServiceUtil.returnError(e.getMessage());
+ }
+ if (ServiceUtil.isError(replResp)) {
+ return replResp;
+ }
+
+ // create the deposit
+ Map depositCtx = FastMap.newInstance();
+ depositCtx.put("productStoreId", productStoreId);
+ depositCtx.put("finAccountId", finAccountId);
+ depositCtx.put("currency", currency);
+ depositCtx.put("partyId", partyId);
+ depositCtx.put("amount", new Double(depositAmount.doubleValue()));
+ depositCtx.put("userLogin", userLogin);
+ Map depositResp;
+ try {
+ depositResp = dispatcher.runSync("finAccountDeposit", depositCtx);
+ } catch (GenericServiceException e) {
+ Debug.logError(e, module);
+ return ServiceUtil.returnError(e.getMessage());
+ }
+ if (ServiceUtil.isError(depositResp)) {
+ return depositResp;
+ }
+
+ return ServiceUtil.returnSuccess();
+ }
+
+ private static String createFinAcctPaymentTransaction(GenericDelegator delegator, LocalDispatcher dispatcher, GenericValue userLogin, Double amount,
+ String productStoreId, String partyId, String currencyUom, String txType, String finAccountId) throws GeneralException {
+
+ final String coParty = ProductStoreWorker.getProductStorePayToPartyId(productStoreId, delegator);
+ final String paymentMethodType = "FIN_ACCOUNT";
+
+ if (UtilValidate.isEmpty(partyId)) {
+ partyId = "_NA_";
+ }
+
+ String paymentType;
+ String partyIdFrom;
+ String partyIdTo;
+
+ // determine the payment type and which direction the parties should go
+ if ("DEPOSIT".equals(txType)) {
+ paymentType = "RECEIPT";
+ partyIdFrom = partyId;
+ partyIdTo = coParty;
+ } else if ("WITHDRAWAL".equals(txType)) {
+ paymentType = "DISBURSEMENT";
+ partyIdFrom = coParty;
+ partyIdTo = partyId;
+ } else if ("ADJUSTMENT".equals(txType)) {
+ paymentType = "CUSTOMER_REFUND";
+ partyIdFrom = coParty;
+ partyIdTo = partyId;
+ } else {
+ throw new GeneralException("Unable to create financial account transaction!");
+ }
+
+ // create the payment for the transaction
+ Map paymentCtx = UtilMisc.toMap("paymentTypeId", paymentType);
+ paymentCtx.put("paymentMethodTypeId", paymentMethodType);
+ paymentCtx.put("partyIdTo", partyIdTo);
+ paymentCtx.put("partyIdFrom", partyIdFrom);
+ paymentCtx.put("statusId", "PMNT_RECEIVED");
+ paymentCtx.put("currencyUomId", currencyUom);
+ paymentCtx.put("amount", amount);
+ paymentCtx.put("userLogin", userLogin);
+ paymentCtx.put("paymentRefNum", Long.toString(UtilDateTime.nowTimestamp().getTime()));
+
+ String paymentId;
+ Map payResult;
+ try {
+ payResult = dispatcher.runSync("createPayment", paymentCtx);
+ } catch (GenericServiceException e) {
+ throw new GeneralException(e);
+ }
+ if (payResult == null) {
+ throw new GeneralException("Unknow error in creating financial account transaction!");
+ }
+ if (ServiceUtil.isError(payResult)) {
+ throw new GeneralException(ServiceUtil.getErrorMessage(payResult));
+ } else {
+ paymentId = (String) payResult.get("paymentId");
+ }
+
+ // create the initial transaction
+ Map transCtx = UtilMisc.toMap("finAccountTransTypeId", txType);
+ transCtx.put("finAccountId", finAccountId);
+ transCtx.put("partyId", userLogin.getString("partyId"));
+ transCtx.put("userLogin", userLogin);
+ transCtx.put("paymentId", paymentId);
+
+ Map transResult;
+ String txId;
+ try {
+ transResult = dispatcher.runSync("createFinAccountTrans", transCtx);
+ } catch (GenericServiceException e) {
+ throw new GeneralException(e);
+ }
+ if (transResult == null) {
+ throw new GeneralException("Unknown error in creating financial account transaction!");
+ }
+ if (ServiceUtil.isError(transResult)) {
+ throw new GeneralException(ServiceUtil.getErrorMessage(transResult));
+ } else {
+ txId = (String) transResult.get("finAccountTransId");
+ }
+
+ return txId;
+ }
+}
Propchange: ofbiz/trunk/applications/accounting/src/org/ofbiz/accounting/finaccount/FinAccountPaymentServices.java
------------------------------------------------------------------------------
svn:eol-style = native
Propchange: ofbiz/trunk/applications/accounting/src/org/ofbiz/accounting/finaccount/FinAccountPaymentServices.java
------------------------------------------------------------------------------
svn:keywords = "Date Rev Author URL Id"
Propchange: ofbiz/trunk/applications/accounting/src/org/ofbiz/accounting/finaccount/FinAccountPaymentServices.java
------------------------------------------------------------------------------
svn:mime-type = text/plain