CRM-13067 tidy up import function by using exception try catch
[civicrm-core.git] / CRM / Member / Import / Parser / Membership.php
index 13c5e106aa6861531dbe59b9f68c61503cd90dfc..db2b47d597c211cec2a20ea97670fefa861d9e42 100644 (file)
@@ -116,7 +116,7 @@ class CRM_Member_Import_Parser_Membership extends CRM_Member_Import_Parser {
    * @access public
    */
   function mapField(&$values) {
-    return CRM_Member_Import_Parser::VALID;
+    return CRM_Import_Parser::VALID;
   }
 
   /**
@@ -154,7 +154,7 @@ class CRM_Member_Import_Parser_Membership extends CRM_Member_Import_Parser {
 
     if ($errorRequired) {
       array_unshift($values, ts('Missing required fields'));
-      return CRM_Member_Import_Parser::ERROR;
+      return CRM_Import_Parser::ERROR;
     }
 
     $params = &$this->getActiveFieldParams();
@@ -240,10 +240,10 @@ class CRM_Member_Import_Parser_Membership extends CRM_Member_Import_Parser {
       $tempMsg = "Invalid value for field(s) : $errorMessage";
       array_unshift($values, $tempMsg);
       $errorMessage = NULL;
-      return CRM_Contact_Import_Parser::ERROR;
+      return CRM_Import_Parser::ERROR;
     }
 
-    return CRM_Member_Import_Parser::VALID;
+    return CRM_Import_Parser::VALID;
   }
 
   /**
@@ -256,10 +256,10 @@ class CRM_Member_Import_Parser_Membership extends CRM_Member_Import_Parser {
    * @access public
    */
   function import($onDuplicate, &$values) {
-
+    try{
     // first make sure this is a valid line
     $response = $this->summary($values);
-    if ($response != CRM_Member_Import_Parser::VALID) {
+    if ($response != CRM_Import_Parser::VALID) {
       return $response;
     }
 
@@ -279,40 +279,24 @@ class CRM_Member_Import_Parser_Membership extends CRM_Member_Import_Parser {
 
     // don't add to recent items, CRM-4399
     $formatted['skipRecentView'] = TRUE;
-
+    $dateLabels = array(
+      'join_date' => ts('Member Since'),
+      'membership_start_date' => ts('Start Date'),
+      'membership_end_date' => ts('End Date'),
+    );
     foreach ($params as $key => $val) {
       if ($val) {
         switch ($key) {
           case 'join_date':
-            if (CRM_Utils_Date::convertToDefaultDate($params, $dateType, $key)) {
-              if (!CRM_Utils_Rule::date($params[$key])) {
-                CRM_Contact_Import_Parser_Contact::addToErrorMsg('Member Since', $errorMessage);
-              }
-            }
-            else {
-              CRM_Contact_Import_Parser_Contact::addToErrorMsg('Member Since', $errorMessage);
-            }
-            break;
-
           case 'membership_start_date':
-            if (CRM_Utils_Date::convertToDefaultDate($params, $dateType, $key)) {
-              if (!CRM_Utils_Rule::date($params[$key])) {
-                CRM_Contact_Import_Parser_Contact::addToErrorMsg('Start Date', $errorMessage);
-              }
-            }
-            else {
-              CRM_Contact_Import_Parser_Contact::addToErrorMsg('Start Date', $errorMessage);
-            }
-            break;
-
           case 'membership_end_date':
             if (CRM_Utils_Date::convertToDefaultDate($params, $dateType, $key)) {
               if (!CRM_Utils_Rule::date($params[$key])) {
-                CRM_Contact_Import_Parser_Contact::addToErrorMsg('End Date', $errorMessage);
+                CRM_Contact_Import_Parser_Contact::addToErrorMsg($dateLabels[$key], $errorMessage);
               }
             }
             else {
-              CRM_Contact_Import_Parser_Contact::addToErrorMsg('End Date', $errorMessage);
+              CRM_Contact_Import_Parser_Contact::addToErrorMsg($dateLabels[$key], $errorMessage);
             }
             break;
 
@@ -360,16 +344,12 @@ class CRM_Member_Import_Parser_Membership extends CRM_Member_Import_Parser {
 
       $formatValues[$key] = $field;
     }
-    require_once 'CRM/Utils/DeprecatedUtils.php';
-    //TODO calling API function directly is unsupported.
-    $formatError = _civicrm_api3_deprecated_membership_format_params($formatValues, $formatted, TRUE);
 
-    if ($formatError) {
-      array_unshift($values, $formatError['error_message']);
-      return CRM_Member_Import_Parser::ERROR;
-    }
+    //format params to meet api v2 requirements.
+    //@todo find a way to test removing this formatting
+    $formatError = $this->membership_format_params($formatValues, $formatted, TRUE);
 
-    if ($onDuplicate != CRM_Member_Import_Parser::DUPLICATE_UPDATE) {
+    if ($onDuplicate != CRM_Import_Parser::DUPLICATE_UPDATE) {
       $formatted['custom'] = CRM_Core_BAO_CustomField::postProcess($formatted,
         CRM_Core_DAO::$_nullObject,
         NULL,
@@ -378,12 +358,12 @@ class CRM_Member_Import_Parser_Membership extends CRM_Member_Import_Parser {
     }
     else {
       //fix for CRM-2219 Update Membership
-      // onDuplicate == CRM_Member_Import_Parser::DUPLICATE_UPDATE
+      // onDuplicate == CRM_Import_Parser::DUPLICATE_UPDATE
       if (CRM_Utils_Array::value('is_override', $formatted) &&
         !CRM_Utils_Array::value('status_id', $formatted)
       ) {
         array_unshift($values, 'Required parameter missing: Status');
-        return CRM_Member_Import_Parser::ERROR;
+        return CRM_Import_Parser::ERROR;
       }
 
       if ($formatValues['membership_id']) {
@@ -410,16 +390,16 @@ class CRM_Member_Import_Parser_Membership extends CRM_Member_Import_Parser {
           $newMembership = CRM_Member_BAO_Membership::create($formatted, $ids, TRUE);
           if (civicrm_error($newMembership)) {
             array_unshift($values, $newMembership['is_error'] . ' for Membership ID ' . $formatValues['membership_id'] . '. Row was skipped.');
-            return CRM_Member_Import_Parser::ERROR;
+            return CRM_Import_Parser::ERROR;
           }
           else {
             $this->_newMemberships[] = $newMembership->id;
-            return CRM_Member_Import_Parser::VALID;
+            return CRM_Import_Parser::VALID;
           }
         }
         else {
           array_unshift($values, 'Matching Membership record not found for Membership ID ' . $formatValues['membership_id'] . '. Row was skipped.');
-          return CRM_Member_Import_Parser::ERROR;
+          return CRM_Import_Parser::ERROR;
         }
       }
     }
@@ -441,7 +421,7 @@ class CRM_Member_Import_Parser_Membership extends CRM_Member_Import_Parser {
         $matchedIDs = explode(',', $error['error_message']['params'][0]);
         if (count($matchedIDs) > 1) {
           array_unshift($values, 'Multiple matching contact records detected for this row. The membership was not imported');
-          return CRM_Member_Import_Parser::ERROR;
+          return CRM_Import_Parser::ERROR;
         }
         else {
           $cid = $matchedIDs[0];
@@ -474,24 +454,19 @@ class CRM_Member_Import_Parser_Membership extends CRM_Member_Import_Parser {
           elseif (!CRM_Utils_Array::value('is_override', $formatted)) {
             if (empty($calcStatus)) {
               array_unshift($values, 'Status in import row (' . $formatValues['status_id'] . ') does not match calculated status based on your configured Membership Status Rules. Record was not imported.');
-              return CRM_Member_Import_Parser::ERROR;
+              return CRM_Import_Parser::ERROR;
             }
             elseif ($formatted['status_id'] != $calcStatus['id']) {
               //Status Hold" is either NOT mapped or is FALSE
               array_unshift($values, 'Status in import row (' . $formatValues['status_id'] . ') does not match calculated status based on your configured Membership Status Rules (' . $calcStatus['name'] . '). Record was not imported.');
-              return CRM_Member_Import_Parser::ERROR;
+              return CRM_Import_Parser::ERROR;
             }
           }
 
-          $formatted['version'] = 3;
-          $newMembership = civicrm_api('membership', 'create', $formatted);
-          if (civicrm_error($newMembership)) {
-            array_unshift($values, $newMembership['error_message']);
-            return CRM_Member_Import_Parser::ERROR;
-          }
+          $newMembership = civicrm_api3('membership', 'create', $formatted);
 
           $this->_newMemberships[] = $newMembership['id'];
-          return CRM_Member_Import_Parser::VALID;
+          return CRM_Import_Parser::VALID;
         }
       }
       else {
@@ -525,7 +500,7 @@ class CRM_Member_Import_Parser_Membership extends CRM_Member_Import_Parser {
         }
 
         array_unshift($values, 'No matching Contact found for (' . $disp . ')');
-        return CRM_Member_Import_Parser::ERROR;
+        return CRM_Import_Parser::ERROR;
       }
     }
     else {
@@ -535,7 +510,7 @@ class CRM_Member_Import_Parser_Membership extends CRM_Member_Import_Parser {
         $checkCid->find(TRUE);
         if ($checkCid->id != $formatted['contact_id']) {
           array_unshift($values, 'Mismatch of External identifier :' . $formatValues['external_identifier'] . ' and Contact Id:' . $formatted['contact_id']);
-          return CRM_Member_Import_Parser::ERROR;
+          return CRM_Import_Parser::ERROR;
         }
       }
 
@@ -566,24 +541,24 @@ class CRM_Member_Import_Parser_Membership extends CRM_Member_Import_Parser {
       elseif (!CRM_Utils_Array::value('is_override', $formatted)) {
         if (empty($calcStatus)) {
           array_unshift($values, 'Status in import row (' . CRM_Utils_Array::value('status_id', $formatValues) . ') does not match calculated status based on your configured Membership Status Rules. Record was not imported.');
-          return CRM_Member_Import_Parser::ERROR;
+          return CRM_Import_Parser::ERROR;
         }
         elseif ($formatted['status_id'] != $calcStatus['id']) {
           //Status Hold" is either NOT mapped or is FALSE
           array_unshift($values, 'Status in import row (' . CRM_Utils_Array::value('status_id', $formatValues) . ') does not match calculated status based on your configured Membership Status Rules (' . $calcStatus['name'] . '). Record was not imported.');
-          return CRM_Member_Import_Parser::ERROR;
+          return CRM_Import_Parser::ERROR;
         }
       }
 
-      $formatted['version'] = 3;
-      $newMembership = civicrm_api('membership', 'create', $formatted);
-      if (civicrm_error($newMembership)) {
-        array_unshift($values, $newMembership['error_message']);
-        return CRM_Member_Import_Parser::ERROR;
-      }
+      $newMembership = civicrm_api3('membership', 'create', $formatted);
 
       $this->_newMemberships[] = $newMembership['id'];
-      return CRM_Member_Import_Parser::VALID;
+      return CRM_Import_Parser::VALID;
+    }
+    }
+    catch (Exception $e) {
+      array_unshift($values, $e->getMessage());
+      return CRM_Import_Parser::ERROR;
     }
   }
 
@@ -632,5 +607,152 @@ class CRM_Member_Import_Parser_Membership extends CRM_Member_Import_Parser {
       }
     }
   }
+  /**
+   * @deprecated - this function formats params according to v2 standards but
+   * need to be sure about the impact of not calling it so retaining on the import class
+   * take the input parameter list as specified in the data model and
+   * convert it into the same format that we use in QF and BAO object
+   *
+   * @param array  $params       Associative array of property name/value
+   *                             pairs to insert in new contact.
+   * @param array  $values       The reformatted properties that we can use internally
+   *
+   * @param array  $create       Is the formatted Values array going to
+   *                             be used for CRM_Member_BAO_Membership:create()
+   *
+   * @return array|error
+   * @access public
+   */
+  function membership_format_params($params, &$values, $create = FALSE) {
+    require_once 'api/v3/utils.php';
+    $fields = CRM_Member_DAO_Membership::fields();
+    _civicrm_api3_store_values($fields, $params, $values);
+
+    $customFields = CRM_Core_BAO_CustomField::getFields( 'Membership');
+
+    foreach ($params as $key => $value) {
+      // ignore empty values or empty arrays etc
+      if (CRM_Utils_System::isNull($value)) {
+        continue;
+      }
+
+      //Handling Custom Data
+      if ($customFieldID = CRM_Core_BAO_CustomField::getKeyID($key)) {
+        $values[$key] = $value;
+        $type = $customFields[$customFieldID]['html_type'];
+        if( $type == 'CheckBox' || $type == 'Multi-Select' || $type == 'AdvMulti-Select') {
+          $mulValues = explode( ',' , $value );
+          $customOption = CRM_Core_BAO_CustomOption::getCustomOption($customFieldID, true);
+          $values[$key] = array();
+          foreach( $mulValues as $v1 ) {
+            foreach($customOption as $customValueID => $customLabel) {
+              $customValue = $customLabel['value'];
+              if (( strtolower($customLabel['label']) == strtolower(trim($v1)) ) ||
+                ( strtolower($customValue) == strtolower(trim($v1)) )) {
+                if ( $type == 'CheckBox' ) {
+                  $values[$key][$customValue] = 1;
+                } else {
+                  $values[$key][] = $customValue;
+                }
+              }
+            }
+          }
+        }
+      }
+
+      switch ($key) {
+        case 'membership_contact_id':
+          if (!CRM_Utils_Rule::integer($value)) {
+            throw new Exception("contact_id not valid: $value");
+          }
+          $dao     = new CRM_Core_DAO();
+          $qParams = array();
+          $svq     = $dao->singleValueQuery("SELECT id FROM civicrm_contact WHERE id = $value",
+            $qParams
+          );
+          if (!$svq) {
+            throw new Exception("Invalid Contact ID: There is no contact record with contact_id = $value.");
+          }
+          $values['contact_id'] = $values['membership_contact_id'];
+          unset($values['membership_contact_id']);
+          break;
+
+        case 'membership_type_id':
+          if (!CRM_Utils_Array::value($value, CRM_Member_PseudoConstant::membershipType())) {
+            throw new Exception('Invalid Membership Type Id');
+          }
+          $values[$key] = $value;
+          break;
+
+        case 'membership_type':
+          $membershipTypeId = CRM_Utils_Array::key(ucfirst($value),
+          CRM_Member_PseudoConstant::membershipType()
+          );
+          if ($membershipTypeId) {
+            if (CRM_Utils_Array::value('membership_type_id', $values) &&
+              $membershipTypeId != $values['membership_type_id']
+            ) {
+              throw new Exception('Mismatched membership Type and Membership Type Id');
+            }
+          }
+          else {
+            throw new Exception('Invalid Membership Type');
+          }
+          $values['membership_type_id'] = $membershipTypeId;
+          break;
+
+        case 'status_id':
+          if (!CRM_Utils_Array::value($value, CRM_Member_PseudoConstant::membershipStatus())) {
+            throw new Exception('Invalid Membership Status Id');
+          }
+          $values[$key] = $value;
+          break;
+
+        case 'membership_status':
+          $membershipStatusId = CRM_Utils_Array::key(ucfirst($value),
+          CRM_Member_PseudoConstant::membershipStatus()
+          );
+          if ($membershipStatusId) {
+            if (CRM_Utils_Array::value('status_id', $values) &&
+              $membershipStatusId != $values['status_id']
+            ) {
+              throw new Exception('Mismatched membership Status and Membership Status Id');
+            }
+          }
+          else {
+            throw new Exception('Invalid Membership Status');
+          }
+          $values['status_id'] = $membershipStatusId;
+          break;
+
+        default:
+          break;
+      }
+    }
+
+    _civicrm_api3_custom_format_params($params, $values, 'Membership');
+
+
+    if ($create) {
+      // CRM_Member_BAO_Membership::create() handles membership_start_date,
+      // membership_end_date and membership_source. So, if $values contains
+      // membership_start_date, membership_end_date  or membership_source,
+      // convert it to start_date, end_date or source
+      $changes = array(
+        'membership_start_date' => 'start_date',
+        'membership_end_date' => 'end_date',
+        'membership_source' => 'source',
+      );
+
+      foreach ($changes as $orgVal => $changeVal) {
+        if (isset($values[$orgVal])) {
+          $values[$changeVal] = $values[$orgVal];
+          unset($values[$orgVal]);
+        }
+      }
+    }
+
+    return NULL;
+  }
 }