From 3779a7f4ced0ca4732f3816a23c39417dd331942 Mon Sep 17 00:00:00 2001 From: Demian Katz <demian.katz@villanova.edu> Date: Fri, 30 Oct 2015 10:59:10 -0400 Subject: [PATCH] Added filter mechanism to combined search. - Now you can provide multiple views into a single search backend. --- config/vufind/combined.ini | 10 +++++++-- .../VuFind/Controller/CombinedController.php | 22 ++++++++++++++----- .../templates/combined/results-ajax.phtml | 6 ++--- .../combined/stack-distributed.phtml | 2 +- .../templates/combined/stack-left.phtml | 2 +- .../templates/combined/stack-right.phtml | 2 +- .../templates/combined/results-ajax.phtml | 2 +- .../templates/combined/results.phtml | 2 +- 8 files changed, 33 insertions(+), 15 deletions(-) diff --git a/config/vufind/combined.ini b/config/vufind/combined.ini index 1e1f1245022..48625a997ba 100644 --- a/config/vufind/combined.ini +++ b/config/vufind/combined.ini @@ -1,6 +1,10 @@ ; This file controls the "combined search" module. Each section is named for a -; search backend (e.g. "Solr", "Summon", "WorldCat", etc.) and contains the -; following settings: +; search backend (e.g. "Solr", "Summon", "WorldCat", etc.). If you want to create +; multiple columns using the same backend but different settings, you may add a +; colon and a suffix (e.g. "Solr:filter1", "Solr:filter2") to differentiate the +; sections. + +; Each section contains some or all of the following settings: ; ; label = The header on the column ; sublabel = Text to display below the header (optional) @@ -22,6 +26,8 @@ ; specified recommendations will be loaded into the top ; area of the column. If set to false, recommendations ; will be suppressed (default). +; filter = One or more filters to apply to search results displayed in the column. +; Use multiple "filter[] = ..." lines if multiple filters are needed. ; ; All display text is subject to translation and may be added to the language ; .ini files. diff --git a/module/VuFind/src/VuFind/Controller/CombinedController.php b/module/VuFind/src/VuFind/Controller/CombinedController.php index 98ff2988a3c..7ff244878f7 100644 --- a/module/VuFind/src/VuFind/Controller/CombinedController.php +++ b/module/VuFind/src/VuFind/Controller/CombinedController.php @@ -70,13 +70,14 @@ class CombinedController extends AbstractSearch $this->getSearchMemory()->disable(); // Validate configuration: - $searchClassId = $this->params()->fromQuery('id'); + $sectionId = $this->params()->fromQuery('id'); $config = $this->getServiceLocator()->get('VuFind\Config')->get('combined') ->toArray(); $tabConfig = $this->getTabConfig($config); - if (!isset($tabConfig[$searchClassId])) { + if (!isset($tabConfig[$sectionId])) { throw new \Exception('Illegal ID'); } + list($searchClassId) = explode(':', $sectionId); // Retrieve results: $options = $this->getServiceLocator() @@ -84,7 +85,7 @@ class CombinedController extends AbstractSearch $currentOptions = $options->get($searchClassId); list($controller, $action) = explode('-', $currentOptions->getSearchAction()); - $settings = $tabConfig[$searchClassId]; + $settings = $tabConfig[$sectionId]; $this->adjustQueryForSettings($settings); $settings['view'] = $this->forwardTo($controller, $action); @@ -151,8 +152,9 @@ class CombinedController extends AbstractSearch $supportsCart = false; $supportsCartOptions = []; foreach ($this->getTabConfig($config) as $current => $settings) { + list($searchClassId) = explode(':', $current); $this->adjustQueryForSettings($settings); - $currentOptions = $options->get($current); + $currentOptions = $options->get($searchClassId); $supportsCartOptions[] = $currentOptions->supportsCart(); if ($currentOptions->supportsCart()) { $supportsCart = true; @@ -160,13 +162,19 @@ class CombinedController extends AbstractSearch list($controller, $action) = explode('-', $currentOptions->getSearchAction()); $combinedResults[$current] = $settings; + + // Calculate a unique DOM id for this section of the search results; + // $searchClassId may contain colons, which must be converted. + $combinedResults[$current]['domId'] + = 'combined_' . str_replace(':', '____', $searchClassId); + $combinedResults[$current]['view'] = (!isset($settings['ajax']) || !$settings['ajax']) ? $this->forwardTo($controller, $action) : $this->createViewModel(['results' => $results]); // Special case: include appropriate "powered by" message: - if (strtolower($current) == 'summon') { + if (strtolower($searchClassId) == 'summon') { $this->layout()->poweredBy = 'Powered by Summonâ„¢ from Serials ' . 'Solutions, a division of ProQuest.'; } @@ -253,6 +261,10 @@ class CombinedController extends AbstractSearch $query = $this->getRequest()->getQuery(); $query->limit = isset($settings['limit']) ? $settings['limit'] : null; + // Apply filters, if any: + $query->filter = isset($settings['filter']) + ? (array)$settings['filter'] : null; + // Reset override to avoid bleed-over from one section to the next! $query->recommendOverride = false; diff --git a/themes/bootstrap3/templates/combined/results-ajax.phtml b/themes/bootstrap3/templates/combined/results-ajax.phtml index d2c9eb3217d..6089b75de42 100644 --- a/themes/bootstrap3/templates/combined/results-ajax.phtml +++ b/themes/bootstrap3/templates/combined/results-ajax.phtml @@ -9,14 +9,14 @@ // Set up Javascript for use below: $searchClassIdEncoded = urlencode($searchClassId); - $searchClassIdHtmlEscaped = $this->escapeHtml($searchClassId); + $targetIdHtmlEscaped = $this->escapeHtml('#' . $currentSearch['domId']); $lookforEncoded = urlencode($lookfor); $loadJs = <<<JS $(document).ready(function(){ var url = path + '/Combined/Result?id=$searchClassIdEncoded&lookfor=$lookforEncoded'; - $('#combined_$searchClassIdHtmlEscaped').load(url, '', function(responseText) { + $('$targetIdHtmlEscaped').load(url, '', function(responseText) { if (responseText.length == 0) { - $('#combined_$searchClassIdHtmlEscaped').hide(); + $('$targetIdHtmlEscaped').hide(); } $('a.openUrlEmbed').click(function() { embedOpenUrlLinks($(this)); diff --git a/themes/bootstrap3/templates/combined/stack-distributed.phtml b/themes/bootstrap3/templates/combined/stack-distributed.phtml index d077ad4d748..bfd7281646e 100644 --- a/themes/bootstrap3/templates/combined/stack-distributed.phtml +++ b/themes/bootstrap3/templates/combined/stack-distributed.phtml @@ -21,7 +21,7 @@ // Enable bulk options if appropriate: $viewParams['showBulkOptions'] = $this->supportsCartOptions[$columnIndex] && $this->showBulkOptions; ?> - <div id="combined_<?=$this->escapeHtmlAttr($searchClassId)?>"> + <div id="<?=$this->escapeHtmlAttr($currentSearch['domId'])?>"> <? $templateSuffix = (isset($currentSearch['ajax']) && $currentSearch['ajax']) ? 'ajax' : 'list'; ?> <?=$this->render('combined/results-' . $templateSuffix . '.phtml', $viewParams)?> </div> diff --git a/themes/bootstrap3/templates/combined/stack-left.phtml b/themes/bootstrap3/templates/combined/stack-left.phtml index c6228f0fe37..b75aa6bc471 100644 --- a/themes/bootstrap3/templates/combined/stack-left.phtml +++ b/themes/bootstrap3/templates/combined/stack-left.phtml @@ -14,7 +14,7 @@ // Enable bulk options if appropriate: $viewParams['showBulkOptions'] = $this->supportsCartOptions[$columnIndex] && $this->showBulkOptions; ?> - <div id="combined_<?=$this->escapeHtmlAttr($searchClassId)?>"> + <div id="<?=$this->escapeHtmlAttr($currentSearch['domId'])?>"> <? $templateSuffix = (isset($currentSearch['ajax']) && $currentSearch['ajax']) ? 'ajax' : 'list'; ?> <?=$this->render('combined/results-' . $templateSuffix . '.phtml', $viewParams)?> </div> diff --git a/themes/bootstrap3/templates/combined/stack-right.phtml b/themes/bootstrap3/templates/combined/stack-right.phtml index 34340ab9bb3..bd6126dc369 100644 --- a/themes/bootstrap3/templates/combined/stack-right.phtml +++ b/themes/bootstrap3/templates/combined/stack-right.phtml @@ -14,7 +14,7 @@ // Enable bulk options if appropriate: $viewParams['showBulkOptions'] = $this->supportsCartOptions[$columnIndex] && $this->showBulkOptions; ?> - <div id="combined_<?=$this->escapeHtmlAttr($searchClassId)?>"> + <div id="<?=$this->escapeHtmlAttr($currentSearch['domId'])?>"> <? $templateSuffix = (isset($currentSearch['ajax']) && $currentSearch['ajax']) ? 'ajax' : 'list'; ?> <?=$this->render('combined/results-' . $templateSuffix . '.phtml', $viewParams)?> </div> diff --git a/themes/jquerymobile/templates/combined/results-ajax.phtml b/themes/jquerymobile/templates/combined/results-ajax.phtml index eaf0b46e084..840e63c31c6 100644 --- a/themes/jquerymobile/templates/combined/results-ajax.phtml +++ b/themes/jquerymobile/templates/combined/results-ajax.phtml @@ -7,7 +7,7 @@ // Set up Javascript for use below: $loadJs = 'var url = path + "/Combined/Result?id=' . urlencode($searchClassId) . '&lookfor=' . urlencode($lookfor) . '";' - . "\$('#combined_" . $this->escapeHtml($searchClassId) . "').load(url, '', function(responseText) {" + . "\$('#" . $this->escapeHtml($currentSearch['domId']) . "').load(url, '', function(responseText) {" . "if (responseText.length == 0) $('#combined_" . $this->escapeHtml($searchClassId) . "').hide();" . "$('.combinedButton').button(); });"; ?> diff --git a/themes/jquerymobile/templates/combined/results.phtml b/themes/jquerymobile/templates/combined/results.phtml index 3bd8b746e26..2620b266742 100644 --- a/themes/jquerymobile/templates/combined/results.phtml +++ b/themes/jquerymobile/templates/combined/results.phtml @@ -13,7 +13,7 @@ <?=$this->flashmessages()?> <? foreach ($this->combinedResults as $searchClassId => $currentSearch): ?> <? if ((!isset($currentSearch['ajax']) || !$currentSearch['ajax']) && isset($currentSearch['hide_if_empty']) && $currentSearch['hide_if_empty'] && $currentSearch['view']->results->getResultTotal() == 0) { continue; } ?> - <div class="combinedResult" id="combined_<?=$this->escapeHtml($searchClassId)?>"> + <div class="combinedResult" id="<?=$this->escapeHtmlAttr($currentSearch['domId'])?>"> <? if (isset($currentSearch['ajax']) && $currentSearch['ajax']): ?> <?=$this->render('combined/results-ajax.phtml', array('searchClassId' => $searchClassId, 'currentSearch' => $currentSearch))?> <? else: ?> -- GitLab