32363b90255d73703d744f637d7667d8369d7a61
[civicrm-core.git] / tests / phpunit / api / v3 / CaseTest.php
1 <?php
2 /**
3 * @file
4 * File for the TestCase class
5 *
6 * (PHP 5)
7 *
8 * @author Walt Haas <walt@dharmatech.org> (801) 534-1262
9 * @copyright Copyright CiviCRM LLC (C) 2009
10 * @license http://www.fsf.org/licensing/licenses/agpl-3.0.html
11 * GNU Affero General Public License version 3
12 * @version $Id: ActivityTest.php 31254 2010-12-15 10:09:29Z eileen $
13 * @package CiviCRM
14 *
15 * This file is part of CiviCRM
16 *
17 * CiviCRM is free software; you can redistribute it and/or
18 * modify it under the terms of the GNU Affero General Public License
19 * as published by the Free Software Foundation; either version 3 of
20 * the License, or (at your option) any later version.
21 *
22 * CiviCRM is distributed in the hope that it will be useful,
23 * but WITHOUT ANY WARRANTY; without even the implied warranty of
24 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
25 * GNU Affero General Public License for more details.
26 *
27 * You should have received a copy of the GNU Affero General Public
28 * License along with this program. If not, see
29 * <http://www.gnu.org/licenses/>.
30 */
31
32 /**
33 * Include class definitions
34 */
35
36 /**
37 * Test APIv3 civicrm_case_* functions
38 *
39 * @package CiviCRM_APIv3
40 * @group headless
41 */
42 class api_v3_CaseTest extends CiviCaseTestCase {
43 protected $_params;
44 protected $_entity;
45 protected $_apiversion = 3;
46 protected $followup_activity_type_value;
47 /**
48 * Activity ID of created case.
49 *
50 * @var int
51 */
52 protected $_caseActivityId;
53
54 /**
55 * Test setup for every test.
56 *
57 * Connect to the database, truncate the tables that will be used
58 * and redirect stdin to a temporary file.
59 */
60 public function setUp() {
61 $this->_entity = 'case';
62
63 parent::setUp();
64
65 $activityTypes = $this->callAPISuccess('option_value', 'get', array(
66 'option_group_id' => 2,
67 'name' => 'Follow Up',
68 'label' => 'Follow Up',
69 'sequential' => 1,
70 ));
71 $this->followup_activity_type_value = $activityTypes['values'][0]['value'];
72
73 $this->_params = array(
74 'case_type_id' => $this->caseTypeId,
75 'subject' => 'Test case',
76 'contact_id' => 17,
77 );
78 }
79
80 /**
81 * Check with empty array.
82 */
83 public function testCaseCreateEmpty() {
84 $this->callAPIFailure('case', 'create', array());
85 }
86
87 /**
88 * Check if required fields are not passed.
89 */
90 public function testCaseCreateWithoutRequired() {
91 $params = array(
92 'subject' => 'this case should fail',
93 'case_type_id' => 1,
94 );
95
96 $this->callAPIFailure('case', 'create', $params);
97 }
98
99 /**
100 * Test Getlist with id and case_id
101 */
102 public function testCaseGetListById() {
103 $params = $this->_params;
104 $params['contact_id'] = $this->individualCreate();
105
106 //Create 3 sample Cases.
107 $case1 = $this->callAPISuccess('case', 'create', $params);
108 $params['subject'] = 'Test Case 2';
109 $case2 = $this->callAPISuccess('case', 'create', $params);
110 $params['subject'] = 'Test Case 3';
111 $case3 = $this->callAPISuccess('case', 'create', $params);
112
113 $getParams = array(
114 'id' => array($case1['id']),
115 'extra' => array('contact_id'),
116 'params' => array(
117 'version' => 3,
118 'case_id' => array('!=' => $case2['id']),
119 'case_id.is_deleted' => 0,
120 'case_id.status_id' => array('!=' => "Closed"),
121 'case_id.end_date' => array('IS NULL' => 1),
122 ),
123 );
124 $result = $this->callAPISuccess('case', 'getlist', $getParams);
125
126 //Only 1 case should be returned.
127 $this->assertEquals(count($result['values']), 1);
128 $this->assertEquals($result['values'][0]['id'], $case1['id']);
129 }
130
131 /**
132 * Test create function with valid parameters.
133 */
134 public function testCaseCreate() {
135 $params = $this->_params;
136 // Test using label instead of value.
137 unset($params['case_type_id']);
138 $params['case_type'] = $this->caseType;
139 $result = $this->callAPIAndDocument('case', 'create', $params, __FUNCTION__, __FILE__);
140 $id = $result['id'];
141
142 // Check result
143 $result = $this->callAPISuccess('case', 'get', array('id' => $id));
144 $this->assertEquals($result['values'][$id]['id'], $id);
145 $this->assertEquals($result['values'][$id]['case_type_id'], $this->caseTypeId);
146 $this->assertEquals($result['values'][$id]['subject'], $params['subject']);
147 }
148
149 /**
150 * Test case create with valid parameters and custom data.
151 */
152 public function testCaseCreateCustom() {
153 $ids = $this->entityCustomGroupWithSingleFieldCreate(__FUNCTION__, __FILE__);
154 $params = $this->_params;
155 $params['custom_' . $ids['custom_field_id']] = "custom string";
156 $result = $this->callAPIAndDocument($this->_entity, 'create', $params, __FUNCTION__, __FILE__);
157 $result = $this->callAPISuccess($this->_entity, 'get', array(
158 'return.custom_' . $ids['custom_field_id'] => 1,
159 'id' => $result['id'],
160 ));
161 $this->assertEquals("custom string", $result['values'][$result['id']]['custom_' . $ids['custom_field_id']], ' in line ' . __LINE__);
162
163 $this->customFieldDelete($ids['custom_field_id']);
164 $this->customGroupDelete($ids['custom_group_id']);
165 }
166
167 /**
168 * Test update (create with id) function with valid parameters.
169 */
170 public function testCaseUpdate() {
171 $params = $this->_params;
172 // Test using name instead of value
173 unset($params['case_type_id']);
174 $params['case_type'] = $this->caseType;
175 $result = $this->callAPISuccess('case', 'create', $params);
176 $id = $result['id'];
177 $case = $this->callAPISuccess('case', 'getsingle', array('id' => $id));
178
179 // Update Case.
180 $params = array('id' => $id);
181 $params['subject'] = $case['subject'] = 'Something Else';
182 $this->callAPISuccess('case', 'create', $params);
183
184 // Verify that updated case is exactly equal to the original with new subject.
185 $result = $this->callAPISuccessGetSingle('Case', array('case_id' => $id));
186 $this->assertAPIArrayComparison($result, $case);
187 }
188
189 /**
190 * Test case update with custom data
191 */
192 public function testCaseUpdateCustom() {
193 $ids = $this->entityCustomGroupWithSingleFieldCreate(__FUNCTION__, __FILE__);
194 $params = $this->_params;
195
196 // Create a case with custom data
197 $params['custom_' . $ids['custom_field_id']] = 'custom string';
198 $result = $this->callAPISuccess($this->_entity, 'create', $params);
199
200 $caseId = $result['id'];
201 $result = $this->callAPISuccess($this->_entity, 'get', array(
202 'return.custom_' . $ids['custom_field_id'] => 1,
203 'version' => 3,
204 'id' => $result['id'],
205 ));
206 $this->assertEquals("custom string", $result['values'][$result['id']]['custom_' . $ids['custom_field_id']]);
207 $fields = $this->callAPISuccess($this->_entity, 'getfields', array('version' => $this->_apiversion));
208 $this->assertTrue(is_array($fields['values']['custom_' . $ids['custom_field_id']]));
209
210 // Update the activity with custom data.
211 $params = array(
212 'id' => $caseId,
213 'custom_' . $ids['custom_field_id'] => 'Updated my test data',
214 'version' => $this->_apiversion,
215 );
216 $result = $this->callAPISuccess($this->_entity, 'create', $params);
217
218 $result = $this->callAPISuccess($this->_entity, 'get', array(
219 'return.custom_' . $ids['custom_field_id'] => 1,
220 'version' => 3,
221 'id' => $result['id'],
222 ));
223 $this->assertEquals("Updated my test data", $result['values'][$result['id']]['custom_' . $ids['custom_field_id']]);
224 }
225
226 /**
227 * Test delete function with valid parameters.
228 */
229 public function testCaseDelete() {
230 // Create Case
231 $result = $this->callAPISuccess('case', 'create', $this->_params);
232
233 // Move Case to Trash
234 $id = $result['id'];
235 $this->callAPISuccess('case', 'delete', array('id' => $id, 'move_to_trash' => 1));
236
237 // Check result - also check that 'case_id' works as well as 'id'
238 $result = $this->callAPISuccess('case', 'get', array('case_id' => $id));
239 $this->assertEquals(1, $result['values'][$id]['is_deleted']);
240
241 // Restore Case from Trash
242 $this->callAPISuccess('case', 'restore', array('id' => $id));
243
244 // Check result
245 $result = $this->callAPISuccess('case', 'get', array('case_id' => $id));
246 $this->assertEquals(0, $result['values'][$id]['is_deleted']);
247
248 // Delete Case Permanently
249 $this->callAPISuccess('case', 'delete', array('case_id' => $id));
250
251 // Check result - case should no longer exist
252 $result = $this->callAPISuccess('case', 'get', array('id' => $id));
253 $this->assertEquals(0, $result['count']);
254 }
255
256 /**
257 * Test get function based on activity.
258 */
259 public function testCaseGetByActivity() {
260 // Create Case
261 $result = $this->callAPISuccess('case', 'create', $this->_params);
262 $id = $result['id'];
263
264 // Check result - we should get a list of activity ids
265 $result = $this->callAPISuccess('case', 'get', array('id' => $id, 'return' => 'activities'));
266 $case = $result['values'][$id];
267 $activity = $case['activities'][0];
268
269 // Fetch case based on an activity id
270 $result = $this->callAPISuccess('case', 'get', array(
271 'activity_id' => $activity,
272 'return' => 'activities',
273 ));
274 $this->assertEquals(FALSE, empty($result['values'][$id]));
275 $this->assertEquals($result['values'][$id], $case);
276 }
277
278 /**
279 * Test get function based on contact id.
280 */
281 public function testCaseGetByContact() {
282 // Create Case
283 $result = $this->callAPISuccess('case', 'create', $this->_params);
284 $id = $result['id'];
285
286 // Store result for later
287 $case = $this->callAPISuccessGetSingle('case', array('id' => $id, 'return' => array('activities', 'contacts')));
288
289 // Fetch case based on client contact id
290 $result = $this->callAPISuccess('case', 'get', array(
291 'client_id' => $this->_params['contact_id'],
292 'return' => array('activities', 'contacts'),
293 ));
294 $this->assertAPIArrayComparison($result['values'][$id], $case);
295 }
296
297 /**
298 * Test get function based on subject.
299 */
300 public function testCaseGetBySubject() {
301 // Create Case
302 $result = $this->callAPISuccess('case', 'create', $this->_params);
303 $id = $result['id'];
304
305 // Store result for later
306 $case = $this->callAPISuccessGetSingle('Case', array('id' => $id, 'return' => 'subject'));
307
308 // Fetch case based on client contact id
309 $result = $this->callAPISuccess('case', 'get', array(
310 'subject' => $this->_params['subject'],
311 'return' => array('subject'),
312 ));
313 $this->assertAPIArrayComparison($result['values'][$id], $case);
314 }
315
316 /**
317 * Test get function based on wrong subject.
318 */
319 public function testCaseGetByWrongSubject() {
320 $result = $this->callAPISuccess('case', 'create', $this->_params);
321
322 // Append 'wrong' to subject so that it is no longer the same.
323 $result = $this->callAPISuccess('case', 'get', array(
324 'subject' => $this->_params['subject'] . 'wrong',
325 'return' => array('activities', 'contacts'),
326 ));
327 $this->assertEquals(0, $result['count']);
328 }
329
330 /**
331 * Test get function with no criteria.
332 */
333 public function testCaseGetNoCriteria() {
334 $result = $this->callAPISuccess('case', 'create', $this->_params);
335 $id = $result['id'];
336
337 // Store result for later
338 $case = $this->callAPISuccessGetSingle('Case', array('id' => $id, 'return' => 'contact_id'));
339
340 $result = $this->callAPISuccess('case', 'get', array('limit' => 0, 'return' => array('contact_id')));
341 $this->assertAPIArrayComparison($result['values'][$id], $case);
342 }
343
344 /**
345 * Test activity api create for case activities.
346 */
347 public function testCaseActivityCreate() {
348 $params = $this->_params;
349 $case = $this->callAPISuccess('case', 'create', $params);
350 $params = array(
351 'case_id' => $case['id'],
352 // follow up
353 'activity_type_id' => $this->followup_activity_type_value,
354 'subject' => 'Test followup 123',
355 'source_contact_id' => $this->_loggedInUser,
356 'target_contact_id' => $this->_params['contact_id'],
357 );
358 $result = $this->callAPISuccess('activity', 'create', $params);
359 $this->assertEquals($result['values'][$result['id']]['activity_type_id'], $params['activity_type_id']);
360
361 // might need this for other tests that piggyback on this one
362 $this->_caseActivityId = $result['values'][$result['id']]['id'];
363
364 // Check other DB tables populated properly - is there a better way to do this? assertDBState() requires that we know the id already.
365 $dao = new CRM_Case_DAO_CaseActivity();
366 $dao->case_id = $case['id'];
367 $dao->activity_id = $this->_caseActivityId;
368 $this->assertEquals($dao->find(), 1, 'case_activity table not populated correctly in line ' . __LINE__);
369 $dao->free();
370
371 $dao = new CRM_Activity_DAO_ActivityContact();
372 $dao->activity_id = $this->_caseActivityId;
373 $dao->contact_id = $this->_params['contact_id'];
374 $dao->record_type_id = 3;
375 $this->assertEquals($dao->find(), 1, 'activity_contact table not populated correctly in line ' . __LINE__);
376 $dao->free();
377
378 // Check that fetching an activity by case id works, as well as returning case_id
379 $result = $this->callAPISuccessGetSingle('Activity', array(
380 'case_id' => $case['id'],
381 'activity_type_id' => $this->followup_activity_type_value,
382 'subject' => 'Test followup 123',
383 'return' => array('case_id'),
384 ));
385 $this->assertContains($case['id'], $result['case_id']);
386 }
387
388 /**
389 * Test activity api update for case activities.
390 */
391 public function testCaseActivityUpdate() {
392 // Need to create the case and activity before we can update it
393 $this->testCaseActivityCreate();
394
395 $params = array(
396 'activity_id' => $this->_caseActivityId,
397 'case_id' => 1,
398 'activity_type_id' => 14,
399 'source_contact_id' => $this->_loggedInUser,
400 'subject' => 'New subject',
401 );
402 $result = $this->callAPISuccess('activity', 'create', $params);
403
404 $this->assertEquals($result['values'][$result['id']]['subject'], $params['subject']);
405
406 // id should be one greater, since this is a new revision
407 $this->assertEquals($result['values'][$result['id']]['id'],
408 $this->_caseActivityId + 1,
409 'in line ' . __LINE__
410 );
411 $this->assertEquals($result['values'][$result['id']]['original_id'],
412 $this->_caseActivityId,
413 'in line ' . __LINE__
414 );
415
416 // Check revision is as expected
417 $revParams = array(
418 'activity_id' => $this->_caseActivityId,
419 );
420 $revActivity = $this->callAPISuccess('activity', 'get', $revParams);
421 $this->assertEquals($revActivity['values'][$this->_caseActivityId]['is_current_revision'],
422 0);
423 $this->assertEquals($revActivity['values'][$this->_caseActivityId]['is_deleted'],
424 0
425 );
426
427 //TODO: check some more things
428 }
429
430 public function testCaseActivityUpdateCustom() {
431 // Create a case first
432 $result = $this->callAPISuccess('case', 'create', $this->_params);
433
434 // Create custom field group
435 // Note the second parameter is Activity on purpose, not Case.
436 $custom_ids = $this->entityCustomGroupWithSingleFieldCreate(__FUNCTION__, 'ActivityTest.php');
437
438 // create activity
439 $params = array(
440 'case_id' => $result['id'],
441 // follow up
442 'activity_type_id' => 14,
443 'subject' => 'Test followup',
444 'source_contact_id' => $this->_loggedInUser,
445 'target_contact_id' => $this->_params['contact_id'],
446 'custom_' . $custom_ids['custom_field_id'] => "custom string",
447 );
448 $result = $this->callAPISuccess('activity', 'create', $params);
449
450 $aid = $result['values'][$result['id']]['id'];
451
452 // Update activity
453 $params = array(
454 'activity_id' => $aid,
455 'case_id' => 1,
456 'activity_type_id' => 14,
457 'source_contact_id' => $this->_loggedInUser,
458 'subject' => 'New subject',
459 );
460 $this->callAPISuccess('activity', 'create', $params);
461
462 // Retrieve revision and check custom fields got copied.
463 $revParams = array(
464 'activity_id' => $aid + 1,
465 'return.custom_' . $custom_ids['custom_field_id'] => 1,
466 );
467 $revAct = $this->callAPISuccess('activity', 'get', $revParams);
468
469 $this->assertEquals($revAct['values'][$aid + 1]['custom_' . $custom_ids['custom_field_id']], "custom string",
470 "Error message: " . CRM_Utils_Array::value('error_message', $revAct));
471
472 $this->customFieldDelete($custom_ids['custom_field_id']);
473 $this->customGroupDelete($custom_ids['custom_group_id']);
474 }
475
476 public function testCaseGetByStatus() {
477 // Create 2 cases with different status ids.
478 $case1 = $this->callAPISuccess('Case', 'create', array(
479 'contact_id' => 17,
480 'subject' => "Test case 1",
481 'case_type_id' => $this->caseTypeId,
482 'status_id' => "Open",
483 'sequential' => 1,
484 ));
485 $this->callAPISuccess('Case', 'create', array(
486 'contact_id' => 17,
487 'subject' => "Test case 2",
488 'case_type_id' => $this->caseTypeId,
489 'status_id' => "Urgent",
490 'sequential' => 1,
491 ));
492 $result = $this->callAPISuccessGetSingle('Case', array(
493 'sequential' => 1,
494 'contact_id' => 17,
495 'status_id' => "Open",
496 ));
497 $this->assertEquals($case1['id'], $result['id']);
498 }
499
500 public function testCaseGetWithRoles() {
501 $case1 = $this->callAPISuccess('Case', 'create', array(
502 'contact_id' => 17,
503 'subject' => "Test case with roles",
504 'case_type_id' => $this->caseTypeId,
505 'status_id' => "Open",
506 ));
507 $result = $this->callAPISuccessGetSingle('Case', array(
508 'id' => $case1['id'],
509 'status_id' => "Open",
510 'return' => array('contacts'),
511 ));
512 foreach ($result['contacts'] as $contact) {
513 if ($contact['role'] == 'Client') {
514 $this->assertEquals(17, $contact['contact_id']);
515 }
516 elseif ($contact['role'] == 'Homeless Services Coordinator') {
517 $this->assertEquals(1, $contact['creator']);
518 $this->assertEquals(1, $contact['manager']);
519 }
520 }
521 }
522
523 public function testCaseGetWithDefinition() {
524 $case1 = $this->callAPISuccess('Case', 'create', array(
525 'contact_id' => 17,
526 'subject' => "Test case with definition",
527 'case_type_id' => $this->caseTypeId,
528 'status_id' => "Open",
529 ));
530 $result1 = $this->callAPISuccessGetSingle('Case', array(
531 'id' => $case1['id'],
532 'status_id' => "Open",
533 'return' => array('case_type_id.definition'),
534 ));
535 $result2 = $this->callAPISuccessGetSingle('Case', array(
536 'id' => $case1['id'],
537 'status_id' => "Open",
538 'return' => array('case_type_id', 'case_type_id.definition'),
539 ));
540 $this->assertEquals($result1['case_type_id.definition'], $result2['case_type_id.definition']);
541 $def = $result1['case_type_id.definition'];
542 $this->assertEquals(array('name' => 'Open Case', 'max_instances' => 1), $def['activityTypes'][0]);
543 $this->assertNotEmpty($def['activitySets'][0]['activityTypes']);
544 $this->assertNotEmpty($def['caseRoles'][0]['manager']);
545 $this->assertNotEmpty($def['caseRoles'][0]['creator']);
546 }
547
548 public function testCaseGetTags() {
549 $case1 = $this->callAPISuccess('Case', 'create', array(
550 'contact_id' => 17,
551 'subject' => "Test case with tags",
552 'case_type_id' => $this->caseTypeId,
553 'status_id' => "Open",
554 ));
555 $tag1 = $this->tagCreate(array(
556 'name' => 'CaseTag1',
557 'used_for' => 'civicrm_case',
558 ));
559 $tag2 = $this->tagCreate(array(
560 'name' => 'CaseTag2',
561 'used_for' => 'civicrm_case',
562 ));
563 $this->callAPISuccess('EntityTag', 'create', array(
564 'entity_table' => 'civicrm_case',
565 'entity_id' => $case1['id'],
566 'tag_id' => $tag1['id'],
567 ));
568 $this->callAPIFailure('Case', 'getsingle', array(
569 'tag_id' => $tag2['id'],
570 ));
571 $result = $this->callAPISuccessGetSingle('Case', array(
572 'tag_id' => $tag1['id'],
573 'return' => 'tag_id.name',
574 ));
575 $this->assertEquals('CaseTag1', $result['tag_id'][$tag1['id']]['tag_id.name']);
576 }
577
578 /**
579 * Test that a chained api call can use the operator syntax.
580 *
581 * E.g. array('IN' => $value.contact_id)
582 *
583 * @throws \Exception
584 */
585 public function testCaseGetChainedOp() {
586 $contact1 = $this->individualCreate(array(), 1);
587 $contact2 = $this->individualCreate(array(), 2);
588 $case1 = $this->callAPISuccess('Case', 'create', array(
589 'contact_id' => $contact1,
590 'subject' => "Test case 1",
591 'case_type_id' => $this->caseTypeId,
592 ));
593 $case2 = $this->callAPISuccess('Case', 'create', array(
594 'contact_id' => $contact2,
595 'subject' => "Test case 2",
596 'case_type_id' => $this->caseTypeId,
597 ));
598 $case3 = $this->callAPISuccess('Case', 'create', array(
599 'contact_id' => array($contact1, $contact2),
600 'subject' => "Test case 3",
601 'case_type_id' => $this->caseTypeId,
602 ));
603
604 // Fetch case 1 and all cases with the same client. Chained get should return case 3.
605 $result = $this->callAPISuccessGetSingle('Case', array(
606 'id' => $case1['id'],
607 'return' => 'contact_id',
608 'api.Case.get' => array(
609 'contact_id' => array('IN' => "\$value.contact_id"),
610 'id' => array('!=' => "\$value.id"),
611 ),
612 ));
613 $this->assertEquals($case3['id'], $result['api.Case.get']['id']);
614
615 // Fetch case 3 and all cases with the same clients. Chained get should return case 1&2.
616 $result = $this->callAPISuccessGetSingle('Case', array(
617 'id' => $case3['id'],
618 'return' => array('contact_id'),
619 'api.Case.get' => array(
620 'return' => 'id',
621 'contact_id' => array('IN' => "\$value.contact_id"),
622 'id' => array('!=' => "\$value.id"),
623 ),
624 ));
625 $this->assertEquals(array($case1['id'], $case2['id']), array_keys(CRM_Utils_Array::rekey($result['api.Case.get']['values'], 'id')));
626 }
627
628 /**
629 * Test the ability to order by client using the join syntax.
630 *
631 * For multi-client cases, should order by the first client.
632 */
633 public function testCaseGetOrderByClient() {
634 $contact1 = $this->individualCreate(array('first_name' => 'Aa', 'last_name' => 'Zz'));
635 $contact2 = $this->individualCreate(array('first_name' => 'Bb', 'last_name' => 'Zz'));
636 $contact3 = $this->individualCreate(array('first_name' => 'Cc', 'last_name' => 'Xx'));
637
638 $case1 = $this->callAPISuccess('Case', 'create', array(
639 'contact_id' => $contact1,
640 'subject' => "Test case 1",
641 'case_type_id' => $this->caseTypeId,
642 ));
643 $case2 = $this->callAPISuccess('Case', 'create', array(
644 'contact_id' => $contact2,
645 'subject' => "Test case 2",
646 'case_type_id' => $this->caseTypeId,
647 ));
648 $case3 = $this->callAPISuccess('Case', 'create', array(
649 'contact_id' => array($contact3, $contact1),
650 'subject' => "Test case 3",
651 'case_type_id' => $this->caseTypeId,
652 ));
653
654 $result = $this->callAPISuccess('Case', 'get', array(
655 'contact_id' => array('IN' => array($contact1, $contact2, $contact3)),
656 'sequential' => 1,
657 'return' => 'id',
658 'options' => array('sort' => 'contact_id.first_name'),
659 ));
660 $this->assertEquals($case3['id'], $result['values'][2]['id']);
661 $this->assertEquals($case2['id'], $result['values'][1]['id']);
662 $this->assertEquals($case1['id'], $result['values'][0]['id']);
663
664 $result = $this->callAPISuccess('Case', 'get', array(
665 'contact_id' => array('IN' => array($contact1, $contact2, $contact3)),
666 'sequential' => 1,
667 'return' => 'id',
668 'options' => array('sort' => 'contact_id.last_name ASC, contact_id.first_name DESC'),
669 ));
670 $this->assertEquals($case1['id'], $result['values'][2]['id']);
671 $this->assertEquals($case2['id'], $result['values'][1]['id']);
672 $this->assertEquals($case3['id'], $result['values'][0]['id']);
673
674 $result = $this->callAPISuccess('Case', 'get', array(
675 'contact_id' => array('IN' => array($contact1, $contact2, $contact3)),
676 'sequential' => 1,
677 'return' => 'id',
678 'options' => array('sort' => 'contact_id.first_name DESC'),
679 ));
680 $this->assertEquals($case1['id'], $result['values'][2]['id']);
681 $this->assertEquals($case2['id'], $result['values'][1]['id']);
682 $this->assertEquals($case3['id'], $result['values'][0]['id']);
683
684 $result = $this->callAPISuccess('Case', 'get', array(
685 'contact_id' => array('IN' => array($contact1, $contact2, $contact3)),
686 'sequential' => 1,
687 'return' => 'id',
688 'options' => array('sort' => 'case_type_id, contact_id DESC, status_id'),
689 ));
690 $this->assertEquals($case1['id'], $result['values'][2]['id']);
691 $this->assertEquals($case2['id'], $result['values'][1]['id']);
692 $this->assertEquals($case3['id'], $result['values'][0]['id']);
693 $this->assertCount(3, $result['values']);
694 }
695
696 /**
697 * Test the ability to add a timeline to an existing case.
698 *
699 * See the case.addtimeline api.
700 *
701 * @throws \Exception
702 */
703 public function testCaseAddtimeline() {
704 $caseSpec = array(
705 'title' => 'Application with Definition',
706 'name' => 'Application_with_Definition',
707 'is_active' => 1,
708 'weight' => 4,
709 'definition' => array(
710 'activityTypes' => array(
711 array('name' => 'Follow up'),
712 ),
713 'activitySets' => array(
714 array(
715 'name' => 'set1',
716 'label' => 'Label 1',
717 'timeline' => 1,
718 'activityTypes' => array(
719 array('name' => 'Open Case', 'status' => 'Completed'),
720 ),
721 ),
722 array(
723 'name' => 'set2',
724 'label' => 'Label 2',
725 'timeline' => 1,
726 'activityTypes' => array(
727 array('name' => 'Follow up'),
728 ),
729 ),
730 ),
731 'caseRoles' => array(
732 array('name' => 'Homeless Services Coordinator', 'creator' => 1, 'manager' => 1),
733 ),
734 ),
735 );
736 $cid = $this->individualCreate();
737 $caseType = $this->callAPISuccess('CaseType', 'create', $caseSpec);
738 $case = $this->callAPISuccess('Case', 'create', array(
739 'case_type_id' => $caseType['id'],
740 'contact_id' => $cid,
741 'subject' => 'Test case with timeline',
742 ));
743 // Created case should only have 1 activity per the spec
744 $result = $this->callAPISuccessGetSingle('Activity', array('case_id' => $case['id'], 'return' => 'activity_type_id.name'));
745 $this->assertEquals('Open Case', $result['activity_type_id.name']);
746 // Add timeline
747 $timeline = civicrm_api('Case', 'addtimeline', array(
748 'case_id' => $case['id'],
749 'timeline' => 'set2',
750 'version' => 3,
751 ));
752 $result = $this->callAPISuccess('Activity', 'get', array(
753 'case_id' => $case['id'],
754 'return' => 'activity_type_id.name',
755 'sequential' => 1,
756 'options' => array('sort' => 'id'),
757 ));
758 $this->assertEquals(2, $result['count']);
759 $this->assertEquals('Follow up', $result['values'][1]['activity_type_id.name']);
760 }
761
762 /**
763 * Test the case merge function.
764 *
765 * 2 cases should be mergeable into 1
766 *
767 * @throws \Exception
768 */
769 public function testCaseMerge() {
770 $contact1 = $this->individualCreate(array(), 1);
771 $case1 = $this->callAPISuccess('Case', 'create', array(
772 'contact_id' => $contact1,
773 'subject' => "Test case 1",
774 'case_type_id' => $this->caseTypeId,
775 ));
776 $case2 = $this->callAPISuccess('Case', 'create', array(
777 'contact_id' => $contact1,
778 'subject' => "Test case 2",
779 'case_type_id' => $this->caseTypeId,
780 ));
781 $result = $this->callAPISuccess('Case', 'getcount', array('contact_id' => $contact1));
782 $this->assertEquals(2, $result);
783
784 $this->callAPISuccess('Case', 'merge', array('case_id_1' => $case1['id'], 'case_id_2' => $case2['id']));
785
786 $result = $this->callAPISuccess('Case', 'getsingle', array('id' => $case2['id']));
787 $this->assertEquals(1, $result['is_deleted']);
788 }
789
790 }