Problem/Motivation
A view with an EntityReference relation does not show all results when a node access module is active. Items with a referenced node are shown depending on whether the user has permissions to view the parent and child node or not. But items without a referenced node are never shown.
Basically the generated SQL looks like this:
SELECT /* columns to select */
FROM {node} node
/* Joins etc. */
WHERE
/* Views generated condition SQL */
AND
/* node_access checks for the node table */
EXISTS(
SELECT na.id AS nid FROM [node_access} na
WHERE /* conditions */
AND (node.nid = na.nid) /* node.nid from parent query to check if user has permission for that node */
)L
AND
/* node_access checks for the relation table */
EXISTS(
SELECT na.id AS nid FROM [node_access} na
WHERE /* conditions */
AND (node_field_data_field_relation_name.nid = na.nid) /* node_field_data_field_relation_name.nid from parent query to check if user has permission for that node joined by the EntityReference relation */
)
If node_field_data_field_relation_name.nid
is NULL because the node does not have a relation the whole EXISTS subquery evaluates to false. And as it is combined with the Views filters using AND the whole query filters out all nodes without a relation.
How to reproduce the problem
To reproduce the problem, follow those steps:
- Install a node access module, e. g. node_view_permissions and keep the default configuration
- Create two content types (e. g. blog and page) and add an EntityReference field to one type allowing only nodes of the other type. (Example: the Blog type contains a reference to a page)
- Create one page and a blog post referencing the page
- Create a blog post without referencing a page
- Create a view for blog posts and add a relation for the EntityReference field.
Proposed resolution
Change the node_access condition from
node_field_data_field_relation_name.nid = na.nid
to
node_field_data_field_relation_name.nid IS NULL OR node_field_data_field_relation_name.nid = na.nid
if it is not the check for the query base table to not check if the user has permission to view NULL (that does not make sense).
Comment | File | Size | Author |
---|---|---|---|
#11 | 2894187-11.patch | 720 bytes | matt_paz |
#4 | sec_172755_fix_hook_node_access_records_entity_ref.patch | 717 bytes | matt_paz |
#2 | node-2894187-1-node_access_allow-relation-null.patch | 1.12 KB | mvonfrie |
Comments
Comment #2
mvonfrie CreditAttribution: mvonfrie commentedComment #3
mvonfrie CreditAttribution: mvonfrie commentedComment #4
matt_paz CreditAttribution: matt_paz commentedI think the same issue persists in Drupal 8.
Tests still to be written, but I've attached is a potential solution for anyone else that encounters this issue.
Note, in my particular case, I was experiencing this in views (that included a reference to an organization/company). About half didn't have a referenced org, folks weren't seeing expected results in the view. Therefore, it was unexpectedly restricting access to content they should have been authorized to see.
Comment #5
matt_paz CreditAttribution: matt_paz commentedAdjusting the title a bit to clarify use and increase visibility
Comment #6
mstrelan CreditAttribution: mstrelan commentedI can confirm the issue as described in #4 on an existing Drupal 8.9.1 site. The patch works, but needs tests.
Comment #7
matt_paz CreditAttribution: matt_paz commentedAdding a related issue that is being worked more actively than this. Need to delve more deeply, but on the surface, I suspect it might resolve the condition.
https://www.drupal.org/project/drupal/issues/1349080?page=1
Comment #8
matt_paz CreditAttribution: matt_paz commentedComment #9
matt_paz CreditAttribution: matt_paz commentedAdjusting the version that this applies to.
Comment #10
matt_paz CreditAttribution: matt_paz commentedAssessment of issue 1349080 is still pending, but it looks like this patch will need to be updated for 9.2
Comment #11
matt_paz CreditAttribution: matt_paz commentedNot sure this is needed any more but I went ahead and updated the patch for 9.2.x-dev
Comment #12
mstrelan CreditAttribution: mstrelan at PreviousNext commentedI have confirmed the issue is resolved by the latest patch in #1349080: node_access filters out accessible nodes when node is left joined after following the steps in the issue summary. Closing this as a duplicate.