CRM-16800 add unit test for membership renewal backoffice form
authorEileen McNaughton <eileen@fuzion.co.nz>
Mon, 6 Jul 2015 01:27:01 +0000 (13:27 +1200)
committerEileen McNaughton <eileen@fuzion.co.nz>
Mon, 6 Jul 2015 01:27:01 +0000 (13:27 +1200)
CRM/Member/Form/MembershipRenewal.php
tests/phpunit/CRM/Member/Form/MembershipRenewalTest.php [new file with mode: 0644]

index 88c775f85f05bdab2cdcd8b789eef331c948c9e0..c8096b8a33c6d6b9aa5beb10337d5190640ed99f 100644 (file)
@@ -429,12 +429,52 @@ class CRM_Member_Form_MembershipRenewal extends CRM_Member_Form {
    * @return void
    */
   public function postProcess() {
-
-    $config = CRM_Core_Config::singleton();
-
     // get the submitted form values.
     $this->_params = $formValues = $this->controller->exportValues($this->_name);
 
+    $statusMsg = $this->submit($formValues);
+
+    CRM_Core_Session::setStatus($statusMsg, ts('Complete'), 'success');
+  }
+
+  /**
+   * Determine if the form has a pending status.
+   *
+   * @deprecated
+   *
+   * @param CRM_Core_Form $form
+   * @param int $membershipID
+   *
+   * @return bool
+   */
+  public static function extractPendingFormValue($form, $membershipID) {
+    $membershipTypeDetails = CRM_Member_BAO_MembershipType::getMembershipTypeDetails($membershipID);
+    $pending = FALSE;
+    // @todo function was shared by 2 not-very-related forms & the below may include irrelevant stuff.
+    if (CRM_Utils_Array::value('minimum_fee', $membershipTypeDetails) > 0.0) {
+      if (((isset($form->_contributeMode) && $form->_contributeMode == 'notify') || !empty($form->_params['is_pay_later'])
+        ) &&
+        (($form->_values['is_monetary'] && $form->_amount > 0.0) ||
+          CRM_Utils_Array::value('record_contribution', $form->_params)
+        )
+      ) {
+        $pending = TRUE;
+      }
+    }
+    return $pending;
+  }
+
+  /**
+   * Process form submission.
+   *
+   * This function is also accessed by a unit test.
+   *
+   * @param array $formValues
+   *   Submitted values.
+   *
+   * @return array
+   */
+  protected function submit($formValues) {
     $this->storeContactFields($formValues);
     // use values from screen
 
@@ -458,7 +498,8 @@ class CRM_Member_Form_MembershipRenewal extends CRM_Member_Form {
     }
 
     if ($this->_mode) {
-      $formValues['total_amount'] = CRM_Utils_Array::value('total_amount', $this->_params, CRM_Core_DAO::getFieldValue('CRM_Member_DAO_MembershipType',
+      $formValues['total_amount'] = CRM_Utils_Array::value('total_amount', $formValues, CRM_Core_DAO::getFieldValue
+      ('CRM_Member_DAO_MembershipType',
         $this->_memType, 'minimum_fee'
       ));
       if (empty($formValues['financial_type_id'])) {
@@ -509,15 +550,17 @@ class CRM_Member_Form_MembershipRenewal extends CRM_Member_Form {
       );
 
       // add all the additional payment params we need
-      $this->_params["state_province-{$this->_bltID}"] = $this->_params["billing_state_province-{$this->_bltID}"] = CRM_Core_PseudoConstant::stateProvinceAbbreviation($this->_params["billing_state_province_id-{$this->_bltID}"]);
-      $this->_params["country-{$this->_bltID}"] = $this->_params["billing_country-{$this->_bltID}"] = CRM_Core_PseudoConstant::countryIsoCode($this->_params["billing_country_id-{$this->_bltID}"]);
+      $this->_params["state_province-{$this->_bltID}"] = $this->_params["billing_state_province-{$this->_bltID}"]
+        = CRM_Core_PseudoConstant::stateProvinceAbbreviation($formValues["billing_state_province_id-{$this->_bltID}"]);
+      $this->_params["country-{$this->_bltID}"] = $this->_params["billing_country-{$this->_bltID}"]
+        = CRM_Core_PseudoConstant::countryIsoCode($formValues["billing_country_id-{$this->_bltID}"]);
 
-      $this->_params['year'] = CRM_Core_Payment_Form::getCreditCardExpirationYear($this->_params);
-      $this->_params['month'] = CRM_Core_Payment_Form::getCreditCardExpirationMonth($this->_params);
+      $this->_params['year'] = CRM_Core_Payment_Form::getCreditCardExpirationYear($formValues);
+      $this->_params['month'] = CRM_Core_Payment_Form::getCreditCardExpirationMonth($formValues);
       $this->_params['description'] = ts('Office Credit Card Membership Renewal Contribution');
       $this->_params['ip_address'] = CRM_Utils_System::ipAddress();
       $this->_params['amount'] = $formValues['total_amount'];
-      $this->_params['currencyID'] = $config->defaultCurrency;
+      $this->_params['currencyID'] = CRM_Core_Config::singleton()->defaultCurrency;
       $this->_params['invoiceID'] = md5(uniqid(rand(), TRUE));
 
       // at this point we've created a contact and stored its address etc
@@ -534,7 +577,7 @@ class CRM_Member_Form_MembershipRenewal extends CRM_Member_Form {
 
       $payment = CRM_Core_Payment::singleton($this->_mode, $this->_paymentProcessor, $this);
 
-      $result = &$payment->doDirectPayment($paymentParams);
+      $result = $payment->doDirectPayment($paymentParams);
 
       if (is_a($result, 'CRM_Core_Error')) {
         CRM_Core_Error::displaySessionError($result);
@@ -555,10 +598,8 @@ class CRM_Member_Form_MembershipRenewal extends CRM_Member_Form {
       $this->assign('trxn_id', $result['trxn_id']);
     }
 
-    $renewalDate = NULL;
-    if ($formValues['renewal_date']) {
-      $renewalDate = CRM_Utils_Date::processDate($formValues['renewal_date']);
-    }
+    $renewalDate = !empty($formValues['renewal_date']) ? $renewalDate = CRM_Utils_Date::processDate($formValues['renewal_date']) : NULL;
+
     // This set is probably obsolete.
     $this->set('renewalDate', $renewalDate);
 
@@ -614,7 +655,7 @@ class CRM_Member_Form_MembershipRenewal extends CRM_Member_Form {
       }
     }
 
-    $renewMembership = CRM_Member_BAO_Membership::renewMembership(
+    list($renewMembership) = CRM_Member_BAO_Membership::renewMembership(
       $this->_contactID, $formValues['membership_type_id'][1], $isTestMembership,
       $renewalDate, NULL, $customFieldsFormatted, $numRenewTerms, $this->_membershipId,
       self::extractPendingFormValue($this, $formValues['membership_type_id'][1]),
@@ -784,36 +825,18 @@ class CRM_Member_Form_MembershipRenewal extends CRM_Member_Form {
 
     if ($receiptSend && $mailSend) {
       $statusMsg .= ' ' . ts('A renewal confirmation and receipt has been sent to %1.', array(1 => $this->_contributorEmail));
+      return $statusMsg;
     }
-
-    CRM_Core_Session::setStatus($statusMsg, ts('Complete'), 'success');
+    return $statusMsg;
   }
 
   /**
-   * Determine if the form has a pending status.
-   *
-   * @deprecated
+   * Wrapper function for unit tests.
    *
-   * @param CRM_Core_Form $form
-   * @param int $membershipID
-   *
-   * @return bool
+   * @param array $formValues
    */
-  public static function extractPendingFormValue($form, $membershipID) {
-    $membershipTypeDetails = CRM_Member_BAO_MembershipType::getMembershipTypeDetails($membershipID);
-    $pending = FALSE;
-    // @todo function was shared by 2 not-very-related forms & the below may include irrelevant stuff.
-    if (CRM_Utils_Array::value('minimum_fee', $membershipTypeDetails) > 0.0) {
-      if (((isset($form->_contributeMode) && $form->_contributeMode == 'notify') || !empty($form->_params['is_pay_later'])
-        ) &&
-        (($form->_values['is_monetary'] && $form->_amount > 0.0) ||
-          CRM_Utils_Array::value('record_contribution', $form->_params)
-        )
-      ) {
-        $pending = TRUE;
-      }
-    }
-    return $pending;
+  public function testSubmit($formValues) {
+    $this->_memType = $formValues['membership_type_id'][1];
+    $this->submit($formValues);
   }
-
 }
diff --git a/tests/phpunit/CRM/Member/Form/MembershipRenewalTest.php b/tests/phpunit/CRM/Member/Form/MembershipRenewalTest.php
new file mode 100644 (file)
index 0000000..fab89ae
--- /dev/null
@@ -0,0 +1,302 @@
+<?php
+/*
+ +--------------------------------------------------------------------+
+ | CiviCRM version 4.6                                                |
+ +--------------------------------------------------------------------+
+ | Copyright CiviCRM LLC (c) 2004-2015                                |
+ +--------------------------------------------------------------------+
+ | This file is a part of CiviCRM.                                    |
+ |                                                                    |
+ | CiviCRM is free software; you can copy, modify, and distribute it  |
+ | under the terms of the GNU Affero General Public License           |
+ | Version 3, 19 November 2007 and the CiviCRM Licensing Exception.   |
+ |                                                                    |
+ | CiviCRM is distributed in the hope that it will be useful, but     |
+ | WITHOUT ANY WARRANTY; without even the implied warranty of         |
+ | MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.               |
+ | See the GNU Affero General Public License for more details.        |
+ |                                                                    |
+ | You should have received a copy of the GNU Affero General Public   |
+ | License and the CiviCRM Licensing Exception along                  |
+ | with this program; if not, contact CiviCRM LLC                     |
+ | at info[AT]civicrm[DOT]org. If you have questions about the        |
+ | GNU Affero General Public License or the licensing of CiviCRM,     |
+ | see the CiviCRM license FAQ at http://civicrm.org/licensing        |
+ +--------------------------------------------------------------------+
+ */
+
+/**
+ *  File for the MembershipTest class
+ *
+ *  (PHP 5)
+ *
+ * @author Walt Haas <walt@dharmatech.org> (801) 534-1262
+ */
+
+/**
+ *  Include class definitions
+ */
+require_once 'CiviTest/CiviUnitTestCase.php';
+
+require_once 'HTML/QuickForm/Page.php';
+
+/**
+ *  Test CRM_Member_Form_Membership functions.
+ *
+ * @package   CiviCRM
+ */
+class CRM_Member_Form_MembershipTest extends CiviUnitTestCase {
+
+  /**
+   * Assume empty database with just civicrm_data.
+   */
+  protected $_individualId;
+  protected $_contribution;
+  protected $_financialTypeId = 1;
+  protected $_apiversion;
+  protected $_entity = 'Membership';
+  protected $_params;
+  protected $_ids = array();
+  protected $_paymentProcessorID;
+
+  /**
+   * Membership type ID for annual fixed membership.
+   *
+   * @var int
+   */
+  protected $membershipTypeAnnualFixedID;
+
+  /**
+   * Parameters to create payment processor.
+   *
+   * @var array
+   */
+  protected $_processorParams = array();
+
+  /**
+   * ID of created membership.
+   *
+   * @var int
+   */
+  protected $_membershipID;
+
+  /**
+   * Payment instrument mapping.
+   *
+   * @var array
+   */
+  protected $paymentInstruments = array();
+
+  /**
+   * Test setup for every test.
+   *
+   * Connect to the database, truncate the tables that will be used
+   * and redirect stdin to a temporary file.
+   */
+  public function setUp() {
+    $this->_apiversion = 3;
+    parent::setUp();
+
+    $this->_individualId = $this->individualCreate();
+    $processor = $this->processorCreate();
+    $this->_paymentProcessorID = $processor->id;
+    // Insert test data.
+    $op = new PHPUnit_Extensions_Database_Operation_Insert();
+    $op->execute($this->_dbconn,
+      $this->createFlatXMLDataSet(
+        dirname(__FILE__) . '/dataset/data.xml'
+      )
+    );
+    $membershipTypeAnnualFixed = $this->callAPISuccess('membership_type', 'create', array(
+      'domain_id' => 1,
+      'name' => "AnnualFixed",
+      'member_of_contact_id' => 23,
+      'duration_unit' => "year",
+      'duration_interval' => 1,
+      'period_type' => "fixed",
+      'fixed_period_start_day' => "101",
+      'fixed_period_rollover_day' => "1231",
+      'relationship_type_id' => 20,
+      'financial_type_id' => 2,
+    ));
+    $this->membershipTypeAnnualFixedID = $membershipTypeAnnualFixed['id'];
+    $membership = $this->callAPISuccess('Membership', 'create', array(
+      'contact_id' => $this->_individualId,
+      'membership_type_id' => $this->membershipTypeAnnualFixedID,
+    ));
+    $this->_membershipID = $membership['id'];
+
+    $instruments = $this->callAPISuccess('contribution', 'getoptions', array('field' => 'payment_instrument_id'));
+    $this->paymentInstruments = $instruments['values'];
+  }
+
+  /**
+   * Clean up after each test.
+   */
+  public function tearDown() {
+    $this->quickCleanUpFinancialEntities();
+    $this->quickCleanup(
+      array(
+        'civicrm_relationship',
+        'civicrm_membership_type',
+        'civicrm_membership',
+        'civicrm_uf_match',
+      )
+    );
+    $this->callAPISuccess('contact', 'delete', array('id' => 17, 'skip_undelete' => TRUE));
+    $this->callAPISuccess('contact', 'delete', array('id' => 23, 'skip_undelete' => TRUE));
+    $this->callAPISuccess('relationship_type', 'delete', array('id' => 20));
+  }
+
+  /**
+   *  Test CRM_Member_Form_Membership::buildQuickForm()
+   */
+  //function testCRMMemberFormMembershipBuildQuickForm()
+  //{
+  //    throw new PHPUnit_Framework_IncompleteTestError( "not implemented" );
+  //}
+
+  /**
+   * Test the submit function of the membership form.
+   */
+  public function testSubmit() {
+    $form = $this->getForm();
+    $this->createLoggedInUser();
+    $params = array(
+      'cid' => $this->_individualId,
+      'join_date' => date('m/d/Y', time()),
+      'start_date' => '',
+      'end_date' => '',
+      // This format reflects the 23 being the organisation & the 25 being the type.
+      'membership_type_id' => array(23, $this->membershipTypeAnnualFixedID),
+      'auto_renew' => '0',
+      'max_related' => '',
+      'num_terms' => '1',
+      'source' => '',
+      'total_amount' => '50.00',
+      'financial_type_id' => '2', //Member dues, see data.xml
+      'soft_credit_type_id' => '',
+      'soft_credit_contact_id' => '',
+      'from_email_address' => '"Demonstrators Anonymous" <info@example.org>',
+      'receipt_text_signup' => 'Thank you text',
+      'payment_processor_id' => $this->_paymentProcessorID,
+      'credit_card_number' => '4111111111111111',
+      'cvv2' => '123',
+      'credit_card_exp_date' => array(
+        'M' => '9',
+        'Y' => '2024', // TODO: Future proof
+      ),
+      'credit_card_type' => 'Visa',
+      'billing_first_name' => 'Test',
+      'billing_middlename' => 'Last',
+      'billing_street_address-5' => '10 Test St',
+      'billing_city-5' => 'Test',
+      'billing_state_province_id-5' => '1003',
+      'billing_postal_code-5' => '90210',
+      'billing_country_id-5' => '1228',
+    );
+    $form->_contactID = $this->_individualId;
+
+    $form->testSubmit($params);
+    $membership = $this->callAPISuccessGetSingle('Membership', array('contact_id' => $this->_individualId));
+    $this->callAPISuccessGetCount('ContributionRecur', array('contact_id' => $this->_individualId), 0);
+    $contribution = $this->callAPISuccess('Contribution', 'get', array(
+      'contact_id' => $this->_individualId,
+      'is_test' => TRUE,
+    ));
+
+    $this->callAPISuccessGetCount('LineItem', array(
+      'entity_id' => $membership['id'],
+      'entity_table' => 'civicrm_membership',
+      'contribution_id' => $contribution['id'],
+    ), 1);
+  }
+
+  /**
+   * Test the submit function of the membership form.
+   */
+  public function testSubmitRecur() {
+    $form = $this->getForm();
+
+    $this->callAPISuccess('MembershipType', 'create', array(
+      'id' => $this->membershipTypeAnnualFixedID,
+      'duration_unit' => 'month',
+      'duration_interval' => 1,
+      'auto_renew' => TRUE,
+    ));
+    $form->preProcess();
+    $this->createLoggedInUser();
+    $params = array(
+      'cid' => $this->_individualId,
+      'price_set_id' => 0,
+      'join_date' => date('m/d/Y', time()),
+      'start_date' => '',
+      'end_date' => '',
+      'campaign_id' => '',
+      // This format reflects the 23 being the organisation & the 25 being the type.
+      'membership_type_id' => array(23, $this->membershipTypeAnnualFixedID),
+      'auto_renew' => '1',
+      'is_recur' => 1,
+      'max_related' => 0,
+      'num_terms' => '1',
+      'source' => '',
+      'total_amount' => '77.00',
+      'financial_type_id' => '2', //Member dues, see data.xml
+      'soft_credit_type_id' => 11,
+      'soft_credit_contact_id' => '',
+      'from_email_address' => '"Demonstrators Anonymous" <info@example.org>',
+      'receipt_text' => 'Thank you text',
+      'payment_processor_id' => $this->_paymentProcessorID,
+      'credit_card_number' => '4111111111111111',
+      'cvv2' => '123',
+      'credit_card_exp_date' => array(
+        'M' => '9',
+        'Y' => '2019', // TODO: Future proof
+      ),
+      'credit_card_type' => 'Visa',
+      'billing_first_name' => 'Test',
+      'billing_middlename' => 'Last',
+      'billing_street_address-5' => '10 Test St',
+      'billing_city-5' => 'Test',
+      'billing_state_province_id-5' => '1003',
+      'billing_postal_code-5' => '90210',
+      'billing_country_id-5' => '1228',
+    );
+    $form->_mode = 'test';
+    $form->_contactID = $this->_individualId;
+
+    $form->testSubmit($params);
+    $membership = $this->callAPISuccessGetSingle('Membership', array('contact_id' => $this->_individualId));
+    //$this->callAPISuccessGetCount('ContributionRecur', array('contact_id' => $this->_individualId), 1);
+    $contribution = $this->callAPISuccess('Contribution', 'get', array(
+      'contact_id' => $this->_individualId,
+      'is_test' => TRUE,
+    ));
+
+    $this->callAPISuccessGetCount('LineItem', array(
+      'entity_id' => $membership['id'],
+      'entity_table' => 'civicrm_membership',
+      'contribution_id' => $contribution['id'],
+    ), 1);
+
+  }
+
+  /**
+   * Get a membership form object.
+   *
+   * We need to instantiate the form to run preprocess, which means we have to trick it about the request method.
+   *
+   * @return \CRM_Member_Form_MembershipRenewal
+   */
+  protected function getForm() {
+    $form = new CRM_Member_Form_MembershipRenewal();
+    $_SERVER['REQUEST_METHOD'] = 'GET';
+    $form->controller = new CRM_Core_Controller();
+    $form->_bltID = 5;
+    $form->_mode = 'test';
+    $form->_id = $this->_membershipID;
+    $form->preProcess();
+    return $form;
+  }
+
+}