/**
  * callApi is the major piece in the puzzle
  *
  * prepares information and call specific xml api
  *
  * @param object $payment Payment Object
  * @param int $amount Amount to charge
  * @param string $type either CIM or AIM
  * @param int $ccSaveId Used to determine whether or not a profile exists for the customer
  * @param int $tokenProfileId Checks if the payment profile already exists, if not, creates it
  */
 public function callApi(Varien_Object $payment, $amount, $type)
 {
     /**
      * =====================================================================
      * BEGIN AAI HACK
      *
      * Cleaned up so it would be a little easier to understand
      * =====================================================================
      */
     $order = $payment->getOrder();
     $orderId = $order->getIncrementId();
     $postData = Mage::app()->getRequest()->getPost('payment', array());
     $ccSaveId = array_key_exists('ccsave_id', $postData) ? $postData['ccsave_id'] : null;
     if ($type != 'authorizeandcaptureAIM') {
         $customerID = $order->getCustomerId();
         // for Guests, set the customerId to the Order's increment_id
         if (!$customerID) {
             $customerID = $orderId;
         }
         // order values
         $customerEmail = $order->getCustomerEmail();
         $billingInfo = $order->getBillingAddress();
         $shippingInfo = $order->getShippingAddress();
         // payment values
         $ccType = $payment->getCcType();
         $ccNumber = $payment->getCcNumber();
         $ccExpDate = $payment->getCcExpYear() . '-' . str_pad($payment->getCcExpMonth(), 2, '0', STR_PAD_LEFT);
         $ccCCV = $payment->getCcCid();
         // CIM token values
         $tokenProfileId = $payment->getTokenProfileId();
         $tokenPaymentProfileId = $payment->getTokenPaymentProfileId();
         if ($tokenProfileId == 0 && $tokenPaymentProfileId == 0 && in_array($type, array('authorize', 'capture', 'authorizeandcapture'))) {
             if (!is_null($ccSaveId)) {
                 $profile = $this->getAuthnetcimCardProfileById($ccSaveId);
                 $profileData = $profile->getData();
                 $tokenProfileId = $profileData['token_profile_id'];
                 $tokenPaymentProfileId = $profileData['token_payment_profile_id'];
             } else {
                 $profileCollection = $this->getAuthnetcimCardProfilesByCustomerId($customerID);
                 if (count($profileCollection) === 0) {
                     // Create new customer profile
                     $responseXML = $this->createCustomerProfileRequest($customerID, $customerEmail, $billingInfo, $shippingInfo, $ccNumber, $ccExpDate, $ccCCV, $ccType);
                     $tokenProfileId = $responseXML->customerProfileId;
                     $tokenPaymentProfileId = $responseXML->customerPaymentProfileIdList->numericString;
                 } else {
                     $tokenProfileId = $profileCollection->getFirstItem()->getTokenProfileId();
                     $tokenPaymentProfileId = null;
                     $ccLast4 = substr($ccNumber, -4, 4);
                     foreach ($profileCollection as $profile) {
                         if ($profile->getData("cc_last4") == $ccLast4) {
                             $tokenPaymentProfileId = $profile->getData("token_payment_profile_id");
                         }
                     }
                     if (is_null($tokenPaymentProfileId)) {
                         $tokenPaymentProfileId = $this->createCustomerPaymentProfileRequest($customerID, $tokenProfileId, $billingInfo, $ccNumber, $ccExpDate, $ccCCV, $ccType);
                     }
                 }
             }
         }
     }
     /**
      * =====================================================================
      * END AAI HACK
      *
      * Cleaned up so it would be a little easier to understand
      * =====================================================================
      */
     // call xml creation functions
     switch ($type) {
         case 'authorize':
             $payment->setTokenProfileId($tokenProfileId);
             $payment->setTokenPaymentProfileId($tokenPaymentProfileId);
             $response = $this->createAuthorize($amount, $tokenProfileId, $tokenPaymentProfileId, $orderId, $ccCCV);
             break;
         case 'capture':
             $teoAuths = Mage::getModel('authorizenetcim/teoauths');
             $authsCollection = $teoAuths->getCollection()->addFieldToFilter('order_id', $orderId);
             if (count($authsCollection) > 1) {
                 $amountLeftToCapture = $amount;
                 foreach ($authsCollection as $auths) {
                     $teoAuths->load($auths->getId());
                     $teoAuthAmount = $teoAuths->getAuthorizationAmount();
                     $teoAuthAmountPaid = $teoAuths->getAmountPaid();
                     if ($amountLeftToCapture > 0) {
                         $amountLeftOnAuth = $teoAuthAmount - $teoAuthAmountPaid;
                         $authorizeTransactionId = $teoAuths->getAuthorizationNumber();
                         if ($amountLeftToCapture > $amountLeftOnAuth) {
                             $response = $this->createCapture($amountLeftOnAuth, $tokenProfileId, $tokenPaymentProfileId, $authorizeTransactionId);
                             $teoAuths->setAmountPaid($amountLeftOnAuth);
                             $teoAuths->save();
                             $amountLeftToCapture = $amountLeftToCapture - $amountLeftOnAuth;
                         } else {
                             $response = $this->createCapture($amountLeftToCapture, $tokenProfileId, $tokenPaymentProfileId, $authorizeTransactionId);
                             $teoAuths->setAmountPaid($amountLeftToCapture);
                             $teoAuths->save();
                             $amountLeftToCapture = 0;
                         }
                     }
                 }
             } else {
                 //get authorize transaction id for capture
                 $authorizeTransactionId = $payment->getCcTransId();
                 $response = $this->createCapture($amount, $tokenProfileId, $tokenPaymentProfileId, $authorizeTransactionId);
             }
             break;
             /**
              * =================================================================
              * BEGIN AAI HACK
              *
              * ADD SPECIFIC METHOD FOR PARTIAL AUTH/CAPTURE(S)
              * =================================================================
              */
         /**
          * =================================================================
          * BEGIN AAI HACK
          *
          * ADD SPECIFIC METHOD FOR PARTIAL AUTH/CAPTURE(S)
          * =================================================================
          */
         case 'partialcapture':
             $teoAuth = $this->getTeoAuthorizationByOrderId($orderId);
             $transId = $teoAuth->getData('authorization_number');
             // Generate the XML for the API request and make a call to the API for a response
             $response = $this->createPartialCapture($amount, $tokenProfileId, $tokenPaymentProfileId, $transId, $order);
             break;
             /**
              * =================================================================
              * END AAI HACK
              *
              * ADD SPECIFIC METHOD FOR PARTIAL AUTH/CAPTURE(S)
              * =================================================================
              */
         /**
          * =================================================================
          * END AAI HACK
          *
          * ADD SPECIFIC METHOD FOR PARTIAL AUTH/CAPTURE(S)
          * =================================================================
          */
         case 'authorizeandcapture':
             $payment->setTokenProfileId($tokenProfileId);
             $payment->setTokenPaymentProfileId($tokenPaymentProfileId);
             $response = $this->createAuthorizeCapture($amount, $tokenProfileId, $tokenPaymentProfileId, $orderId, $ccCCV);
             break;
         case 'void':
             $refundTransactionId = $payment->getRefundTransactionId();
             $response = $this->createVoid($tokenProfileId, $tokenPaymentProfileId, $refundTransactionId);
             break;
         case 'refund':
             $teoAuths = Mage::getModel('authorizenetcim/teoauths');
             $authsCollection = $teoAuths->getCollection()->addFieldToFilter('order_id', $orderId);
             if (count($authsCollection) > 1) {
                 $amountLeftToRefund = $amount;
                 foreach ($authsCollection as $auths) {
                     $teoAuths->load($auths->getId());
                     $teoAuthAmount = $teoAuths->getAuthorizationAmount();
                     $teoAuthAmountRefunded = $teoAuths->getAmountRefunded();
                     if ($amountLeftToRefund > 0) {
                         $amountLeftOnAuth = $teoAuthAmount - $teoAuthAmountRefunded;
                         $authorizeTransactionId = $teoAuths->getAuthorizationNumber();
                         if ($amountLeftToRefund > $amountLeftOnAuth) {
                             $response = $this->createRefund($amountLeftOnAuth, $tokenProfileId, $tokenPaymentProfileId, $authorizeTransactionId);
                             $teoAuths->setAmountRefunded($amountLeftOnAuth);
                             $teoAuths->save();
                             $amountLeftToRefund = $amountLeftToRefund - $amountLeftOnAuth;
                         } else {
                             $response = $this->createRefund($amountLeftToRefund, $tokenProfileId, $tokenPaymentProfileId, $authorizeTransactionId);
                             $teoAuths->setAmountRefunded($amountLeftToRefund);
                             $teoAuths->save();
                             $amountLeftToRefund = 0;
                         }
                     }
                 }
             } else {
                 $refundTransactionId = $payment->getRefundTransactionId();
                 $response = $this->createRefund($amount, $tokenProfileId, $tokenPaymentProfileId, $refundTransactionId);
             }
             break;
         case 'authorizeandcaptureAIM':
             $response = $this->createAuthorizeCaptureAIM($amount, $payment, $order);
             break;
         case 'captureAIM':
             $response = $this->captureAIM($tokenProfileId);
             break;
             /**
              * AAI HACK
              *
              * clone of 'captureAIM' but adds an amount to be captured
              * instead of assuming that the full amount will be captured
              */
         /**
          * AAI HACK
          *
          * clone of 'captureAIM' but adds an amount to be captured
          * instead of assuming that the full amount will be captured
          */
         case 'captureWithAmountAIM':
             $teoAuth = $this->getTeoAuthorizationByOrderId($orderId);
             $transId = $teoAuth->getData('authorization_number');
             $response = $this->captureWithAmountAIM($transId, $amount);
             break;
             /**
              * END AAI HACK
              */
         /**
          * END AAI HACK
          */
         case 'createauthorizeaim':
             $response = $this->createAuthorizeAim($amount, $payment, $order);
             break;
         case 'refundAIM':
             $response = $this->createRefundAIM($amount, $payment, $order);
             break;
     }
     return $response;
 }