Development issueshttps://lab.civicrm.org/groups/dev/-/issues2022-12-08T09:42:33Zhttps://lab.civicrm.org/dev/core/-/issues/4023Check Clean URLs check: Frequent error noise when no contribution pages and p...2022-12-08T09:42:33ZJonGoldCheck Clean URLs check: Frequent error noise when no contribution pages and public can't access events#### Replication Steps
* Be on WordPress.
* Have no contribution pages.
* Have at least 1 active event.
* Remove "CiviEvent: register for events" permission from anonymous user.
Get a bunch of these errors:
```
[error]
$Fatal Error De...#### Replication Steps
* Be on WordPress.
* Have no contribution pages.
* Have at least 1 active event.
* Remove "CiviEvent: register for events" permission from anonymous user.
Get a bunch of these errors:
```
[error]
$Fatal Error Details = array:3 [
"message" => "You do not have permission to access this page."
"code" => null
"exception" => CRM_Core_Exception {#8688
#message: "You do not have permission to access this page."
#code: 0
#file: "/home/jon/local/nmysite/web/wp-content/plugins/civicrm/civicrm/CRM/Utils/System/WordPress.php"
#line: 615
#cause: null
-_trace: null
-errorData: array:1 [
"error_code" => 0
]
trace: {
/home/jon/local/nmysite/web/wp-content/plugins/civicrm/civicrm/CRM/Utils/System/WordPress.php:615 {
› $civicrm_wp_title = ts('You do not have permission to access this page.');
› throw new CRM_Core_Exception(ts('You do not have permission to access this page.'));
› }
}
/home/jon/local/nmysite/web/wp-content/plugins/civicrm/civicrm/CRM/Utils/System.php:62 { …}
/home/jon/local/nmysite/web/wp-content/plugins/civicrm/civicrm/CRM/Event/Page/EventInfo.php:42 { …}
/home/jon/local/nmysite/web/wp-content/plugins/civicrm/civicrm/CRM/Core/Invoke.php:319 { …}
/home/jon/local/nmysite/web/wp-content/plugins/civicrm/civicrm/CRM/Core/Invoke.php:69 { …}
/home/jon/local/nmysite/web/wp-content/plugins/civicrm/civicrm/CRM/Core/Invoke.php:36 { …}
/home/jon/local/nmysite/web/wp-content/plugins/civicrm/civicrm.php:1199 { …}
/home/jon/local/nmysite/web/wp-content/plugins/civicrm/includes/civicrm.basepage.php:380 { …}
/home/jon/local/nmysite/web/wp-includes/class-wp-hook.php:308 { …}
/home/jon/local/nmysite/web/wp-includes/class-wp-hook.php:332 { …}
/home/jon/local/nmysite/web/wp-includes/plugin.php:565 { …}
/home/jon/local/nmysite/web/wp-includes/class-wp.php:797 { …}
/home/jon/local/nmysite/web/wp-includes/functions.php:1332 { …}
/home/jon/local/nmysite/web/wp-blog-header.php:16 { …}
/home/jon/local/nmysite/web/index.php:17 { …}
}
}
]
```
I want to ping Eli Lisseck but I don't think they're pingable?https://lab.civicrm.org/dev/core/-/issues/4024progress output on stdout when emails are processed as activities2022-12-08T09:43:19Zsebalisprogress output on stdout when emails are processed as activitiesOn a CiviCRM instance I administrate, the Civi cron job is run via “cv api job.execute” with appropriate user and cwd parameters. The output is normally in JSON, so I decided to parse the output to see if there have been any problems. If...On a CiviCRM instance I administrate, the Civi cron job is run via “cv api job.execute” with appropriate user and cwd parameters. The output is normally in JSON, so I decided to parse the output to see if there have been any problems. If there are no problems, I suppress the output completely, to prevent Linux cron (which triggers the whole thing) from sending an automatic email to the admins. This has worked well so far.
For a short while we have defined two new email accounts that we use for “email to activity”. When there are new emails, we now get output on stdout that makes it impossible to parse the output as JSON. This prevents making the automatic decision on whether there has been a problem, so I revert to sending an email and I keep the output.
I looked into the cause and found that CRM/Utils/Mail/EmailProcessor.php contains several lines that write to stdout. To me these outputs should better go to the CiviCRM log or to stderr. But I don’t know what standards you follow for this or other components, so at this point I am not able to submit a pull request.
You can find the output I am referring to by searching CRM/Utils/Mail/EmailProcessor.php for the string “echo”. I quote them here, together with my opinion of what I would do with them (biased because of my current problem of course):
```
212 catch (Exception $e) {
213 echo $e->getMessage();
214 $store->markIgnored($key);
215 continue;
216 }
```
This seems better placed on stderr or as an error entry in the Civi log.
```
229 echo "Failed Processing: {$mail->subject}. Reason: {$result['error_message']}\n";
```
Same as above.
```
234 echo "Processed as Activity: {$mail->subject}\n";
```
This is the line I regularly get. I think a Civi log entry with an appropriate level below warning should be enough, or it should go to stderr.
```
391 echo "Failed Processing: {$mail->subject}, Action: $action, Job ID: $job, Queue ID: $queue, Hash: $hash. Reason: {$r esult['error_message']}\n";
```
Same as earlier, error entry in the Civi log or stderr
These lines have been around for many years (I checked), and there might be similar examples in several other places. Again, I don’t know what your conventions are.https://lab.civicrm.org/dev/core/-/issues/4025Import Memberships: activity date set to date of import instead of Membership...2023-11-08T00:50:05ZcomposerjkImport Memberships: activity date set to date of import instead of Membership Start DateOverview
----------------------------------------
For _Memberships > Import Memberships_, I would expect that the _Activity Date_ for _Membership Signup_ would be the required _Membership Start Date_. Instead, when one views Activities,...Overview
----------------------------------------
For _Memberships > Import Memberships_, I would expect that the _Activity Date_ for _Membership Signup_ would be the required _Membership Start Date_. Instead, when one views Activities, the _Membership Signup_ activity date is the date/time of the import.
Query on chat.civicrm.org (no replies, yet): https://chat.civicrm.org/civicrm/pl/jgrmtpxr878w3fbtrm6iia4rsw
It looks like @petednz also mentioned this issue back in 2017: https://chat.civicrm.org/civicrm/pl/sbj5yeuccfr65yy9wwmam3mxte
Reproduction steps
----------------------------------------
1. _Memberships > Import Memberships_ for an existing contact with a Membership Start Date set to some date in the past.
1. View the Membership Signup activity, perhaps via _Search > Find Activities_.
Current behaviour
----------------------------------------
The listed Activity Date is the date of the import.
Expected behaviour
----------------------------------------
I would expect that the _Activity Date_ would be the _Membership Start Date_, similar to how the _Activity Date_ for a _Contribution_ is set to the _Payment Received Date_.
Environment information
----------------------------------------
<!-- Some of the items below may not be relevant for every bug - if in doubt please include more information than you think is neccessary. -->
- __CiviCRM:__ 5.56.0, 5.55.2, 5.55.0, 5.54.0
- __CMS:__ WordPress 6.1.1
- __PHP:__ 8.1.13 (fpm-fcgi)
- __Database:__ 10.3.31-MariaDB engine: InnoDB 10 row format: Dynamic
- __Webserver:__ nginx/1.20.2
- __OS:__ Linux
Comments
----------------------------------------
In my case, part of this is maintaining history. At some point, I hope to import data for membership archives going back 80 years. From @petednz's mention, it sounds like the _Membership Dashboard_ will also look wrong.https://lab.civicrm.org/dev/joomla/-/issues/43PHP 8 causes 500 error2023-04-24T14:17:55Zjoshjosh@civicrm.orgPHP 8 causes 500 errorUpgrading from PHP 7.4 to PHP 8.0 on Joomla 4.2.5 and CiviCRM 5.56 results in a 500 error. Sample can be viewed at https://cividemo.com (currently running PHP 8.0), specifically at a public contribution page: https://cividemo.com/simple-...Upgrading from PHP 7.4 to PHP 8.0 on Joomla 4.2.5 and CiviCRM 5.56 results in a 500 error. Sample can be viewed at https://cividemo.com (currently running PHP 8.0), specifically at a public contribution page: https://cividemo.com/simple-contribution-page?view=Contributions&task=civicrm/contribute/transact&id=1&reset=1 as well as in the admin interface when browsing to: https://cividemo.com/administrator/index.php?option=com_civicrm
I believe this is related to permissions. If I enable or disable a user in Joomla, the site throws the same here. Here's a screencast: https://www.awesomescreenshot.com/video/13122436?key=fa4d6f06dd5831141ce90b1f9f89e82c
Note that I'm clicking the back button in the browser (not viewable in the screencast), yet you can see that the change to the user's state does take effect.
Moreoever, when reviewing user permissions for CiviCRM in the global configuration I receive this error:
`An error has occurred.
0 Failed opening required '/home/cividemo/public_html/libraries/joomla/form/fields/rules.php' (include_path='.:/opt/remi/php80/root/usr/share/pear:/opt/remi/php80/root/usr/share/php:/usr/share/pear:/usr/share/php')`seamusleeseamusleehttps://lab.civicrm.org/dev/core/-/issues/4030Searchkit: Escaping for regex breaks search with join2022-12-12T08:10:01ZlarsssandergreenSearchkit: Escaping for regex breaks search with joinIf you try a Searchkit search for Addresses with Street Address matching pattern `[a-z]\s`, the results will return as expected, with the regex pattern shown as `"[a-z]\\s"`. However, if you do a search for Contacts with or without Addre...If you try a Searchkit search for Addresses with Street Address matching pattern `[a-z]\s`, the results will return as expected, with the regex pattern shown as `"[a-z]\\s"`. However, if you do a search for Contacts with or without Addresses with Street Address matching pattern `[a-z]\s`, the results will be borked because the pattern will be `"\"[a-z]\\\\s\""`. Similar results are found with other fields or entities.
Tested on dmaster (5.58) and 5.49.5.https://lab.civicrm.org/dev/core/-/issues/4032civicrm_group_contact has a email_id field, but this does not appear to be used2022-12-20T10:04:29ZBradley Taylorcivicrm_group_contact has a email_id field, but this does not appear to be usedOverview
----------------------------------------
I'm currently working with an organisation who are moving to CiviCRM. They have contacts, who frequently have multiple employers, typically with a work email address for each employment. ...Overview
----------------------------------------
I'm currently working with an organisation who are moving to CiviCRM. They have contacts, who frequently have multiple employers, typically with a work email address for each employment. When signing up to email groups, it's often useful for these contacts to be able to control which group subscription goes to which email address.
For example:
We have a contact, Bob.
Bob is employed by CompanyA and CompanyB, and has the email addresses bob@company-a.com and bob@company-b.com. bob@company-a.com is the primary email address.
Bob signs up for two three mailing lists, but wants two to go to his primary email address and one to go to his secondary email address.
Current behaviour
----------------------------------------
This isn't something which is possible through the current CiviCRM UI, which is fine (I can't imagine this use-case is that common).
However, looking at the database table `civicrm_group_contact` it has a field `email_id`, with the comment `Optional email to associate with this membership`. This field is exposed in the CiviCRM API and SearchKit.
As far as I can tell, it appears that this `email_id` field is not actually used by any logic within CiviCRM core. It seems to be at least 10 years old (dating back to the pre-Git days), and so it's possible the `email_id` was introduced as part of a feature that was never finished.
Expected behaviour
----------------------------------------
I had assumed that when `email_id` was set, this email address would be used as the email address to actually be emailed, when sending a bulk mailing to a group via the CiviMail component. This unfortunately does not seem to be the case.
I think if the field exists, it should be used in this way. If not it should probably be deprecated and removed from core.
Currently it is possible to set the "Location Type" and "Selection Method" when selecting a group as part of the new mailing form. If a location type is set I would expect it to take precedence over the configured `email_id` (although this detail could be debated either way).
Whilst it might be nice if there was an associated UI to select the email address, I don't think any UI changes are required to make the `email_id` field useful - if CiviCRM simply uses the value (as set via plugin code or the API) that would be enough to enable the use case detailed above.
Comments
----------------------------------------
It's possible that I'm completely misunderstanding what the `email_id` field is for, and it is actually used - if so I'd love to know the details from someone closer to this area of the core code!https://lab.civicrm.org/dev/core/-/issues/4033Proposal: Add optional separate mailing label format for organizations2023-01-11T23:31:32ZlarsssandergreenProposal: Add optional separate mailing label format for organizationsOften, I find myself editing the mailing label format when making mailing labels for organizations. In this case, we want Addressee and Name (the name of the person at the org plus the name of the org on the next line), while for individ...Often, I find myself editing the mailing label format when making mailing labels for organizations. In this case, we want Addressee and Name (the name of the person at the org plus the name of the org on the next line), while for individuals we just want the Addressee (otherwise, it would say their name twice). I imagine we aren't alone in this.
In order to avoid this hassle, it would make sense to have an option to add a second mailing label format for organizations. If there is a format specified in this field, it would be used for organizations. If this field is left blank, the default label format would be used for organizations. I think that would keep it simple and wouldn't change anything unless someone intentionally added an organizational label format. We could also add a format for households if desired - would that be valuable to anyone?https://lab.civicrm.org/dev/core/-/issues/4034CRM Builder - Profiles allow multiple Formatting Free HTML fields in forms2023-01-03T14:46:14ZJonny ToomeyCRM Builder - Profiles allow multiple Formatting Free HTML fields in formsOverview
----------------------------------------
When building a conribution form, or altering the profile for a form, the Javascript rightly detects duplciate fields and prevents saving. Would like to make an exception for Free HTML fi...Overview
----------------------------------------
When building a conribution form, or altering the profile for a form, the Javascript rightly detects duplciate fields and prevents saving. Would like to make an exception for Free HTML fields (could be expanded to anything from the Formatting section if that section should expand)
Current workaround
----------------------------------------
Saving after each change gets around this for now
Proposed behaviour
----------------------------------------
alter the markDuplicates() method so that is_duplicate class is only applied when the ufFieldModel does not have the label 'Free HTML'. This will allow multiple Free HTML fields for formatting forms
Proposed solution
----------------------------------------
civicrm/js/model/crm.uf.js
![markDuplicates](/uploads/fe6b7f9c7da464418d2bd6a27f75639a/markDuplicates.PNG)https://lab.civicrm.org/dev/core/-/issues/4040FormBuilder - can no longer customise via GUI editor2022-12-20T10:00:19ZeileenFormBuilder - can no longer customise via GUI editorDeduper has long had an afform supplied by the extension. It pre-dates much recent work.
I seem to have lost the ability to edit these - even though the code editor is enabled
![image](/uploads/ddbaf635f2ee64fe325df5f3493638ae/image.pn...Deduper has long had an afform supplied by the extension. It pre-dates much recent work.
I seem to have lost the ability to edit these - even though the code editor is enabled
![image](/uploads/ddbaf635f2ee64fe325df5f3493638ae/image.png)
I understand the code editor is deprecated but I find myself a bit stuck
- Deduper ships with a form that displays basic contact info an uses the editable angular plugin to do a kind of editability I don't think I can do with a configured afform - ie
Both contact panes are instances of `basicContact.aff`
![image](/uploads/b2780a2cf589716008db7a1c383f6fa0/image.png)
However the editability is edit-in-place but Not edit field-by-field in place (& not all fields are permitted)
![image](/uploads/96f5aa35f12bfda5a91a5349593bbde9/image.png)
My expectation was that sites would use the Code Editor to add non-standard fields in (in our case 'Partner') - but I no longer seem to be able to (it's been a while since I last tried).
Ideally I would simplify / standardise the form using FormBuilder https://github.com/eileenmcnaughton/deduper/blob/master/ang/contactBasic.aff.html
- but I don't think it can provide all the features
Note - I don't quite know why the edit links are gone - perhaps that is resolvable? I did just check the extension is enabled & permissions are there - @colemanw do you know?https://lab.civicrm.org/dev/core/-/issues/4041Should we hard-code messages that event registration cancellations are not re...2022-12-20T10:01:32ZlarsssandergreenShould we hard-code messages that event registration cancellations are not refundable?Self-service cancellation of event registrations does not support refunds, so there are at least two places where the registrants are told that there are no refunds (in the registration confirmation email if self-service cancellation is ...Self-service cancellation of event registrations does not support refunds, so there are at least two places where the registrants are told that there are no refunds (in the registration confirmation email if self-service cancellation is enabled and when they actually try to cancel, though this has been broken since 5.43).
I wonder if it makes sense for CiviCRM to put this expectation that there are no refunds into code. Even though refunds are not supported via the self-service form, organizations may have policies that are different and may manually process refunds in some cases. I think it would make more sense to simply not say anything about refunds and allow organizations to define their own policies in the event registration.
So my proposal: Remove the warning about no refunds from self-service cancellation (which doesn't currently work anyways), remove the text about no refunds from event registration confirmation templates and remove the help text that mentions no refunds from the self-service cancellation option on the event registration set up.
It's far from ideal either way, but I think leaving it open is better than specifying a policy that may not work for all.https://lab.civicrm.org/dev/core/-/issues/4042Link to import search display goes to front end form in wordpress2022-12-20T10:02:03ZeileenLink to import search display goes to front end form in wordpressAfter doing an import with Civi-Import enabled there is a link from the import summary screen to the error page (perhaps not if there are no errors?) - that links to the search kit display, filtered for errors - but on Wordpress I'm lan...After doing an import with Civi-Import enabled there is a link from the import summary screen to the error page (perhaps not if there are no errors?) - that links to the search kit display, filtered for errors - but on Wordpress I'm landing on a front end url.
E.g you can go back to the contact summary screen via Reports->My imports
![image](/uploads/f729ec641ae159fdbf18e922fc4f12b9/image.png)
And I'm looking at the link to view errors
![image](/uploads/05b060cfa95c0b5371a3e104235db5c0/image.png)
On drupal I correctly end up at https://dmaster.localhost:32353/civicrm/search#/display/Import_5/Import_5?_status=ERROR
Currently it is being assigned [here](https://github.com/civicrm/civicrm-core/blob/da9cd2454fbca7e38a78f7cb1539decaa5c2f4ff/ext/civiimport/civiimport.php#L278) in a non-WP-friendly way
```
if ($formName === 'CRM_Contact_Import_Form_Summary') {
$form->assign('downloadErrorRecordsUrl', '/civicrm/search#/display/Import_' . $form->getUserJobID() . '/Import_' . $form->getUserJobID() . '?_status=ERROR');
}
```
On my WP site the search display url is
The correct url is
https://bepartoftheart.co.nz/wp-admin/admin.php?page=CiviCRM&q=civicrm%2Fsearch#/display/Import_36/Import_36
- with the `_status=Error` added - which doesn't seem to work...
But the things I tried to generate the url didn't work...
```
if ($formName === 'CRM_Contact_Import_Form_Summary') {
$form->assign('downloadErrorRecordsUrl', CRM_Utils_System::url('civicrm/search', ['_status'=> 'ERROR'], FALSE, '/display/Import_' . $form->getUserJobID() . '/Import_' . $form->getUserJobID(), FALSE, TRUE));
}
```
But wind up at
https://bepartoftheart.co.nz/civicrm/search/?_status=ERROR#/display/Import_36/Import_36
Or
```
if ($formName === 'CRM_Contact_Import_Form_Summary') {
$form->assign('downloadErrorRecordsUrl', CRM_Utils_System::url('civicrm/search/display/Import_' . $form->getUserJobID() . '/Import_' . $form->getUserJobID(), ['_status'=> 'ERROR'], FALSE, NULL, FALSE, TRUE));
}
```
But wind up at
https://bepartoftheart.co.nz/civicrm/search/display/Import_36/Import_36/?_status=ERRORdhttps://lab.civicrm.org/dev/core/-/issues/4044User authentication via authx is not working for non CMS users using formbuil...2022-12-22T08:14:28ZKurund JalmiUser authentication via authx is not working for non CMS users using formbuilder formsSteps to replicate:
- Create a form and enable tokens
- Send an email with form's complete url token to the non CMS user contact
- Open link in the email in the incognito window
- Form does not set defaults for the contact and saving the...Steps to replicate:
- Create a form and enable tokens
- Send an email with form's complete url token to the non CMS user contact
- Open link in the email in the incognito window
- Form does not set defaults for the contact and saving the form also fails.https://lab.civicrm.org/dev/core/-/issues/4045Ideas for (funded) speed improvements in mailings2023-08-28T14:44:15ZAndrew WestIdeas for (funded) speed improvements in mailingsWe'd be interested in funding some speed improvements when building mailing recipients in CiviMail. They'd inherently feed through to Mosaico, I think.
We find the mailings screens pretty snappy apart from selecting recipients. There a...We'd be interested in funding some speed improvements when building mailing recipients in CiviMail. They'd inherently feed through to Mosaico, I think.
We find the mailings screens pretty snappy apart from selecting recipients. There are few bottlenecks that it'd be nice to get rid of:
**Improve the dropdown**
When you have lots of groups and mailings the dropdown doesn't work very well. It stalls, with multiple spinners appearing, or wipes out your text while typing, or says 'none found' for a bit before updating, or alternates between 'Searching' and 'Loading', and generally takes an achingly long time to find the groups in its own dropdown.
![image](/uploads/91dcd7a0a2c2e7d3230c4016d1d49db0/image.png)
Compare this to the smart group dropdown in Search Kit, which is blindingly fast.
Maybe this could be replaced with the new API4-based entityref? Possibly split into two (or even four?): Groups to include / Groups to Exclude / Mailings to include / Mailings to exclude?
**Improve generating the list of recipients**
A complicated selection of groups can easily take 30 seconds to update and save, for us. This is very frustrating when adding one smart group at a time in the dropdown. Possible fixes:
- Refactor CRM_Mailing_BAO_Mailing::getRecipients(). At the moment this function seems to create a lot of temp tables, and uses a bunch of heavy queries to compare them against each other. Again, Search Kit can do complicated includes/excludes way faster. So I figure this could be modernised.
- Possibly the slow part here is emptying/filling civicrm_mailing_recipients each time the criteria are changed. Maybe add a 'getRecipientCountPreview' function to get a count of recipients without actually populating the table? This would let people experiment in the mailing screen quickly. Then only generate the actual recipient list when the mailing is scheduled or saved as a draft?
Any other ideas? Or thoughts on whether the above makes sense?
We could fund maybe 15hrs on this atm. If anyone wants to join us that'd be great too :-)https://lab.civicrm.org/dev/core/-/issues/4047htmlspecialchars() issue on PHP8 and CiviReport2023-01-04T07:44:17ZJonGoldhtmlspecialchars() issue on PHP8 and CiviReport**Note** I've been seeing this `htmlspecialchars()` error on this line frequently on PHP 8. This is just the one instance I investigated thoroughly.
When attempting to use a particular CiviReport instance, we get a WSOD with this error...**Note** I've been seeing this `htmlspecialchars()` error on this line frequently on PHP 8. This is just the one instance I investigated thoroughly.
When attempting to use a particular CiviReport instance, we get a WSOD with this error in watchdog:
```
TypeError: htmlspecialchars(): Argument #1 ($string) must be of type string, array given in htmlspecialchars() (line 144 of /var/www/mysite/vendor/civicrm/civicrm-packages/HTML/Common.php)
#0 /home/jon/local/mysite/vendor/civicrm/civicrm-packages/HTML/Common.php(144): htmlspecialchars()
#1 /home/jon/local/mysite/vendor/civicrm/civicrm-packages/HTML/QuickForm/input.php(154): HTML_Common->_getAttrString()
#2 /home/jon/local/mysite/vendor/civicrm/civicrm-packages/HTML/QuickForm/Renderer/Array.php(307): HTML_QuickForm_input->toHtml()
#3 /home/jon/local/mysite/vendor/civicrm/civicrm-packages/HTML/QuickForm/Renderer/ArraySmarty.php(189): HTML_QuickForm_Renderer_Array->_elementToArray()
#4 /home/jon/local/mysite/vendor/civicrm/civicrm-core/CRM/Core/Form/Renderer.php(87): HTML_QuickForm_Renderer_ArraySmarty->_elementToArray()
#5 /home/jon/local/mysite/vendor/civicrm/civicrm-packages/HTML/QuickForm/Renderer/Array.php(221): CRM_Core_Form_Renderer->_elementToArray()
#6 /home/jon/local/mysite/vendor/civicrm/civicrm-packages/HTML/QuickForm/element.php(415): HTML_QuickForm_Renderer_Array->renderElement()
#7 /home/jon/local/mysite/vendor/civicrm/civicrm-packages/HTML/QuickForm.php(1705): HTML_QuickForm_element->accept()
#8 /home/jon/local/mysite/vendor/civicrm/civicrm-core/CRM/Core/Form.php(1136): HTML_QuickForm->accept()
#9 /home/jon/local/mysite/vendor/civicrm/civicrm-core/CRM/Core/QuickForm/Action/Display.php(95): CRM_Core_Form->toSmarty()
#10 /home/jon/local/mysite/vendor/civicrm/civicrm-core/CRM/Core/QuickForm/Action/Display.php(83): CRM_Core_QuickForm_Action_Display->renderForm()
#11 /home/jon/local/mysite/vendor/civicrm/civicrm-packages/HTML/QuickForm/Controller.php(203): CRM_Core_QuickForm_Action_Display->perform()
#12 /home/jon/local/mysite/vendor/civicrm/civicrm-packages/HTML/QuickForm/Page.php(103): HTML_QuickForm_Controller->handle()
#13 /home/jon/local/mysite/vendor/civicrm/civicrm-core/CRM/Core/Controller.php(355): HTML_QuickForm_Page->handle()
#14 /home/jon/local/mysite/vendor/civicrm/civicrm-core/CRM/Utils/Wrapper.php(98): CRM_Core_Controller->run()
#15 /home/jon/local/mysite/vendor/civicrm/civicrm-core/CRM/Report/Page/Instance.php(74): CRM_Utils_Wrapper->run()
#16 /home/jon/local/mysite/vendor/civicrm/civicrm-core/CRM/Core/Invoke.php(319): CRM_Report_Page_Instance->run()
#17 /home/jon/local/mysite/vendor/civicrm/civicrm-core/CRM/Core/Invoke.php(69): CRM_Core_Invoke::runItem()
#18 /home/jon/local/mysite/vendor/civicrm/civicrm-core/CRM/Core/Invoke.php(36): CRM_Core_Invoke::_invoke()
#19 /home/jon/local/mysite/web/modules/contrib/civicrm/src/Civicrm.php(88): CRM_Core_Invoke::invoke()
#20 /home/jon/local/mysite/web/modules/contrib/civicrm/src/Controller/CivicrmController.php(80): Drupal\civicrm\Civicrm->invoke()
#21 [internal function]: Drupal\civicrm\Controller\CivicrmController->main()
#22 /home/jon/local/mysite/web/core/lib/Drupal/Core/EventSubscriber/EarlyRenderingControllerWrapperSubscriber.php(123): call_user_func_array()
#23 /home/jon/local/mysite/web/core/lib/Drupal/Core/Render/Renderer.php(580): Drupal\Core\EventSubscriber\EarlyRenderingControllerWrapperSubscriber->Drupal\Core\EventSubscriber\{closure}()
#24 /home/jon/local/mysite/web/core/lib/Drupal/Core/EventSubscriber/EarlyRenderingControllerWrapperSubscriber.php(124): Drupal\Core\Render\Renderer->executeInRenderContext()
#25 /home/jon/local/mysite/web/core/lib/Drupal/Core/EventSubscriber/EarlyRenderingControllerWrapperSubscriber.php(97): Drupal\Core\EventSubscriber\EarlyRenderingControllerWrapperSubscriber->wrapControllerExecutionInRenderContext()
#26 /home/jon/local/mysite/vendor/symfony/http-kernel/HttpKernel.php(169): Drupal\Core\EventSubscriber\EarlyRenderingControllerWrapperSubscriber->Drupal\Core\EventSubscriber\{closure}()
#27 /home/jon/local/mysite/vendor/symfony/http-kernel/HttpKernel.php(81): Symfony\Component\HttpKernel\HttpKernel->handleRaw()
#28 /home/jon/local/mysite/web/core/lib/Drupal/Core/StackMiddleware/Session.php(58): Symfony\Component\HttpKernel\HttpKernel->handle()
#29 /home/jon/local/mysite/web/core/lib/Drupal/Core/StackMiddleware/KernelPreHandle.php(48): Drupal\Core\StackMiddleware\Session->handle()
#30 /home/jon/local/mysite/web/core/modules/page_cache/src/StackMiddleware/PageCache.php(106): Drupal\Core\StackMiddleware\KernelPreHandle->handle()
#31 /home/jon/local/mysite/web/core/modules/page_cache/src/StackMiddleware/PageCache.php(85): Drupal\page_cache\StackMiddleware\PageCache->pass()
#32 /home/jon/local/mysite/web/core/lib/Drupal/Core/StackMiddleware/ReverseProxyMiddleware.php(48): Drupal\page_cache\StackMiddleware\PageCache->handle()
#33 /home/jon/local/mysite/web/core/lib/Drupal/Core/StackMiddleware/NegotiationMiddleware.php(51): Drupal\Core\StackMiddleware\ReverseProxyMiddleware->handle()
#34 /home/jon/local/mysite/vendor/stack/builder/src/Stack/StackedHttpKernel.php(23): Drupal\Core\StackMiddleware\NegotiationMiddleware->handle()
#35 /home/jon/local/mysite/web/core/lib/Drupal/Core/DrupalKernel.php(707): Stack\StackedHttpKernel->handle()
#36 /home/jon/local/mysite/web/index.php(19): Drupal\Core\DrupalKernel->handle()
#37 {main}
```
I tracked it down to my `form_values` which is this:
```
a:27:{s:6:"fields";a:4:{s:9:"sort_name";s:1:"1";s:8:"event_id";s:1:"1";s:9:"status_id";s:1:"1";s:7:"role_id";s:1:"1";}s:12:"sort_name_op";s:3:"has";s:15:"sort_name_value";s:0:"";s:8:"email_op";s:3:"has";s:11:"email_value";s:0:"";s:11:"event_id_op";s:2:"in";s:14:"event_id_value";a:0:{}s:6:"sid_op";s:2:"in";s:9:"sid_value";a:0:{}s:6:"rid_op";s:2:"in";s:9:"rid_value";a:0:{}s:34:"participant_register_date_relative";s:1:"0";s:30:"participant_register_date_from";s:0:"";s:28:"participant_register_date_to";s:0:"";s:6:"eid_op";s:2:"in";s:9:"eid_value";a:0:{}s:11:"custom_4_op";s:2:"in";s:14:"custom_4_value";a:0:{}s:16:"blank_column_end";s:0:"";s:11:"description";s:44:"Provides lists of participants for an event.";s:13:"email_subject";s:0:"";s:8:"email_to";s:0:"";s:8:"email_cc";s:0:"";s:10:"permission";s:16:"access CiviEvent";s:6:"groups";s:0:"";s:7:"options";N;s:9:"domain_id";i:1;}
```
Unserialized:
```
array (
'fields' =>
array (
'sort_name' => '1',
'event_id' => '1',
'status_id' => '1',
'role_id' => '1',
),
'sort_name_op' => 'has',
'sort_name_value' => '',
'email_op' => 'has',
'email_value' => '',
'event_id_op' => 'in',
'event_id_value' => array (),
'sid_op' => 'in',
'sid_value' => array (),
'rid_op' => 'in',
'rid_value' => array (),
'participant_register_date_relative' => '0',
'participant_register_date_from' => '',
'participant_register_date_to' => '',
'eid_op' => 'in',
'eid_value' => array (),
'custom_4_op' => 'in',
'custom_4_value' => array (),
'blank_column_end' => '',
'description' => 'Provides lists of participants for an event.',
'email_subject' => '',
'email_to' => '',
'email_cc' => '',
'permission' => 'access CiviEvent',
'groups' => '',
'options' => NULL,
'domain_id' => 1,
)
```
The issue is `custom_4`, which is save as `in` `array()`. However, this is (and always has been) a free-entry text field, so "IN" should never have been an option. Pre-PHP8, this was ignored, now it's a fatal error.
I see @seamuslee made a [partial fix](https://github.com/civicrm/civicrm-packages/pull/346) but I'll submit a patch to handle the "empty array" case.JonGoldJonGoldhttps://lab.civicrm.org/dev/core/-/issues/4048Fatal error when changing membership type, on membership with 0 contributions2024-01-12T17:29:15ZBradley TaylorFatal error when changing membership type, on membership with 0 contributions## Steps to reproduce
1. Create a membership without a contribution.
2. Edit the membership you just created, change the membership type, and save (again without a contribution)
## Expected result
The membership should correctly save ...## Steps to reproduce
1. Create a membership without a contribution.
2. Edit the membership you just created, change the membership type, and save (again without a contribution)
## Expected result
The membership should correctly save both times.
## Expected result
The second save does not save correctly/ causes a 500 server error.
The error message is:
```
Fatal error: Uncaught Error: max(): Argument #1 ($value) must contain at least one element
in /app/web/app/plugins/civicrm/civicrm/CRM/Member/Form/Membership.php on line 1547
Call stack:
1. max()
app/plugins/civicrm/civicrm/CRM/Member/Form/Membership.php:1547
2. CRM_Member_Form_Membership::setStatusMessage()
app/plugins/civicrm/civicrm/CRM/Member/Form/Membership.php:1380
3. CRM_Member_Form_Membership::submit()
app/plugins/civicrm/civicrm/CRM/Member/Form/Membership.php:881
4. CRM_Member_Form_Membership::postProcess()
app/plugins/civicrm/civicrm/CRM/Core/Form.php:573
...
```
The membership does appear to actually be saved correctly upon refreshing the page.
## Environment information
PHP 8.1
I cannot reproduce this on dmaster. I think this is because calling `max(array_keys([]))` on PHP 7.4 merely causes a warning, whereas on PHP 8.x it causes an `Uncaught ValueError`.https://lab.civicrm.org/dev/core/-/issues/4051ApiV4 - add options2022-12-27T20:14:54ZeileenApiV4 - add options@totten has added something to `cv` where you can add an option to an existing field - I think this feature makes sense, but as a an apiv4 feature (rather than a cv feature) and across multiple entities rather than just Settings. There a...@totten has added something to `cv` where you can add an option to an existing field - I think this feature makes sense, but as a an apiv4 feature (rather than a cv feature) and across multiple entities rather than just Settings. There are different ways it could look but in essence you are looking to be able to offer stuff like
```
Setting::update()->addWhere('name', '=', 'enable_components')->addOption(['CiviCampaign'])->execute();
Setting::update()->addWhere('name', '=', 'enable_components')->removeOption(['CiviCampaign'])->execute();
Contact::update()->addWhere('id', '=', 123)->addOption(['contact_sub_type' => 'Student'])->execute();
Contact::update()->addWhere('id', '=', 123)->removeOption(['contact_sub_type' => 'Student'])->execute();
```
I'm not sure the exact syntax or whether it should be on the `update` action - one for @colemanw
- This would probably be limited to fields with `is_multiple` or `serialize` or some other indicator of multiple-value-ness (whatever we land on for settings) & be validated against the relevant pseudoconstant or callback-option-listhttps://lab.civicrm.org/dev/core/-/issues/4054Redis cache of Extensions persists between builds2023-01-05T21:57:54ZeileenRedis cache of Extensions persists between buildsI'm hitting an issue where if I run civibuild to rebuild a site shortly after enabling afform it fails - the reason is the Redis cache is used to retrieve enabled extensions, including afform so the afform alterMenu hook is called when i...I'm hitting an issue where if I run civibuild to rebuild a site shortly after enabling afform it fails - the reason is the Redis cache is used to retrieve enabled extensions, including afform so the afform alterMenu hook is called when installing CiviCRM - but the extension is not yet installed & hence the function fatals as it fails to find the Afform class it calls
When determining which hook is called we see
```
/**
* @param $moduleList
*/
public function requireCiviModules(&$moduleList) {
$civiModules = CRM_Core_PseudoConstant::getModuleExtensions();
```
This winds up at
![image](/uploads/e0a82bcf50371e56217b8a0d5c048e2a/image.png)
And it gets the previous build's module list here
![image](/uploads/69f06caeb86421b3923c41e152028f23/image.png)
The cache name is a bit convoluted - but it should be flushed on install to avoid this between-install leakage.
I'm not quite sure where though ... @tottenhttps://lab.civicrm.org/dev/core/-/issues/4057Cannot remove contact from group from Groups tab UI within ACL environment2023-01-10T09:36:07ZRichCannot remove contact from group from Groups tab UI within ACL environmentHave a staff user, *Pebbles*, in an ACL, with access to a contact, *Wilma*.
When Pebbles views the Groups tab of Wilma's record, they are able to add Wilma to a group via the UI, but should they click **remove** or **delete** next to a ...Have a staff user, *Pebbles*, in an ACL, with access to a contact, *Wilma*.
When Pebbles views the Groups tab of Wilma's record, they are able to add Wilma to a group via the UI, but should they click **remove** or **delete** next to a group, an error shows:
> API permission check failed for GroupContact/delete call; insufficient permission: require access CiviCRM and edit all contacts
I don't think this is a security/permissions thing.
Pebbles is able to remove Wilma from the group by simply clicking Edit to get to the hideous edit-flippin-everything form, and then removing the group from the select2 element in the Groups accordion.
## Suggested fix (v1)
I think it's useful for ACL-ed staffers to be able to use groups; it's such a core feature of Civi. And it's fairly weird that they can add a contact to a group, but not remove one - or not by the main UI.
I implemented this as follows in a custom extension, but I'm sure there's a better way to do it upstream.
```
/**
* @see https://docs.civicrm.org/dev/en/latest/hooks/hook_civicrm_alterAPIPermissions/
*/
function myextension_civicrm_alterAPIPermissions($entity, $action, &$params, &$permissions) {
if ($entity === 'group_contact' && $action == 'delete' && !empty($params['id'])) {
$gc = \Civi\Api4\GroupContact::get(FALSE)
->addWhere('id', '=', $params['id'])
->addSelect('contact_id', 'group_id.group_type:name')
->execute()->single();
$mayEditContact = \Civi\Api4\Contact::checkAccess()
->setAction('update')
->addValue('id', $gc['contact_id'])
->execute()->first()['access'] ?? FALSE;
$groupIsNotAcl = !in_array('Access Control', $gc['group_id.group_type:name'] ?? []);
if ($mayEditContact && $groupIsNotAcl) {
// Reduce the access permissions for this call.
$permissions['group_contact']['delete'] = 'access CiviCRM';
}
}
}
```https://lab.civicrm.org/dev/core/-/issues/4058Search Tasks limited by certain ACLs when they should not be2023-01-10T09:35:37ZRichSearch Tasks limited by certain ACLs when they should not beSometimes an incomplete list of search tasks are shown to a user whose access is ACL limited.
I think this problem is caused by this line:
https://lab.civicrm.org/dev/core/-/blob/5.56/CRM/ACL/BAO/ACL.php#L503
I think the loop `break`s...Sometimes an incomplete list of search tasks are shown to a user whose access is ACL limited.
I think this problem is caused by this line:
https://lab.civicrm.org/dev/core/-/blob/5.56/CRM/ACL/BAO/ACL.php#L503
I think the loop `break`s when it shouldn't. I think what's intended is to simply shift that `break` up within the `if {}` that ends on the line above it.
I think the intention of the code is:
- loop through the DAO results that lists permissions
- if the object_id is empty (typically, zero) then the permission applies to all "objects of that type" by which I think it means groups.
- there's an allowance that this record might be for a different permission type (e.g. View instead of Edit) which we would want to ignore
- if the type does match, then all groups are permissioned and we merge those onto our `$ids` array
However where it fails is if there are, say, 2 rows returned. The first says View all, the 2nd says Edit all, and we're asking about edit permission. Because of the `break` where it is, once the first row is looked at and discarded, we break and don't loko at the 2nd row!
Shifting the `break` up seems to fix this and seems to me to be probably what was intended.
Because this bug is highly sensitive to a load of stuff, it's likely that this shows up in weird situations and could be hard to reproduce.
If this makes sense to anyone I'll submit a PR.
In case it's helpful, my proposal is
```diff
diff --git a/sites/all/modules/civicrm/CRM/ACL/BAO/ACL.php b/sites/all/modules/civicrm/CRM/ACL/BAO/ACL.php
index 58b388b73..3d036a3a3 100644
--- a/CRM/ACL/BAO/ACL.php
+++ b/CRM/ACL/BAO/ACL.php
@@ -499,8 +499,8 @@ ORDER BY a.object_id
foreach ($allGroups as $id => $dontCare) {
$ids[] = $id;
}
+ break;
}
- break;
}
}
return $ids;
```https://lab.civicrm.org/dev/core/-/issues/4061Send letter in bulk to pledgers2023-01-10T09:34:22ZyashodhaSend letter in bulk to pledgersFunctional specifications:
- We are replicating the existing feature for contributions “Thank you letters - print or email” for the pledges.
- In menu Pledges, Find Pledges, make the Pledge statuses Pending, In progress and Overdue sele...Functional specifications:
- We are replicating the existing feature for contributions “Thank you letters - print or email” for the pledges.
- In menu Pledges, Find Pledges, make the Pledge statuses Pending, In progress and Overdue selected by default
- In menu Actions, add “Pledge Letters - print or email”
- When we select “Pledge Letters - print or email”, we land on a screen (replicate of the one for contributions)
- Replace Thank-you Letter for Contributions (PDF) by Pledge Letter
- Replace Update thank-you dates for these contributions by Update pledge letter dates for these pledges
- Remove Update receipt dates for these contributions
- Replace MAKE THANK-YOU LETTERS by MAKE PLEDGE LETTERS
The following tokens need to be available in the drop down Tokens so they can be included in a message template and resolved when included in the letter:
- Total pledge amount
- Total pledge payments
- Pledge balance
- Upcoming pledge payment amount
- Upcoming pledge payment due date