return TRUE;
}
// Do this before the "Select" string search because date fields have a "Select Date" html_type
- // and contactRef fields have an "Autocomplete-Select" html_type - contacts are an FK not an option list.
+ // and entityRef fields have an "Autocomplete-Select" html_type - references are an FK not an option list.
if (in_array($field['data_type'], ['EntityReference', 'ContactReference', 'Date'])) {
return FALSE;
}
$includeEmail = civicrm_api3('setting', 'getvalue', ['name' => 'includeEmailInName', 'group' => 'Search Preferences']);
$options = [
'sort_name' => $includeEmail ? ts('Name/Email') : ts('Name'),
- 'contact_id' => ts('Contact ID'),
+ 'id' => ts('Contact ID'),
'external_identifier' => ts('External ID'),
'first_name' => ts('First Name'),
'last_name' => ts('Last Name'),
- 'email' => ts('Email'),
- 'phone_numeric' => ts('Phone'),
- 'street_address' => ts('Street Address'),
- 'city' => ts('City'),
- 'postal_code' => ts('Postal Code'),
+ 'email_primary.email' => ts('Email'),
+ 'phone_primary.phone_numeric' => ts('Phone'),
+ 'address_primary.street_address' => ts('Street Address'),
+ 'address_primary.city' => ts('City'),
+ 'address_primary.postal_code' => ts('Postal Code'),
'job_title' => ts('Job Title'),
];
- $custom = civicrm_api3('CustomField', 'get', [
- 'return' => ['name', 'label', 'custom_group_id.title'],
- 'custom_group_id.extends' => ['IN' => array_merge(['Contact'], CRM_Contact_BAO_ContactType::basicTypes())],
- 'data_type' => ['NOT IN' => ['ContactReference', 'Date', 'File']],
- 'custom_group_id.is_active' => 1,
- 'is_active' => 1,
- 'is_searchable' => 1,
- 'options' => ['sort' => ['custom_group_id.weight', 'weight'], 'limit' => 0],
+ $custom = civicrm_api4('CustomField', 'get', [
+ 'checkPermissions' => FALSE,
+ 'select' => ['name', 'label', 'custom_group_id.name', 'custom_group_id.title', 'option_group_id'],
+ 'where' => [
+ ['custom_group_id.extends', 'IN', array_merge(['Contact'], CRM_Contact_BAO_ContactType::basicTypes())],
+ ['data_type', 'NOT IN', ['ContactReference', 'Date', 'File']],
+ ['custom_group_id.is_active', '=', TRUE],
+ ['is_active', '=', TRUE],
+ ['is_searchable', '=', TRUE],
+ ],
+ 'orderBy' => [
+ 'custom_group_id.weight' => 'ASC',
+ 'weight' => 'ASC',
+ ],
]);
- foreach ($custom['values'] as $field) {
- $options['custom_' . $field['name']] = $field['custom_group_id.title'] . ': ' . $field['label'];
+ foreach ($custom as $field) {
+ $options[$field['custom_group_id.name'] . '.' . $field['name'] . ($field['option_group_id'] ? ':label' : '')] = $field['custom_group_id.title'] . ': ' . $field['label'];
}
return $options;
}
$this->addTask('Add fields to civicrm_mail_settings to allow more flexibility for email to activity', 'addMailSettingsFields');
$this->addTask('Update afform tab names', 'updateAfformTabs');
$this->addTask('Add in Client Removed Activity Type', 'addCaseClientRemovedActivity');
+ $this->addTask('Update quicksearch options to v4 format', 'updateQuicksearchOptions');
}
/**
return TRUE;
}
+ public static function updateQuicksearchOptions($ctx): bool {
+ $map = [
+ 'sort_name' => 'sort_name',
+ 'contact_id' => 'id',
+ 'external_identifier' => 'external_identifier',
+ 'first_name' => 'first_name',
+ 'last_name' => 'last_name',
+ 'email' => 'email_primary.email',
+ 'phone_numeric' => 'phone_primary.phone_numeric',
+ 'street_address' => 'address_primary.street_address',
+ 'city' => 'address_primary.city',
+ 'postal_code' => 'address_primary.postal_code',
+ 'job_title' => 'job_title',
+ ];
+ $custom = civicrm_api4('CustomField', 'get', [
+ 'checkPermissions' => FALSE,
+ 'select' => ['name', 'label', 'custom_group_id.name', 'custom_group_id.title', 'option_group_id'],
+ 'where' => [
+ ['custom_group_id.extends', 'IN', array_merge(['Contact'], CRM_Contact_BAO_ContactType::basicTypes())],
+ ['data_type', 'NOT IN', ['ContactReference', 'Date', 'File']],
+ ['custom_group_id.is_active', '=', TRUE],
+ ['is_active', '=', TRUE],
+ ['is_searchable', '=', TRUE],
+ ],
+ ]);
+ foreach ($custom as $field) {
+ $map['custom_' . $field['name']] = $field['custom_group_id.name'] . '.' . $field['name'] . ($field['option_group_id'] ? ':label' : '');
+ }
+
+ $oldOpts = Civi::settings()->get('quicksearch_options');
+ if ($oldOpts) {
+ $newOpts = [];
+ foreach ($oldOpts as $oldOpt) {
+ // In case the upgrade has run already, check new and old options
+ if (in_array($oldOpt, $map) || array_key_exists($oldOpt, $map)) {
+ $newOpts[] = $map[$oldOpt] ?? $oldOpt;
+ }
+ }
+ Civi::settings()->set('quicksearch_options', $newOpts);
+ }
+ else {
+ Civi::settings()->revert('quicksearch_options');
+ }
+ return TRUE;
+ }
+
}
namespace Civi\Api4\Service\Autocomplete;
+use Civi\API\Event\PrepareEvent;
use Civi\Core\Event\GenericHookEvent;
use Civi\Core\HookInterface;
*/
class ContactAutocompleteProvider extends \Civi\Core\Service\AutoService implements HookInterface {
+ /**
+ * Set filters for the menubar quicksearch.
+ *
+ * @param \Civi\API\Event\PrepareEvent $event
+ */
+ public static function on_civi_api_prepare(PrepareEvent $event) {
+ $apiRequest = $event->getApiRequest();
+ if (is_object($apiRequest) &&
+ is_a($apiRequest, 'Civi\Api4\Generic\AutocompleteAction') &&
+ $apiRequest->getFormName() === 'crmMenubar' &&
+ $apiRequest->getFieldName() === 'crm-qsearch-input'
+ ) {
+ $allowedFilters = \Civi::settings()->get('quicksearch_options');
+ foreach ($apiRequest->getFilters() as $fieldName => $val) {
+ if (in_array($fieldName, $allowedFilters)) {
+ $apiRequest->addFilter($fieldName, $val);
+ }
+ }
+ }
+ }
+
/**
* Provide default SearchDisplay for Contact autocompletes
*
],
],
];
+ // Adjust display for quicksearch input - the display only needs one column
+ // as the menubar autocomplete does not support descriptions
+ if (($e->context['formName'] ?? NULL) === 'crmMenubar' && ($e->context['fieldName'] ?? NULL) === 'crm-qsearch-input') {
+ $column = ['type' => 'field'];
+ // If doing a search by a field other than the default
+ if (!empty($e->context['filters'])) {
+ $filterField = array_keys($e->context['filters'])[0];
+ }
+ elseif (\Civi::settings()->get('includeEmailInName')) {
+ $filterField = 'email_primary.email';
+ }
+ if ($filterField) {
+ $column['key'] = $filterField;
+ $column['rewrite'] = "[sort_name] :: [$filterField]";
+ $column['empty_value'] = '[sort_name]';
+ }
+ else {
+ $column['key'] = 'sort_name';
+ }
+ $e->display['settings']['columns'] = [$column];
+ }
}
}
var
option = $('input[name=quickSearchField]:checked'),
params = {
- name: request.term,
- field_name: option.val()
+ formName: 'crmMenubar',
+ fieldName: 'crm-qsearch-input',
+ filters: {},
};
- CRM.api3('contact', 'getquick', params).done(function(result) {
+ if (option.val() === 'sort_name') {
+ params.input = request.term;
+ } else {
+ params.filters[option.val()] = request.term;
+ }
+ CRM.api4('Contact', 'autocomplete', params).then(function(result) {
var ret = [];
- if (result.values.length > 0) {
+ if (result.length > 0) {
$('#crm-qsearch-input').autocomplete('widget').menu('option', 'disabled', false);
- $.each(result.values, function(k, v) {
- ret.push({value: v.id, label: v.data});
+ $.each(result, function(key, item) {
+ ret.push({value: item.id, label: item.label});
});
} else {
$('#crm-qsearch-input').autocomplete('widget').menu('option', 'disabled', true);
'pseudoconstant' => [
'callback' => 'CRM_Core_SelectValues::quicksearchOptions',
],
- 'default' => ['sort_name', 'contact_id', 'external_identifier', 'first_name', 'last_name', 'email', 'phone_numeric', 'street_address', 'city', 'postal_code', 'job_title'],
+ 'default' => [
+ 'sort_name',
+ 'id',
+ 'external_identifier',
+ 'first_name',
+ 'last_name',
+ 'email_primary.email',
+ 'phone_primary.phone_numeric',
+ 'address_primary.street_address',
+ 'address_primary.city',
+ 'address_primary.postal_code',
+ 'job_title',
+ ],
'add' => '5.8',
'title' => ts('Quicksearch options'),
'is_domain' => '1',