remove duplicate assignments
[civicrm-core.git] / tests / phpunit / api / v3 / SyntaxConformanceTest.php
CommitLineData
6a488035
TO
1<?php
2/*
3 +--------------------------------------------------------------------+
06a1bc01 4 | CiviCRM version 4.5 |
6a488035 5 +--------------------------------------------------------------------+
06a1bc01 6 | Copyright CiviCRM LLC (c) 2004-2014 |
6a488035
TO
7 +--------------------------------------------------------------------+
8 | This file is a part of CiviCRM. |
9 | |
10 | CiviCRM is free software; you can copy, modify, and distribute it |
11 | under the terms of the GNU Affero General Public License |
12 | Version 3, 19 November 2007 and the CiviCRM Licensing Exception. |
13 | |
14 | CiviCRM is distributed in the hope that it will be useful, but |
15 | WITHOUT ANY WARRANTY; without even the implied warranty of |
16 | MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. |
17 | See the GNU Affero General Public License for more details. |
18 | |
19 | You should have received a copy of the GNU Affero General Public |
20 | License and the CiviCRM Licensing Exception along |
21 | with this program; if not, contact CiviCRM LLC |
22 | at info[AT]civicrm[DOT]org. If you have questions about the |
23 | GNU Affero General Public License or the licensing of CiviCRM, |
24 | see the CiviCRM license FAQ at http://civicrm.org/licensing |
25 +--------------------------------------------------------------------+
26*/
27
28require_once 'CiviTest/CiviUnitTestCase.php';
29
30
31/**
32 * Test APIv3 civicrm_sytanc conformance* functions
33 *
34 * @package CiviCRM_APIv3
35 * @subpackage API_Core
36 */
37
8086a0bf 38class api_v3_SyntaxConformanceTest extends CiviUnitTestCase {
18eee50e 39 protected $_apiversion = 3;
6a488035 40
4a97890c
TO
41 /**
42 * @var array e.g. $this->deletes['CRM_Contact_DAO_Contact'][] = $contactID;
43 */
44 protected $deletableTestObjects;
45
afb0ff51 46 /** This test case doesn't require DB reset */
6a488035 47 public $DBResetRequired = FALSE;
6ead217b 48
8efea814
EM
49 protected $_entity;
50
6a488035
TO
51 /* they are two types of missing APIs:
52 - Those that are to be implemented
53 (in some future version when someone steps in -hint hint-). List the entities in toBeImplemented[ {$action} ]
54 Those that don't exist
55 and that will never exist (eg an obsoleted Entity
56 they need to be returned by the function toBeSkipped_{$action} (because it has to be a static method and therefore couldn't access a this->toBeSkipped)
18eee50e 57 */
58 function setUp() {
6a488035 59 parent::setUp();
6ead217b 60 $this->enableCiviCampaign();
0121533e 61 $this->toBeImplemented['get'] = array('Profile', 'CustomValue', 'Constant', 'CustomSearch', 'Extension', 'ReportTemplate', 'System', 'Setting');
6a488035
TO
62 $this->toBeImplemented['create'] = array('SurveyRespondant', 'OptionGroup', 'MailingRecipients', 'UFMatch', 'LocationType', 'CustomSearch', 'Extension', 'ReportTemplate', 'System');
63 $this->toBeImplemented['delete'] = array('MembershipPayment', 'OptionGroup', 'SurveyRespondant', 'UFJoin', 'UFMatch', 'Extension', 'LocationType', 'System');
64 $this->onlyIDNonZeroCount['get'] = array('ActivityType', 'Entity', 'Domain','Setting');
65 $this->deprecatedAPI = array('Location', 'ActivityType', 'SurveyRespondant');
4a97890c 66 $this->deletableTestObjects = array();
6a488035
TO
67 }
68
4a97890c
TO
69 function tearDown() {
70 foreach ($this->deletableTestObjects as $entityName => $entities) {
71 foreach ($entities as $entityID) {
72 CRM_Core_DAO::deleteTestObjects($entityName, array('id' => $entityID));
73 }
74 }
75 }
6a488035 76
6a488035 77 public static function entities($skip = NULL) {
dcf56200
TO
78 // To only test specific entities, call phpunit with SYNTAX_CONFORMANCE_ENTITIES="TheEntityName"
79 // or uncomment this line:
6a488035 80 //return array(array ('Tag'), array ('Activity') );
dcf56200
TO
81
82 if (getenv('SYNTAX_CONFORMANCE_ENTITIES')) {
83 $result = array();
84 foreach (explode(' ', getenv('SYNTAX_CONFORMANCE_ENTITIES')) as $entity) {
85 $result[] = array($entity);
86 }
87 return $result;
88 }
89
6a488035
TO
90 $tmp = civicrm_api('Entity', 'Get', array('version' => 3));
91 if (!is_array($skip)) {
92 $skip = array();
93 }
94 $tmp = array_diff($tmp['values'], $skip);
95 $entities = array();
96 foreach ($tmp as $e) {
97 $entities[] = array($e);
98 }
99 return $entities;
100 }
101
102 public static function entities_get() {
103 // all the entities, beside the ones flagged
97715495 104 return static::entities(static::toBeSkipped_get(TRUE));
6a488035
TO
105 }
106
107 public static function entities_create() {
97715495 108 return static::entities(static::toBeSkipped_create(TRUE));
6a488035
TO
109 }
110
111 public static function entities_updatesingle() {
97715495 112 return static::entities(static::toBeSkipped_updatesingle(TRUE));
6a488035
TO
113 }
114
b9af4758
E
115 public static function entities_getlimit() {
116 return static::entities(static::toBeSkipped_getlimit());
117 }
118
6a488035 119 public static function entities_delete() {
97715495 120 return static::entities(static::toBeSkipped_delete(TRUE));
6a488035
TO
121 }
122
2fc5f1e7
EM
123 public static function custom_data_entities_get() {
124 return static::custom_data_entities();
125 }
126
127 public static function custom_data_entities() {
128 $entities = CRM_Core_BAO_CustomQuery::$extendsMap;
129 $customDataEntities = array();
130 $invalidEntities = array('Individual', 'Organization', 'Household');
2f6264b4 131 $entitiesToFix = array('Case', 'Relationship');
2fc5f1e7 132 foreach ($entities as $entityName => $entity ) {
2f6264b4
EM
133 if(!in_array($entityName, $invalidEntities)
134 && !in_array($entityName, $entitiesToFix)) {
2fc5f1e7
EM
135 $customDataEntities[] = array($entityName );
136 }
137 }
138 return $customDataEntities;
139 }
140
6a488035
TO
141 public static function toBeSkipped_get($sequential = FALSE) {
142 $entitiesWithoutGet = array('MailingEventSubscribe', 'MailingEventConfirm', 'MailingEventResubscribe', 'MailingEventUnsubscribe', 'MailingGroup', 'Location');
143 if ($sequential === TRUE) {
144 return $entitiesWithoutGet;
145 }
146 $entities = array();
147 foreach ($entitiesWithoutGet as $e) {
148 $entities[] = array($e);
149 }
150 return $entities;
151 }
b7d29345 152
b14ce773 153 /**
154 * Mailing Contact Just doesn't support id. We have always insisted on finding a way to
155 * support id in API but in this case the underlying tables are crying out for a restructue
156 * & it just doesn't make sense
b7d29345
EM
157 *
158 * @param bool|\unknown_type $sequential
159 *
b14ce773 160 * @return multitype:string |multitype:multitype:string
161 */
162 public static function toBeSkipped_getByID($sequential = FALSE) {
163 return array('MailingContact');
164 }
6a488035
TO
165
166 public static function toBeSkipped_create($sequential = FALSE) {
167 $entitiesWithoutCreate = array('MailingGroup', 'Constant', 'Entity', 'Location', 'Profile', 'MailingRecipients');
168 if ($sequential === TRUE) {
169 return $entitiesWithoutCreate;
170 }
171 $entities = array();
172 foreach ($entitiesWithoutCreate as $e) {
173 $entities[] = array($e);
174 }
175 return $entities;
176 }
177
178 public static function toBeSkipped_delete($sequential = FALSE) {
510513d8 179 $entitiesWithout = array('MailingContact', 'MailingEventConfirm', 'MailingEventResubscribe', 'MailingEventSubscribe', 'MailingEventUnsubscribe', 'MailingGroup', 'MailingRecipients', 'Constant', 'Entity', 'Location', 'Domain', 'Profile', 'CustomValue', 'Setting');
6a488035
TO
180 if ($sequential === TRUE) {
181 return $entitiesWithout;
182 }
183 $entities = array();
184 foreach ($entitiesWithout as $e) {
185 $entities[] = array($e);
186 }
187 return $entities;
188 }
b7d29345 189
faacb3e4 190/**
191 * Generate list of entities to test for get by id functions
192 * @param boolean $sequential
193 * @return multitype:string |multitype:multitype:string
194 */
b07a3bf9 195 public static function toBeSkipped_automock($sequential = FALSE) {
dcf56200 196 $entitiesWithoutGet = array('MailingContact', 'EntityTag', 'Participant', 'ParticipantPayment', 'Setting', 'SurveyRespondant', 'MailingRecipients', 'CustomSearch', 'Extension', 'ReportTemplate', 'System');
b07a3bf9
TO
197 if ($sequential === TRUE) {
198 return $entitiesWithoutGet;
199 }
200 $entities = array();
201 foreach ($entitiesWithoutGet as $e) {
202 $entities[] = array($e);
203 }
204 return $entities;
205 }
206
207
b7d29345 208 /**
6a488035
TO
209 * At this stage exclude the ones that don't pass & add them as we can troubleshoot them
210 */
6a488035
TO
211 public static function toBeSkipped_updatesingle($sequential = FALSE) {
212 $entitiesWithout = array(
213 'Mailing',
214 'MailingGroup',
215 'MailingJob',
216 'Address',
217 'MailingEventUnsubscribe',
218 'MailingEventSubscribe',
219 'Constant',
220 'Entity',
221 'Location',
222 'Domain',
223 'Profile',
224 'CustomValue',
225 'SurveyRespondant',
226 'Tag',
227 'UFMatch',
228 'UFJoin',
229 'UFField',
230 'OptionValue',
231 'Relationship',
232 'RelationshipType',
233 'ParticipantStatusType',
234 'Note',
235 'OptionGroup',
236 'Membership',
237 'MembershipType',
238 'MembershipStatus',
239 'Group',
240 'GroupOrganization',
241 'GroupNesting',
242 'Job',
243 'File',
244 'EntityTag',
245 'CustomField',
246 'CustomGroup',
247 'Contribution',
248 'ContributionRecur',
249 'ActivityType',
250 'MailingEventConfirm',
251 'Case',
252 'Contact',
253 'ContactType',
254 'MailingEventResubscribe',
255 'UFGroup',
256 'Activity',
257 'Email',
258 'Event',
259 'GroupContact',
260 'MembershipPayment',
261 'Participant',
262 'ParticipantPayment',
263 'LineItem',
264 'PriceSet',
265 'PriceField',
266 'PriceFieldValue',
267 'PledgePayment',
268 'ContributionPage',
269 'Phone',
faacb3e4 270 'PaymentProcessor',
6a488035
TO
271 'MailSettings',
272 'Setting',
b14ce773 273 'MailingContact',
61ef23bd 274 'SystemLog' //skip this because it doesn't make sense to update logs
6a488035
TO
275 );
276 if ($sequential === TRUE) {
277 return $entitiesWithout;
278 }
279 $entities = array();
280 foreach ($entitiesWithout as $e) {
281 $entities[] = array(
282 $e,
283 );
284 }
285 return array('pledge');
286 return $entities;
287 }
288
b7d29345 289 /**
b9af4758 290 * At this stage exclude the ones that don't pass & add them as we can troubleshoot them
b7d29345 291 */
b9af4758
E
292 public static function toBeSkipped_getlimit() {
293 $entitiesWithout = array(
294 'Case',//case api has non-std mandatory fields one of (case_id, contact_id, activity_id, contact_id)
b9af4758
E
295 'EntityTag', // non-standard api - has inappropriate mandatory fields & doesn't implement limit
296 'Event', // failed 'check that a 5 limit returns 5' - probably is_template field is wrong or something, or could be limit doesn't work right
297 'Extension', // can't handle creating 25
b9af4758
E
298 'MailingGroup', // no get call on MailingGroup
299 'Note', // fails on 5 limit - probably a set up problem
b9af4758 300 'Setting', //a bit of a pseudoapi - keys by domain
b9af4758
E
301 );
302 return $entitiesWithout;
303 }
304
0f583c8f
EM
305 /**
306 * @param $entity
307 * @param $key
308 *
309 * @return array
310 */
6a488035
TO
311 public function getKnownUnworkablesUpdateSingle($entity, $key){
312 // can't update values are values for which updates don't result in the value being changed
313 $knownFailures = array(
03fe1a00
TO
314 'ActionSchedule' => array(
315 'cant_update' => array(
316 'group_id',
317 ),
318 ),
0f583c8f
EM
319 'ActivityContact' => array(
320 'cant_update' => array(
321 'activity_id', //we have an FK on activity_id + contact_id + record id so if we don't leave this one distinct we get an FK constraint error
322 ),
323 ),
6a488035
TO
324 'Address' => array(
325 'cant_update' => array(
326 'state_province_id', //issues with country id - need to ensure same country
327 'master_id',//creates relationship
328 ),
329 'cant_return' => array(
330 )
331 ),
6ead217b
E
332 'Batch' => array(
333 'cant_update' => array(
334 'entity_table', // believe this field is defined in error
335 ),
336 'cant_return' => array(
337 'entity_table',
338 )
339 ),
6a488035
TO
340 'Pledge' => array(
341 'cant_update' => array(
342 'pledge_original_installment_amount',
343 'installments',
344 'original_installment_amount',
345 'next_pay_date',
346 'amount' // can't be changed through API
347 ),
348 'break_return' => array(// if these are passed in they are retrieved from the wrong table
349 'honor_contact_id',
350 'cancel_date',
351 'contribution_page_id',
352 'financial_account_id',
353 'financial_type_id',
354 'currency'
355 ),
356 'cant_return' => array(// can't be retrieved from api
357 'honor_type_id', //due to uniquename missing
358 'end_date',
359 'modified_date',
360 'acknowledge_date',
361 'start_date',
362 'frequency_day',
363 'currency',
364 'max_reminders',
365 'initial_reminder_day',
366 'additional_reminder_day',
367 'frequency_unit',
368 'pledge_contribution_page_id',
369 'pledge_status_id',
370 'pledge_campaign_id',
371 )
372 ),
373 'PaymentProcessorType' => array(
374 'cant_update' => array(
375 'billing_mode',
376 ),
377 'break_return' => array(
378 ),
379 'cant_return' => array(
380 ),
381 ),
382 );
383 if(empty($knownFailures[$entity]) || empty($knownFailures[$entity][$key])){
384 return array();
385 }
386 return $knownFailures[$entity][$key];
387 }
388
389 /** testing the _get **/
390
391 /**
392 * @dataProvider toBeSkipped_get
393 entities that don't need a get action
394 */
395 public function testNotImplemented_get($Entity) {
396 $result = civicrm_api($Entity, 'Get', array('version' => 3));
397 $this->assertEquals(1, $result['is_error'], 'In line ' . __LINE__);
311873a0
TO
398 // $this->assertContains("API ($Entity, Get) does not exist", $result['error_message']);
399 $this->assertRegExp('/API (.*) does not exist/', $result['error_message']);
6a488035
TO
400 }
401
402 /**
403 * @dataProvider entities
404 * @expectedException PHPUnit_Framework_Error
405 */
406 public function testWithoutParam_get($Entity) {
407 // should get php complaining that a param is missing
408 $result = civicrm_api($Entity, 'Get');
409 }
410
411 /**
412 * @dataProvider entities
413 */
414 public function testGetFields($Entity) {
415 if (in_array($Entity, $this->deprecatedAPI) || $Entity == 'Entity' || $Entity == 'CustomValue' || $Entity == 'MailingGroup') {
416 return;
417 }
418
419 $result = civicrm_api($Entity, 'getfields', array('version' => 3));
420 $this->assertTrue(is_array($result['values']), "$Entity ::get fields doesn't return values array in line " . __LINE__);
421 foreach ($result['values'] as $key => $value) {
422 $this->assertTrue(is_array($value), $Entity . "::" . $key . " is not an array in line " . __LINE__);
423 }
424 }
425
426 /**
427 * @dataProvider entities_get
428 */
429 public function testEmptyParam_get($Entity) {
430
431 if (in_array($Entity, $this->toBeImplemented['get'])) {
432 // $this->markTestIncomplete("civicrm_api3_{$Entity}_get to be implemented");
433 return;
434 }
435 $result = civicrm_api($Entity, 'Get', array());
436 $this->assertEquals(1, $result['is_error'], 'In line ' . __LINE__);
437 $this->assertContains("Mandatory key(s) missing from params array", $result['error_message']);
438 }
439 /**
440 * @dataProvider entities_get
441 */
442 public function testEmptyParam_getString($Entity) {
443
444 if (in_array($Entity, $this->toBeImplemented['get'])) {
445 // $this->markTestIncomplete("civicrm_api3_{$Entity}_get to be implemented");
446 return;
447 }
d0e1eff2 448 $result = $this->callAPIFailure($Entity, 'Get', 'string');
6a488035
TO
449 $this->assertEquals(2000, $result['error_code']);
450 $this->assertEquals('Input variable `params` is not an array', $result['error_message']);
451 }
452 /**
453 * @dataProvider entities_get
454 * @Xdepends testEmptyParam_get // no need to test the simple if the empty doesn't work/is skipped. doesn't seem to work
455 */
456 public function testSimple_get($Entity) {
457 // $this->markTestSkipped("test gives core error on test server (but not on our locals). Skip until we can get server to pass");
6a488035
TO
458 if (in_array($Entity, $this->toBeImplemented['get'])) {
459 return;
460 }
461 $result = civicrm_api($Entity, 'Get', array('version' => 3));
462 // @TODO: list the get that have mandatory params
463 if ($result['is_error']) {
464 $this->assertContains("Mandatory key(s) missing from params array", $result['error_message']);
465 // either id or contact_id or entity_id is one of the field missing
466 $this->assertContains("id", $result['error_message']);
467 }
468 else {
469 $this->assertEquals(3, $result['version']);
470 $this->assertArrayHasKey('count', $result);
471 $this->assertArrayHasKey('values', $result);
472 }
473 }
474
2fc5f1e7
EM
475 /**
476 * @dataProvider custom_data_entities_get
477 */
478 public function testCustomDataGet($entityName) {
479 $this->createLoggedInUser();// so subsidiary activities are created
480 $ids = $this->entityCustomGroupWithSingleFieldCreate(__FUNCTION__, $entityName . 'Test.php');
481 $customFieldName = 'custom_' . $ids['custom_field_id'];
482 $objects = $this->getMockableBAOObjects($entityName, 1);
483 $params = array('id' => $objects[0]->id, 'custom_' . $ids['custom_field_id'] => "custom string");
484 $result = $this->callAPISuccess($entityName, 'create', $params);
485
486 $getParams = array('id' => $result['id'], 'return' => array($customFieldName));
487 $check = $this->callAPISuccess($entityName, 'get', $getParams);
488 $this->assertEquals("custom string", $check['values'][$check['id']][$customFieldName]);
489
490 $this->customFieldDelete($ids['custom_field_id']);
491 $this->customGroupDelete($ids['custom_group_id']);
492 $this->callAPISuccess($entityName, 'delete', array('id' => $result['id']));
493 }
494
6a488035
TO
495 /**
496 * @dataProvider entities_get
497 */
498 public function testAcceptsOnlyID_get($Entity) {
499 // big random number. fun fact: if you multiply it by pi^e, the result is another random number, but bigger ;)
500 $nonExistantID = 30867307034;
b14ce773 501 if (in_array($Entity, $this->toBeImplemented['get'])
502 || in_array($Entity, $this->toBeSkipped_getByID())
503 ) {
6a488035
TO
504 return;
505 }
506
507 // FIXME
508 // the below function returns different values and hence an early return
509 // we'll fix this once beta1 is released
510 // return;
511
c679daca 512 $result = civicrm_api($Entity, 'Get', array('version' => 3, 'id' => $nonExistantID));
6a488035
TO
513
514 if ($result['is_error']) {
515 // just to get a clearer message in the log
516 $this->assertEquals("only id should be enough", $result['error_message']);
517 }
518 if (!in_array($Entity, $this->onlyIDNonZeroCount['get'])) {
519 $this->assertEquals(0, $result['count']);
520 }
521 }
522
523 /**
4a97890c
TO
524 * Create two entities and make sure we can fetch them individually by ID
525 *
526 * @dataProvider entities_get
527 *
528 * limitations include the problem with avoiding loops when creating test objects -
529 * hence FKs only set by createTestObject when required. e.g parent_id on campaign is not being followed through
530 * Currency - only seems to support US
531 */
532 public function testByID_get($entityName) {
b07a3bf9 533 if (in_array($entityName, self::toBeSkipped_automock(TRUE))) {
4a97890c
TO
534 // $this->markTestIncomplete("civicrm_api3_{$Entity}_create to be implemented");
535 return;
536 }
537
18eee50e 538 $baos = $this->getMockableBAOObjects($entityName);
539 list($baoObj1, $baoObj2) = $baos;
4a97890c
TO
540
541 // fetch first by ID
6ead217b 542 $result = $this->callAPISuccess($entityName, 'get', array(
4a97890c
TO
543 'id' => $baoObj1->id,
544 ));
6ead217b 545
4a97890c
TO
546 $this->assertTrue(!empty($result['values'][$baoObj1->id]), 'Should find first object by id');
547 $this->assertEquals($baoObj1->id, $result['values'][$baoObj1->id]['id'], 'Should find id on first object');
548 $this->assertEquals(1, count($result['values']));
549
550 // fetch second by ID
6ead217b 551 $result = $this->callAPISuccess($entityName, 'get', array(
4a97890c
TO
552 'id' => $baoObj2->id,
553 ));
4a97890c
TO
554 $this->assertTrue(!empty($result['values'][$baoObj2->id]), 'Should find second object by id');
555 $this->assertEquals($baoObj2->id, $result['values'][$baoObj2->id]['id'], 'Should find id on second object');
556 $this->assertEquals(1, count($result['values']));
557 }
558
b9af4758
E
559 /**
560 * Ensure that the "get" operation accepts limiting the #result records.
561 *
562 * TODO Consider making a separate entity list ("entities_getlimit")
563 * For the moment, the "entities_updatesingle" list should give a good
564 * sense for which entities support createTestObject
565 *
566 * @dataProvider entities_getlimit
8efea814
EM
567 *
568 * @param $entityName
569 *
570 * @internal param string $entity
b9af4758
E
571 */
572 function testLimit($entityName) {
573 $cases = array(); // each case is array(0 => $inputtedApiOptions, 1 => $expectedResultCount)
574 $cases[] = array(
575 array('options' => array('limit' => NULL)),
ebddc2d9
EM
576 30,
577 'check that a NULL limit returns unlimited',
b9af4758
E
578 );
579 $cases[] = array(
580 array('options' => array('limit' => FALSE)),
ebddc2d9
EM
581 30,
582 'check that a FALSE limit returns unlimited',
b9af4758
E
583 );
584 $cases[] = array(
585 array('options' => array('limit' => 0)),
ebddc2d9
EM
586 30,
587 'check that a 0 limit returns unlimited',
b9af4758
E
588 );
589 $cases[] = array(
590 array('options' => array('limit' => 5)),
591 5,
592 'check that a 5 limit returns 5',
593 );
594 $cases[] = array(
595 array(),
596 25,
597 'check that no limit returns 25',
598 );
599
600 $baoString = _civicrm_api3_get_DAO($entityName);
601 if (empty($baoString)) {
602 $this->markTestIncomplete("Entity [$entityName] cannot be mocked - no known DAO");
603 return;
604 }
605
606 // make 30 test items -- 30 > 25 (the default limit)
4038f8ec 607 $ids = array();
b9af4758 608 for ($i = 0; $i < 30; $i++) {
8d5544c5 609 $baoObj = CRM_Core_DAO::createTestObject($baoString, array('currency' => 'USD'));
4038f8ec 610 $ids[] = $baoObj->id;
b9af4758
E
611 }
612
613 // each case is array(0 => $inputtedApiOptions, 1 => $expectedResultCount)
614 foreach ($cases as $case) {
ebddc2d9 615 $this->checkLimitAgainstExpected($entityName, $case[0], $case[1], $case[2]);
a85a667f
EM
616
617 //non preferred / legacy syntax
618 if(isset($case[0]['options']['limit'])) {
ebddc2d9
EM
619 $this->checkLimitAgainstExpected($entityName, array('rowCount' => $case[0]['options']['limit']), $case[1], $case[2]);
620 $this->checkLimitAgainstExpected($entityName, array('option_limit' => $case[0]['options']['limit']), $case[1], $case[2]);
621 $this->checkLimitAgainstExpected($entityName, array('option.limit' => $case[0]['options']['limit']), $case[1], $case[2]);
a85a667f 622 }
b9af4758 623 }
4038f8ec
TO
624 foreach ($ids as $id) {
625 CRM_Core_DAO::deleteTestObjects($baoString, array('id' => $id));
626 }
8d5544c5 627 $baoObj->free();
b9af4758
E
628 }
629
ebddc2d9
EM
630 /**
631 * Check that get fetches an appropriate number of results
632 *
633 * @param string $entityName Name of entity to test
634 * @param unknown $params
635 * @param unknown $limit
636 * @param unknown $message
637 */
638 function checkLimitAgainstExpected($entityName, $params, $limit, $message) {
639 $result = $this->callAPISuccess($entityName, 'get', $params);
640 if($limit == 30) {
641 $this->assertGreaterThanOrEqual($limit, $result['count'], $message);
642 $this->assertGreaterThanOrEqual($limit, $result['count'], $message);
643 }
644 else {
645 $this->assertEquals($limit, $result['count'], $message);
646 $this->assertEquals($limit, count($result['values']), $message);
647 }
648 }
afb0ff51
TO
649 /**
650 * Create two entities and make sure we can fetch them individually by ID (e.g. using "contact_id=>2"
651 * or "group_id=>4")
652 *
653 * @dataProvider entities_get
654 *
655 * limitations include the problem with avoiding loops when creating test objects -
656 * hence FKs only set by createTestObject when required. e.g parent_id on campaign is not being followed through
657 * Currency - only seems to support US
658 */
659 public function testByIDAlias_get($entityName) {
c4de8b59 660 if (in_array($entityName, self::toBeSkipped_automock(TRUE))) {
afb0ff51
TO
661 // $this->markTestIncomplete("civicrm_api3_{$Entity}_create to be implemented");
662 return;
663 }
664
665 $baoString = _civicrm_api3_get_DAO($entityName);
666 if (empty($baoString)) {
667 $this->markTestIncomplete("Entity [$entityName] cannot be mocked - no known DAO");
668 return;
669 }
670
c4de8b59
TO
671 $idFieldName = _civicrm_api_get_entity_name_from_camel($entityName) . '_id';
672
afb0ff51
TO
673 // create entities
674 $baoObj1 = CRM_Core_DAO::createTestObject($baoString, array('currency' => 'USD'));
675 $this->assertTrue(is_integer($baoObj1->id), 'check first id');
676 $this->deletableTestObjects[$baoString][] = $baoObj1->id;
677 $baoObj2 = CRM_Core_DAO::createTestObject($baoString, array('currency' => 'USD'));
678 $this->assertTrue(is_integer($baoObj2->id), 'check second id');
679 $this->deletableTestObjects[$baoString][] = $baoObj2->id;
680
681 // fetch first by ID
682 $result = civicrm_api($entityName, 'get', array(
683 'version' => 3,
c4de8b59 684 $idFieldName => $baoObj1->id,
afb0ff51
TO
685 ));
686 $this->assertAPISuccess($result);
687 $this->assertTrue(!empty($result['values'][$baoObj1->id]), 'Should find first object by id');
688 $this->assertEquals($baoObj1->id, $result['values'][$baoObj1->id]['id'], 'Should find id on first object');
689 $this->assertEquals(1, count($result['values']));
690
691 // fetch second by ID
692 $result = civicrm_api($entityName, 'get', array(
693 'version' => 3,
c4de8b59 694 $idFieldName => $baoObj2->id,
afb0ff51
TO
695 ));
696 $this->assertAPISuccess($result);
697 $this->assertTrue(!empty($result['values'][$baoObj2->id]), 'Should find second object by id');
698 $this->assertEquals($baoObj2->id, $result['values'][$baoObj2->id]['id'], 'Should find id on second object');
699 $this->assertEquals(1, count($result['values']));
700 }
701
702 /**
6a488035
TO
703 * @dataProvider entities_get
704 */
705 public function testNonExistantID_get($Entity) {
706 // cf testAcceptsOnlyID_get
707 $nonExistantID = 30867307034;
708 if (in_array($Entity, $this->toBeImplemented['get'])) {
709 return;
710 }
711
712 $result = civicrm_api($Entity, 'Get', array('version' => 3, 'id' => $nonExistantID));
713
714 // redundant with testAcceptsOnlyID_get
715 if ($result['is_error']) {
716 return;
717 }
718
719
720 $this->assertArrayHasKey('version', $result);
721 $this->assertEquals(3, $result['version']);
722 if (!in_array($Entity, $this->onlyIDNonZeroCount['get'])) {
723 $this->assertEquals(0, $result['count']);
724 }
725 }
726
727 /** testing the _create **/
728
729 /**
730 * @dataProvider toBeSkipped_create
731 entities that don't need a create action
732 */
733 public function testNotImplemented_create($Entity) {
734 $result = civicrm_api($Entity, 'Create', array('version' => 3));
735 $this->assertEquals(1, $result['is_error'], 'In line ' . __LINE__);
311873a0 736 $this->assertContains(strtolower("API ($Entity, Create) does not exist"), strtolower($result['error_message']));
6a488035
TO
737 }
738
739 /**
740 * @dataProvider entities
741 * @expectedException PHPUnit_Framework_Error
742 */
743 public function testWithoutParam_create($Entity) {
744 // should create php complaining that a param is missing
745 $result = civicrm_api($Entity, 'Create');
746 }
747
748 /**
749 * @dataProvider entities_create
750 */
751 public function testEmptyParam_create($Entity) {
f27f2724 752 $this->markTestIncomplete("fixing this test to test the api functions fails on numberous tests
753 which will either create a completely blank entity (batch, participant status) or
18eee50e 754 have a damn good crack at it (e.g mailing job). Marking this as incomplete beats false success");
f27f2724 755 //
18eee50e 756 return;
6a488035
TO
757 if (in_array($Entity, $this->toBeImplemented['create'])) {
758 // $this->markTestIncomplete("civicrm_api3_{$Entity}_create to be implemented");
759 return;
760 }
18eee50e 761 $result = $this->callAPIFailure($Entity, 'Create', array());
6a488035
TO
762 $this->assertContains("Mandatory key(s) missing from params array", $result['error_message']);
763 }
764
18eee50e 765 /**
766 * @dataProvider entities_create
767 *
768 * Check that create doesn't work with an invalid
769 */
770 public function testInvalidID_create($Entity) {
771 // turn test off for noew
6ead217b 772 $this->markTestIncomplete("Entity [ $Entity ] cannot be mocked - no known DAO");
18eee50e 773 return;
774 if (in_array($Entity, $this->toBeImplemented['create'])) {
775 // $this->markTestIncomplete("civicrm_api3_{$Entity}_create to be implemented");
776 return;
777 }
778 $result = $this->callAPIFailure($Entity, 'Create', array('id' => 999));
779 }
780
6a488035
TO
781 /**
782 * @dataProvider entities
783 */
784 public function testCreateWrongTypeParamTag_create() {
785 $result = civicrm_api("Tag", 'Create', 'this is not a string');
786 $this->assertEquals(1, $result['is_error'], 'In line ' . __LINE__);
787 $this->assertEquals("Input variable `params` is not an array", $result['error_message']);
788 }
789
790 /**
791 * @dataProvider entities_updatesingle
792 *
793 * limitations include the problem with avoiding loops when creating test objects -
794 * hence FKs only set by createTestObject when required. e.g parent_id on campaign is not being followed through
795 * Currency - only seems to support US
796 */
797 public function testCreateSingleValueAlter($entityName) {
798 if (in_array($entityName, $this->toBeImplemented['create'])) {
799 // $this->markTestIncomplete("civicrm_api3_{$Entity}_create to be implemented");
800 return;
801 }
802
803 $baoString = _civicrm_api3_get_DAO($entityName);
804 $this->assertNotEmpty($baoString, $entityName);
805 $this->assertNotEmpty($entityName, $entityName);
39bc176e 806 $fieldsGet = $fields = $this->callAPISuccess($entityName, 'getfields', array('action' => 'get'));
6a488035 807 if($entityName != 'Pledge'){
6ead217b 808 $fields = $this->callAPISuccess($entityName, 'getfields', array('action' => 'create'));
6a488035
TO
809 }
810 $fields = $fields['values'];
39bc176e 811 $return = array_keys($fieldsGet['values']);
6a488035
TO
812 $valuesNotToReturn = $this->getKnownUnworkablesUpdateSingle($entityName, 'break_return');
813 // these can't be requested as return values
1fd111c8 814 $entityValuesThatDoNotWork = array_merge(
6a488035
TO
815 $this->getKnownUnworkablesUpdateSingle($entityName, 'cant_update'),
816 $this->getKnownUnworkablesUpdateSingle($entityName, 'cant_return'),
817 $valuesNotToReturn
818 );
819
820 $return = array_diff($return,$valuesNotToReturn);
821 $baoObj = new CRM_Core_DAO();
822 $baoObj->createTestObject($baoString, array('currency' => 'USD'), 2, 0);
39bc176e
EM
823
824 $getEntities = $this->callAPISuccess($entityName, 'get', array(
6ead217b
E
825 'sequential' => 1,
826 'return' => $return,
827 'options' => array(
828 'sort' => 'id DESC',
829 'limit' => 2,
830 ),
831 ));
6a488035 832 // lets use first rather than assume only one exists
39bc176e
EM
833 $entity = $getEntities['values'][0];
834 $entity2 = $getEntities['values'][1];
835 $this->deletableTestObjects[$baoString][] = $entity['id'];
836 $this->deletableTestObjects[$baoString][] = $entity2['id'];
6a488035
TO
837 foreach ($fields as $field => $specs) {
838 $fieldName = $field;
839 if (!empty($specs['uniquename'])) {
840 $fieldName = $specs['uniquename'];
841 }
842 if ($field == 'currency' || $field == 'id' || $field == strtolower($entityName) . '_id'
1fd111c8 843 || in_array($field,$entityValuesThatDoNotWork)) {
6a488035
TO
844 //@todo id & entity_id are correct but we should fix currency & frequency_day
845 continue;
846 }
0ce6d639 847 $this->assertArrayHasKey('type', $specs, "the _spec function for $entityName field $field does not specify the type");
6a488035
TO
848 switch ($specs['type']) {
849 case CRM_Utils_Type::T_DATE:
850 case CRM_Utils_Type::T_TIMESTAMP:
851 $entity[$fieldName] = '2012-05-20';
852 break;
853 //case CRM_Utils_Type::T_DATETIME:
854
855 case 12:
856 $entity[$fieldName] = '2012-05-20 03:05:20';
857 break;
858
859 case CRM_Utils_Type::T_STRING:
860 case CRM_Utils_Type::T_BLOB:
861 case CRM_Utils_Type::T_MEDIUMBLOB:
862 case CRM_Utils_Type::T_TEXT:
863 case CRM_Utils_Type::T_LONGTEXT:
864 case CRM_Utils_Type::T_EMAIL:
865 $entity[$fieldName] = substr('New String',0, CRM_Utils_Array::Value('maxlength',$specs,100));
866 break;
867
868 case CRM_Utils_Type::T_INT:
869 // probably created with a 1
870 $entity[$fieldName] = '6';
a7488080 871 if (!empty($specs['FKClassName'])) {
6a488035
TO
872 if($specs['FKClassName'] == $baoString){
873 $entity[$fieldName] = (string) $entity2['id'];
874 }
875 else{
6ead217b
E
876 $uniqueName = CRM_Utils_Array::value('uniqueName', $specs);
877 $entity[$fieldName] = (string) empty($entity2[$field]) ? CRM_Utils_Array::value($uniqueName, $entity2) : $entity2[$field];
6a488035
TO
878 //todo - there isn't always something set here - & our checking on unset values is limited
879 if (empty($entity[$field])) {
880 unset($entity[$field]);
881 }
882 }
883 }
884 break;
885
6a488035
TO
886 case CRM_Utils_Type::T_BOOLEAN:
887 // probably created with a 1
888 $entity[$fieldName] = '0';
889 break;
890
891 case CRM_Utils_Type::T_FLOAT:
892 case CRM_Utils_Type::T_MONEY:
edd31a24 893 $entity[$field] = '22.75';
6a488035
TO
894 break;
895
896 case CRM_Utils_Type::T_URL:
897 $entity[$field] = 'warm.beer.com';
898 }
4b5ff63c 899 if (!empty($specs['pseudoconstant'])) {
6ead217b 900 $options = $this->callAPISuccess($entityName, 'getoptions', array('context' => 'create', 'field' => $field));
3d3ef918 901 if (empty($options['values'])) {
edd31a24
EM
902 //eg. pdf_format id doesn't ship with any
903 if(isset($specs['pseudoconstant']['optionGroupName'])) {
904 $optionGroupID = $this->callAPISuccess('option_group', 'getvalue', array('name' => 'pdf_format', 'return' => 'id'));
905 $optionValue = $this->callAPISuccess('option_value', 'create', array('option_group_id' => $optionGroupID, 'label' => 'new option value'));
906 $options['values'][] = $optionValue['id'];
907 }
3d3ef918
CW
908 }
909 $entity[$field] = array_rand($options['values']);
6a488035
TO
910 }
911 $updateParams = array(
6a488035 912 'id' => $entity['id'],
6ead217b 913 $field => isset($entity[$field]) ? $entity[$field] : NULL,
6a488035
TO
914 );
915
f27f2724 916 $update = $this->callAPISuccess($entityName, 'create', $updateParams);
6a488035
TO
917 $checkParams = array(
918 'id' => $entity['id'],
6a488035
TO
919 'sequential' => 1,
920 'return' => $return,
921 'options' => array(
922 'sort' => 'id DESC',
923 'limit' => 2,
924 ),
925 );
926
f27f2724 927 $checkEntity = $this->callAPISuccess($entityName, 'getsingle', $checkParams);
b7e3da74 928 $this->assertAPIArrayComparison($entity, $checkEntity, array(), "checking if $fieldName was correctly updated\n" . print_r(array('update-params' => $updateParams, 'update-result' => $update, 'getsingle-params' => $checkParams, 'getsingle-result' => $checkEntity, 'expected entity' => $entity), TRUE));
6a488035 929 }
6a488035
TO
930 $baoObj->free();
931 }
932
933 /** testing the _getFields **/
934
935 /** testing the _delete **/
936
937 /**
938 * @dataProvider toBeSkipped_delete
939 entities that don't need a delete action
940 */
941 public function testNotImplemented_delete($Entity) {
942 $nonExistantID = 151416349;
943 $result = civicrm_api($Entity, 'Delete', array('version' => 3, 'id' => $nonExistantID));
944 $this->assertEquals(1, $result['is_error'], 'In line ' . __LINE__);
311873a0 945 $this->assertContains(strtolower("API ($Entity, Delete) does not exist"), strtolower($result['error_message']));
6a488035
TO
946 }
947
948 /**
949 * @dataProvider entities
950 * @expectedException PHPUnit_Framework_Error
951 */
952 public function testWithoutParam_delete($Entity) {
953 // should delete php complaining that a param is missing
954 $result = civicrm_api($Entity, 'Delete');
955 }
956
957 /**
958 * @dataProvider entities_delete
959 */
960 public function testEmptyParam_delete($Entity) {
961 if (in_array($Entity, $this->toBeImplemented['delete'])) {
962 // $this->markTestIncomplete("civicrm_api3_{$Entity}_delete to be implemented");
963 return;
964 }
965 $result = civicrm_api($Entity, 'Delete', array());
966 $this->assertEquals(1, $result['is_error'], 'In line ' . __LINE__);
967 $this->assertContains("Mandatory key(s) missing from params array", $result['error_message']);
968 }
18eee50e 969 /**
970 * @dataProvider entities_delete
971 */
972 public function testInvalidID_delete($Entity) {
6ead217b
E
973 // turn test off for now
974 $this->markTestIncomplete("Entity [ $Entity ] cannot be mocked - no known DAO");
18eee50e 975 return;
976 if (in_array($Entity, $this->toBeImplemented['delete'])) {
977 // $this->markTestIncomplete("civicrm_api3_{$Entity}_delete to be implemented");
978 return;
979 }
980 $result = $this->callAPIFailure($Entity, 'Delete', array('id' => 999));
981 }
6a488035
TO
982 /**
983 * @dataProvider entities
984 */
985 public function testDeleteWrongTypeParamTag_delete() {
986 $result = civicrm_api("Tag", 'Delete', 'this is not a string');
987 $this->assertEquals(1, $result['is_error'], 'In line ' . __LINE__);
988 $this->assertEquals("Input variable `params` is not an array", $result['error_message']);
989 }
990
18eee50e 991 /**
992 * Create two entities and make sure delete action only deletes one!
993 *
994 * @dataProvider entities_delete
995 *
996 * limitations include the problem with avoiding loops when creating test objects -
997 * hence FKs only set by createTestObject when required. e.g parent_id on campaign is not being followed through
998 * Currency - only seems to support US
999 */
1000 public function testByID_delete($entityName) {
1001 // turn test off for noew
1002 $this->markTestIncomplete("Entity [$entityName] cannot be mocked - no known DAO");
1003 return;
1004
1005 if (in_array($entityName, self::toBeSkipped_automock(TRUE))) {
1006 // $this->markTestIncomplete("civicrm_api3_{$Entity}_create to be implemented");
1007 return;
1008 }
1009 $startCount = $this->callAPISuccess($entityName, 'getcount', array());
1010 $createcount = 2;
1011 $baos = $this->getMockableBAOObjects($entityName, $createcount);
1012 list($baoObj1, $baoObj2) = $baos;
1013
1014 // make sure exactly 2 exist
1015 $result = $this->callAPISuccess($entityName, 'getcount', array(),
1016 $createcount + $startCount
1017 );
1018
1019 $this->callAPISuccess($entityName, 'delete', array('id' => $baoObj2->id));
1020 //make sure 1 less exists now
1021 $result = $this->callAPISuccess($entityName, 'getcount', array(),
1022 ($createcount + $startCount) -1
1023 );
1024
1025 //make sure id #1 exists
1026 $result = $this->callAPISuccess($entityName, 'getcount', array('id' => $baoObj1->id),
1027 1
1028 );
1029 //make sure id #2 desn't exist
1030 $result = $this->callAPISuccess($entityName, 'getcount', array('id' => $baoObj2->id),
1031 0
1032 );
1033 }
1034
8efea814
EM
1035 /**
1036 * @param $entityName
1037 * @param int $count
1038 *
1039 * @internal param $entityName
1040 *
1041 * @return array
1042 */
1043 private function getMockableBAOObjects($entityName, $count = 2) {
18eee50e 1044 $baoString = _civicrm_api3_get_DAO($entityName);
1045 if (empty($baoString)) {
1046 $this->markTestIncomplete("Entity [$entityName] cannot be mocked - no known DAO");
1047 return;
1048 }
1049 $baos = array();
6ead217b 1050 $i = 0;
18eee50e 1051 while($i < $count) {
1052 // create entities
1053 $baoObj = CRM_Core_DAO::createTestObject($baoString, array('currency' => 'USD'));
1054 $this->assertTrue(is_integer($baoObj->id), 'check first id');
1055 $this->deletableTestObjects[$baoString][] = $baoObj->id;
1056 $baos[] = $baoObj;
1057 $i ++;
1058 }
1059 return $baos;
1060 }
1061
1062
6a488035
TO
1063 /**
1064 * Verify that HTML metacharacters provided as inputs appear consistently
1065 * as outputs.
1066 *
1067 * At time of writing, the encoding scheme requires (for example) that an
1068 * event title be partially-HTML-escaped before writing to DB. To provide
1069 * consistency, the API must perform extra encoding and decoding on some
1070 * fields.
1071 *
1072 * In this example, the event 'title' is subject to encoding, but the
1073 * event 'description' is not.
1074 */
1075 public function testEncodeDecodeConsistency() {
1076 // Create example
1077 $createResult = civicrm_api('Event', 'Create', array(
1078 'version' => 3,
1079 'title' => 'CiviCRM <> TheRest',
1080 'description' => 'TheRest <> CiviCRM',
1081 'event_type_id' => 1,
1082 'is_public' => 1,
1083 'start_date' => 20081021,
1084 ));
1085 $this->assertAPISuccess($createResult);
1086 $eventId = $createResult['id'];
1087 $this->assertEquals('CiviCRM <> TheRest', $createResult['values'][$eventId]['title']);
1088 $this->assertEquals('TheRest <> CiviCRM', $createResult['values'][$eventId]['description']);
1089
1090 // Verify "get" handles decoding in result value
1091 $getByIdResult = civicrm_api('Event', 'Get', array(
1092 'version' => 3,
1093 'id' => $eventId,
1094 ));
1095 $this->assertAPISuccess($getByIdResult);
1096 $this->assertEquals('CiviCRM <> TheRest', $getByIdResult['values'][$eventId]['title']);
1097 $this->assertEquals('TheRest <> CiviCRM', $getByIdResult['values'][$eventId]['description']);
1098
1099 // Verify "get" handles encoding in search value
1100 $getByTitleResult = civicrm_api('Event', 'Get', array(
1101 'version' => 3,
1102 'title' => 'CiviCRM <> TheRest',
1103 ));
1104 $this->assertAPISuccess($getByTitleResult);
1105 $this->assertEquals('CiviCRM <> TheRest', $getByTitleResult['values'][$eventId]['title']);
1106 $this->assertEquals('TheRest <> CiviCRM', $getByTitleResult['values'][$eventId]['description']);
1107
1108 // Verify that "getSingle" handles decoding
6ead217b 1109 $getSingleResult = $this->callAPISuccess('Event', 'GetSingle', array(
6a488035
TO
1110 'id' => $eventId,
1111 ));
1112
6a488035
TO
1113 $this->assertEquals('CiviCRM <> TheRest', $getSingleResult['title']);
1114 $this->assertEquals('TheRest <> CiviCRM', $getSingleResult['description']);
1115
1116 // Verify that chaining handles decoding
6ead217b 1117 $chainResult = $this->callAPISuccess('Event', 'Get', array(
6a488035
TO
1118 'id' => $eventId,
1119 'api.event.get' => array(
1120 ),
1121 ));
1122 $this->assertEquals('CiviCRM <> TheRest', $chainResult['values'][$eventId]['title']);
1123 $this->assertEquals('TheRest <> CiviCRM', $chainResult['values'][$eventId]['description']);
1124 $this->assertEquals('CiviCRM <> TheRest', $chainResult['values'][$eventId]['api.event.get']['values'][0]['title']);
1125 $this->assertEquals('TheRest <> CiviCRM', $chainResult['values'][$eventId]['api.event.get']['values'][0]['description']);
1126
1127 // Verify that "setvalue" handles encoding for updates
1128 $setValueTitleResult = civicrm_api('Event', 'setvalue', array(
1129 'version' => 3,
1130 'id' => $eventId,
1131 'field' => 'title',
1132 'value' => 'setValueTitle: CiviCRM <> TheRest',
1133 ));
1134 $this->assertAPISuccess($setValueTitleResult);
1135 $this->assertEquals('setValueTitle: CiviCRM <> TheRest', $setValueTitleResult['values']['title']);
1136 $setValueDescriptionResult = civicrm_api('Event', 'setvalue', array(
1137 'version' => 3,
1138 'id' => $eventId,
1139 'field' => 'description',
1140 'value' => 'setValueDescription: TheRest <> CiviCRM',
1141 ));
bc2bc079 1142 //$this->assertTrue((bool)$setValueDescriptionResult['is_error']); // not supported by setValue
1143 $this->assertEquals('setValueDescription: TheRest <> CiviCRM', $setValueDescriptionResult['values']['description']);
6a488035
TO
1144}
1145
1146 /**
1147 * Verify that write operations (create/update) use partial HTML-encoding
1148 *
1149 * In this example, the event 'title' is subject to encoding, but the
1150 * event 'description' is not.
1151 */
1152 public function testEncodeWrite() {
1153 // Create example
1154 $createResult = civicrm_api('Event', 'Create', array(
1155 'version' => 3,
1156 'title' => 'createNew: CiviCRM <> TheRest',
1157 'description' => 'createNew: TheRest <> CiviCRM',
1158 'event_type_id' => 1,
1159 'is_public' => 1,
1160 'start_date' => 20081021,
1161 ));
1162 $this->assertAPISuccess($createResult);
1163 $eventId = $createResult['id'];
1164 $this->assertDBQuery('createNew: CiviCRM &lt;&gt; TheRest', 'SELECT title FROM civicrm_event WHERE id = %1', array(
1165 1 => array($eventId, 'Integer')
1166 ));
1167 $this->assertDBQuery('createNew: TheRest <> CiviCRM', 'SELECT description FROM civicrm_event WHERE id = %1', array(
1168 1 => array($eventId, 'Integer')
1169 ));
1170
1171 // Verify that "create" handles encoding for updates
1172 $createWithIdResult = civicrm_api('Event', 'Create', array(
1173 'version' => 3,
1174 'id' => $eventId,
1175 'title' => 'createWithId: CiviCRM <> TheRest',
1176 'description' => 'createWithId: TheRest <> CiviCRM',
1177 ));
1178 $this->assertAPISuccess($createWithIdResult);
1179 $this->assertDBQuery('createWithId: CiviCRM &lt;&gt; TheRest', 'SELECT title FROM civicrm_event WHERE id = %1', array(
1180 1 => array($eventId, 'Integer')
1181 ));
1182 $this->assertDBQuery('createWithId: TheRest <> CiviCRM', 'SELECT description FROM civicrm_event WHERE id = %1', array(
1183 1 => array($eventId, 'Integer')
1184 ));
1185
1186 // Verify that "setvalue" handles encoding for updates
1187 $setValueTitleResult = civicrm_api('Event', 'setvalue', array(
1188 'version' => 3,
1189 'id' => $eventId,
1190 'field' => 'title',
1191 'value' => 'setValueTitle: CiviCRM <> TheRest',
1192 ));
1193 $this->assertAPISuccess($setValueTitleResult);
1194 $this->assertDBQuery('setValueTitle: CiviCRM &lt;&gt; TheRest', 'SELECT title FROM civicrm_event WHERE id = %1', array(
1195 1 => array($eventId, 'Integer')
1196 ));
1197 $setValueDescriptionResult = civicrm_api('Event', 'setvalue', array(
1198 'version' => 3,
1199 'id' => $eventId,
1200 'field' => 'description',
1201 'value' => 'setValueDescription: TheRest <> CiviCRM',
1202 ));
bc2bc079 1203 //$this->assertTrue((bool)$setValueDescriptionResult['is_error']); // not supported by setValue
1204 $this->assertAPISuccess($setValueDescriptionResult);
1205 $this->assertDBQuery('setValueDescription: TheRest <> CiviCRM', 'SELECT description FROM civicrm_event WHERE id = %1', array(
1206 1 => array($eventId, 'Integer')
1207 ));
6a488035
TO
1208 }
1209
1210}