access_policy-1.0.x-dev/tests/src/Kernel/Plugin/AccessRule/EntityFieldEntityReferenceTest.php
tests/src/Kernel/Plugin/AccessRule/EntityFieldEntityReferenceTest.php
<?php namespace Drupal\Tests\access_policy\Kernel\Plugin\AccessRule; use Drupal\access_policy\Entity\AccessPolicy; use Drupal\access_policy\Plugin\access_policy\OperatorValidationTrait; use Drupal\field\Entity\FieldConfig; use Drupal\field\Entity\FieldStorageConfig; use Drupal\taxonomy\Entity\Vocabulary; use Drupal\Tests\access_policy\Kernel\AccessPolicyKernelTestBase; use Drupal\Tests\taxonomy\Traits\TaxonomyTestTrait; /** * Tests EntityFieldEntityReference plugin features. * * @group access_policy */ class EntityFieldEntityReferenceTest extends AccessPolicyKernelTestBase { use TaxonomyTestTrait; use OperatorValidationTrait; /** * The tags vocabulary. * * @var \Drupal\Core\Entity\EntityInterface */ protected $vocabulary; /** * The modules to install. * * @var string[] */ protected static $modules = [ 'field', 'filter', 'node', 'taxonomy', 'options', 'access_policy', 'access_policy_test', 'system', 'text', 'user', 'datetime', ]; /** * {@inheritdoc} */ protected function setUp(): void { parent::setUp(); $this->installConfig(['access_policy_test']); $this->installEntitySchema('taxonomy_term'); // Create a tags vocabulary. $this->vocabulary = Vocabulary::create([ 'name' => 'tags', 'vid' => 'tags', ]); $this->vocabulary->save(); // Create the taxonomy term entity reference field for the node and user. $field_storage = FieldStorageConfig::create([ 'field_name' => 'field_tags', 'entity_type' => 'user', 'type' => 'entity_reference', 'cardinality' => -1, 'settings' => [ 'target_type' => 'taxonomy_term', ], ]); $field_storage->save(); $field = FieldConfig::create([ 'field_storage' => $field_storage, 'field_name' => 'field_tags', 'bundle' => 'user', 'translatable' => FALSE, ]); $field->save(); $field_storage = FieldStorageConfig::create([ 'field_name' => 'field_tags', 'entity_type' => 'node', 'type' => 'entity_reference', 'cardinality' => -1, 'settings' => [ 'target_type' => 'taxonomy_term', ], ]); $field_storage->save(); $field = FieldConfig::create([ 'field_storage' => $field_storage, 'field_name' => 'field_tags', 'bundle' => 'page', 'translatable' => FALSE, ]); $field->save(); // Creating a policy is necessary to register the plugins. $policy = AccessPolicy::create([ 'id' => 'basic_policy', 'label' => 'Basic test policy', 'target_entity_type_id' => 'node', ]); $policy->save(); } /** * Tests the entity reference access rule. * * @dataProvider providerEntityFieldEntityReference */ public function testEntityFieldEntityReference($settings, $value, $expected, $expected_query) { // Test entity reference fields. $term_1 = $this->createTerm($this->vocabulary, [ 'title' => 'Term 1', ]); $term_1->save(); $term_2 = $this->createTerm($this->vocabulary, [ 'name' => 'Term 2', ]); $term_2->save(); $policy = AccessPolicy::create([ 'id' => 'match_reference_value', 'label' => 'Matching entity reference with value', 'target_entity_type_id' => 'node', ]); $policy->save(); $access_rule = $this->accessRuleManager->getHandler('node', 'field_tags'); $access_rule->setSettings($settings); $policy->addHandler('access_rule', $access_rule); $policy->save(); // This is referencing node 1 in the access policy and should not be // visible. $node_1 = $this->createNode([ 'title' => 'Node 1', 'type' => 'page', 'status' => 1, 'field_tags' => $value, 'access_policy' => ['match_reference_value'], ]); $web_user = $this->createUser([ 'access content', 'view match_reference_value content', ]); $access = $this->accessPolicyValidator->validate($node_1, $web_user, 'view'); $this->assertEquals($expected, $access); $contexts = $this->accessPolicyValidator->getCacheContexts($node_1); $this->assertEquals(['user.permissions'], $contexts); $this->setCurrentUser($web_user); $this->assertQueryResults('node', $expected_query); } /** * Provides access rule settings. */ public function providerEntityFieldEntityReference() { return [ 'term reference field has matching term id is true' => [ ['operator' => 'in', 'value' => [['target_id' => 1]]], 1, TRUE, [1], ], 'term reference field has matching term id is false' => [ ['operator' => 'in', 'value' => [['target_id' => 1]]], 2, FALSE, [], ], 'term reference field should not have matching term id is true' => [ ['operator' => 'not in', 'value' => [['target_id' => 1]]], 2, TRUE, [1], ], 'term reference field should not have matching term id is false' => [ ['operator' => 'not in', 'value' => [['target_id' => 1]]], 1, FALSE, [], ], ]; } /** * Tests entity reference field with multiple access rules. */ public function testEntityFieldEntityReferenceWithMultipleRules() { $policy = AccessPolicy::create([ 'id' => 'policy_with_multiple_rules', 'label' => 'Basic test policy with multiple rules', 'target_entity_type_id' => 'node', ]); $policy->save(); // Test entity reference fields. $term_1 = $this->createTerm($this->vocabulary, [ 'title' => 'Term 1', ]); $term_1->save(); $term_2 = $this->createTerm($this->vocabulary, [ 'name' => 'Term 2', ]); $term_2->save(); $access_rule = $this->accessRuleManager->getHandler('node', 'field_tags'); $access_rule->setSettings([ 'value' => [ ['target_id' => $term_1->id()], ], 'operator' => 'in', 'query' => TRUE, ]); $policy->addHandler('access_rule', $access_rule); $access_rule_2 = $this->accessRuleManager->getHandler('node', 'field_tags'); $access_rule_2->setSettings([ 'value' => [ ['target_id' => $term_2->id()], ], 'operator' => 'not in', 'query' => TRUE, ]); $policy->addHandler('access_rule', $access_rule_2); $policy->save(); // Create a basic node. $node_1 = $this->createNode([ 'title' => 'Node 1', 'type' => 'page', 'status' => 1, 'field_tags' => [ $term_1, ], 'access_policy' => ['policy_with_multiple_rules'], ]); // Create a basic node. $node_2 = $this->createNode([ 'title' => 'Node 2', 'type' => 'page', 'status' => 1, 'field_tags' => [ $term_2, ], 'access_policy' => ['policy_with_multiple_rules'], ]); $user = $this->createUser([ 'view policy_with_multiple_rules content', ]); $user->save(); $access = $this->accessPolicyValidator->validate($node_1, $user, 'view'); $this->assertTrue($access, 'The user should have access'); $access = $this->accessPolicyValidator->validate($node_2, $user, 'view'); $this->assertFalse($access, 'The user should not have access'); $this->setCurrentUser($user); $this->assertQueryResults('node', [ $node_1->id(), ]); } }