fix: harden encoded filter settings against malformed and stale input
This commit is contained in:
@@ -87,12 +87,16 @@ class SearchController extends ActionController
|
||||
|
||||
public function initializeSearchresultAction()
|
||||
{
|
||||
// Process encoded filtersettings from static search result
|
||||
// Process encoded filtersettings from static search result.
|
||||
// Explicit filter settings win: they carry the visitor's current selection,
|
||||
// whereas a stale 'f' riding along on a link would silently replace it.
|
||||
$encodedFilterSettings = GeneralUtility::_GET('f');
|
||||
if ($encodedFilterSettings) {
|
||||
if ($encodedFilterSettings && !$this->request->hasArgument('filterSettings')) {
|
||||
$filterSettingsEncoder = new FilterSettingsEncoder();
|
||||
$filterSettings = $filterSettingsEncoder->decode($encodedFilterSettings);
|
||||
$this->request->setArgument('filterSettings', $filterSettings);
|
||||
if (count($filterSettings) > 0) {
|
||||
$this->request->setArgument('filterSettings', $filterSettings);
|
||||
}
|
||||
}
|
||||
$forcedConceptUids = GeneralUtility::intExplode(',', $this->settings['forcedConceptUids'], true);
|
||||
$this->processFilterSettingsArgument($forcedConceptUids);
|
||||
|
||||
@@ -76,11 +76,28 @@ class FilterSettingsEncoder
|
||||
return implode('|', $encoded);
|
||||
}
|
||||
|
||||
/**
|
||||
* Decodes an encoded filter settings string.
|
||||
*
|
||||
* The format is strictly positional, so a string whose field count does not
|
||||
* match the mapping cannot be interpreted: every field after a missing one
|
||||
* would be read into the wrong setting. Such input is rejected outright
|
||||
* rather than silently producing a shifted - and therefore wrong - result.
|
||||
*
|
||||
* @param string $data
|
||||
* @return array the decoded settings, or an empty array if $data is malformed
|
||||
*/
|
||||
public function decode(string $data): array
|
||||
{
|
||||
$decoded = [];
|
||||
$mapping = $this->getMapping();
|
||||
$values = explode('|', $data);
|
||||
foreach ($this->getMapping() as $index => $property)
|
||||
|
||||
if (count($values) !== count($mapping)) {
|
||||
return [];
|
||||
}
|
||||
|
||||
$decoded = [];
|
||||
foreach ($mapping as $index => $property)
|
||||
{
|
||||
[$name, $type] = $property;
|
||||
$value = $values[$index];
|
||||
|
||||
Reference in New Issue
Block a user