From b012db62572a2d57535c57e402dc259a535fdcac Mon Sep 17 00:00:00 2001 From: eileen Date: Mon, 19 Oct 2020 16:46:23 +1300 Subject: [PATCH] Membership BAO - do not require date fields to be passed in on update A lot of complexity in membership code is that the BAO currently REQUIRES already-saved date fields to be passed in. This alters that such that the are loaded from the DB if not passed in. --- CRM/Member/BAO/Membership.php | 25 ++++++++++++++++++++----- CRM/Member/Form/MembershipRenewal.php | 8 +------- 2 files changed, 21 insertions(+), 12 deletions(-) diff --git a/CRM/Member/BAO/Membership.php b/CRM/Member/BAO/Membership.php index 60331c3330..f4fe3370dd 100644 --- a/CRM/Member/BAO/Membership.php +++ b/CRM/Member/BAO/Membership.php @@ -250,11 +250,26 @@ class CRM_Member_BAO_Membership extends CRM_Member_DAO_Membership { // eg pay later membership, membership update cron CRM-3984 if (empty($params['is_override']) && empty($params['skipStatusCal'])) { - // @todo - we should be able to count on dates being correctly formatted by they time they hit the BAO. - // Maybe do some tests & throw some deprecation warnings if they aren't? - $params['start_date'] = trim($params['start_date']) ? date('Ymd', strtotime(trim($params['start_date']))) : 'null'; - $params['end_date'] = trim($params['end_date']) ? date('Ymd', strtotime(trim($params['end_date']))) : 'null'; - $params['join_date'] = trim($params['join_date']) ? date('Ymd', strtotime(trim($params['join_date']))) : 'null'; + $fieldsToLoad = []; + foreach (['start_date', 'end_date', 'join_date'] as $dateField) { + if (!empty($params[$dateField]) && $params[$dateField] !== 'null' && strpos($params[$dateField], date('Ymd', strtotime(trim($params[$dateField])))) !== 0) { + $params[$dateField] = date('Ymd', strtotime(trim($params[$dateField]))); + // @todo enable this once core is using the api. + // Civi::log()->warning('Relying on the BAO to clean up dates is deprecated. Call membership create via the api', ['civi.tag' => 'deprecated']); + } + if (!empty($params['id']) && empty($params[$dateField])) { + $fieldsToLoad[] = $dateField; + } + } + if (!empty($fieldsToLoad)) { + $membership = civicrm_api3('Membership', 'getsingle', ['id' => $params['id'], 'return' => $fieldsToLoad]); + foreach ($fieldsToLoad as $fieldToLoad) { + $params[$fieldToLoad] = $membership[$fieldToLoad]; + } + } + $params['start_date'] = $params['start_date'] ?: 'null'; + $params['end_date'] = $params['end_date'] ?: 'null'; + $params['join_date'] = $params['join_date'] ?: 'null'; //fix for CRM-3570, during import exclude the statuses those having is_admin = 1 $excludeIsAdmin = $params['exclude_is_admin'] ?? FALSE; diff --git a/CRM/Member/Form/MembershipRenewal.php b/CRM/Member/Form/MembershipRenewal.php index 87be031903..f779867e9d 100644 --- a/CRM/Member/Form/MembershipRenewal.php +++ b/CRM/Member/Form/MembershipRenewal.php @@ -732,7 +732,6 @@ class CRM_Member_Form_MembershipRenewal extends CRM_Member_Form { $ids = []; $currentMembership = civicrm_api3('Membership', 'getsingle', ['id' => $memParams['id']]); - $memParams['join_date'] = $currentMembership['join_date']; // Do NOT do anything. //1. membership with status : PENDING/CANCELLED (CRM-2395) //2. Paylater/IPN renew. CRM-4556. @@ -741,14 +740,9 @@ class CRM_Member_Form_MembershipRenewal extends CRM_Member_Form { // CRM-15475 array_search('Cancelled', CRM_Member_PseudoConstant::membershipStatus(NULL, " name = 'Cancelled' ", 'name', FALSE, TRUE)), ])) { - $memParams = array_merge($memParams, [ - 'status_id' => $currentMembership['status_id'], - 'start_date' => $currentMembership['start_date'], - 'end_date' => $currentMembership['end_date'], - ]); return CRM_Member_BAO_Membership::create($memParams); } - + $memParams['join_date'] = date('Ymd', strtotime($currentMembership['join_date'])); $isMembershipCurrent = CRM_Core_DAO::getFieldValue('CRM_Member_DAO_MembershipStatus', $currentMembership['status_id'], 'is_current_member'); // CRM-7297 Membership Upsell - calculate dates based on new membership type -- 2.25.1