use processor class to determine if backoffice processing is supported
authorEileen McNaughton <eileen@fuzion.co.nz>
Fri, 31 Oct 2014 18:58:07 +0000 (07:58 +1300)
committerEileen McNaughton <eileen@fuzion.co.nz>
Fri, 31 Oct 2014 18:58:07 +0000 (07:58 +1300)
CRM/Contribute/Form/AbstractEditPayment.php
CRM/Core/Config.php
CRM/Core/Payment.php
CRM/Core/Payment/AuthorizeNet.php
CRM/Core/Payment/Dummy.php
CRM/Core/Payment/Form.php
CRM/Core/Payment/PayPalImpl.php
CRM/Financial/BAO/PaymentProcessor.php

index 21dee704ab3588a717a253fe5d2f38bd3f93c1df..25d9469ec7aa60b6cb386d9d750a6df0dcb98caf 100644 (file)
@@ -343,39 +343,29 @@ LEFT JOIN  civicrm_contribution on (civicrm_contribution.contact_id = civicrm_co
   /**
    * @return array (0 => array(int $ppId => string $label), 1 => array(...payproc details...))
    */
-  public function getValidProcessorsAndAssignFutureStartDate() {
+  /**
+   * @return array of valid processors
+   * @throws Exception
+   */
+  public function getValidProcessors() {
     $validProcessors = array();
-    // restrict to payment_type = 1 (credit card only) and billing mode 1 and 3
-    $processors = CRM_Core_PseudoConstant::paymentProcessor(FALSE, FALSE, "billing_mode IN ( 1, 3 ) AND payment_type = 1");
-
-    foreach ($processors as $ppID => $label) {
-      $paymentProcessor = CRM_Financial_BAO_PaymentProcessor::getPayment($ppID, $this->_mode);
-      // at this stage only Authorize.net has been tested to support future start dates so if it's enabled let the template know
-      // to show receive date
-      $processorsSupportingFutureStartDate = array('AuthNet');
-      if (in_array($paymentProcessor['payment_processor_type'], $processorsSupportingFutureStartDate)) {
-        $this->assign('processorSupportsFutureStartDate', TRUE);
-      }
-      if ($paymentProcessor['payment_processor_type'] == 'PayPal' && !$paymentProcessor['user_name']) {
-        continue;
-      }
-      elseif ($paymentProcessor['payment_processor_type'] == 'Dummy' && $this->_mode == 'live') {
-        continue;
-      }
-      else {
-        $paymentObject = CRM_Core_Payment::singleton($this->_mode, $paymentProcessor, $this);
-        $error = $paymentObject->checkConfig();
-        if (empty($error)) {
-          $validProcessors[$ppID] = $label;
-        }
-        $paymentObject = NULL;
-      }
+    $defaultID = NULL;
+    $capabilities = array('BackOffice');
+    if ($this->_mode == 'live') {
+      $capabilities[] = 'LiveMode';
+    }
+    $processors = CRM_Financial_BAO_PaymentProcessor::getPaymentProcessors($capabilities);
+    foreach ($processors as $id => $processor) {
+       if ($processor['is_default']) {
+         $defaultID = $id;
+       }
+       $validProcessors[$id] = ts($processor['name']);
     }
     if (empty($validProcessors)) {
-      CRM_Core_Error::fatal(ts('You will need to configure the %1 settings for your Payment Processor before you can submit credit card transactions.', array(1 => $this->_mode)));
+      throw new CRM_Core_Exception(ts('You will need to configure the %1 settings for your Payment Processor before you can submit a credit card transactions.', array(1 => $this->_mode)));
     }
     else {
-      return array($validProcessors, $paymentProcessor);
+      return array($validProcessors, $processors[$defaultID]['object']);
     }
   }
 
@@ -401,7 +391,8 @@ LEFT JOIN  civicrm_contribution on (civicrm_contribution.contact_id = civicrm_co
     //ensure that processor has a valid config
     //only valid processors get display to user
     if ($this->_mode) {
-      list($this->_processors, $paymentProcessor) = $this->getValidProcessorsAndAssignFutureStartDate();
+      $this->assign(CRM_Financial_BAO_PaymentProcessor::hasPaymentProcessorSupporting(array('supportsFutureRecurStartDate')), TRUE);
+      list($this->_processors, $paymentProcessor) = $this->getValidProcessors();
 
       //get the valid recurring processors.
       $recurring = CRM_Core_PseudoConstant::paymentProcessor(FALSE, FALSE, 'is_recur = 1');
index 72553ed90eec137d449a46ea199fd880713da50e..d47da2e48967692982692b7e17cb13305eb670ed 100644 (file)
@@ -862,19 +862,10 @@ AND
 
   /**
    * Is back office credit card processing enabled for this site - ie are there any installed processors that support
-   * on-site processing
+   * it?
    * @return bool
    */
   static function isEnabledBackOfficeCreditCardPayments() {
-    // restrict to type=1 (credit card) payment processor payment_types and only include billing mode types 1 and 3
-    $processors = CRM_Core_PseudoConstant::paymentProcessor(FALSE, FALSE,
-      "billing_mode IN ( 1, 3 ) AND payment_type = 1"
-    );
-    if (count($processors) > 0) {
-      return TRUE;
-    }
-    return FALSE;
+    return CRM_Financial_BAO_PaymentProcessor::hasPaymentProcessorSupporting('BackOffice');
   }
 }
-// end CRM_Core_Config
-
index 9d143ea7ba3b64de517973b6f87c232825fbb896..b9ee08d5740edf0c5bb728122caa988a6551539a 100644 (file)
@@ -145,6 +145,45 @@ abstract class CRM_Core_Payment {
     $log->alert($message, $_REQUEST);
   }
 
+  /**
+   * check if capability is supported
+   * @param string $capability e.g BackOffice, LiveMode, FutureRecurStartDate
+   *
+   * @return bool
+   */
+  public function supports($capability) {
+    $function = 'supports' . ucfirst($capability);
+    if (method_exists($this, $function)) {
+      return $this->$function();
+    }
+    return FALSE;
+  }
+
+  /**
+   * are back office payments supported - e.g paypal standard won't permit you to enter a credit card associated with someone else's login
+   * @return bool
+   */
+  private function supportsBackOffice() {
+    return TRUE;
+  }
+
+  /**
+   * are back office payments supported - e.g paypal standard won't permit you to enter a credit card associated with someone else's login
+   * @return bool
+   */
+  private function supportsLiveMode() {
+    return TRUE;
+  }
+
+  /**
+   * should the first payment date be configurable when setting up back office recurring payments
+   * We set this to false for historical consistency but in fact most new processors use tokens for recurring and can support this
+   * @return bool
+   */
+  private function supportsFutureRecurStartDate() {
+    return FALSE;
+  }
+
   /**
    * Setter for the payment form that wants to use the processor
    *
index 16d2b6d7efeae398cc10c0ffd4ff5ec529173f5b..ce115deabcd1d636354fa9f5d6fb1bbf3d8aee22 100644 (file)
@@ -83,6 +83,15 @@ class CRM_Core_Payment_AuthorizeNet extends CRM_Core_Payment {
     return self::$_singleton[$processorName];
   }
 
+  /**
+   * should the first payment date be configurable when setting up back office recurring payments
+   * In the case of Authorize.net this is an option
+   * @return bool
+   */
+  private function supportsFutureRecurStartDate() {
+    return TRUE;
+  }
+
   /**
    * Submit a payment using Advanced Integration Method
    *
index 05d19d37e2c2448b9404e1a70096f6462665fafd..5312ee0deedd5ac6c6fbe14c585e549fc5ea82b5 100644 (file)
@@ -122,6 +122,14 @@ class CRM_Core_Payment_Dummy extends CRM_Core_Payment {
     return $params;
   }
 
+  /**
+   * are back office payments supported - e.g paypal standard won't permit you to enter a credit card associated with someone else's login
+   * @return bool
+   */
+  private function supportsLiveMode() {
+    return FALSE;
+  }
+
   /**
    * @param null $errorCode
    * @param null $errorMessage
index 59ced78187e20be7dc657c518b35ad2cacd6f8dd..e3be88183e429e79cfc75a26d706ab89f714498e 100644 (file)
@@ -512,6 +512,4 @@ class CRM_Core_Payment_Form {
   static function getCreditCardExpirationYear($src) {
     return CRM_Utils_Array::value('Y', $src['credit_card_exp_date']);
   }
-
 }
-
index 8481a4ec81cc3bcf5c98c1bad65025e1d1bef1cd..8a74b9e6083e84ec0af1a5af8cf13a8bb444445b 100644 (file)
@@ -94,6 +94,16 @@ class CRM_Core_Payment_PayPalImpl extends CRM_Core_Payment {
     return self::$_singleton[$processorName];
   }
 
+  /**
+   * are back office payments supported - e.g paypal standard won't permit you to enter a credit card associated with someone else's login
+   * @return bool
+   */
+  private function supportsBackOffice() {
+    if ($this->_processorName == ts('PayPal Pro')) {
+      return TRUE;
+    }
+    return FALSE;
+  }
   /**
    * express checkout code. Check PayPal documentation for more information
    *
index 08a1d230fec2a73da00cc2fdcde9e58f8f8855ec..b14e0b55c1b78bb4648ae5c3416cded1433f653a 100644 (file)
@@ -283,6 +283,79 @@ class CRM_Financial_BAO_PaymentProcessor extends CRM_Financial_DAO_PaymentProces
     return $result;
   }
 
+  /**
+   * get all payment processors as an array of objects.
+   *
+   * @param $isExcludeTest
+   * @param bool $reset
+   *
+   * @throws CiviCRM_API3_Exception
+   * @return array
+   */
+  static function getAllPaymentProcessors($isExcludeTest, $reset = FALSE) {
+    /**
+     * $cacheKey = 'CRM_Financial_BAO_Payment_Processor_' . ($isExcludeTest ? 'test' : 'all');
+    if (!$reset) {
+      $processors = CRM_Utils_Cache::singleton()->get($cacheKey);
+      if (!empty($processors)) {
+        return $processors;
+      }
+    }
+     * */
+    $retrievalParameters = array('is_active' => TRUE, 'options' => array('sort' => 'is_default, name'));
+    if ($isExcludeTest) {
+      $retrievalParameters['is_test'] = 0;
+    }
+    $processors = civicrm_api3('payment_processor', 'get', $retrievalParameters);
+    foreach ($processors['values'] as $processor) {
+      $processors['values'][$processor['id']]['object'] = CRM_Core_Payment::singleton(empty($processor['is_test']) ? 'live' : 'test', $processor);
+    }
+    /*
+     CRM_Utils_Cache::singleton()->set($cacheKey, $processors);
+     */
+    return $processors['values'];
+  }
+
+  /**
+   * get Payment processors with specified capabilities.
+   * Note that both the singleton & the pseudoconstant function have caching so we don't add
+   * arguably this could go on the pseudoconstant class
+   *
+   * @param array $capabilities
+   * @param bool $isIncludeTest
+   *
+   * @return array available processors
+   */
+  static function getPaymentProcessors($capabilities = array(), $isIncludeTest = FALSE, $reset = FALSE) {
+    $processors = self::getAllPaymentProcessors(!$isIncludeTest);
+    if ($capabilities) {
+      foreach ($processors as $index => $processor) {
+        if (($error = $processor['object']->checkConfig()) != NULL) {
+          unset ($processors[$index]);
+          continue;
+        }
+        foreach ($capabilities as $capability) {
+          if ($capability && !$processor['object']->supports($capability)) {
+            unset ($processors[$index]);
+          }
+        }
+      }
+    }
+    return $processors;
+  }
+
+  /**
+   * Is there a processor on this site with the specified capability
+   * @param array $capabilities
+   * @param bool $isIncludeTest
+   *
+   * @return bool
+   */
+  static function hasPaymentProcessorSupporting($capabilities = array(), $isIncludeTest = FALSE) {
+    $result = self::getPaymentProcessors($capabilities, $isIncludeTest);
+    return (!empty($result)) ? TRUE : FALSE;
+  }
+
   /**
    * Function to retrieve payment processor id / info/ object based on component-id.
    *