Merge pull request #19017 from eileenmcnaughton/remove_recur
[civicrm-core.git] / tests / phpunit / api / v3 / EntityTagACLTest.php
1 <?php
2 /*
3 +--------------------------------------------------------------------+
4 | Copyright CiviCRM LLC. All rights reserved. |
5 | |
6 | This work is published under the GNU AGPLv3 license with some |
7 | permitted exceptions and without any warranty. For full license |
8 | and copyright information, see https://civicrm.org/licensing |
9 +--------------------------------------------------------------------+
10 */
11
12 /**
13 * Test APIv3 civicrm_entity_tag_* functions
14 *
15 * @package CiviCRM_APIv3
16 * @subpackage API_Core
17 */
18
19 /**
20 * Class api_v3_EntityTagTest.
21 *
22 * This test class was introduced to ensure that the fix for CRM-17350 (reducing the required permission
23 * from edit all contacts to has right to edit this contact) would not result in inappropriate permission opening on
24 * other entities. Other entities are still too restricted but that is a larger job.
25 * @group headless
26 */
27 class api_v3_EntityTagACLTest extends CiviUnitTestCase {
28
29 use CRMTraits_ACL_PermissionTrait;
30
31 /**
32 * API Version in use.
33 *
34 * @var int
35 */
36 protected $_apiversion = 3;
37
38 /**
39 * Entity being tested.
40 *
41 * @var string
42 */
43 protected $_entity = 'entity_tag';
44
45 /**
46 * Set up permissions for test.
47 */
48 public function setUp() {
49 $this->useTransaction(TRUE);
50 parent::setUp();
51 $individualID = $this->individualCreate();
52 $daoObj = new CRM_Core_DAO();
53 $this->callAPISuccess('Attachment', 'create', [
54 'entity_table' => 'civicrm_contact',
55 'entity_id' => $individualID,
56 'mime_type' => 'k',
57 'name' => 'p',
58 'content' => 'l',
59 ]);
60 $daoObj->createTestObject('CRM_Activity_BAO_Activity', [], 1, 0);
61 $daoObj->createTestObject('CRM_Case_BAO_Case', [], 1, 0);
62 $entities = $this->getTagOptions();
63 foreach ($entities as $key => $entity) {
64 $this->callAPISuccess('Tag', 'create', [
65 'used_for' => $key,
66 'name' => $entity,
67 'description' => $entity,
68 ]);
69 }
70 CRM_Core_Config::singleton()->userPermissionClass->permissions = ['access CiviCRM'];
71 }
72
73 /**
74 * Get the options for the used_for fields.
75 *
76 * @return array
77 */
78 public function getTagOptions() {
79 $options = $this->callAPISuccess('Tag', 'getoptions', ['field' => 'used_for']);
80 return $options['values'];
81 }
82
83 /**
84 * Get the entity table for a tag label.
85 *
86 * @param string $entity
87 *
88 * @return string
89 */
90 protected function getTableForTag($entity) {
91 $options = $this->getTagOptions();
92 return array_search($entity, $options);
93 }
94
95 /**
96 * Get entities which can be tagged in data provider format.
97 */
98 public function taggableEntities() {
99 $return = [];
100 foreach ($this->getTagOptions() as $entity) {
101 $return[] = [$entity];
102 }
103 return $return;
104 }
105
106 /**
107 * This test checks that users with edit all contacts can edit all tags.
108 *
109 * @dataProvider taggableEntities
110 *
111 * We are looking to see that a contact with edit all contacts can still add all tags (for all
112 * tag entities since that was how it was historically and we are not fixing non-contact entities).
113 *
114 * @param string $entity
115 * Entity to test
116 */
117 public function testThatForEntitiesEditAllContactsCanAddTags($entity) {
118
119 CRM_Core_Config::singleton()->userPermissionClass->permissions = ['edit all contacts', 'access CiviCRM'];
120 $this->callAPISuccess('EntityTag', 'create', [
121 'entity_id' => 1,
122 'tag_id' => $entity,
123 'check_permissions' => TRUE,
124 'entity_table' => $this->getTableForTag($entity),
125 ]);
126 $this->callAPISuccessGetCount('EntityTag', [
127 'entity_id' => 1,
128 'entity_table' => $this->getTableForTag($entity),
129 ], 1);
130 }
131
132 /**
133 * This test checks that an ACL or edit all contacts is required to be able to create a contact.
134 *
135 * @dataProvider taggableEntities
136 */
137 public function testThatForEntityWithoutACLOrEditAllThereIsNoAccess($entity) {
138
139 CRM_Core_Config::singleton()->userPermissionClass->permissions = ['access CiviCRM', 'view all contacts'];
140 $this->callAPIFailure('EntityTag', 'create', [
141 'entity_id' => 1,
142 'tag_id' => $entity,
143 'check_permissions' => TRUE,
144 'entity_table' => $this->getTableForTag($entity),
145 ]);
146 }
147
148 /**
149 * This test checks that permissions are not applied when check_permissions is off.
150 *
151 * @dataProvider taggableEntities
152 *
153 * @param string $entity
154 * Entity to test
155 */
156 public function testCheckPermissionsOffWorks($entity) {
157
158 CRM_Core_Config::singleton()->userPermissionClass->permissions = ['access CiviCRM', 'view all contacts'];
159 $result = $this->callAPISuccess('EntityTag', 'create', [
160 'entity_id' => 1,
161 'tag_id' => $entity,
162 'check_permissions' => 0,
163 'entity_table' => $this->getTableForTag($entity),
164 ]);
165 $this->assertEquals(1, $result['added']);
166 $this->callAPISuccessGetCount('EntityTag', [
167 'entity_id' => 1,
168 'entity_table' => $this->getTableForTag($entity),
169 'check_permissions' => 0,
170 ], 1);
171 }
172
173 /**
174 * This test checks ACLs can be used to control who can edit a contact.
175 *
176 * Note that for other entities this hook will not allow them to edit the entity_tag and they still need
177 * edit all contacts (pending a more extensive fix).
178 *
179 * @dataProvider taggableEntities
180 *
181 * @param string $entity
182 * Entity to test
183 */
184 public function testThatForEntitiesACLApplies($entity) {
185
186 CRM_Core_Config::singleton()->userPermissionClass->permissions = ['access CiviCRM', 'view all contacts'];
187 $this->hookClass->setHook('civicrm_aclWhereClause', [$this, 'aclWhereHookAllResults']);
188 civicrm_api('EntityTag', 'create', [
189 'version' => 3,
190 'entity_id' => 1,
191 'tag_id' => $entity,
192 'entity_table' => $this->getTableForTag($entity),
193 'check_permissions' => TRUE,
194 ]);
195 $this->callAPISuccessGetCount('EntityTag', [
196 'entity_id' => 1,
197 'entity_table' => $this->getTableForTag($entity),
198 ], ($entity == 'Contacts' ? 1 : 0));
199 }
200
201 }