1: <?php
2: 3: 4: 5: 6: 7: 8: 9: 10: 11: 12: 13: 14: 15: 16: 17: 18: 19: 20: 21: 22: 23: 24: 25:
26:
27:
28: class Mage_Paygate_Model_Authorizenet extends Mage_Payment_Model_Method_Cc
29: {
30: 31: 32:
33: const CGI_URL = 'https://secure.authorize.net/gateway/transact.dll';
34:
35: 36: 37:
38: const CGI_URL_TD = 'https://apitest.authorize.net/xml/v1/request.api';
39:
40: const REQUEST_METHOD_CC = 'CC';
41: const REQUEST_METHOD_ECHECK = 'ECHECK';
42:
43: const REQUEST_TYPE_AUTH_CAPTURE = 'AUTH_CAPTURE';
44: const REQUEST_TYPE_AUTH_ONLY = 'AUTH_ONLY';
45: const REQUEST_TYPE_CAPTURE_ONLY = 'CAPTURE_ONLY';
46: const REQUEST_TYPE_CREDIT = 'CREDIT';
47: const REQUEST_TYPE_VOID = 'VOID';
48: const REQUEST_TYPE_PRIOR_AUTH_CAPTURE = 'PRIOR_AUTH_CAPTURE';
49:
50: const ECHECK_ACCT_TYPE_CHECKING = 'CHECKING';
51: const ECHECK_ACCT_TYPE_BUSINESS = 'BUSINESSCHECKING';
52: const ECHECK_ACCT_TYPE_SAVINGS = 'SAVINGS';
53:
54: const ECHECK_TRANS_TYPE_CCD = 'CCD';
55: const ECHECK_TRANS_TYPE_PPD = 'PPD';
56: const ECHECK_TRANS_TYPE_TEL = 'TEL';
57: const ECHECK_TRANS_TYPE_WEB = 'WEB';
58:
59: const RESPONSE_DELIM_CHAR = '(~)';
60:
61: const RESPONSE_CODE_APPROVED = 1;
62: const RESPONSE_CODE_DECLINED = 2;
63: const RESPONSE_CODE_ERROR = 3;
64: const RESPONSE_CODE_HELD = 4;
65:
66: const RESPONSE_REASON_CODE_APPROVED = 1;
67: const RESPONSE_REASON_CODE_NOT_FOUND = 16;
68: const RESPONSE_REASON_CODE_PARTIAL_APPROVE = 295;
69: const RESPONSE_REASON_CODE_PENDING_REVIEW_AUTHORIZED = 252;
70: const RESPONSE_REASON_CODE_PENDING_REVIEW = 253;
71: const RESPONSE_REASON_CODE_PENDING_REVIEW_DECLINED = 254;
72:
73: const PARTIAL_AUTH_CARDS_LIMIT = 5;
74:
75: const PARTIAL_AUTH_LAST_SUCCESS = 'last_success';
76: const PARTIAL_AUTH_LAST_DECLINED = 'last_declined';
77: const PARTIAL_AUTH_ALL_CANCELED = 'all_canceled';
78: const PARTIAL_AUTH_CARDS_LIMIT_EXCEEDED = 'card_limit_exceeded';
79: const PARTIAL_AUTH_DATA_CHANGED = 'data_changed';
80:
81: const METHOD_CODE = 'authorizenet';
82:
83: const TRANSACTION_STATUS_EXPIRED = 'expired';
84:
85: protected $_code = self::METHOD_CODE;
86:
87: 88: 89:
90: protected $_formBlockType = 'paygate/authorizenet_form_cc';
91:
92: 93: 94:
95: protected $_infoBlockType = 'paygate/authorizenet_info_cc';
96:
97: 98: 99:
100: protected $_isGateway = true;
101: protected $_canAuthorize = true;
102: protected $_canCapture = true;
103: protected $_canCapturePartial = false;
104: protected $_canRefund = true;
105: protected $_canRefundInvoicePartial = true;
106: protected $_canVoid = true;
107: protected $_canUseInternal = true;
108: protected $_canUseCheckout = true;
109: protected $_canUseForMultishipping = true;
110: protected $_canSaveCc = false;
111: protected $_canFetchTransactionInfo = true;
112:
113: protected $_allowCurrencyCode = array('USD');
114:
115: 116: 117: 118: 119:
120: protected $_debugReplacePrivateDataKeys = array('x_login', 'x_tran_key',
121: 'x_card_num', 'x_exp_date',
122: 'x_card_code', 'x_bank_aba_code',
123: 'x_bank_name', 'x_bank_acct_num',
124: 'x_bank_acct_type','x_bank_acct_name',
125: 'x_echeck_type');
126:
127: 128: 129: 130:
131: protected $_isTransactionFraud = 'is_transaction_fraud';
132:
133: 134: 135: 136:
137: protected $_realTransactionIdKey = 'real_transaction_id';
138:
139: 140: 141: 142:
143: protected $_splitTenderIdKey = 'split_tender_id';
144:
145: 146: 147: 148:
149: protected $_isGatewayActionsLockedKey = 'is_gateway_actions_locked';
150:
151: 152: 153: 154:
155: protected $_partialAuthorizationLastActionStateSessionKey = 'paygate_authorizenet_last_action_state';
156:
157: 158: 159: 160:
161: protected $_partialAuthorizationChecksumSessionKey = 'paygate_authorizenet_checksum';
162:
163: 164: 165: 166: 167:
168: protected $_partialAuthorizationChecksumDataKeys = array(
169: 'x_version', 'x_test_request', 'x_login', 'x_test_request', 'x_allow_partial_auth', 'x_amount',
170: 'x_currency_code', 'x_type', 'x_first_name', 'x_last_name', 'x_company', 'x_address', 'x_city', 'x_state',
171: 'x_zip', 'x_country', 'x_phone', 'x_fax', 'x_cust_id', 'x_customer_ip', 'x_customer_tax_id', 'x_email',
172: 'x_email_customer', 'x_merchant_email', 'x_ship_to_first_name', 'x_ship_to_last_name', 'x_ship_to_company',
173: 'x_ship_to_address', 'x_ship_to_city', 'x_ship_to_state', 'x_ship_to_zip', 'x_ship_to_country', 'x_po_num',
174: 'x_tax', 'x_freight'
175: );
176:
177: 178: 179: 180: 181:
182: protected $_centinelFieldMap = array(
183: 'centinel_cavv' => 'x_cardholder_authentication_value',
184: 'centinel_eci' => 'x_authentication_indicator'
185: );
186:
187: 188: 189: 190: 191: 192:
193: public function canUseForCurrency($currencyCode)
194: {
195: if (!in_array($currencyCode, $this->getAcceptedCurrencyCodes())) {
196: return false;
197: }
198: return true;
199: }
200:
201: 202: 203: 204: 205:
206: public function getAcceptedCurrencyCodes()
207: {
208: if (!$this->hasData('_accepted_currency')) {
209: $acceptedCurrencyCodes = $this->_allowCurrencyCode;
210: $acceptedCurrencyCodes[] = $this->getConfigData('currency');
211: $this->setData('_accepted_currency', $acceptedCurrencyCodes);
212: }
213: return $this->_getData('_accepted_currency');
214: }
215:
216: 217: 218: 219: 220:
221: public function canCapture()
222: {
223: if ($this->_isGatewayActionsLocked($this->getInfoInstance())) {
224: return false;
225: }
226: if ($this->_isPreauthorizeCapture($this->getInfoInstance())) {
227: return true;
228: }
229:
230: 231: 232:
233: foreach($this->getCardsStorage()->getCards() as $card) {
234: $lastTransaction = $this->getInfoInstance()->getTransaction($card->getLastTransId());
235: if ($lastTransaction) {
236: return false;
237: }
238: }
239: return true;
240: }
241:
242: 243: 244: 245: 246:
247: public function canRefund()
248: {
249: if ($this->_isGatewayActionsLocked($this->getInfoInstance())
250: || $this->getCardsStorage()->getCardsCount() <= 0
251: ) {
252: return false;
253: }
254: foreach($this->getCardsStorage()->getCards() as $card) {
255: $lastTransaction = $this->getInfoInstance()->getTransaction($card->getLastTransId());
256: if ($lastTransaction
257: && $lastTransaction->getTxnType() == Mage_Sales_Model_Order_Payment_Transaction::TYPE_CAPTURE
258: && !$lastTransaction->getIsClosed()
259: ) {
260: return true;
261: }
262: }
263: return false;
264: }
265:
266: 267: 268: 269: 270: 271:
272: public function canVoid(Varien_Object $payment)
273: {
274: if ($this->_isGatewayActionsLocked($this->getInfoInstance())) {
275: return false;
276: }
277: return $this->_isPreauthorizeCapture($this->getInfoInstance());
278: }
279:
280: 281: 282: 283: 284: 285:
286: public function setPartialAuthorizationLastActionState($state)
287: {
288: $this->_getSession()->setData($this->_partialAuthorizationLastActionStateSessionKey, $state);
289: return $this;
290: }
291:
292: 293: 294: 295: 296:
297: public function getPartialAuthorizationLastActionState()
298: {
299: return $this->_getSession()->getData($this->_partialAuthorizationLastActionStateSessionKey);
300: }
301:
302: 303: 304: 305: 306:
307: public function unsetPartialAuthorizationLastActionState()
308: {
309: $this->_getSession()->setData($this->_partialAuthorizationLastActionStateSessionKey, false);
310: return $this;
311: }
312:
313: 314: 315: 316: 317: 318: 319:
320: public function authorize(Varien_Object $payment, $amount)
321: {
322: if ($amount <= 0) {
323: Mage::throwException(Mage::helper('paygate')->__('Invalid amount for authorization.'));
324: }
325:
326: $this->_initCardsStorage($payment);
327:
328: if ($this->isPartialAuthorization($payment)) {
329: $this->_partialAuthorization($payment, $amount, self::REQUEST_TYPE_AUTH_ONLY);
330: $payment->setSkipTransactionCreation(true);
331: return $this;
332: }
333:
334: $this->_place($payment, $amount, self::REQUEST_TYPE_AUTH_ONLY);
335: $payment->setSkipTransactionCreation(true);
336: return $this;
337: }
338:
339: 340: 341: 342: 343: 344: 345:
346: public function capture(Varien_Object $payment, $amount)
347: {
348: if ($amount <= 0) {
349: Mage::throwException(Mage::helper('paygate')->__('Invalid amount for capture.'));
350: }
351: $this->_initCardsStorage($payment);
352: if ($this->_isPreauthorizeCapture($payment)) {
353: $this->_preauthorizeCapture($payment, $amount);
354: } else if ($this->isPartialAuthorization($payment)) {
355: $this->_partialAuthorization($payment, $amount, self::REQUEST_TYPE_AUTH_CAPTURE);
356: } else {
357: $this->_place($payment, $amount, self::REQUEST_TYPE_AUTH_CAPTURE);
358: }
359: $payment->setSkipTransactionCreation(true);
360: return $this;
361: }
362:
363: 364: 365: 366: 367: 368:
369: public function void(Varien_Object $payment)
370: {
371: $cardsStorage = $this->getCardsStorage($payment);
372:
373: $messages = array();
374: $isSuccessful = false;
375: $isFiled = false;
376: foreach($cardsStorage->getCards() as $card) {
377: try {
378: $newTransaction = $this->_voidCardTransaction($payment, $card);
379: $messages[] = $newTransaction->getMessage();
380: $isSuccessful = true;
381: } catch (Exception $e) {
382: $messages[] = $e->getMessage();
383: $isFiled = true;
384: continue;
385: }
386: $cardsStorage->updateCard($card);
387: }
388:
389: if ($isFiled) {
390: $this->_processFailureMultitransactionAction($payment, $messages, $isSuccessful);
391: }
392:
393: $payment->setSkipTransactionCreation(true);
394: return $this;
395: }
396:
397: 398: 399: 400: 401: 402:
403: public function cancel(Varien_Object $payment)
404: {
405: return $this->void($payment);
406: }
407:
408: 409: 410: 411: 412: 413: 414: 415:
416: public function refund(Varien_Object $payment, $requestedAmount)
417: {
418: $cardsStorage = $this->getCardsStorage($payment);
419:
420: if ($this->_formatAmount(
421: $cardsStorage->getCapturedAmount() - $cardsStorage->getRefundedAmount()
422: ) < $requestedAmount
423: ) {
424: Mage::throwException(Mage::helper('paygate')->__('Invalid amount for refund.'));
425: }
426:
427: $messages = array();
428: $isSuccessful = false;
429: $isFiled = false;
430: foreach($cardsStorage->getCards() as $card) {
431: if ($requestedAmount > 0) {
432: $cardAmountForRefund = $this->_formatAmount($card->getCapturedAmount() - $card->getRefundedAmount());
433: if ($cardAmountForRefund <= 0) {
434: continue;
435: }
436: if ($cardAmountForRefund > $requestedAmount) {
437: $cardAmountForRefund = $requestedAmount;
438: }
439: try {
440: $newTransaction = $this->_refundCardTransaction($payment, $cardAmountForRefund, $card);
441: $messages[] = $newTransaction->getMessage();
442: $isSuccessful = true;
443: } catch (Exception $e) {
444: $messages[] = $e->getMessage();
445: $isFiled = true;
446: continue;
447: }
448: $card->setRefundedAmount($this->_formatAmount($card->getRefundedAmount() + $cardAmountForRefund));
449: $cardsStorage->updateCard($card);
450: $requestedAmount = $this->_formatAmount($requestedAmount - $cardAmountForRefund);
451: } else {
452: $payment->setSkipTransactionCreation(true);
453: return $this;
454: }
455: }
456:
457: if ($isFiled) {
458: $this->_processFailureMultitransactionAction($payment, $messages, $isSuccessful);
459: }
460:
461: $payment->setSkipTransactionCreation(true);
462: return $this;
463: }
464:
465: 466: 467: 468: 469:
470: public function cancelPartialAuthorization(Mage_Payment_Model_Info $payment) {
471: if (!$payment->getAdditionalInformation($this->_splitTenderIdKey)) {
472: Mage::throwException(Mage::helper('paygate')->__('Invalid split tenderId ID.'));
473: }
474:
475: $request = $this->_getRequest();
476: $request->setXSplitTenderId($payment->getAdditionalInformation($this->_splitTenderIdKey));
477:
478: $request
479: ->setXType(self::REQUEST_TYPE_VOID)
480: ->setXMethod(self::REQUEST_METHOD_CC);
481: $result = $this->_postRequest($request);
482:
483: switch ($result->getResponseCode()) {
484: case self::RESPONSE_CODE_APPROVED:
485: $payment->setAdditionalInformation($this->_splitTenderIdKey, null);
486: $this->_getSession()->setData($this->_partialAuthorizationChecksumSessionKey, null);
487: $this->getCardsStorage($payment)->flushCards();
488: $this->setPartialAuthorizationLastActionState(self::PARTIAL_AUTH_ALL_CANCELED);
489: return;
490: default:
491: Mage::throwException(Mage::helper('paygate')->__('Payment canceling error.'));
492: }
493:
494: }
495:
496: 497: 498: 499: 500: 501: 502: 503: 504:
505: protected function _place($payment, $amount, $requestType)
506: {
507: $payment->setAnetTransType($requestType);
508: $payment->setAmount($amount);
509: $request= $this->_buildRequest($payment);
510: $result = $this->_postRequest($request);
511:
512: switch ($requestType) {
513: case self::REQUEST_TYPE_AUTH_ONLY:
514: $newTransactionType = Mage_Sales_Model_Order_Payment_Transaction::TYPE_AUTH;
515: $defaultExceptionMessage = Mage::helper('paygate')->__('Payment authorization error.');
516: break;
517: case self::REQUEST_TYPE_AUTH_CAPTURE:
518: $newTransactionType = Mage_Sales_Model_Order_Payment_Transaction::TYPE_CAPTURE;
519: $defaultExceptionMessage = Mage::helper('paygate')->__('Payment capturing error.');
520: break;
521: }
522:
523: switch ($result->getResponseCode()) {
524: case self::RESPONSE_CODE_APPROVED:
525: $this->getCardsStorage($payment)->flushCards();
526: $card = $this->_registerCard($result, $payment);
527: $this->_addTransaction(
528: $payment,
529: $card->getLastTransId(),
530: $newTransactionType,
531: array('is_transaction_closed' => 0),
532: array($this->_realTransactionIdKey => $card->getLastTransId()),
533: Mage::helper('paygate')->getTransactionMessage(
534: $payment, $requestType, $card->getLastTransId(), $card, $amount
535: )
536: );
537: if ($requestType == self::REQUEST_TYPE_AUTH_CAPTURE) {
538: $card->setCapturedAmount($card->getProcessedAmount());
539: $this->getCardsStorage($payment)->updateCard($card);
540: }
541: return $this;
542: case self::RESPONSE_CODE_HELD:
543: if ($result->getResponseReasonCode() == self::RESPONSE_REASON_CODE_PENDING_REVIEW_AUTHORIZED
544: || $result->getResponseReasonCode() == self::RESPONSE_REASON_CODE_PENDING_REVIEW
545: ) {
546: $card = $this->_registerCard($result, $payment);
547: $this->_addTransaction(
548: $payment,
549: $card->getLastTransId(),
550: $newTransactionType,
551: array('is_transaction_closed' => 0),
552: array(
553: $this->_realTransactionIdKey => $card->getLastTransId(),
554: $this->_isTransactionFraud => true
555: ),
556: Mage::helper('paygate')->getTransactionMessage(
557: $payment, $requestType, $card->getLastTransId(), $card, $amount
558: )
559: );
560: if ($requestType == self::REQUEST_TYPE_AUTH_CAPTURE) {
561: $card->setCapturedAmount($card->getProcessedAmount());
562: $this->getCardsStorage()->updateCard($card);
563: }
564: $payment
565: ->setIsTransactionPending(true)
566: ->setIsFraudDetected(true);
567: return $this;
568: }
569: if ($result->getResponseReasonCode() == self::RESPONSE_REASON_CODE_PARTIAL_APPROVE) {
570: $checksum = $this->_generateChecksum($request, $this->_partialAuthorizationChecksumDataKeys);
571: $this->_getSession()->setData($this->_partialAuthorizationChecksumSessionKey, $checksum);
572: if ($this->_processPartialAuthorizationResponse($result, $payment)) {
573: return $this;
574: }
575: }
576: Mage::throwException($defaultExceptionMessage);
577: case self::RESPONSE_CODE_DECLINED:
578: case self::RESPONSE_CODE_ERROR:
579: Mage::throwException($this->_wrapGatewayError($result->getResponseReasonText()));
580: default:
581: Mage::throwException($defaultExceptionMessage);
582: }
583: return $this;
584: }
585:
586: 587: 588: 589: 590: 591: 592: 593:
594: protected function _partialAuthorization($payment, $amount, $requestType)
595: {
596: $payment->setAnetTransType($requestType);
597:
598: 599: 600:
601: if ($this->getConfigData('partial_authorization_checksum_checking')) {
602: $payment->setAmount($amount);
603: $firstPlacingRequest= $this->_buildRequest($payment);
604: $newChecksum = $this->_generateChecksum($firstPlacingRequest, $this->_partialAuthorizationChecksumDataKeys);
605: $previosChecksum = $this->_getSession()->getData($this->_partialAuthorizationChecksumSessionKey);
606: if ($newChecksum != $previosChecksum) {
607: $quotePayment = $payment->getOrder()->getQuote()->getPayment();
608: $this->cancelPartialAuthorization($payment);
609: $this->_clearAssignedData($quotePayment);
610: $this->setPartialAuthorizationLastActionState(self::PARTIAL_AUTH_DATA_CHANGED);
611: $quotePayment->setAdditionalInformation($payment->getAdditionalInformation());
612: throw new Mage_Payment_Model_Info_Exception(
613: Mage::helper('paygate')->__('Shopping cart contents and/or address has been changed.')
614: );
615: }
616: }
617:
618: $amount = $amount - $this->getCardsStorage()->getProcessedAmount();
619: if ($amount <= 0) {
620: Mage::throwException(Mage::helper('paygate')->__('Invalid amount for partial authorization.'));
621: }
622: $payment->setAmount($amount);
623: $request = $this->_buildRequest($payment);
624: $result = $this->_postRequest($request);
625: $this->_processPartialAuthorizationResponse($result, $payment);
626:
627: switch ($requestType) {
628: case self::REQUEST_TYPE_AUTH_ONLY:
629: $newTransactionType = Mage_Sales_Model_Order_Payment_Transaction::TYPE_AUTH;
630: break;
631: case self::REQUEST_TYPE_AUTH_CAPTURE:
632: $newTransactionType = Mage_Sales_Model_Order_Payment_Transaction::TYPE_CAPTURE;
633: break;
634: }
635:
636: foreach ($this->getCardsStorage()->getCards() as $card) {
637: $this->_addTransaction(
638: $payment,
639: $card->getLastTransId(),
640: $newTransactionType,
641: array('is_transaction_closed' => 0),
642: array($this->_realTransactionIdKey => $card->getLastTransId()),
643: Mage::helper('paygate')->getTransactionMessage(
644: $payment, $requestType, $card->getLastTransId(), $card, $card->getProcessedAmount()
645: )
646: );
647: if ($requestType == self::REQUEST_TYPE_AUTH_CAPTURE) {
648: $card->setCapturedAmount($card->getProcessedAmount());
649: $this->getCardsStorage()->updateCard($card);
650: }
651: }
652: $this->_getSession()->setData($this->_partialAuthorizationChecksumSessionKey, null);
653: return $this;
654: }
655:
656: 657: 658: 659: 660: 661:
662: protected function _isPreauthorizeCapture($payment)
663: {
664: if ($this->getCardsStorage()->getCardsCount() <= 0) {
665: return false;
666: }
667: foreach($this->getCardsStorage()->getCards() as $card) {
668: $lastTransaction = $payment->getTransaction($card->getLastTransId());
669: if (!$lastTransaction
670: || $lastTransaction->getTxnType() != Mage_Sales_Model_Order_Payment_Transaction::TYPE_AUTH
671: ) {
672: return false;
673: }
674: }
675: return true;
676: }
677:
678: 679: 680: 681: 682: 683: 684:
685: protected function _preauthorizeCapture($payment, $requestedAmount)
686: {
687: $cardsStorage = $this->getCardsStorage($payment);
688:
689: if ($this->_formatAmount(
690: $cardsStorage->getProcessedAmount() - $cardsStorage->getCapturedAmount()
691: ) < $requestedAmount
692: ) {
693: Mage::throwException(Mage::helper('paygate')->__('Invalid amount for capture.'));
694: }
695:
696: $messages = array();
697: $isSuccessful = false;
698: $isFiled = false;
699: foreach($cardsStorage->getCards() as $card) {
700: if ($requestedAmount > 0) {
701: $cardAmountForCapture = $card->getProcessedAmount();
702: if ($cardAmountForCapture > $requestedAmount) {
703: $cardAmountForCapture = $requestedAmount;
704: }
705: try {
706: $newTransaction = $this->_preauthorizeCaptureCardTransaction(
707: $payment, $cardAmountForCapture , $card
708: );
709: $messages[] = $newTransaction->getMessage();
710: $isSuccessful = true;
711: } catch (Exception $e) {
712: $messages[] = $e->getMessage();
713: $isFiled = true;
714: continue;
715: }
716: $card->setCapturedAmount($cardAmountForCapture);
717: $cardsStorage->updateCard($card);
718: $requestedAmount = $this->_formatAmount($requestedAmount - $cardAmountForCapture);
719: } else {
720: 721: 722:
723:
724: }
725: }
726:
727: if ($isFiled) {
728: $this->_processFailureMultitransactionAction($payment, $messages, $isSuccessful);
729: }
730: return $this;
731: }
732:
733: 734: 735: 736: 737: 738: 739: 740:
741: protected function _preauthorizeCaptureCardTransaction($payment, $amount, $card)
742: {
743: $authTransactionId = $card->getLastTransId();
744: $authTransaction = $payment->getTransaction($authTransactionId);
745: $realAuthTransactionId = $authTransaction->getAdditionalInformation($this->_realTransactionIdKey);
746:
747: $payment->setAnetTransType(self::REQUEST_TYPE_PRIOR_AUTH_CAPTURE);
748: $payment->setXTransId($realAuthTransactionId);
749: $payment->setAmount($amount);
750:
751: $request= $this->_buildRequest($payment);
752: $result = $this->_postRequest($request);
753:
754: switch ($result->getResponseCode()) {
755: case self::RESPONSE_CODE_APPROVED:
756: if ($result->getResponseReasonCode() == self::RESPONSE_REASON_CODE_APPROVED) {
757: $captureTransactionId = $result->getTransactionId() . '-capture';
758: $card->setLastTransId($captureTransactionId);
759: return $this->_addTransaction(
760: $payment,
761: $captureTransactionId,
762: Mage_Sales_Model_Order_Payment_Transaction::TYPE_CAPTURE,
763: array(
764: 'is_transaction_closed' => 0,
765: 'parent_transaction_id' => $authTransactionId
766: ),
767: array($this->_realTransactionIdKey => $result->getTransactionId()),
768: Mage::helper('paygate')->getTransactionMessage(
769: $payment, self::REQUEST_TYPE_PRIOR_AUTH_CAPTURE, $result->getTransactionId(), $card, $amount
770: )
771: );
772: }
773: $exceptionMessage = $this->_wrapGatewayError($result->getResponseReasonText());
774: break;
775: case self::RESPONSE_CODE_HELD:
776: case self::RESPONSE_CODE_DECLINED:
777: case self::RESPONSE_CODE_ERROR:
778: $exceptionMessage = $this->_wrapGatewayError($result->getResponseReasonText());
779: break;
780: default:
781: $exceptionMessage = Mage::helper('paygate')->__('Payment capturing error.');
782: break;
783: }
784:
785: $exceptionMessage = Mage::helper('paygate')->getTransactionMessage(
786: $payment, self::REQUEST_TYPE_PRIOR_AUTH_CAPTURE, $realAuthTransactionId, $card, $amount, $exceptionMessage
787: );
788: Mage::throwException($exceptionMessage);
789: }
790:
791: 792: 793: 794: 795: 796: 797:
798: protected function _voidCardTransaction($payment, $card)
799: {
800: $authTransactionId = $card->getLastTransId();
801: $authTransaction = $payment->getTransaction($authTransactionId);
802: $realAuthTransactionId = $authTransaction->getAdditionalInformation($this->_realTransactionIdKey);
803:
804: $payment->setAnetTransType(self::REQUEST_TYPE_VOID);
805: $payment->setXTransId($realAuthTransactionId);
806:
807: $request= $this->_buildRequest($payment);
808: $result = $this->_postRequest($request);
809:
810: switch ($result->getResponseCode()) {
811: case self::RESPONSE_CODE_APPROVED:
812: if ($result->getResponseReasonCode() == self::RESPONSE_REASON_CODE_APPROVED) {
813: $voidTransactionId = $result->getTransactionId() . '-void';
814: $card->setLastTransId($voidTransactionId);
815: return $this->_addTransaction(
816: $payment,
817: $voidTransactionId,
818: Mage_Sales_Model_Order_Payment_Transaction::TYPE_VOID,
819: array(
820: 'is_transaction_closed' => 1,
821: 'should_close_parent_transaction' => 1,
822: 'parent_transaction_id' => $authTransactionId
823: ),
824: array($this->_realTransactionIdKey => $result->getTransactionId()),
825: Mage::helper('paygate')->getTransactionMessage(
826: $payment, self::REQUEST_TYPE_VOID, $result->getTransactionId(), $card
827: )
828: );
829: }
830: $exceptionMessage = $this->_wrapGatewayError($result->getResponseReasonText());
831: break;
832: case self::RESPONSE_CODE_DECLINED:
833: case self::RESPONSE_CODE_ERROR:
834: if ($result->getResponseReasonCode() == self::RESPONSE_REASON_CODE_NOT_FOUND
835: && $this->_isTransactionExpired($realAuthTransactionId)
836: ) {
837: $voidTransactionId = $realAuthTransactionId . '-void';
838: return $this->_addTransaction(
839: $payment,
840: $voidTransactionId,
841: Mage_Sales_Model_Order_Payment_Transaction::TYPE_VOID,
842: array(
843: 'is_transaction_closed' => 1,
844: 'should_close_parent_transaction' => 1,
845: 'parent_transaction_id' => $authTransactionId
846: ),
847: array(),
848: Mage::helper('paygate')->getExtendedTransactionMessage(
849: $payment,
850: self::REQUEST_TYPE_VOID,
851: null,
852: $card,
853: false,
854: false,
855: Mage::helper('paygate')->__(
856: 'Parent Authorize.Net transaction (ID %s) expired',
857: $realAuthTransactionId
858: )
859: )
860: );
861: }
862: $exceptionMessage = $this->_wrapGatewayError($result->getResponseReasonText());
863: break;
864: default:
865: $exceptionMessage = Mage::helper('paygate')->__('Payment voiding error.');
866: break;
867: }
868:
869: $exceptionMessage = Mage::helper('paygate')->getTransactionMessage(
870: $payment, self::REQUEST_TYPE_VOID, $realAuthTransactionId, $card, false, $exceptionMessage
871: );
872: Mage::throwException($exceptionMessage);
873: }
874:
875: 876: 877: 878: 879: 880:
881: protected function _isTransactionExpired($realAuthTransactionId)
882: {
883: $transactionDetails = $this->_getTransactionDetails($realAuthTransactionId);
884: return $transactionDetails->getTransactionStatus() == self::TRANSACTION_STATUS_EXPIRED;
885: }
886:
887: 888: 889: 890: 891: 892: 893:
894: protected function _refundCardTransaction($payment, $amount, $card)
895: {
896: 897: 898: 899:
900: $captureTransactionId = $card->getLastTransId();
901: $captureTransaction = $payment->getTransaction($captureTransactionId);
902: $realCaptureTransactionId = $captureTransaction->getAdditionalInformation($this->_realTransactionIdKey);
903:
904: $payment->setAnetTransType(self::REQUEST_TYPE_CREDIT);
905: $payment->setXTransId($realCaptureTransactionId);
906: $payment->setAmount($amount);
907:
908: $request = $this->_buildRequest($payment);
909: $request->setXCardNum($card->getCcLast4());
910: $result = $this->_postRequest($request);
911:
912: switch ($result->getResponseCode()) {
913: case self::RESPONSE_CODE_APPROVED:
914: if ($result->getResponseReasonCode() == self::RESPONSE_REASON_CODE_APPROVED) {
915: $refundTransactionId = $result->getTransactionId() . '-refund';
916: $shouldCloseCaptureTransaction = 0;
917: 918: 919: 920:
921: if ($this->_formatAmount($card->getCapturedAmount() - $card->getRefundedAmount()) == $amount) {
922: $card->setLastTransId($refundTransactionId);
923: $shouldCloseCaptureTransaction = 1;
924: }
925: return $this->_addTransaction(
926: $payment,
927: $refundTransactionId,
928: Mage_Sales_Model_Order_Payment_Transaction::TYPE_REFUND,
929: array(
930: 'is_transaction_closed' => 1,
931: 'should_close_parent_transaction' => $shouldCloseCaptureTransaction,
932: 'parent_transaction_id' => $captureTransactionId
933: ),
934: array($this->_realTransactionIdKey => $result->getTransactionId()),
935: Mage::helper('paygate')->getTransactionMessage(
936: $payment, self::REQUEST_TYPE_CREDIT, $result->getTransactionId(), $card, $amount
937: )
938: );
939: }
940: $exceptionMessage = $this->_wrapGatewayError($result->getResponseReasonText());
941: break;
942: case self::RESPONSE_CODE_DECLINED:
943: case self::RESPONSE_CODE_ERROR:
944: $exceptionMessage = $this->_wrapGatewayError($result->getResponseReasonText());
945: break;
946: default:
947: $exceptionMessage = Mage::helper('paygate')->__('Payment refunding error.');
948: break;
949: }
950:
951: $exceptionMessage = Mage::helper('paygate')->getTransactionMessage(
952: $payment, self::REQUEST_TYPE_CREDIT, $realCaptureTransactionId, $card, $amount, $exceptionMessage
953: );
954: Mage::throwException($exceptionMessage);
955: }
956:
957: 958: 959: 960: 961:
962: protected function _initCardsStorage($payment)
963: {
964: $this->_cardsStorage = Mage::getModel('paygate/authorizenet_cards')->setPayment($payment);
965: }
966:
967: 968: 969: 970: 971: 972:
973: public function getCardsStorage($payment = null)
974: {
975: if (is_null($payment)) {
976: $payment = $this->getInfoInstance();
977: }
978: if (is_null($this->_cardsStorage)) {
979: $this->_initCardsStorage($payment);
980: }
981: return $this->_cardsStorage;
982: }
983:
984: 985: 986: 987: 988: 989:
990: public function isPartialAuthorization($payment = null)
991: {
992: if (is_null($payment)) {
993: $payment = $this->getInfoInstance();
994: }
995: return $payment->getAdditionalInformation($this->_splitTenderIdKey);
996: }
997:
998: 999: 1000: 1001: 1002: 1003: 1004:
1005: public function processInvoice($invoice, $payment)
1006: {
1007: $invoice->setTransactionId(1);
1008: return $this;
1009: }
1010:
1011: 1012: 1013: 1014: 1015: 1016:
1017: public function processCreditmemo($creditmemo, $payment)
1018: {
1019: $creditmemo->setTransactionId(1);
1020: return $this;
1021: }
1022:
1023: 1024: 1025: 1026: 1027: 1028: 1029: 1030: 1031:
1032: public function fetchTransactionInfo(Mage_Payment_Model_Info $payment, $transactionId)
1033: {
1034: $cardsStorage = $this->getCardsStorage($payment);
1035: if ($cardsStorage->getCardsCount() != 1) {
1036: return parent::fetchTransactionInfo($payment, $transactionId);
1037: }
1038: $cards = $cardsStorage->getCards();
1039: $card = array_shift($cards);
1040: $transactionId = $card->getLastTransId();
1041: $transaction = $payment->getTransaction($transactionId);
1042:
1043: if (!$transaction->getAdditionalInformation($this->_isTransactionFraud)) {
1044: return parent::fetchTransactionInfo($payment, $transactionId);
1045: }
1046:
1047: $response = $this->_getTransactionDetails($transactionId);
1048: if ($response->getResponseCode() == self::RESPONSE_CODE_APPROVED) {
1049: $transaction->setAdditionalInformation($this->_isTransactionFraud, false);
1050: $payment->setIsTransactionApproved(true);
1051: } elseif ($response->getResponseReasonCode() == self::RESPONSE_REASON_CODE_PENDING_REVIEW_DECLINED) {
1052: $payment->setIsTransactionDenied(true);
1053: }
1054: return parent::fetchTransactionInfo($payment, $transactionId);
1055: }
1056:
1057: 1058: 1059: 1060: 1061: 1062: 1063:
1064: protected function _processPartialAuthorizationResponse($response, $orderPayment) {
1065: if (!$response->getSplitTenderId()) {
1066: return false;
1067: }
1068:
1069: $quotePayment = $orderPayment->getOrder()->getQuote()->getPayment();
1070: $this->setPartialAuthorizationLastActionState(self::PARTIAL_AUTH_LAST_DECLINED);
1071: $exceptionMessage = null;
1072:
1073: try {
1074: switch ($response->getResponseCode()) {
1075: case self::RESPONSE_CODE_APPROVED:
1076: $this->_registerCard($response, $orderPayment);
1077: $this->_clearAssignedData($quotePayment);
1078: $this->setPartialAuthorizationLastActionState(self::PARTIAL_AUTH_LAST_SUCCESS);
1079: return true;
1080: case self::RESPONSE_CODE_HELD:
1081: if ($response->getResponseReasonCode() != self::RESPONSE_REASON_CODE_PARTIAL_APPROVE) {
1082: return false;
1083: }
1084: if ($this->getCardsStorage($orderPayment)->getCardsCount() + 1 >= self::PARTIAL_AUTH_CARDS_LIMIT) {
1085: $this->cancelPartialAuthorization($orderPayment);
1086: $this->_clearAssignedData($quotePayment);
1087: $this->setPartialAuthorizationLastActionState(self::PARTIAL_AUTH_CARDS_LIMIT_EXCEEDED);
1088: $quotePayment->setAdditionalInformation($orderPayment->getAdditionalInformation());
1089: $exceptionMessage = Mage::helper('paygate')->__('You have reached the maximum number of credit card allowed to be used for the payment.');
1090: break;
1091: }
1092: $orderPayment->setAdditionalInformation($this->_splitTenderIdKey, $response->getSplitTenderId());
1093: $this->_registerCard($response, $orderPayment);
1094: $this->_clearAssignedData($quotePayment);
1095: $this->setPartialAuthorizationLastActionState(self::PARTIAL_AUTH_LAST_SUCCESS);
1096: $quotePayment->setAdditionalInformation($orderPayment->getAdditionalInformation());
1097: $exceptionMessage = null;
1098: break;
1099: case self::RESPONSE_CODE_DECLINED:
1100: case self::RESPONSE_CODE_ERROR:
1101: $this->setPartialAuthorizationLastActionState(self::PARTIAL_AUTH_LAST_DECLINED);
1102: $quotePayment->setAdditionalInformation($orderPayment->getAdditionalInformation());
1103: $exceptionMessage = $this->_wrapGatewayError($response->getResponseReasonText());
1104: break;
1105: default:
1106: $this->setPartialAuthorizationLastActionState(self::PARTIAL_AUTH_LAST_DECLINED);
1107: $quotePayment->setAdditionalInformation($orderPayment->getAdditionalInformation());
1108: $exceptionMessage = $this->_wrapGatewayError(
1109: Mage::helper('paygate')->__('Payment partial authorization error.')
1110: );
1111: }
1112: } catch (Exception $e) {
1113: $exceptionMessage = $e->getMessage();
1114: }
1115:
1116: throw new Mage_Payment_Model_Info_Exception($exceptionMessage);
1117: }
1118:
1119: 1120: 1121: 1122: 1123:
1124: protected function _getRequest()
1125: {
1126: $request = Mage::getModel('paygate/authorizenet_request')
1127: ->setXVersion(3.1)
1128: ->setXDelimData('True')
1129: ->setXRelayResponse('False')
1130: ->setXTestRequest($this->getConfigData('test') ? 'TRUE' : 'FALSE')
1131: ->setXLogin($this->getConfigData('login'))
1132: ->setXTranKey($this->getConfigData('trans_key'));
1133:
1134: return $request;
1135: }
1136:
1137: 1138: 1139: 1140: 1141: 1142: 1143:
1144: protected function _buildRequest(Varien_Object $payment)
1145: {
1146: $order = $payment->getOrder();
1147:
1148: $this->setStore($order->getStoreId());
1149:
1150: $request = $this->_getRequest()
1151: ->setXType($payment->getAnetTransType())
1152: ->setXMethod(self::REQUEST_METHOD_CC);
1153:
1154: if ($order && $order->getIncrementId()) {
1155: $request->setXInvoiceNum($order->getIncrementId());
1156: }
1157:
1158: if($payment->getAmount()){
1159: $request->setXAmount($payment->getAmount(),2);
1160: $request->setXCurrencyCode($order->getBaseCurrencyCode());
1161: }
1162:
1163: switch ($payment->getAnetTransType()) {
1164: case self::REQUEST_TYPE_AUTH_CAPTURE:
1165: $request->setXAllowPartialAuth($this->getConfigData('allow_partial_authorization') ? 'True' : 'False');
1166: if ($payment->getAdditionalInformation($this->_splitTenderIdKey)) {
1167: $request->setXSplitTenderId($payment->getAdditionalInformation($this->_splitTenderIdKey));
1168: }
1169: break;
1170: case self::REQUEST_TYPE_AUTH_ONLY:
1171: $request->setXAllowPartialAuth($this->getConfigData('allow_partial_authorization') ? 'True' : 'False');
1172: if ($payment->getAdditionalInformation($this->_splitTenderIdKey)) {
1173: $request->setXSplitTenderId($payment->getAdditionalInformation($this->_splitTenderIdKey));
1174: }
1175: break;
1176: case self::REQUEST_TYPE_CREDIT:
1177: 1178: 1179: 1180:
1181: $request->setXCardNum($payment->getCcLast4());
1182: $request->setXTransId($payment->getXTransId());
1183: break;
1184: case self::REQUEST_TYPE_VOID:
1185: $request->setXTransId($payment->getXTransId());
1186: break;
1187: case self::REQUEST_TYPE_PRIOR_AUTH_CAPTURE:
1188: $request->setXTransId($payment->getXTransId());
1189: break;
1190: case self::REQUEST_TYPE_CAPTURE_ONLY:
1191: $request->setXAuthCode($payment->getCcAuthCode());
1192: break;
1193: }
1194:
1195: if ($this->getIsCentinelValidationEnabled()){
1196: $params = $this->getCentinelValidator()->exportCmpiData(array());
1197: $request = Varien_Object_Mapper::accumulateByMap($params, $request, $this->_centinelFieldMap);
1198: }
1199:
1200: if (!empty($order)) {
1201: $billing = $order->getBillingAddress();
1202: if (!empty($billing)) {
1203: $request->setXFirstName($billing->getFirstname())
1204: ->setXLastName($billing->getLastname())
1205: ->setXCompany($billing->getCompany())
1206: ->setXAddress($billing->getStreet(1))
1207: ->setXCity($billing->getCity())
1208: ->setXState($billing->getRegion())
1209: ->setXZip($billing->getPostcode())
1210: ->setXCountry($billing->getCountry())
1211: ->setXPhone($billing->getTelephone())
1212: ->setXFax($billing->getFax())
1213: ->setXCustId($order->getCustomerId())
1214: ->setXCustomerIp($order->getRemoteIp())
1215: ->setXCustomerTaxId($billing->getTaxId())
1216: ->setXEmail($order->getCustomerEmail())
1217: ->setXEmailCustomer($this->getConfigData('email_customer'))
1218: ->setXMerchantEmail($this->getConfigData('merchant_email'));
1219: }
1220:
1221: $shipping = $order->getShippingAddress();
1222: if (!empty($shipping)) {
1223: $request->setXShipToFirstName($shipping->getFirstname())
1224: ->setXShipToLastName($shipping->getLastname())
1225: ->setXShipToCompany($shipping->getCompany())
1226: ->setXShipToAddress($shipping->getStreet(1))
1227: ->setXShipToCity($shipping->getCity())
1228: ->setXShipToState($shipping->getRegion())
1229: ->setXShipToZip($shipping->getPostcode())
1230: ->setXShipToCountry($shipping->getCountry());
1231: }
1232:
1233: $request->setXPoNum($payment->getPoNumber())
1234: ->setXTax($order->getBaseTaxAmount())
1235: ->setXFreight($order->getBaseShippingAmount());
1236: }
1237:
1238: if($payment->getCcNumber()){
1239: $request->setXCardNum($payment->getCcNumber())
1240: ->setXExpDate(sprintf('%02d-%04d', $payment->getCcExpMonth(), $payment->getCcExpYear()))
1241: ->setXCardCode($payment->getCcCid());
1242: }
1243:
1244: return $request;
1245: }
1246:
1247: 1248: 1249: 1250: 1251: 1252:
1253: protected function _postRequest(Varien_Object $request)
1254: {
1255: $debugData = array('request' => $request->getData());
1256:
1257: $result = Mage::getModel('paygate/authorizenet_result');
1258:
1259: $client = new Varien_Http_Client();
1260:
1261: $uri = $this->getConfigData('cgi_url');
1262: $client->setUri($uri ? $uri : self::CGI_URL);
1263: $client->setConfig(array(
1264: 'maxredirects'=>0,
1265: 'timeout'=>30,
1266:
1267: ));
1268: foreach ($request->getData() as $key => $value) {
1269: $request->setData($key, str_replace(self::RESPONSE_DELIM_CHAR, '', $value));
1270: }
1271: $request->setXDelimChar(self::RESPONSE_DELIM_CHAR);
1272:
1273: $client->setParameterPost($request->getData());
1274: $client->setMethod(Zend_Http_Client::POST);
1275:
1276: try {
1277: $response = $client->request();
1278: } catch (Exception $e) {
1279: $result->setResponseCode(-1)
1280: ->setResponseReasonCode($e->getCode())
1281: ->setResponseReasonText($e->getMessage());
1282:
1283: $debugData['result'] = $result->getData();
1284: $this->_debug($debugData);
1285: Mage::throwException($this->_wrapGatewayError($e->getMessage()));
1286: }
1287:
1288: $responseBody = $response->getBody();
1289:
1290: $r = explode(self::RESPONSE_DELIM_CHAR, $responseBody);
1291:
1292: if ($r) {
1293: $result->setResponseCode((int)str_replace('"','',$r[0]))
1294: ->setResponseSubcode((int)str_replace('"','',$r[1]))
1295: ->setResponseReasonCode((int)str_replace('"','',$r[2]))
1296: ->setResponseReasonText($r[3])
1297: ->setApprovalCode($r[4])
1298: ->setAvsResultCode($r[5])
1299: ->setTransactionId($r[6])
1300: ->setInvoiceNumber($r[7])
1301: ->setDescription($r[8])
1302: ->setAmount($r[9])
1303: ->setMethod($r[10])
1304: ->setTransactionType($r[11])
1305: ->setCustomerId($r[12])
1306: ->setMd5Hash($r[37])
1307: ->setCardCodeResponseCode($r[38])
1308: ->setCAVVResponseCode( (isset($r[39])) ? $r[39] : null)
1309: ->setSplitTenderId($r[52])
1310: ->setAccNumber($r[50])
1311: ->setCardType($r[51])
1312: ->setRequestedAmount($r[53])
1313: ->setBalanceOnCard($r[54])
1314: ;
1315: }
1316: else {
1317: Mage::throwException(
1318: Mage::helper('paygate')->__('Error in payment gateway.')
1319: );
1320: }
1321:
1322: $debugData['result'] = $result->getData();
1323: $this->_debug($debugData);
1324:
1325: return $result;
1326: }
1327:
1328: 1329: 1330: 1331: 1332: 1333:
1334: protected function _wrapGatewayError($text)
1335: {
1336: return Mage::helper('paygate')->__('Gateway error: %s', $text);
1337: }
1338:
1339: 1340: 1341: 1342: 1343:
1344: protected function _getSession()
1345: {
1346: if (Mage::app()->getStore()->isAdmin()) {
1347: return Mage::getSingleton('adminhtml/session_quote');
1348: } else {
1349: return Mage::getSingleton('checkout/session');
1350: }
1351: }
1352:
1353: 1354: 1355: 1356: 1357: 1358: 1359:
1360: protected function _registerCard(Varien_Object $response, Mage_Sales_Model_Order_Payment $payment)
1361: {
1362: $cardsStorage = $this->getCardsStorage($payment);
1363: $card = $cardsStorage->registerCard();
1364: $card
1365: ->setRequestedAmount($response->getRequestedAmount())
1366: ->setBalanceOnCard($response->getBalanceOnCard())
1367: ->setLastTransId($response->getTransactionId())
1368: ->setProcessedAmount($response->getAmount())
1369: ->setCcType($payment->getCcType())
1370: ->setCcOwner($payment->getCcOwner())
1371: ->setCcLast4($payment->getCcLast4())
1372: ->setCcExpMonth($payment->getCcExpMonth())
1373: ->setCcExpYear($payment->getCcExpYear())
1374: ->setCcSsIssue($payment->getCcSsIssue())
1375: ->setCcSsStartMonth($payment->getCcSsStartMonth())
1376: ->setCcSsStartYear($payment->getCcSsStartYear());
1377:
1378: $cardsStorage->updateCard($card);
1379: $this->_clearAssignedData($payment);
1380: return $card;
1381: }
1382:
1383: 1384: 1385: 1386: 1387: 1388:
1389: private function _clearAssignedData($payment)
1390: {
1391: $payment->setCcType(null)
1392: ->setCcOwner(null)
1393: ->setCcLast4(null)
1394: ->setCcNumber(null)
1395: ->setCcCid(null)
1396: ->setCcExpMonth(null)
1397: ->setCcExpYear(null)
1398: ->setCcSsIssue(null)
1399: ->setCcSsStartMonth(null)
1400: ->setCcSsStartYear(null)
1401: ;
1402: return $this;
1403: }
1404:
1405: 1406: 1407: 1408: 1409: 1410: 1411: 1412: 1413: 1414:
1415: protected function _addTransaction(Mage_Sales_Model_Order_Payment $payment, $transactionId, $transactionType,
1416: array $transactionDetails = array(), array $transactionAdditionalInfo = array(), $message = false
1417: ) {
1418: $payment->setTransactionId($transactionId);
1419: $payment->resetTransactionAdditionalInfo();
1420: foreach ($transactionDetails as $key => $value) {
1421: $payment->setData($key, $value);
1422: }
1423: foreach ($transactionAdditionalInfo as $key => $value) {
1424: $payment->setTransactionAdditionalInfo($key, $value);
1425: }
1426: $transaction = $payment->addTransaction($transactionType, null, false , $message);
1427: foreach ($transactionDetails as $key => $value) {
1428: $payment->unsetData($key);
1429: }
1430: $payment->unsLastTransId();
1431:
1432: 1433: 1434:
1435: $transaction->setMessage($message);
1436:
1437: return $transaction;
1438: }
1439:
1440: 1441: 1442: 1443: 1444: 1445: 1446:
1447: protected function _formatAmount($amount, $asFloat = false)
1448: {
1449: $amount = sprintf('%.2F', $amount);
1450: return $asFloat ? (float)$amount : $amount;
1451: }
1452:
1453: 1454: 1455: 1456: 1457: 1458:
1459: protected function _isGatewayActionsLocked($payment)
1460: {
1461: return $payment->getAdditionalInformation($this->_isGatewayActionsLockedKey);
1462: }
1463:
1464: 1465: 1466: 1467: 1468: 1469: 1470:
1471: protected function _processFailureMultitransactionAction($payment, $messages, $isSuccessfulTransactions)
1472: {
1473: if ($isSuccessfulTransactions) {
1474: $messages[] = Mage::helper('paygate')->__('Gateway actions are locked because the gateway cannot complete one or more of the transactions. Please log in to your Authorize.Net account to manually resolve the issue(s).');
1475: 1476: 1477: 1478: 1479: 1480:
1481: $currentOrderId = $payment->getOrder()->getId();
1482: $copyOrder = Mage::getModel('sales/order')->load($currentOrderId);
1483: $copyOrder->getPayment()->setAdditionalInformation($this->_isGatewayActionsLockedKey, 1);
1484: foreach($messages as $message) {
1485: $copyOrder->addStatusHistoryComment($message);
1486: }
1487: $copyOrder->save();
1488: }
1489: Mage::throwException(Mage::helper('paygate')->convertMessagesToMessage($messages));
1490: }
1491:
1492: 1493: 1494: 1495: 1496: 1497: 1498:
1499: protected function _generateChecksum(Varien_Object $object, $checkSumDataKeys = array())
1500: {
1501: $data = array();
1502: foreach($checkSumDataKeys as $dataKey) {
1503: $data[] = $dataKey;
1504: $data[] = $object->getData($dataKey);
1505: }
1506: return md5(implode($data, '_'));
1507: }
1508:
1509: 1510: 1511: 1512: 1513: 1514: 1515: 1516:
1517: protected function _getTransactionDetails($transactionId)
1518: {
1519: $requestBody = sprintf(
1520: '<?xml version="1.0" encoding="utf-8"?>'
1521: . '<getTransactionDetailsRequest xmlns="AnetApi/xml/v1/schema/AnetApiSchema.xsd">'
1522: . '<merchantAuthentication><name>%s</name><transactionKey>%s</transactionKey></merchantAuthentication>'
1523: . '<transId>%s</transId>'
1524: . '</getTransactionDetailsRequest>',
1525: $this->getConfigData('login'),
1526: $this->getConfigData('trans_key'),
1527: $transactionId
1528: );
1529:
1530: $client = new Varien_Http_Client();
1531: $uri = $this->getConfigData('cgi_url_td');
1532: $client->setUri($uri ? $uri : self::CGI_URL_TD);
1533: $client->setConfig(array('timeout'=>45));
1534: $client->setHeaders(array('Content-Type: text/xml'));
1535: $client->setMethod(Zend_Http_Client::POST);
1536: $client->setRawData($requestBody);
1537:
1538: $debugData = array('request' => $requestBody);
1539:
1540: try {
1541: $responseBody = $client->request()->getBody();
1542: $debugData['result'] = $responseBody;
1543: $this->_debug($debugData);
1544: libxml_use_internal_errors(true);
1545: $responseXmlDocument = new Varien_Simplexml_Element($responseBody);
1546: libxml_use_internal_errors(false);
1547: } catch (Exception $e) {
1548: Mage::throwException(Mage::helper('paygate')->__('Payment updating error.'));
1549: }
1550:
1551: $response = new Varien_Object;
1552: $response
1553: ->setResponseCode((string)$responseXmlDocument->transaction->responseCode)
1554: ->setResponseReasonCode((string)$responseXmlDocument->transaction->responseReasonCode)
1555: ->setTransactionStatus((string)$responseXmlDocument->transaction->transactionStatus)
1556: ;
1557: return $response;
1558: }
1559: }
1560: