Using drupal 7 I have implemented hook_node_access but am having real trouble figuring out how to go a step further and achieve the following using hook_node_access_records and hook_node_grants.

For a given content type ('submission') I want to limit users with a particular role ('curator') and an additionally set field in their user profile ('location') to see only nodes that have a specific matching field value set ('location').

So in this case curators from London can only see submissions to the gallery in London rather than see all 'submission' nodes.


I have made some progress here in my understanding. See the code below. My question now is can i do the following to check set a realm and grant id that i can use to lock specific users out?

Below I am trying to set a lock such that any user who has the grant id cannot access the node (this will be a subset of people within a given role) and for everyone else I just want the sites normal configured access permissions to apply.

function hook_node_access_records($node) {

$grants = array();

if ($node->type == 'submission') {

    $grants[] = array(
      // Say this node is in our realm.
      // By convention we prefix the name of the realm
      // with the module name.
      'realm' => 'submission-permissions',
      // Define the grant id - users in the realm must
      // have this grant id to access this node.
      'gid' => $node->field_location[LANGUAGE_NONE][0]['target_id'],
      // Users who match cannot view the node.
      'grant_view' => 0,
      // Users who match cannot update the node.
      'grant_update' => 0,
      // Users who match cannot delete the node.
      'grant_delete' => 0,
      // In the case another module provides exactly
      // this access record, the one with the highest
      // priority wins. Usually leave this as 0.
      'priority' => 100,


 * Implements hook_node_grants().
function hook_node_grants($account, $op) {

    $grants = array();

    $role = is_string($account) ? $account : $account->roles[4];

    if (($role == 'curator') && ($op == 'view')){

        // Get the currently looged in users accounts details
        $user_fields = user_load($account->uid);    

        $location = is_string($user_fields) ? $user_fields : $user_fields->field_curator_location[LANGUAGE_NONE][0]['target_id'];

        if (!empty($location)){

            $grants['submission-permissions'][] = $user_fields->field_curator_location[LANGUAGE_NONE][0]['target_id'];



    return $grants;

  • what problem are you facing with the mentioned code?
    – arpitr
    Oct 26, 2016 at 9:47
  • The code above works just fine... I just don't understand how to apply the same logic using hook_node_access_record and hook_node_grants Oct 27, 2016 at 8:09

1 Answer 1


I had to do something similar in a project last year and ended up using Taxonomy Access Control (TAC). If you make your location field a taxonomy and use the same taxonomy field on your user profile and content type, you can set perms for your curator role relative to the taxonomy term. It has to be enabled on a role by role basis so it won't impact any other roles on your site.

  • The field in both cases is actually a taxonomy term but in the case of the 'submission' node it is actually an entity reference that uses a view to look at the taxonomy term on the parent node (the 'exhibition') so the above probably won't work Oct 27, 2016 at 11:51

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service and acknowledge you have read our privacy policy.

Not the answer you're looking for? Browse other questions tagged or ask your own question.