Views exposed form doesn't handle non-array values correctly, where an array is expected ("Allow multiple selections")

Created on 22 July 2024, about 1 year ago

Problem/Motivation

Views exposed filters allow multiple selections using the "Allow multiple selections" checkbox.

This can for example be tested using a filter on a node content type, which then allows filtering using multiple checkboxes for the different node types.

In the form this leads to an array structure like
type[] = article
type[] = page

using GET to submit the form, you can even make that visible.

The problem is that Views Exposed Filters expect the given parameter "type" to be an array (type[]) and nothing else (e.g. type=) and fails with an exception indirectly:

LogicException: Cannot create key "article" on non-array value. in Drupal\Component\Utility\NestedArray::setValue() (line 154 of core/lib/Drupal/Component/Utility/NestedArray.php).

LogicException: Cannot create key "article" on non-array value. in Drupal\Component\Utility\NestedArray::setValue() (line 154 of core/lib/Drupal/Component/Utility/NestedArray.php).

Drupal\Core\Form\FormBuilder->handleInputElement() (Line: 999)
Drupal\Core\Form\FormBuilder->doBuildForm() (Line: 1069)
Drupal\Core\Form\FormBuilder->doBuildForm() (Line: 1069)
Drupal\Core\Form\FormBuilder->doBuildForm() (Line: 579)
Drupal\Core\Form\FormBuilder->processForm() (Line: 326)
Drupal\Core\Form\FormBuilder->buildForm() (Line: 134)
Drupal\views\Plugin\views\exposed_form\ExposedFormPluginBase->renderExposedForm() (Line: 1297)
Drupal\views\ViewExecutable->build() (Line: 393)
Drupal\views\Plugin\views\display\PathPluginBase->execute() (Line: 198)
Drupal\views\Plugin\views\display\Page->execute() (Line: 1689)
Drupal\views\ViewExecutable->executeDisplay() (Line: 81)
Drupal\views\Element\View::preRenderViewElement()
call_user_func_array() (Line: 113)
Drupal\Core\Render\Renderer->doTrustedCallback() (Line: 870)
Drupal\Core\Render\Renderer->doCallback() (Line: 432)
Drupal\Core\Render\Renderer->doRender() (Line: 248)
Drupal\Core\Render\Renderer->render() (Line: 238)
Drupal\Core\Render\MainContent\HtmlRenderer->Drupal\Core\Render\MainContent\{closure}() (Line: 638)
Drupal\Core\Render\Renderer->executeInRenderContext() (Line: 231)
Drupal\Core\Render\MainContent\HtmlRenderer->prepare() (Line: 128)
Drupal\Core\Render\MainContent\HtmlRenderer->renderResponse() (Line: 90)
Drupal\Core\EventSubscriber\MainContentViewSubscriber->onViewRenderArray()
call_user_func() (Line: 111)
Drupal\Component\EventDispatcher\ContainerAwareEventDispatcher->dispatch() (Line: 186)
Symfony\Component\HttpKernel\HttpKernel->handleRaw() (Line: 76)
Symfony\Component\HttpKernel\HttpKernel->handle() (Line: 53)
Drupal\Core\StackMiddleware\Session->handle() (Line: 48)
Drupal\Core\StackMiddleware\KernelPreHandle->handle() (Line: 28)
Drupal\Core\StackMiddleware\ContentLength->handle() (Line: 32)
Drupal\big_pipe\StackMiddleware\ContentLength->handle() (Line: 106)
Drupal\page_cache\StackMiddleware\PageCache->pass() (Line: 85)
Drupal\page_cache\StackMiddleware\PageCache->handle() (Line: 50)
Drupal\ban\BanMiddleware->handle() (Line: 48)
Drupal\Core\StackMiddleware\ReverseProxyMiddleware->handle() (Line: 51)
Drupal\Core\StackMiddleware\NegotiationMiddleware->handle() (Line: 36)
Drupal\Core\StackMiddleware\AjaxPageState->handle() (Line: 49)
Drupal\remove_http_headers\StackMiddleware\RemoveHttpHeadersMiddleware->handle() (Line: 51)
Drupal\Core\StackMiddleware\StackedHttpKernel->handle() (Line: 741)
Drupal\Core\DrupalKernel->handle() (Line: 19)

Steps to reproduce

See above

Proposed resolution

Ensure to validate the given value to be an array in form validation or other input validation, so it's not getting processed on lower levels running into lower level exceptions.

Also consider that when using a GET form, the parameter might also be changed / manipulated on the user-side. (intentionally or unintentionally)

Remaining tasks

User interface changes

None

API changes

None

Data model changes

None

Release notes snippet

πŸ› Bug report
Status

Active

Version

11.0 πŸ”₯

Component
ViewsΒ  β†’

Last updated about 1 month ago

Created by

πŸ‡©πŸ‡ͺGermany Anybody Porta Westfalica

Live updates comments and jobs are added and updated live.
Sign in to follow issues

Comments & Activities

  • Issue created by @Anybody
  • πŸ‡©πŸ‡ͺGermany Anybody Porta Westfalica
  • πŸ‡³πŸ‡ΏNew Zealand quietone
  • πŸ‡³πŸ‡±Netherlands Lendude Amsterdam

    How would you get these 'wrong' URLs? Manually I would guess? Or is there some way that these are generated through Drupal?

    Making this a little more robust makes sense, but doesn't feel like a bug unless Drupal generates these URLs sometimes.

  • πŸ‡©πŸ‡ͺGermany Anybody Porta Westfalica

    Thanks for the reply @Lendude! We had these log entries popping up, it seems it's caused by hacking attempts or some kind of crawlers / spiders. We're not generating these links and I'm really unsure how this happens, but I don't think it's by humans. So I'd still consider the result to be kind of a bug.

  • πŸ‡©πŸ‡ͺGermany pminf Nuremburg (Germany), formerly Dresden

    Since the update to Drupal 10.3, these errors are also occurring for us according to the log. I also don't know how to reproduce them, except by customizing the URL.

  • πŸ‡©πŸ‡ͺGermany pminf Nuremburg (Germany), formerly Dresden

    In our project, the error is most frequently caused by a URL like https://www.example.com/search?search=test&type= – so without parameter array notation and without a value. Shouldn't this be handled as an empty parameter? It also feels like a bug to me.

  • πŸ‡©πŸ‡ͺGermany pminf Nuremburg (Germany), formerly Dresden

    There is another issue with views exposed filter and query parameters without a value, but explicitly for numeric filters: TypeError: Cannot access offset of type string on string in Drupal\views\Plugin\views\filter\NumericFilter->valueForm() πŸ› TypeError: Cannot access offset of type string on string in Drupal\views\Plugin\views\filter\NumericFilter->valueForm() Needs work

  • πŸ‡©πŸ‡ͺGermany szeidler Berlin

    @pminf good find. In my case it was really about an numeric filter and the patch from the linked issue fixes the problem of an exception.

Production build 0.71.5 2024