Merge pull request #925 from GiantRobot/CRM-12737
[civicrm-core.git] / tests / phpunit / api / v3 / ACLPermissionTest.php
CommitLineData
6a488035 1<?php
6a488035
TO
2
3/*
4 +--------------------------------------------------------------------+
5 | CiviCRM version 4.3 |
6 +--------------------------------------------------------------------+
7 | Copyright CiviCRM LLC (c) 2004-2013 |
8 +--------------------------------------------------------------------+
9 | This file is a part of CiviCRM. |
10 | |
11 | CiviCRM is free software; you can copy, modify, and distribute it |
12 | under the terms of the GNU Affero General Public License |
13 | Version 3, 19 November 2007 and the CiviCRM Licensing Exception. |
14 | |
15 | CiviCRM is distributed in the hope that it will be useful, but |
16 | WITHOUT ANY WARRANTY; without even the implied warranty of |
17 | MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. |
18 | See the GNU Affero General Public License for more details. |
19 | |
20 | You should have received a copy of the GNU Affero General Public |
21 | License and the CiviCRM Licensing Exception along |
22 | with this program; if not, contact CiviCRM LLC |
23 | at info[AT]civicrm[DOT]org. If you have questions about the |
24 | GNU Affero General Public License or the licensing of CiviCRM, |
25 | see the CiviCRM license FAQ at http://civicrm.org/licensing |
26 +--------------------------------------------------------------------+
27 */
28
29require_once 'CiviTest/CiviUnitTestCase.php';
30
31/**
32 * This class is intended to test ACL permission using the multisite module
33 *
34 * @package CiviCRM_APIv3
35 * @subpackage API_Contact
36 */
37
38class api_v3_ACLPermissionTest extends CiviUnitTestCase {
39 protected $_apiversion;
40 protected $_params;
41 protected $hookClass = null;
42
43 public $_eNoticeCompliant = TRUE;
44
45 protected $_entity; function setUp() {
46 $this->_apiversion = 3;
47
48 parent::setUp();
49 $baoObj = new CRM_Core_DAO();
50 $baoObj->createTestObject('CRM_Pledge_BAO_Pledge', array(), 1, 0);
51 $baoObj->createTestObject('CRM_Core_BAO_Phone', array(), 1, 0);
52 $this->hookClass = CRM_Utils_Hook::singleton();
53 $config = CRM_Core_Config::singleton();
54 $config->userPermissionClass->permissions = array();
55 }
56/**
57 * (non-PHPdoc)
58 * @see CiviUnitTestCase::tearDown()
59 */
60 function tearDown() {
61 $this->hookClass->reset();
62 $tablesToTruncate = array(
63 'civicrm_contact',
64 );
65 $this->quickCleanup($tablesToTruncate);
66 $config = CRM_Core_Config::singleton();
67 unset($config->userPermissionClass->permissions);
68 }
69/**
70 * Function just tests that an empty where hook returns the 2 expected results
71 */
72 function testContactGetNoResultsHook(){
73 $this->hookClass->setHook('civicrm_aclWhereClause', array($this, 'aclWhereHookNoResults'));
74 $result = civicrm_api('contact', 'get', array(
75 'version' => $this->_apiversion,
76 'check_permissions' => 1,
77 'return' => 'display_name',
78 ));
79
80 $this->assertAPISuccess($result,"this should succeed but return no results. line " . __LINE__);
81 $this->assertEquals(0, $result['count']);
82 }
83
84 /**
85 * Function tests all results are returned
86 */
87 function testContactGetAllResultsHook(){
88 $this->hookClass->setHook('civicrm_aclWhereClause', array($this, 'aclWhereHookAllResults'));
89 $result = civicrm_api('contact', 'get', array(
90 'version' => $this->_apiversion,
91 'check_permissions' => 1,
92 'return' => 'display_name',
93 ));
94
95 $this->assertAPISuccess($result,"this should succeed but return no results. line " . __LINE__);
96 $this->assertEquals(2, $result['count']);
97 }
98 /**
99 * Function just tests that an empty where hook returns the 2 expected results
100 */
101 function testContactGetPermissionHookNoDeleted(){
102 civicrm_api('contact', 'create', array('id' => 2, 'version' => $this->_apiversion, 'is_deleted' => 1));
103 $this->hookClass->setHook('civicrm_aclWhereClause', array($this, 'aclWhereHookAllResults'));
104 $result = civicrm_api('contact', 'get', array(
105 'version' => $this->_apiversion,
106 'check_permissions' => 1,
107 'return' => 'display_name',
108 ));
109
110 $this->assertAPISuccess($result,"this should succeed but return one results. line " . __LINE__);
111 $this->assertEquals(1, $result['count']);
112 }
113
114 /**
115 * test permissions limited by hook
116 */
117 function testContactGetHookLimitingHook(){
118 $this->hookClass->setHook('civicrm_aclWhereClause', array($this, 'aclWhereOnlySecond'));
119
120 $result = civicrm_api('contact', 'get', array(
121 'version' => $this->_apiversion,
122 'check_permissions' => 1,
123 'return' => 'display_name',
124 ));
125 $this->assertAPISuccess($result, 'api call succeeded');
126 $this->assertEquals(1, $result['count']);
127 }
128
129/**
130 * confirm that without check permissions we still get 2 contacts returned
131 */
132 function testContactGetHookLimitingHookDontCheck(){
133 //
134 $result = civicrm_api('contact', 'get', array(
135 'version' => $this->_apiversion,
136 'check_permissions' => 0,
137 'return' => 'display_name',
138 ));
139 $this->assertAPISuccess($result, 'api call succeeded');
140 $this->assertEquals(2, $result['count']);
141 }
142 /**
143 * Check that id works as a filter
144 */
145 function testContactGetIDFilter(){
146 $this->hookClass->setHook('civicrm_aclWhereClause', array($this, 'aclWhereHookAllResults'));
147 $result = civicrm_api('contact', 'get', array(
148 'version' => $this->_apiversion,
149 'sequential' => 1,
150 'id' => 2,
151 'check_permissions' => 1,
152 ));
153
154 $this->assertAPISuccess($result, 'api call succeeded');
155 $this->assertEquals(1, $result['count']);
156 $this->assertEquals(2, $result['id']);
157 }
158
159/**
160 * Check that address IS returned
161 */
162 function testContactGetAddressReturned(){
163 $this->hookClass->setHook('civicrm_aclWhereClause', array($this, 'aclWhereOnlySecond'));
164 $fullresult = civicrm_api('contact', 'get', array(
165 'version' => $this->_apiversion,
166 'sequential' => 1,
167 ));
168 //return doesn't work for all keys - can't fix that here so let's skip ...
169 //prefix & suffix are inconsistent due to CRM-7929
170 // unsure about others but return doesn't work on them
171 $elementsReturnDoesntSupport = array(
172 'prefix_id',
173 'prefix',
174 'suffix_id',
175 'suffix',
176 'gender_id',
177 'gender',
178 'current_employer',
179 'phone_id',
180 'phone_type_id',
181 'phone',
182 'worldregion_id',
183 'world_region');
184 $expectedReturnElements = array_diff(array_keys($fullresult['values'][0]),$elementsReturnDoesntSupport);
185 $result = civicrm_api('contact', 'get', array(
186 'version' => $this->_apiversion,
187 'check_permissions' => 1,
188 'return' => $expectedReturnElements,
189 'sequential' => 1,
190 ));
191 $this->assertAPISuccess($result, 'api call succeeded');
192 $this->assertEquals(1, $result['count']);
193 foreach ($expectedReturnElements as $element){
194 $this->assertArrayHasKey($element, $result['values'][0]);
195 }
196 }
197 /**
198 * Check that pledge IS not returned
199 */
200 function testContactGetPledgeIDNotReturned(){
201 $this->hookClass->setHook('civicrm_aclWhereClause', array($this, 'aclWhereHookAllResults'));
202 $fullresult = civicrm_api('contact', 'get', array(
203 'version' => $this->_apiversion,
204 'sequential' => 1,
205 ));
206 $result = civicrm_api('contact', 'get', array(
207 'version' => $this->_apiversion,
208 'check_permissions' => 1,
209 'return' => 'pledge_id',
210 'sequential' => 1,
211 ));
212 $this->assertAPISuccess($result);
213 $this->assertArrayNotHasKey('pledge_id', $result['values'][0]);
214 }
215
216 /**
217 * Check that pledge IS not an allowable filter
218 */
219 function testContactGetPledgeIDNotFiltered(){
220 $this->hookClass->setHook('civicrm_aclWhereClause', array($this, 'aclWhereHookAllResults'));
221 $fullresult = civicrm_api('contact', 'get', array(
222 'version' => $this->_apiversion,
223 'sequential' => 1,
224 ));
225 $result = civicrm_api('contact', 'get', array(
226 'version' => $this->_apiversion,
227 'check_permissions' => 1,
228 'pledge_id' => 1,
229 'sequential' => 1,
230 ));
231 $this->assertAPISuccess($result, 'api call succeeded');
232 $this->assertEquals(2, $result['count']);
233 }
234
235 /**
236 * Check that chaining doesn't bypass permissions
237 */
238 function testContactGetPledgeNotChainable(){
239 $this->hookClass->setHook('civicrm_aclWhereClause', array($this, 'aclWhereOnlySecond'));
240 $fullresult = civicrm_api('contact', 'get', array(
241 'version' => $this->_apiversion,
242 'sequential' => 1,
243 ));
244 $result = civicrm_api('contact', 'get', array(
245 'version' => $this->_apiversion,
246 'check_permissions' => 1,
247 'api.pledge.get' => 1,
248 'sequential' => 1,
249 ));
250 $this->assertEquals('Error in call to pledge_get : API permission check failed for pledge/get call; missing permission: access CiviCRM.', $result['error_message']);
251 }
252
253 /**
254 * no results returned
255 */
256 function aclWhereHookNoResults($type, &$tables, &$whereTables, &$contactID, &$where) {
257 }
258 /**
259 * all results returned
260 */
261 function aclWhereHookAllResults($type, &$tables, &$whereTables, &$contactID, &$where) {
262 $where = " (1) ";
263 }
264 /**
265 * full results returned
266 */
267 function aclWhereOnlySecond($type, &$tables, &$whereTables, &$contactID, &$where) {
268 $where = " contact_a.id > 1";
269 }
270
271
272}
273