diff --git a/include/ajax.tickets.php b/include/ajax.tickets.php index 3d93e9a9cf3585d38189e8c705dafe54246fa2aa..31776edb86d683629b1eeafa7915151d68172b80 100644 --- a/include/ajax.tickets.php +++ b/include/ajax.tickets.php @@ -208,13 +208,16 @@ class TicketsAjaxAPI extends AjaxController { $cdata_search = false; foreach (TicketForm::getInstance()->getFields() as $f) { if (isset($req[$f->getFormName()]) - && ($val = $req[$f->getFormName()]) - && strlen(trim($val))) { + && ($val = $req[$f->getFormName()])) { $name = $f->get('name') ? $f->get('name') : 'field_'.$f->get('id'); - if ($f->getImpl()->hasIdValue() && is_numeric($val)) { - $cwhere = "cdata.`{$name}_id` = ".db_input($val); - $criteria["cdata.{$name}_id"] = $val; + if (is_array($val)) { + $cwhere = '(' . implode(' OR ', array_map( + function($k) use ($name) { + return sprintf('FIND_IN_SET(%s, `%s`)', db_input($k), $name); + }, $val) + ) . ')'; + $criteria["cdata.{$name}"] = $val; } else { $cwhere = "cdata.`$name` LIKE '%".db_real_escape($val)."%'"; diff --git a/include/class.dynamic_forms.php b/include/class.dynamic_forms.php index 1add7ca244e2b2d4d6a844cc7f9264dc51df53ec..c5133c9d6a40e81df5c47406c13e6fe38565f617 100644 --- a/include/class.dynamic_forms.php +++ b/include/class.dynamic_forms.php @@ -196,16 +196,19 @@ class DynamicForm extends VerySimpleModel { if (!$impl->hasData() || $impl->isPresentationOnly()) continue; + $id = $f->get('id'); $name = ($f->get('name')) ? $f->get('name') - : 'field_'.$f->get('id'); + : 'field_'.$id; - $fields[] = sprintf( - 'MAX(IF(field.name=\'%1$s\',ans.value,NULL)) as `%1$s`', - $name); - if ($impl->hasIdValue()) { + if ($impl instanceof ChoiceField || $impl instanceof SelectionField) { $fields[] = sprintf( - 'MAX(IF(field.name=\'%1$s\',ans.value_id,NULL)) as `%1$s_id`', - $name); + 'MAX(CASE WHEN field.id=\'%1$s\' THEN REPLACE(REPLACE(REPLACE(REPLACE(coalesce(ans.value_id, ans.value), \'{\', \'\'), \'}\', \'\'), \'"\', \'\'), \':\', \',\') ELSE NULL END) as `%2$s`', + $id, $name); + } + else { + $fields[] = sprintf( + 'MAX(IF(field.id=\'%1$s\',coalesce(ans.value_id, ans.value),NULL)) as `%2$s`', + $id, $name); } } return $fields; @@ -321,10 +324,8 @@ class TicketForm extends DynamicForm { $f = $answer->getField(); $name = $f->get('name') ? $f->get('name') : 'field_'.$f->get('id'); - $ids = $f->hasIdValue(); - $fields = sprintf('`%s`=', $name) . db_input($answer->get('value')); - if ($f->hasIdValue()) - $fields .= sprintf(',`%s_id`=', $name) . db_input($answer->getIdValue()); + $fields = sprintf('`%s`=', $name) . db_input( + implode(',', $answer->getSearchKeys())); $sql = 'INSERT INTO `'.TABLE_PREFIX.'ticket__cdata` SET '.$fields .', `ticket_id`='.db_input($answer->getEntry()->get('object_id')) .' ON DUPLICATE KEY UPDATE '.$fields; @@ -944,6 +945,14 @@ class DynamicFormEntryAnswer extends VerySimpleModel { ); } + function getSearchKeys() { + $val = $this->getField()->to_php($this->getValue()); + if (is_array($val)) + return array_keys($val); + + return [$val]; + } + function asVar() { return (is_object($this->getValue())) ? $this->getValue() : $this->toString(); @@ -1004,15 +1013,13 @@ class SelectionField extends FormField { } function to_database($value) { - $id = null; if (is_array($value)) { reset($value); - $id = key($value); } if ($value && is_array($value)) $value = JsonDataEncoder::encode($value); - return array($value, $id); + return $value; } function to_php($value, $id=false) { @@ -1023,13 +1030,11 @@ class SelectionField extends FormField { if (isset($choices[$value])) $value = $choices[$value]; } + // Don't set the ID here as multiselect prevents using exactly one + // ID value. Instead, stick with the JSON value only. return $value; } - function hasIdValue() { - return true; - } - function hasSubFields() { return true; } diff --git a/include/class.forms.php b/include/class.forms.php index 018c5b76535a1d9db12c32d5653e46e34b066751..040cd255425d55c5a24140bbda9da0cffa463606 100644 --- a/include/class.forms.php +++ b/include/class.forms.php @@ -1688,7 +1688,7 @@ class ChoicesWidget extends Widget { function render($mode=false) { - if ($mode && $mode == 'view') { + if ($mode == 'view') { if (!($val = (string) $this->field)) $val = sprintf('<span class="faded">%s</span>', __('None')); @@ -1697,6 +1697,10 @@ class ChoicesWidget extends Widget { } $config = $this->field->getConfiguration(); + if ($mode == 'search') { + $config['multiselect'] = true; + } + // Determine the value for the default (the one listed if nothing is // selected) $choices = $this->field->getChoices(true); diff --git a/include/class.search.php b/include/class.search.php index 270e0322055ae05714954431ae8c7a812ff2bcf2..9e3a380efbfc081c42fe27ddf5b32a95f7f244d4 100644 --- a/include/class.search.php +++ b/include/class.search.php @@ -331,7 +331,17 @@ class MysqlSearchBackend extends SearchBackend { // Search ticket CDATA table $cdata_search = true; $name = substr($name, 6); - $where[] = sprintf("cdata.%s = %s", $name, db_input($value)); + if (is_array($value)) { + $where[] = '(' . implode(' OR ', array_map( + function($k) use ($name) { + return sprintf('FIND_IN_SET(%s, cdata.`%s`)', + db_input($k), $name); + }, $value) + ) . ')'; + } + else { + $where[] = sprintf("cdata.%s = %s", $name, db_input($value)); + } } } } diff --git a/include/staff/tickets.inc.php b/include/staff/tickets.inc.php index ee55d4152a2444cfeb97a5db94049501be4d18e8..671600b785e20d90df39173482da78c8a5803d9f 100644 --- a/include/staff/tickets.inc.php +++ b/include/staff/tickets.inc.php @@ -255,7 +255,7 @@ $qselect.=' ,IF(ticket.duedate IS NULL,IF(sla.id IS NULL, NULL, DATE_ADD(ticket. .' ,ticket.created as ticket_created, CONCAT_WS(" ", staff.firstname, staff.lastname) as staff, team.name as team ' .' ,IF(staff.staff_id IS NULL,team.name,CONCAT_WS(" ", staff.lastname, staff.firstname)) as assigned ' .' ,IF(ptopic.topic_pid IS NULL, topic.topic, CONCAT_WS(" / ", ptopic.topic, topic.topic)) as helptopic ' - .' ,cdata.priority_id, cdata.subject, pri.priority_desc, pri.priority_color'; + .' ,cdata.priority as priority_id, cdata.subject, pri.priority_desc, pri.priority_color'; $qfrom.=' LEFT JOIN '.TICKET_LOCK_TABLE.' tlock ON (ticket.ticket_id=tlock.ticket_id AND tlock.expire>NOW() AND tlock.staff_id!='.db_input($thisstaff->getId()).') ' @@ -265,7 +265,7 @@ $qfrom.=' LEFT JOIN '.TICKET_LOCK_TABLE.' tlock ON (ticket.ticket_id=tlock.ticke .' LEFT JOIN '.TOPIC_TABLE.' topic ON (ticket.topic_id=topic.topic_id) ' .' LEFT JOIN '.TOPIC_TABLE.' ptopic ON (ptopic.topic_id=topic.topic_pid) ' .' LEFT JOIN '.TABLE_PREFIX.'ticket__cdata cdata ON (cdata.ticket_id = ticket.ticket_id) ' - .' LEFT JOIN '.PRIORITY_TABLE.' pri ON (pri.priority_id = cdata.priority_id)'; + .' LEFT JOIN '.PRIORITY_TABLE.' pri ON (pri.priority_id = cdata.priority)'; TicketForm::ensureDynamicDataView();