From: eileen Date: Fri, 2 Feb 2024 04:05:20 +0000 (+1300) Subject: Fix 5.67 regression on loading custom data defaults on contribution page X-Git-Url: https://vcs.fsf.org/?a=commitdiff_plain;h=4a5e1e0ffc0f8122943166d7bb3e25366fe19e1d;p=civicrm-core.git Fix 5.67 regression on loading custom data defaults on contribution page --- diff --git a/CRM/Contribute/Form/Contribution/Main.php b/CRM/Contribute/Form/Contribution/Main.php index cd5fe3c026..501b950a4d 100644 --- a/CRM/Contribute/Form/Contribution/Main.php +++ b/CRM/Contribute/Form/Contribution/Main.php @@ -139,36 +139,26 @@ class CRM_Contribute_Form_Contribution_Main extends CRM_Contribute_Form_Contribu * Set the default values. */ public function setDefaultValues() { + $fields = $this->getProfileCustomFields(); + // Set defaults for custom fields based on their configured default values. + // Note that these will be overridden further down to those relevant to the + // specific contact or entity, if one is determined. + foreach (array_keys($fields) as $customFieldID) { + if ($customFieldID) { + CRM_Core_BAO_CustomField::setProfileDefaults($customFieldID, 'custom_' . $customFieldID, $this->_defaults, + NULL, CRM_Profile_Form::MODE_REGISTER + ); + } + } // check if the user is registered and we have a contact ID $contactID = $this->getContactID(); - if (!empty($contactID)) { - $fields = []; - $contribFields = CRM_Contribute_BAO_Contribution::getContributionFields(); - - // remove component related fields - foreach ($this->_fields as $name => $fieldInfo) { - //don't set custom data Used for Contribution (CRM-1344) - if (substr($name, 0, 7) === 'custom_') { - $id = substr($name, 7); - if (!CRM_Core_BAO_CustomGroup::checkCustomField($id, ['Contribution', 'Membership'])) { - continue; - } - // ignore component fields - } - elseif (array_key_exists($name, $contribFields) || (substr($name, 0, 11) === 'membership_') || (substr($name, 0, 13) == 'contribution_')) { - continue; - } - $fields[$name] = $fieldInfo; - } - - if (!empty($fields)) { - CRM_Core_BAO_UFGroup::setProfileDefaults($contactID, $fields, $this->_defaults); - } - $billingDefaults = $this->getProfileDefaults('Billing', $contactID); $this->_defaults = array_merge($this->_defaults, $billingDefaults); + $fields = $this->getContactProfileFields(); + CRM_Core_BAO_UFGroup::setProfileDefaults($contactID, $fields, $this->_defaults); } + $balance = $this->getContributionBalance(); if ($balance) { $this->_defaults['total_amount'] = CRM_Utils_Money::formatLocaleNumericRoundedForDefaultCurrency($balance); @@ -230,7 +220,7 @@ class CRM_Contribute_Form_Contribution_Main extends CRM_Contribute_Form_Contribu $this->_defaults["billing_state_province_id-{$this->_bltID}"] = $config->defaultContactStateProvince; } - $entityId = $memtypeID = NULL; + $memtypeID = NULL; if ($this->_priceSetId) { if (($this->isMembershipPriceSet() && !$this->isDefined('CurrentMembership')) || $this->_defaultMemTypeId) { $selectedCurrentMemTypes = []; @@ -261,7 +251,23 @@ class CRM_Contribute_Form_Contribution_Main extends CRM_Contribute_Form_Contribu } } } - $entityId = CRM_Utils_Array::value('id', CRM_Member_BAO_Membership::getContactMembership($contactID, $memtypeID, NULL)); + $membershipID = CRM_Utils_Array::value('id', CRM_Member_BAO_Membership::getContactMembership($contactID, $memtypeID, NULL)); + if ($contactID) { + // Set the default values for any membership custom fields on the page via a profile. + // Note that this will have been done further up if the contact ID was not determined. + foreach ($this->_fields as $name => $field) { + if ($customFieldID = CRM_Core_BAO_CustomField::getKeyID($name)) { + // check if the custom field is on a membership, we only want to load + // defaults for membership custom fields here, not contact fields + if (!CRM_Core_BAO_CustomGroup::checkCustomField($customFieldID, ['Membership']) + ) { + CRM_Core_BAO_CustomField::setProfileDefaults($customFieldID, $name, $this->_defaults, + $membershipID, CRM_Profile_Form::MODE_REGISTER + ); + } + } + } + } } else { CRM_Price_BAO_PriceSet::setDefaultPriceSet($this, $this->_defaults); @@ -274,21 +280,6 @@ class CRM_Contribute_Form_Contribution_Main extends CRM_Contribute_Form_Contribu if (array_key_exists('contribution_campaign_id', $this->_fields)) { $this->_defaults['contribution_campaign_id'] = $this->_values['campaign_id'] ?? NULL; } - - //set custom field defaults - foreach ($this->_fields as $name => $field) { - if ($customFieldID = CRM_Core_BAO_CustomField::getKeyID($name)) { - // check if the custom field is on a membership, we only want to load - // defaults for membership custom fields here, not contact fields - if (!isset($this->_defaults[$name]) - && !CRM_Core_BAO_CustomGroup::checkCustomField($customFieldID, ['Membership']) - ) { - CRM_Core_BAO_CustomField::setProfileDefaults($customFieldID, $name, $this->_defaults, - $entityId, CRM_Profile_Form::MODE_REGISTER - ); - } - } - } } if (!empty($this->_paymentProcessors)) { @@ -1898,4 +1889,59 @@ class CRM_Contribute_Form_Contribution_Main extends CRM_Contribute_Form_Contribu return TRUE; } + /** + * Get fields from the profiles in use that related to contacts. + * + * The fields are keyed by the field name and the keys are the metadata. + * Fields that extend Membership or Contribution are excluded. + * + * @return array + * @throws \CRM_Core_Exception + */ + private function getContactProfileFields(): array { + $fields = []; + $contribFields = CRM_Contribute_BAO_Contribution::getContributionFields(); + + // remove component related fields + foreach ($this->_fields as $name => $fieldInfo) { + //don't set custom data Used for Contribution (CRM-1344) + if (substr($name, 0, 7) === 'custom_') { + $id = substr($name, 7); + if (!CRM_Core_BAO_CustomGroup::checkCustomField($id, [ + 'Contribution', + 'Membership', + ])) { + continue; + } + // ignore component fields + } + elseif (array_key_exists($name, $contribFields) || (substr($name, 0, 11) === 'membership_') || (substr($name, 0, 13) == 'contribution_')) { + continue; + } + $fields[$name] = $fieldInfo; + } + return $fields; + } + + /** + * Get metadata for all custom fields in the attached profiles. + * + * Fields are keyed by the custom field ID. + * + * @return array + */ + private function getProfileCustomFields (): array { + // remove component related fields + $customFields = []; + foreach ($this->_fields as $name => $fieldInfo) { + //don't set custom data Used for Contribution (CRM-1344) + if (str_starts_with($name, 'custom_')) { + $id = substr($name, 7); + $customFields[(int) $id] = $fieldInfo; + } + } + return $customFields; + + } + }