5 * Test module for testing the node access system.
7 * This module's functionality depends on the following state variables:
8 * - node_access_test.no_access_uid: Used in NodeQueryAlterTest to enable the
9 * node_access_all grant realm.
10 * - node_access_test.private: When TRUE, the module controls access for nodes
11 * with a 'private' property set, and inherits the default core access for
12 * nodes without this flag. When FALSE, the module controls access for all
14 * - node_access_test_secret_catalan: When set to TRUE and using the Catalan
15 * 'ca' language code, makes all Catalan content secret.
17 * @see node_access_test_node_grants()
18 * @see \Drupal\node\Tests\NodeQueryAlterTest
19 * @see \Drupal\node\Tests\NodeAccessBaseTableTest
22 use Drupal\Core\Session\AccountInterface;
23 use Drupal\Core\Access\AccessResult;
24 use Drupal\field\Entity\FieldStorageConfig;
25 use Drupal\field\Entity\FieldConfig;
26 use Drupal\node\NodeTypeInterface;
27 use Drupal\node\NodeInterface;
30 * Implements hook_node_grants().
32 * Provides three grant realms:
33 * - node_access_test_author: Grants users view, update, and delete privileges
34 * on nodes they have authored. Users receive a group ID matching their user
36 * - node_access_test: Grants users view privileges when they have the
37 * 'node test view' permission. Users with this permission receive two group
38 * IDs for the realm, 8888 and 8889. Access for both realms is identical;
39 * the second group is added so that the interaction of multiple groups on
40 * a given grant realm can be tested in NodeAccessPagerTest.
41 * - node_access_all: Provides grants for the user whose user ID matches the
42 * 'node_access_test.no_access_uid' state variable. Access control on this
43 * realm is not provided in this module; instead,
44 * NodeQueryAlterTest::testNodeQueryAlterOverride() manually writes a node
45 * access record defining the access control for this realm.
47 * @see \Drupal\node\Tests\NodeQueryAlterTest::testNodeQueryAlterOverride()
48 * @see \Drupal\node\Tests\NodeAccessPagerTest
49 * @see node_access_test.permissions.yml
50 * @see node_access_test_node_access_records()
52 function node_access_test_node_grants($account, $op) {
54 $grants['node_access_test_author'] = [$account->id()];
55 if ($op == 'view' && $account->hasPermission('node test view', $account)) {
56 $grants['node_access_test'] = [8888, 8889];
59 $no_access_uid = \Drupal::state()->get('node_access_test.no_access_uid') ?: 0;
60 if ($op == 'view' && $account->id() == $no_access_uid) {
61 $grants['node_access_all'] = [0];
67 * Implements hook_node_access_records().
69 * By default, records are written for all nodes. When the
70 * 'node_access_test.private' state variable is set to TRUE, records
71 * are only written for nodes with a "private" property set, which causes the
72 * Node module to write the default global view grant for nodes that are not
75 * @see \Drupal\node\Tests\NodeAccessBaseTableTest::setUp()
76 * @see node_access_test_node_grants()
77 * @see node_access_test.permissions.yml
79 function node_access_test_node_access_records(NodeInterface $node) {
81 // For NodeAccessBaseTableTestCase, only set records for private nodes.
82 if (!\Drupal::state()->get('node_access_test.private') || $node->private->value) {
83 // Groups 8888 and 8889 for the node_access_test realm both receive a view
84 // grant for all controlled nodes. See node_access_test_node_grants().
86 'realm' => 'node_access_test',
94 'realm' => 'node_access_test',
101 // For the author realm, the group ID is equivalent to a user ID, which
102 // means there are many many groups of just 1 user.
104 'realm' => 'node_access_test_author',
105 'gid' => $node->getOwnerId(),
117 * Adds the private field to a node type.
119 * @param \Drupal\node\NodeTypeInterface $type
120 * A node type entity.
122 function node_access_test_add_field(NodeTypeInterface $type) {
123 $field_storage = FieldStorageConfig::create([
124 'field_name' => 'private',
125 'entity_type' => 'node',
128 $field_storage->save();
129 $field = FieldConfig::create([
130 'field_name' => 'private',
131 'entity_type' => 'node',
132 'bundle' => $type->id(),
133 'label' => 'Private',
137 // Assign widget settings for the 'default' form mode.
138 entity_get_form_display('node', $type->id(), 'default')
139 ->setComponent('private', [
146 * Implements hook_node_access().
148 function node_access_test_node_access(NodeInterface $node, $op, AccountInterface $account) {
149 $secret_catalan = \Drupal::state()
150 ->get('node_access_test_secret_catalan') ?: 0;
151 if ($secret_catalan && $node->language()->getId() == 'ca') {
152 // Make all Catalan content secret.
153 return AccessResult::forbidden()->setCacheMaxAge(0);
156 return AccessResult::neutral()->setCacheMaxAge(0);