get state_province_id given non numeric country_id or country parameter for APIv3...
authorMark Hanna <mark@skvare.com>
Tue, 2 Apr 2019 15:19:47 +0000 (10:19 -0500)
committerMark Hanna <mark@skvare.com>
Tue, 2 Apr 2019 23:18:15 +0000 (18:18 -0500)
api/v3/utils.php
tests/phpunit/api/v3/AddressTest.php

index b13b31aa9dccb30575e3091060eff43c9c07c98a..de3253668a41d886c049b28cdc6494517665d954 100644 (file)
@@ -2070,8 +2070,11 @@ function _civicrm_api3_validate_integer(&$params, $fieldName, &$fieldInfo, $enti
     }
     if (!empty($fieldInfo['pseudoconstant']) || !empty($fieldInfo['options'])) {
       $additional_lookup_params = [];
-      if (strtolower($entity) == 'address' && $fieldName == 'state_province_id' && !empty($params['country_id'])) {
-        $additional_lookup_params = ['country_id' => $params['country_id']];
+      if (strtolower($entity) == 'address' && $fieldName == 'state_province_id') {
+        $country_id = _civicrm_api3_resolve_country_id($params);
+        if (!empty($country_id)) {
+          $additional_lookup_params = ['country_id' => $country_id];
+        }
       }
       _civicrm_api3_api_match_pseudoconstant($fieldValue, $entity, $fieldName, $fieldInfo, $op, $additional_lookup_params);
     }
@@ -2100,6 +2103,50 @@ function _civicrm_api3_validate_integer(&$params, $fieldName, &$fieldInfo, $enti
   }
 }
 
+/**
+ * Helper function to determine country_id given the myriad of values for country_id or country that are supported
+ * @param $params
+ *
+ * @return int|null
+ */
+function _civicrm_api3_resolve_country_id($params) {
+  if (!empty($params['country_id'])) {
+    if (is_numeric($params['country_id'])) {
+      $country_id = $params['country_id'];
+    }
+    else {
+      $country = new CRM_Core_DAO_Country();
+      $country->name = $params['country_id'];
+      if (!$country->find(TRUE)) {
+        $country->name = NULL;
+        $country->iso_code = $params['country_id'];
+        $country->find(TRUE);
+      }
+      if (!empty($country->id)) {
+        $country_id = $country->id;
+      }
+    }
+  }
+  elseif (!empty($params['country'])) {
+    if (is_numeric($params['country'])) {
+      $country_id = $params['country'];
+    }
+    else {
+      $country = new CRM_Core_DAO_Country();
+      $country->name = $params['country'];
+      if (!$country->find(TRUE)) {
+        $country->name = NULL;
+        $country->iso_code = $params['country'];
+        $country->find(TRUE);
+      }
+      if (!empty($country->id)) {
+        $country_id = $country->id;
+      }
+    }
+  }
+  return !empty($country_id) ? $country_id : NULL;
+}
+
 /**
  * Determine a contact ID using a string expression.
  *
index 31d1cb6207ff92253ef257c5307dfb1460b58ede..0307114cccf1e22e916ed470bdf8add9f59aabab 100644 (file)
@@ -436,4 +436,43 @@ class api_v3_AddressTest extends CiviUnitTestCase {
     $this->assertEquals('3497', $address2['values'][0]['state_province_id']);
   }
 
+  public function getSymbolicCountryStateExamples() {
+    return [
+      // [mixed $inputCountry, mixed $inputState, int $expectCountry, int $expectState]
+      [1228, 1004, 1228, 1004],
+      //['US', 'CA', 1228, 1004],
+      //['US', 'TX', 1228, 1042],
+      ['US', 'California', 1228, 1004],
+      [1228, 'Texas', 1228, 1042],
+      // Don't think these have been supported?
+      // ['United States', 1004, 1228, 1004] ,
+      // ['United States', 'TX', 1228, 1042],
+    ];
+  }
+
+  /**
+   * @param mixed $inputCountry
+   *   Ex: 1228 or 'US'
+   * @param mixed $inputState
+   *   Ex: 1004 or 'CA'
+   * @param int $expectCountry
+   * @param int $expectState
+   * @dataProvider getSymbolicCountryStateExamples
+   */
+  public function testCreateAddressSymbolicCountryAndState($inputCountry, $inputState, $expectCountry, $expectState) {
+    $cid = $this->individualCreate();
+    $r = $this->callAPISuccess('Address', 'create', [
+      'contact_id' => $cid,
+      'location_type_id' => 1,
+      'street_address' => '123 Some St',
+      'city' => 'Hereville',
+      'country_id' => $inputCountry, //'US',
+      'state_province_id' => $inputState, // 'California',
+      'postal_code' => '94100',
+    ]);
+    $created = CRM_Utils_Array::first($r['values']);
+    $this->assertEquals($expectCountry, $created['country_id']);
+    $this->assertEquals($expectState, $created['state_province_id']);
+  }
+
 }