Details
-
Type: Bug
-
Status: Done/Fixed
-
Priority: Critical
-
Resolution: Fixed/Completed
-
Affects Version/s: 4.7.9
-
Fix Version/s: 4.7.10
-
Component/s: CiviContribute, CiviMember
-
Labels:
-
Documentation Required?:None
-
Funding Source:Core Team Funds
Description
Creating a new membership using a front-end contribution form with cid=0 can, under some circumstances, overwrite the information of an unrelated membership record if the membership_id of the existing membership record is the same as the contribution_id of the newly-created contribution record.
If there is no existing membership record whose membership_id as the new contribution_id, there is no issue.
I can reproduce this on our test site. After completing the "new membership" form with cid=0, there are three new entries created in the civicrm_membership_log table. Two have the membership_id of the newly-created membership; the third has a different membership_id, which is that of an older existing membership. The data in that membership is overwritten with that of the newly submitted membership. And, in several tests, the overwritten membership_id always matches the contribution_id of the form submission.
There are also two records created in table membership_payment, one with the correct (new) membership, the other with the membership_id (incorrectly) matching the contribution_id.
It's an insidious bug because each occurrence will silently corrupt an existing membership record. But you need to have a membership_id at least as high as the next contribution_id for it to manifest. (We have more memberships than contributions, so it does.)
I think I may have found a logic error that, at least, leads to the duplicate membership_payment entry. In
file: civicrm/CRM/Price/BAO/LineItem.php
function: processPriceSet($entityId, $lineItem, $contributionDetails = NULL, $entityTable = 'civicrm_contribution', $update = FALSE)
This function beginning at line 422 gets called with $entityId set to the contribution_id and $entityTable set to 'civicrm_contribution'.
But down at line 439, we have:
if (!empty($line['membership_type_id']))
{ $line['entity_table'] = 'civicrm_membership'; }For a membership form, $line['membership_type_id'] is, in fact, non-empty, so $line['entity_table'] does get set to 'civicrm_membership'. But $line['entity_id'] is left at its original value, that of the contribution_id.
So that, at line 454, we have
$lineItems = CRM_Price_BAO_LineItem::create($line);
which, I infer, would create a new entry related to a membership record whose membership_id is equal to the contribution_id.
Sorry I can't pin it down more closely, but I hope that is something to go on. (Note, this is same use case, but different behavior, than https://issues.civicrm.org/jira/browse/CRM-19092.)
Attachments
Issue Links
- links to