X-Git-Url: https://vcs.fsf.org/?a=blobdiff_plain;f=CRM%2FCore%2FBAO%2FBlock.php;h=12c30e1ef74365948ea2e10764b89429a27a9ea8;hb=8ded2b4dfdf2bf072fa1f555afe09605d9c8b99f;hp=7913238590aa8b5c36d129b14c5f86b0fc4f052a;hpb=9d7bd4647883c990d70a401e1c2a698cd2cbd68a;p=civicrm-core.git diff --git a/CRM/Core/BAO/Block.php b/CRM/Core/BAO/Block.php index 7913238590..12c30e1ef7 100644 --- a/CRM/Core/BAO/Block.php +++ b/CRM/Core/BAO/Block.php @@ -223,14 +223,18 @@ class CRM_Core_BAO_Block { * CRM_Core_BAO_Block object on success, null otherwise */ public static function create($blockName, &$params, $entity = NULL, $contactId = NULL) { + if (!self::blockExists($blockName, $params)) { return NULL; } - $name = ucfirst($blockName); - $contactId = NULL; - $isPrimary = $isBilling = TRUE; + // Set up required information / defaults $entityElements = $blocks = array(); + $resetPrimary = $primarySet = $billingSet = FALSE; + $contactId = NULL; + + $baoString = 'CRM_Core_BAO_' . ucfirst($blockName); + $updateBlankLocInfo = CRM_Utils_Array::value('updateBlankLocInfo', $params, FALSE); if ($entity) { $entityElements = array( @@ -242,140 +246,130 @@ class CRM_Core_BAO_Block { $contactId = $params['contact_id']; } - $updateBlankLocInfo = CRM_Utils_Array::value('updateBlankLocInfo', $params, FALSE); + // Get current and submitted values + $existingValues = self::getBlockIds($blockName, $contactId, $entityElements, $updateBlankLocInfo); + $submittedValues = $params[$blockName]; - //get existsing block ids. - $blockIds = self::getBlockIds($blockName, $contactId, $entityElements, $updateBlankLocInfo); - - if (!$updateBlankLocInfo) { - $resetPrimaryId = NULL; - $primaryId = FALSE; - foreach ($params[$blockName] as $count => $value) { - $blockId = CRM_Utils_Array::value('id', $value); - if ($blockId) { - if (is_array($blockIds) - && array_key_exists($blockId, $blockIds) - ) { - unset($blockIds[$blockId]); - } - else { - unset($value['id']); - } - } - //lets allow to update primary w/ more cleanly. - if (!$resetPrimaryId && !empty($value['is_primary'])) { - $primaryId = TRUE; - if (is_array($blockIds)) { - foreach ($blockIds as $blockId => $blockValue) { - if (!empty($blockValue['is_primary'])) { - $resetPrimaryId = $blockId; - break; - } - } - } - if ($resetPrimaryId) { - $baoString = 'CRM_Core_BAO_' . $blockName; + // For each submitted value + foreach ($submittedValues as $count => $submittedValue) { + + // Set the contact ID + $submittedValue['contact_id'] = $contactId; + + // If this is a primary value, and we haven't unset a primary value yet, and there are values on the contact + // Then unset any primary value currently on the Contact + if (!empty($submittedValue['is_primary']) && !$resetPrimary && is_array($existingValues)) { + foreach ($existingValues as $existingValueId => $existingValue) { + if (!empty($existingValue['is_primary'])) { + + // @todo Can we refactor this? $block = new $baoString(); $block->selectAdd(); $block->selectAdd("id, is_primary"); - $block->id = $resetPrimaryId; + $block->id = $existingValue['id']; if ($block->find(TRUE)) { $block->is_primary = FALSE; $block->save(); } $block->free(); + + // Stop looping since we found a match + $resetPrimary = TRUE; + break; } } } - } - foreach ($params[$blockName] as $count => $value) { - if (!is_array($value)) { - continue; + // If there is already an ID passed in + if (!empty($submittedValue['id'])) { + // If the ID already exists on the contact + // Then we don't want to match on it later, so unset it + if (array_key_exists($submittedValue['id'], $existingValues)) { + unset($existingValues[$existingValueId]); + } + // Otherwise it is a new value, so ignore the passed in ID + else { + unset($submittedValue['id']); + } } - $contactFields = array( - 'contact_id' => $contactId, - 'location_type_id' => CRM_Utils_Array::value('location_type_id', $value), - ); - //check for update - if (empty($value['id']) && - is_array($blockIds) && !empty($blockIds) - ) { - foreach ($blockIds as $blockId => $blockValue) { - if ($updateBlankLocInfo) { - if (!empty($blockIds[$count])) { - $value['id'] = $blockIds[$count]['id']; - unset($blockIds[$count]); - } - } - else { - if ($blockValue['locationTypeId'] == CRM_Utils_Array::value('location_type_id', $value)) { - $valueId = FALSE; - - if ($blockName == 'phone') { - $phoneTypeBlockValue = CRM_Utils_Array::value('phoneTypeId', $blockValue); - if ($phoneTypeBlockValue == CRM_Utils_Array::value('phone_type_id', $value)) { - $valueId = TRUE; - } - } - elseif ($blockName == 'im') { - $providerBlockValue = CRM_Utils_Array::value('providerId', $blockValue); - if ($providerBlockValue == $value['provider_id']) { - $valueId = TRUE; - } + // Otherwise, if there was no ID passed in + // Loop through the current values, and find the first match on location type + else { + foreach ($existingValues as $existingValueId => $existingValue) { + if ($existingValue['locationTypeId'] == $submittedValue['location_type_id']) { + + // Also require a match on 'type id' for phone and IM blocks + $matchFound = FALSE; + + if ($blockName == 'phone') { + if (CRM_Utils_Array::value('phoneTypeId', $existingValue) == CRM_Utils_Array::value('phone_type_id', $submittedValue)) { + $matchFound = TRUE; } - else { - $valueId = TRUE; + } + elseif ($blockName == 'im') { + if (CRM_Utils_Array::value('providerId', $existingValue) == CRM_Utils_Array::value('provider_id', $submittedValue)) { + $matchFound = TRUE; } + } + else { + $matchFound = TRUE; + } - if ($valueId) { - //assigned id as first come first serve basis - $value['id'] = $blockValue['id']; - if (!$primaryId && !empty($blockValue['is_primary'])) { - $value['is_primary'] = $blockValue['is_primary']; - } - unset($blockIds[$blockId]); - break; + // If we found a match + if ($matchFound) { + // Match up the ID + $submittedValue['id'] = $existingValue['id']; + // If the submitted value is not primary, but the matched value is + // Then set the submitted value to be primary + if (empty($submittedValue['is_primary']) && !empty($existingValue['is_primary'])) { + $submittedValue['is_primary'] = 1; } + // Remove the original value from the array so we don't match on it again + unset($existingValues[$existingValueId]); + break; } } } } - $dataExits = self::dataExists(self::$requiredBlockFields[$blockName], $value); + // Check if data exists in the submitted value + $dataExists = self::dataExists(self::$requiredBlockFields[$blockName], $submittedValue); - // Note there could be cases when block info already exist ($value[id] is set) for a contact/entity - // BUT info is not present at this time, and therefore we should be really careful when deleting the block. - // $updateBlankLocInfo will help take appropriate decision. CRM-5969 - if (!empty($value['id']) && !$dataExits && $updateBlankLocInfo) { - //delete the existing record - self::blockDelete($blockName, array('id' => $value['id'])); - continue; - } - elseif (!$dataExits) { - continue; - } + // If there is data + if ($dataExists) { - if ($isPrimary && !empty($value['is_primary'])) { - $contactFields['is_primary'] = $value['is_primary']; - $isPrimary = FALSE; - } - else { - $contactFields['is_primary'] = 0; + // "There can be only one" primary / billing block + if (!$primarySet && !empty($submittedValue['is_primary'])) { + $submittedValue['is_primary'] = 1; + $primarySet = TRUE; + } + else { + $contactFields['is_primary'] = 0; + } + + if (!$billingSet && !empty($submittedValue['is_billing'])) { + $submittedValue['is_billing'] = 1; + $billingSet = TRUE; + } + else { + $contactFields['is_billing'] = 0; + } + + // Add the value to the list of blocks + $blocks[] = $baoString::add($submittedValue); } - if ($isBilling && !empty($value['is_billing'])) { - $contactFields['is_billing'] = $value['is_billing']; - $isBilling = FALSE; + // Otherwise, if there is no data, and there is an ID, and we are deleting 'blanked' values + // Then delete it + elseif (!empty($submittedValue['id']) && $updateBlankLocInfo) { + self::blockDelete($blockName, array('id' => $submittedValue['id'])); } + + // Otherwise we ignore it else { - $contactFields['is_billing'] = 0; } - $blockFields = array_merge($value, $contactFields); - $baoString = 'CRM_Core_BAO_' . $name; - $blocks[] = $baoString::add($blockFields); } return $blocks;