Exemple #1
0
        private async Task <bool> HasBeenCapturedPreviouslyAsync(HSOrder order, HSPaymentTransaction transaction)
        {
            var inquire = await _cardConnect.Inquire(new CardConnectInquireRequest
            {
                merchid  = transaction.xp.CardConnectResponse.merchid,
                orderid  = order.ID,
                set      = "1",
                currency = order.xp.Currency.ToString(),
                retref   = transaction.xp.CardConnectResponse.retref
            });

            return(!string.IsNullOrEmpty(inquire.capturedate));
        }
Exemple #2
0
        private async Task CapturePaymentAsync(HSOrder order, HSPayment payment, HSPaymentTransaction transaction)
        {
            try
            {
                var response = await _cardConnect.Capture(new CardConnectCaptureRequest
                {
                    merchid  = transaction.xp.CardConnectResponse.merchid,
                    retref   = transaction.xp.CardConnectResponse.retref,
                    currency = order.xp.Currency.ToString()
                });

                await _oc.Payments.CreateTransactionAsync(OrderDirection.Incoming, order.ID, payment.ID, CardConnectMapper.Map(payment, response));
            }
            catch (CardConnectInquireException ex)
            {
                throw new PaymentCaptureJobException("Error inquiring payment. Message: {ex.ApiError.Message}, ErrorCode: {ex.ApiError.ErrorCode}", order.ID, payment.ID, transaction.ID);
            }
            catch (CardConnectCaptureException ex)
            {
                await _oc.Payments.CreateTransactionAsync(OrderDirection.Incoming, order.ID, payment.ID, CardConnectMapper.Map(payment, ex.Response));

                throw new PaymentCaptureJobException($"Error capturing payment. Message: {ex.ApiError.Message}, ErrorCode: {ex.ApiError.ErrorCode}", order.ID, payment.ID, transaction.ID);
            }
        }
Exemple #3
0
        public virtual async Task HandleRefundTransaction(HSOrderWorksheet worksheet, HSPayment creditCardPayment, HSPaymentTransaction creditCardPaymentTransaction, decimal totalToRefund, RMA rma)
        {
            try
            {
                CardConnectRefundRequest requestedRefund = new CardConnectRefundRequest()
                {
                    currency = worksheet.Order.xp.Currency.ToString(),
                    merchid  = creditCardPaymentTransaction.xp.CardConnectResponse.merchid,
                    retref   = creditCardPaymentTransaction.xp.CardConnectResponse.retref,
                    amount   = totalToRefund.ToString("F2"),
                };
                CardConnectRefundResponse response = await _cardConnect.Refund(requestedRefund);

                HSPayment newCreditCardPayment = new HSPayment()
                {
                    Amount = response.amount
                };
                await _oc.Payments.CreateTransactionAsync(OrderDirection.Incoming, rma.SourceOrderID, creditCardPayment.ID, CardConnectMapper.Map(newCreditCardPayment, response));
            }
            catch (CreditCardRefundException ex)
            {
                throw new CatalystBaseException(new ApiError
                {
                    ErrorCode = "Payment.FailedToRefund",
                    Message   = ex.ApiError.Message
                });
            }
        }
Exemple #4
0
        public virtual async Task HandleRefund(RMA rma, CosmosListPage <RMA> allRMAsOnThisOrder, HSOrderWorksheet worksheet, DecodedToken decodedToken)
        {
            // Get payment info from the order
            ListPage <HSPayment> paymentResponse = await _oc.Payments.ListAsync <HSPayment>(OrderDirection.Incoming, rma.SourceOrderID);

            HSPayment creditCardPayment = paymentResponse.Items.FirstOrDefault(payment => payment.Type == OrderCloud.SDK.PaymentType.CreditCard);

            if (creditCardPayment == null)
            {
                // Items were not paid for with a credit card.  No refund to process via CardConnect.
                return;
            }
            HSPaymentTransaction creditCardPaymentTransaction = creditCardPayment.Transactions
                                                                .OrderBy(x => x.DateExecuted)
                                                                .LastOrDefault(x => x.Type == "CreditCard" && x.Succeeded);
            decimal purchaseOrderTotal = (decimal)paymentResponse.Items
                                         .Where(payment => payment.Type == OrderCloud.SDK.PaymentType.PurchaseOrder)
                                         .Select(payment => payment.Amount)
                                         .Sum();

            // Refund via CardConnect
            CardConnectInquireResponse inquiry = await _cardConnect.Inquire(new CardConnectInquireRequest
            {
                merchid  = creditCardPaymentTransaction.xp.CardConnectResponse.merchid,
                orderid  = rma.SourceOrderID,
                set      = "1",
                currency = worksheet.Order.xp.Currency.ToString(),
                retref   = creditCardPaymentTransaction.xp.CardConnectResponse.retref
            });

            decimal shippingRefund = rma.Type == RMAType.Cancellation ? GetShippingRefundIfCancellingAll(worksheet, rma, allRMAsOnThisOrder) : 0M;

            decimal lineTotalToRefund = rma.LineItems
                                        .Where(li => li.IsResolved &&
                                               !li.IsRefunded &&
                                               li.RefundableViaCreditCard &&
                                               (li.Status == RMALineItemStatus.PartialQtyComplete || li.Status == RMALineItemStatus.Complete)
                                               ).Select(li => li.LineTotalRefund)
                                        .Sum();

            decimal totalToRefund = lineTotalToRefund + shippingRefund;

            // Update Total Credited on RMA
            rma.TotalCredited += totalToRefund;

            // Transactions that are queued for capture can only be fully voided, and we are only allowing partial voids moving forward.
            if (inquiry.voidable == "Y" && inquiry.setlstat == QUEUED_FOR_CAPTURE)
            {
                throw new CatalystBaseException(new ApiError
                {
                    ErrorCode = "Payment.FailedToVoidAuthorization",
                    Message   = "This customer's credit card transaction is currently queued for capture and cannot be refunded at this time.  Please try again later."
                });
            }

            // If voidable, but not refundable, void the refund amount off the original order total
            if (inquiry.voidable == "Y")
            {
                await HandleVoidTransaction(worksheet, creditCardPayment, creditCardPaymentTransaction, totalToRefund, rma);
            }

            // If refundable, but not voidable, do a refund
            if (inquiry.voidable == "N")
            {
                await HandleRefundTransaction(worksheet, creditCardPayment, creditCardPaymentTransaction, totalToRefund, rma);
            }
        }