When filtering a view with AJAX enabled, in some situations ajaxViewResponse will replace the HTML with nothing, so the user will see the view "disappear" after updating the filters. If AJAX is disabled, filtering the view works fine.

The bug is triggered when having a view display with attachments, because the attachments' view-dom-id class is not the same before and after applying a filter:

Before applying a filter:
<div class="attachment attachment-before"><div class="view view-my-view view-id-my_view view-display-id-attachment_1 view-dom-id-my-view-attachment-1-1">
After applying a filter:
<div class="attachment attachment-before"><div class="view view-my-view view-id-my_view view-display-id-attachment_1 view-dom-id-my-view-my-page-1">

Analysis

  • ViewsAjaxView uses the view-dom-id class as the unique selector for the view: 'var view = .view-dom-id-' + settings.view_dom_id
  • ajaxViewResponse receives this selector as its "target" argument
  • this selector is made into a jQuery object with the following code: var $view = $(target);
  • ajaxViewResponse fails if this selector matches more than one element, making it replace the current HTML of the view with a blank output
  • after applying a filter, the attachments get the same view-dom-id class as their parent display (in the example above, "view-dom-id-my-view-my-page-1"), triggering the bug

Mitigation

I didn't found why the view-dom-id class of the attachments are modified when filtering the view, but we can make sure ajaxViewResponse will only act on the first matched DOM element by using var $view = $(target).filter(':first');. As the parent view is matched before the attachments, it works around the bug.

How to reproduce

  1. Create a new view
  2. Add a page display
  3. Make sure "Use AJAX" is set to "Yes"
  4. Add some exposed filters with autosubmit for the exposed form
  5. Add an attachment display and attach it to the page display
  6. Save the view
  7. Go to the new page
  8. Filter the view once: it should work
  9. Unset the filter or set a second filter: the view should become blank

Comments

mdupont’s picture

I stand corrected, it is Nodereference Explorer messing with the dom_id in its hook_view_pre_execute(). However it would be good to prevent ajaxViewResponse from producing blank output if given a selector matching more than one element.

mdupont’s picture

Title: ajaxViewResponse may make view blank » ajaxViewResponse produces blank output if target selector matches several elements
mdupont’s picture

Priority: Major » Normal
Status: Active » Needs review
StatusFileSize
new393 bytes

Patch implementing the workaround described in the summary, to get the ball rolling.

mustanggb’s picture

Status: Needs review » Closed (won't fix)