564efa0b02477b189bf1f83f4f0743b2adcbe39f
[tine20] / tests / tine20 / Tinebase / Frontend / JsonTest.php
1 <?php
2 /**
3  * Tine 2.0
4  * 
5  * @package     Tinebase
6  * @subpackage  Json
7  * @license     http://www.gnu.org/licenses/agpl.html AGPL Version 3
8  * @author      Philipp Schüle <p.schuele@metaways.de>
9  * @copyright   Copyright (c) 2007-2013 Metaways Infosystems GmbH (http://www.metaways.de)
10  *
11  */
12
13 /**
14  * Test helper
15  */
16 require_once dirname(dirname(dirname(__FILE__))) . DIRECTORY_SEPARATOR . 'TestHelper.php';
17
18 /**
19  * Test class for Tinebase_Group
20  */
21 class Tinebase_Frontend_JsonTest extends PHPUnit_Framework_TestCase
22 {
23     /**
24      * unit under test (UIT)
25      * @var Tinebase_Frontend_Json
26      */
27     protected $_instance;
28
29     /**
30      * @var array test objects
31      */
32     protected $_objects = array();
33     
34     /**
35      * Runs the test methods of this class.
36      */
37     public static function main()
38     {
39         $suite  = new PHPUnit_Framework_TestSuite('Tinebase_Frontend_JsonTest');
40         PHPUnit_TextUI_TestRunner::run($suite);
41     }
42     
43     /**
44      * set up tests
45      *
46      */
47     public function setUp()
48     {
49         Tinebase_TransactionManager::getInstance()->startTransaction(Tinebase_Core::getDb());
50         
51         $this->_instance = new Tinebase_Frontend_Json();
52         
53         $this->_objects['record'] = array(
54             'id'        => 1,
55             'model'     => 'Addressbook_Model_Contact',
56             'backend'    => 'Sql',
57         );
58
59         $this->_objects['group'] = new Tinebase_Model_Group(array(
60             'name'            => 'phpunit test group',
61             'description'    => 'phpunit test group'
62         ));
63
64         $this->_objects['role'] = new Tinebase_Model_Role(array(
65             'name'            => 'phpunit test role',
66             'description'    => 'phpunit test role'
67         ));
68
69         $this->_objects['note'] = new Tinebase_Model_Note(array(
70             'note_type_id'      => 1,
71             'note'              => 'phpunit test note',
72             'record_model'      => $this->_objects['record']['model'],
73             'record_backend'    => $this->_objects['record']['backend'],
74             'record_id'         => $this->_objects['record']['id']
75         ));
76     }
77     
78     /**
79      * tear down
80      */
81     public function tearDown()
82     {
83         Tinebase_TransactionManager::getInstance()->rollBack();
84         
85         // reset tz in core
86         Tinebase_Core::set(Tinebase_Core::USERTIMEZONE, Tinebase_Core::getPreference()->getValue(Tinebase_Preference::TIMEZONE));
87     }
88     
89     /**
90      * try to add a note type
91      *
92      */
93     public function testSearchNotes()
94     {
95         Tinebase_Notes::getInstance()->addNote($this->_objects['note']);
96
97         $filter = array(array(
98             'field' => 'query',
99             'operator' => 'contains',
100             'value' => 'phpunit'
101         ));
102         $paging = array();
103         
104         $notes = $this->_instance->searchNotes($filter, $paging);
105         
106         $this->assertGreaterThan(0, $notes['totalcount']);
107         $found = false;
108         foreach ($notes['results'] as $note) {
109             if ($this->_objects['note']->note === $note['note']) {
110                 $found = true;
111             }
112         }
113         $this->assertTrue($found, 'note not found in notes: ' . print_r($notes['results'], true));
114         
115         // delete note
116         Tinebase_Notes::getInstance()->deleteNotesOfRecord(
117             $this->_objects['record']['model'], 
118             $this->_objects['record']['backend'], 
119             $this->_objects['record']['id']
120         );
121     }
122     
123     /**
124      * try to delete role and then search
125      */
126     public function testSearchRoles()
127     {
128         $role = Tinebase_Acl_Roles::getInstance()->createRole($this->_objects['role']);
129         
130         $filter = array(array(
131             'field'     => 'query',
132             'operator'     => 'contains',
133             'value'     => 'phpunit test role'
134         ));
135         $paging = array(
136             'start'    => 0,
137             'limit'    => 1
138         );
139         
140         $roles = $this->_instance->searchRoles($filter, $paging);
141         
142         $this->assertGreaterThan(0, $roles['totalcount']);
143         $this->assertEquals($this->_objects['role']->name, $roles['results'][0]['name']);
144         
145         // delete role
146         Tinebase_Acl_Roles::getInstance()->deleteRoles($role->id);
147     }
148     
149     /**
150      * test getCountryList
151      *
152      */
153     public function testGetCountryList()
154     {
155         $list = $this->_instance->getCountryList();
156         $this->assertTrue(count($list['results']) > 200);
157     }
158     
159     /**
160      * test get translations
161      *
162      */
163     public function testGetAvailableTranslations()
164     {
165         $list = $this->_instance->getAvailableTranslations();
166         $this->assertTrue(count($list['results']) > 3);
167     }
168     
169     /**
170      * tests locale fallback
171      */
172     public function testSetLocaleFallback()
173     {
174         // de_LU -> de
175         $this->_instance->setLocale('de_LU', FALSE, FALSE);
176         $this->assertEquals('de', (string)Zend_Registry::get('locale'), 'Fallback to generic german did not succseed');
177         
178         $this->_instance->setLocale('zh', FALSE, FALSE);
179         $this->assertEquals('zh_CN', (string)Zend_Registry::get('locale'), 'Fallback to simplified chinese did not succseed');
180         
181         $this->_instance->setLocale('foo_bar', FALSE, FALSE);
182         $this->assertEquals('en', (string)Zend_Registry::get('locale'), 'Exception fallback to english did not succseed');
183     }
184     
185     /**
186      * test set locale and save it in db
187      */
188     public function testSetLocaleAsPreference()
189     {
190         $oldPreference = Tinebase_Core::getPreference()->{Tinebase_Preference::LOCALE};
191         
192         $locale = 'de';
193         $result = $this->_instance->setLocale($locale, TRUE, FALSE);
194         
195         // get config setting from db
196         $preference = Tinebase_Core::getPreference()->{Tinebase_Preference::LOCALE};
197         $this->assertEquals($locale, $preference, "Didn't get right locale preference.");
198         
199         // restore old setting
200         Tinebase_Core::getPreference()->{Tinebase_Preference::LOCALE} = $oldPreference;
201     }
202
203     /**
204      * test set timezone and save it in db
205      */
206     public function testSetTimezoneAsPreference()
207     {
208         $oldPreference = Tinebase_Core::getPreference()->{Tinebase_Preference::TIMEZONE};
209         
210         $timezone = 'America/Vancouver';
211         $result = $this->_instance->setTimezone($timezone, true);
212         
213         // check json result
214         $this->assertEquals($timezone, $result);
215         
216         // get config setting from db
217         $preference = Tinebase_Core::getPreference()->{Tinebase_Preference::TIMEZONE};
218         $this->assertEquals($timezone, $preference, "Didn't get right timezone preference.");
219         
220         // restore old settings
221         Tinebase_Core::set('userTimeZone', $oldPreference);
222         Tinebase_Core::getPreference()->{Tinebase_Preference::TIMEZONE} = $oldPreference;
223     }
224     
225     /**
226      * get notes types
227      */
228     public function testGetNotesTypes()
229     {
230         $noteTypes = $this->_instance->getNoteTypes();
231         $this->assertTrue($noteTypes['totalcount'] >= 5);
232     }
233     
234     /**
235      * search preferences by application
236      *
237      */
238     public function testSearchPreferences()
239     {
240         // search prefs
241         $result = $this->_instance->searchPreferencesForApplication('Tinebase', $this->_getPreferenceFilter());
242         
243         // check results
244         $this->assertTrue(isset($result['results']));
245         $this->assertGreaterThan(2, $result['totalcount']);
246         
247         //check locale/timezones options
248         foreach ($result['results'] as $pref) {
249             switch($pref['name']) {
250                 case Tinebase_Preference::LOCALE:
251                     $this->assertGreaterThan(10, count($pref['options']));
252                     break;
253                 case Tinebase_Preference::TIMEZONE:
254                     $this->assertGreaterThan(100, count($pref['options']));
255                     break;
256             }
257             // check label and description
258             $this->assertTrue(isset($pref['label']) && !empty($pref['label']));
259             $this->assertTrue(isset($pref['description']) && !empty($pref['description']));
260         }
261     }
262
263     /**
264      * search preferences by application felamimail
265      *
266      */
267     public function testSearchFelamimailPreferences()
268     {
269         // search prefs
270         $result = $this->_instance->searchPreferencesForApplication('Felamimail', '');
271         
272         // check results
273         $this->assertTrue(isset($result['results']));
274         $this->assertGreaterThan(0, $result['totalcount']);
275     }
276
277     /**
278      * search preferences by application
279      *
280      */
281     public function testSearchPreferencesWithOptions()
282     {
283         // add new default pref
284         $pref = $this->_getPreferenceWithOptions();
285         $pref = Tinebase_Core::getPreference()->create($pref);
286         
287         // search prefs
288         $results = $this->_instance->searchPreferencesForApplication('Tinebase', $this->_getPreferenceFilter());
289         
290         // check results
291         $this->assertTrue(isset($results['results']));
292         $this->assertGreaterThan(3, $results['totalcount']);
293         
294         foreach ($results['results'] as $result) {
295             if ($result['name'] == 'defaultapp') {
296                 $this->assertEquals(Tinebase_Model_Preference::DEFAULT_VALUE, $result['value']);
297                 $this->assertTrue(is_array($result['options']));
298                 $this->assertEquals(3, count($result['options']));
299                 $this->assertContains('option1', $result['options'][1][1]);
300             } else if ($result['name'] == Tinebase_Preference::TIMEZONE) {
301                 $this->assertTrue(is_array($result['options'][0]), 'options should be arrays');
302             }
303         }
304         
305         Tinebase_Core::getPreference()->delete($pref);
306     }
307     
308     /**
309      * search preferences of another user
310      *
311      * @todo add check for the case that searching user has no admin rights
312      */
313     public function testSearchPreferencesOfOtherUsers()
314     {
315         // add new default pref
316         $pref = $this->_getPreferenceWithOptions();
317         $pref->account_id   = '2';
318         $pref->account_type = Tinebase_Acl_Rights::ACCOUNT_TYPE_USER;
319         $pref = Tinebase_Core::getPreference()->create($pref);
320         
321         // search prefs
322         $results = $this->_instance->searchPreferencesForApplication('Tinebase', $this->_getPreferenceFilter(TRUE, FALSE, '2'));
323         
324         // check results
325         $this->assertTrue(isset($results['results']));
326         $this->assertEquals(1, $results['totalcount']);
327     }
328     
329     /**
330      * save preferences for user
331      *
332      * @todo add test for saving of other users prefs and acl check
333      */
334     public function testSavePreferences()
335     {
336         $prefData = $this->_getUserPreferenceData();
337         $this->_instance->savePreferences($prefData, false);
338
339         // search saved prefs
340         $results = $this->_instance->searchPreferencesForApplication('Tinebase', $this->_getPreferenceFilter(FALSE));
341         
342         // check results
343         $this->assertTrue(isset($results['results']));
344         $this->assertGreaterThan(2, $results['totalcount']);
345         
346         $savedPrefData = array();
347         foreach ($results['results'] as $result) {
348             if ($result['name'] == 'timezone') {
349                 $savedPrefData['Tinebase'][$result['name']] = array('value' => $result['value']);
350             
351                 $this->assertTrue(is_array($result['options']), 'options missing');
352                 $this->assertGreaterThan(100, count($result['options']));
353             }
354         }
355         $this->assertEquals($prefData, $savedPrefData);
356     }
357     
358     /**
359      * tests if 'use default' appears in options and if it can be selected and if it changes if default changes
360      */
361     public function testGetSetChangeDefaultPref()
362     {
363         $locale = $this->_getLocalePref();
364         foreach ($locale['options'] as $option) {
365             if ($option[0] == Tinebase_Model_Preference::DEFAULT_VALUE) {
366                 $result = $option;
367                 $defaultString = $option[1];
368             }
369         }
370         
371         $this->assertTrue(isset($defaultString));
372         $this->assertContains('(auto)', $defaultString);
373
374         // set user pref to en first then to 'use default'
375         Tinebase_Core::getPreference()->{Tinebase_Preference::LOCALE} = 'en';
376         Tinebase_Core::getPreference()->{Tinebase_Preference::LOCALE} = Tinebase_Model_Preference::DEFAULT_VALUE;
377         $this->assertEquals('auto', Tinebase_Core::getPreference()->{Tinebase_Preference::LOCALE});
378         
379         // set new default locale
380         $prefData['Tinebase']['default' . $locale['id']] = array('value' => 'de', 'type' => 'default', 'name' => Tinebase_Preference::LOCALE);
381         $this->_instance->savePreferences($prefData, true);
382         
383         $updatedLocale = $this->_getLocalePref();
384         foreach ($updatedLocale['options'] as $option) {
385             if ($option[0] == Tinebase_Model_Preference::DEFAULT_VALUE) {
386                 $result = $option;
387                 $defaultString = $option[1];
388             }
389         }
390         $this->assertEquals(count($locale['options']), count($updatedLocale['options']), 'option count has to be equal');
391         $this->assertContains('(Deutsch)', $defaultString);
392         $this->assertEquals('de', Tinebase_Core::getPreference()->{Tinebase_Preference::LOCALE});
393     }
394     
395     /**
396      * get locale pref
397      */
398     protected function _getLocalePref()
399     {
400         $results = $this->_instance->searchPreferencesForApplication('Tinebase', $this->_getPreferenceFilter());
401         foreach ($results['results'] as $result) {
402             if ($result['name'] == Tinebase_Preference::LOCALE) {
403                 $locale = $result;
404             }
405         }
406         
407         $this->assertTrue(isset($locale));
408         
409         return $locale;
410     }
411
412     /**
413      * get admin prefs
414      */
415     public function testGetAdminPreferences()
416     {
417         $this->testGetSetChangeDefaultPref();
418         
419         // set new default locale
420         $locale = $this->_getLocalePref();
421         $prefData['Tinebase'][$locale['id']] = array('value' => 'de', 'type' => 'default', 'name' => Tinebase_Preference::LOCALE);
422         $this->_instance->savePreferences($prefData, true);
423         
424         // check as admin
425         $results = $this->_instance->searchPreferencesForApplication('Tinebase', $this->_getPreferenceFilter(FALSE, TRUE));
426         foreach ($results['results'] as $pref) {
427             if ($pref['name'] !== Tinebase_Preference::LOCALE) {
428                 $this->assertEquals(Tinebase_Model_Preference::DEFAULT_VALUE, $pref['value']);
429             } else {
430                 $this->assertEquals(Tinebase_Model_Preference::TYPE_ADMIN, $pref['type']);
431                 $this->assertEquals('de', $pref['value'], print_r($pref, TRUE));
432             }
433         }
434
435         // check as user
436         $locale = $this->_getLocalePref();
437         $this->assertEquals(Tinebase_Model_Preference::TYPE_ADMIN, $locale['type'], 'pref should be of type admin: ' . print_r($locale, TRUE));
438         $this->assertEquals(Tinebase_Model_Preference::DEFAULT_VALUE, $locale['value'], 'pref should be default value: ' . print_r($locale, TRUE));
439     }
440     
441     /**
442      * save admin prefs
443      *
444      */
445     public function testSaveAdminPreferences()
446     {
447         // add new default pref
448         $pref = $this->_getPreferenceWithOptions();
449         $pref = Tinebase_Core::getPreference()->create($pref);
450         
451         $prefData = array();
452         $prefData['Tinebase'][$pref->getId()] = array('value' => 'test', 'type' => 'forced');
453         $this->_instance->savePreferences($prefData, true);
454
455         // search saved prefs
456         $results = $this->_instance->searchPreferencesForApplication('Tinebase', $this->_getPreferenceFilter(TRUE));
457         
458         // check results
459         $this->assertTrue(isset($results['results']));
460         $this->assertEquals(1, $results['totalcount']);
461         $this->assertEquals($prefData['Tinebase'][$pref->getId()]['value'], $results['results'][0]['value']);
462         $this->assertEquals($prefData['Tinebase'][$pref->getId()]['type'], $results['results'][0]['type']);
463     }
464     
465     /**
466      * save state and load it with registry data
467      */
468     public function testSaveAndGetState()
469     {
470         $testData = array(
471             'bla'   => 'blubb',
472             'zzing' => 'zzang'
473         );
474         
475         foreach ($testData as $key => $value) {
476             Tinebase_State::getInstance()->setState($key, $value);
477         }
478         
479         $stateInfo = Tinebase_State::getInstance()->loadStateInfo();
480         
481         $this->assertEquals($testData, $stateInfo);
482     }
483     
484     /**
485      * test get all registry data
486      * 
487      * @return void
488      * 
489      * @see 0007934: change pw button active even if it is not allowed
490      * @see 0008310: apps should be sorted the other way round in menu
491      */
492     public function testGetAllRegistryData()
493     {
494         $registryData = $this->_instance->getAllRegistryData();
495         $currentUser = Tinebase_Core::getUser();
496         
497         $this->assertEquals($currentUser->toArray(), $registryData['Tinebase']['currentAccount']);
498         $this->assertEquals(
499             Addressbook_Controller_Contact::getInstance()->getContactByUserId($currentUser->getId())->toArray(), 
500             $registryData['Tinebase']['userContact']
501         );
502         $this->assertEquals(TRUE, $registryData['Tinebase']['config']['changepw']['value'], 'changepw should be TRUE');
503         
504         Tinebase_Config::getInstance()->set('changepw', 0);
505         $registryData = $this->_instance->getAllRegistryData();
506         $changepwValue = $registryData['Tinebase']['config']['changepw']['value'];
507         $this->assertEquals(FALSE, $changepwValue, 'changepw should be (bool) false');
508         $this->assertTrue(is_bool($changepwValue), 'changepw should be (bool) false: ' . var_export($changepwValue, TRUE));
509         
510         $userApps = $registryData['Tinebase']['userApplications'];
511         $this->assertEquals('Admin', $userApps[0]['name'], 'first app should be Admin: ' . print_r($userApps, TRUE));
512     }
513     
514     /**
515      * testGetUserProfile
516      */
517     public function testGetUserProfile()
518     {
519         $profile = $this->_instance->getUserProfile(Tinebase_Core::getUser()->getId());
520
521         $this->assertTrue(is_array($profile));
522         $this->assertTrue((isset($profile['userProfile']) || array_key_exists('userProfile', $profile)));
523         $this->assertTrue(is_array($profile['userProfile']));
524         $this->assertTrue((isset($profile['readableFields']) || array_key_exists('readableFields', $profile)));
525         $this->assertTrue(is_array($profile['readableFields']));
526         $this->assertTrue((isset($profile['updateableFields']) || array_key_exists('updateableFields', $profile)));
527         $this->assertTrue(is_array($profile['updateableFields']));
528         
529         // try to get user profile of different user
530         $this->setExpectedException('Tinebase_Exception_AccessDenied');
531         
532         $sclever = array_value('sclever',Zend_Registry::get('personas'));
533         $this->_instance->getUserProfile($sclever->getId());
534     }
535     
536     /**
537      * testGetUserProfileConfig
538      */
539     public function testGetUserProfileConfig()
540     {
541         $config = $this->_instance->getUserProfileConfig();
542         
543         $this->assertTrue(is_array($config));
544         $this->assertTrue((isset($config['possibleFields']) || array_key_exists('possibleFields', $config)));
545         $this->assertTrue(is_array($config['possibleFields']));
546         $this->assertTrue((isset($config['readableFields']) || array_key_exists('readableFields', $config)));
547         $this->assertTrue(is_array($config['readableFields']));
548         $this->assertTrue((isset($config['updateableFields']) || array_key_exists('updateableFields', $config)));
549         $this->assertTrue(is_array($config['updateableFields']));
550     }
551     
552     /**
553      * testSetUserProfileConfig
554      */
555     public function testSetUserProfileConfig()
556     {
557         $config = $this->_instance->getUserProfileConfig();
558         
559         $idx = array_search('n_prefix', $config['readableFields']);
560         if ($idx !== false) {
561             unset ($config['readableFields'][$idx]);
562         }
563         
564         $idx = array_search('tel_home', $config['updateableFields']);
565         if ($idx !== false) {
566             unset ($config['updateableFields'][$idx]);
567         }
568         
569         $this->_instance->setUserProfileConfig($config);
570     }
571     
572     /**
573      * testupdateUserProfile
574      */
575     public function testUpdateUserProfile()
576     {
577         $profile = $this->_instance->getUserProfile(Tinebase_Core::getUser()->getId());
578         $profileData = $profile['userProfile'];
579         
580         $this->assertFalse(array_search('n_prefix', $profileData));
581         
582         $profileData['tel_home'] = 'mustnotchange';
583         $profileData['email_home'] = 'email@userprofile.set';
584         
585         $this->_instance->updateUserProfile($profileData);
586         
587         $updatedProfile = $this->_instance->getUserProfile(Tinebase_Core::getUser()->getId());
588         $updatedProfileData = $updatedProfile['userProfile'];
589         $this->assertNotEquals('mustnotchange', $updatedProfileData['tel_home']);
590         $this->assertEquals('email@userprofile.set', $updatedProfileData['email_home']);
591     }
592     
593     /**
594      * testGetSaveApplicationConfig
595      */
596     public function testGetSaveApplicationConfig()
597     {
598         $config = $this->_instance->getConfig('Admin');
599         $this->assertGreaterThan(0, count($config));
600         
601         $data = array(
602             'id'        => 'Admin',
603             'settings'  => Admin_Controller::getInstance()->getConfigSettings(),
604         );
605         
606         $newConfig = $this->_instance->saveConfig($data);
607         
608         $this->assertEquals($config, $newConfig);
609     }
610     
611     /******************** protected helper funcs ************************/
612     
613     /**
614      * get preference filter
615      *
616      * @param bool $_savedPrefs
617      * @return array
618      */
619     protected function _getPreferenceFilter($_savedPrefs = FALSE, $_adminPrefs = FALSE, $_userId = NULL)
620     {
621         if ($_userId === NULL) {
622             $_userId = Tinebase_Core::getUser()->getId();
623         }
624         
625         $result = array(
626             array(
627                 'field' => 'account', 
628                 'operator' => 'equals', 
629                 'value' => array(
630                     'accountId'     => ($_adminPrefs) ? 0 : $_userId,
631                     'accountType'   => ($_adminPrefs) 
632                         ? Tinebase_Acl_Rights::ACCOUNT_TYPE_ANYONE 
633                         : Tinebase_Acl_Rights::ACCOUNT_TYPE_USER
634                 )
635             )
636         );
637
638         if ($_savedPrefs) {
639             $result[] = array(
640                 'field' => 'name', 
641                 'operator' => 'contains', 
642                 'value' => 'defaultapp'
643             );
644         }
645         
646         return $result;
647     }
648
649     /**
650      * get preference data for testSavePreferences()
651      *
652      * @return array
653      */
654     protected function _getUserPreferenceData()
655     {
656         return array(
657             'Tinebase' => array(
658                 'timezone' => array('value' => 'Europe/Amsterdam'),
659             )
660         );
661     }
662     
663     /**
664      * get preference with options
665      *
666      * @return Tinebase_Model_Preference
667      */
668     protected function _getPreferenceWithOptions()
669     {
670         return new Tinebase_Model_Preference(array(
671             'application_id'    => Tinebase_Application::getInstance()->getApplicationByName('Tinebase')->getId(),
672             'name'              => 'defaultapp',
673             'value'             => 'value1',
674             'account_id'        => '0',
675             'account_type'      => Tinebase_Acl_Rights::ACCOUNT_TYPE_ANYONE,
676             'type'              => Tinebase_Model_Preference::TYPE_ADMIN,
677             'options'           => '<?xml version="1.0" encoding="UTF-8"?>
678                 <options>
679                     <option>
680                         <label>option1</label>
681                         <value>value1</value>
682                     </option>
683                     <option>
684                         <label>option2</label>
685                         <value>value2</value>
686                     </option>
687                 </options>'
688         ));
689     }
690 }