source: trunk/zpush/backend/expresso/providers/calendarProvider.php @ 8022

Revision 8022, 51.6 KB checked in by cristiano, 11 years ago (diff)

Ticket #3393 - Desconsiderar sincronização de agendas compartilhadas no Z-Push

Line 
1<?php
2
3require_once __DIR__ . '/../../../lib/default/diffbackend/diffbackend.php';
4require_once EXPRESSO_PATH . '/prototype/api/controller.php';
5require_once EXPRESSO_PATH . '/prototype/api/config.php';
6require_once EXPRESSO_PATH . '/prototype/modules/calendar/constants.php';
7
8use prototype\api\Config as Config;
9
10class ExpressoCalendarProvider extends BackendDiff
11{
12
13    var $_uidnumber;
14
15    function __construct()
16    {
17
18    }
19
20    /**
21     * Returns a list (array) of folders, each entry being an associative array
22     * with the same entries as StatFolder(). This method should return stable information; ie
23     * if nothing has changed, the items in the array must be exactly the same. The order of
24     * the items within the array is not important though.
25     *
26     * @access protected
27     * @return array/boolean        false if the list could not be retrieved
28     */
29    public function GetFolderList()
30    {
31        $return = array();
32        $criteria = CALENDAR_SYNC_SIGNED_CALENDARS ? array( 'filter' => array( 'AND' , array( '=' , 'type' , '0' ) , array( '=' , 'user' , $this->_uidnumber ))) : array( 'filter' => array ( 'AND'  ,array( '=' , 'isOwner' , '1' ),array( '=' , 'type' , '0' ) , array( '=' , 'user' , $this->_uidnumber )));
33        $sigs = Controller::find(array('concept' => 'calendarSignature'), array( 'id','calendar' ), $criteria);
34
35        if(Request::GetDeviceType()  == 'iPhone')
36        {
37            foreach($sigs as $sig)
38            {
39                $calendar =  Controller::read( array( 'concept' => 'calendar' , 'id' => $sig['calendar'] ));
40                $tmpSig = array();
41                $tmpSig["id"] = 'calendar'.$sig['id'];
42                $tmpSig["parent"] = 0;
43                $tmpSig["mod"] = $calendar['name'];
44                $return[] = $tmpSig;
45            }
46        }
47        else
48        {
49            $defaultCalendar = Controller::find(array('concept' => 'modulePreference'), array('value','id') , array('filter' => array( 'and' , array('=' , 'name' , 'defaultCalendar') , array('=' , 'module' , 'expressoCalendar') , array('=' , 'user' , $this->_uidnumber )  )) );
50
51            if(isset($defaultCalendar[0])) //Prioriza agenda default de importação pois o android so sincroniza a primeira agenda.
52            {
53                foreach($sigs as $i => $sig)
54                {
55                    if($sig['calendar'] == $defaultCalendar[0]['value'])
56                    {
57                        $calendar =  Controller::read( array( 'concept' => 'calendar' , 'id' => $sig['calendar'] ));
58                        $tmpSig = array();
59                        $tmpSig["id"] = 'calendar'.$sig['id'];
60                        $tmpSig["parent"] = 0;
61                        $tmpSig["mod"] = $calendar['name'];
62                        $return[] = $tmpSig;
63                    }
64                }
65            }
66            else
67            {
68                $sig = $sigs[0];
69                $calendar =  Controller::read( array( 'concept' => 'calendar' , 'id' => $sig['calendar'] ));
70                $tmpSig = array();
71                $tmpSig["id"] = 'calendar'.$sig['id'];
72                $tmpSig["parent"] = 0;
73                $tmpSig["mod"] = $calendar['name'];
74                $return[] = $tmpSig;
75
76            }
77        }
78
79        return $return;
80    }
81
82    /**
83     * Returns an actual SyncFolder object with all the properties set. Folders
84     * are pretty simple, having only a type, a name, a parent and a server ID.
85     *
86     * @param string        $id           id of the folder
87     *
88     * @access public
89     * @return object   SyncFolder with information
90     */
91    public function GetFolder($id)
92    {
93        $idNumber = (int)str_replace('calendar' , '' , $id);
94
95        $calendarSignature =  Controller::read( array( 'concept' => 'calendarSignature' , 'id' => $idNumber ));
96        $calendar =  Controller::read( array( 'concept' => 'calendar' , 'id' => $calendarSignature['calendar'] ));
97
98        if(is_array($calendarSignature) && count($calendarSignature) > 0 )
99        {
100            $folder = new SyncFolder();
101            $folder->serverid = $id;
102            $folder->parentid = "0";
103            $folder->displayname = $calendar['name'];
104            $folder->type = SYNC_FOLDER_TYPE_APPOINTMENT;
105            return $folder;
106        }
107
108        return false;
109    }
110
111    /**
112     * Returns folder stats. An associative array with properties is expected.
113     *
114     * @param string        $id             id of the folder
115     *
116     * @access public
117     * @return array
118     *          Associative array(
119     *              string  "id"            The server ID that will be used to identify the folder. It must be unique, and not too long
120     *                                      How long exactly is not known, but try keeping it under 20 chars or so. It must be a string.
121     *              string  "parent"        The server ID of the parent of the folder. Same restrictions as 'id' apply.
122     *              long    "mod"           This is the modification signature. It is any arbitrary string which is constant as long as
123     *                                      the folder has not changed. In practice this means that 'mod' can be equal to the folder name
124     *                                      as this is the only thing that ever changes in folders. (the type is normally constant)
125     *          )
126     */
127    public function StatFolder($id)
128    {
129        $return = array();
130        $idNumber = (int)str_replace('calendar' , '' , $id);
131        $calendarSignature =  Controller::read( array( 'concept' => 'calendarSignature' , 'id' => $idNumber ));
132        $calendar =  Controller::read( array( 'concept' => 'calendar' , 'id' => $calendarSignature['calendar'] ));
133
134        $return["id"] = $id;
135        $return["parent"] = 0;
136        $return["mod"] = $calendar['name'];
137
138        return $return;
139    }
140
141    /**
142     * Creates or modifies a folder
143     *
144     * @param string        $folderid       id of the parent folder
145     * @param string        $oldid          if empty -> new folder created, else folder is to be renamed
146     * @param string        $displayname    new folder name (to be created, or to be renamed to)
147     * @param int           $type           folder type
148     *
149     * @access public
150     * @return boolean                      status
151     * @throws StatusException              could throw specific SYNC_FSSTATUS_* exceptions
152     *
153     */
154    public function ChangeFolder($folderid, $oldid, $displayname, $type)
155    {
156        return false;
157
158    }
159
160    /**
161     * Deletes a folder
162     *
163     * @param string        $id
164     * @param string        $parent         is normally false
165     *
166     * @access public
167     * @return boolean                      status - false if e.g. does not exist
168     * @throws StatusException              could throw specific SYNC_FSSTATUS_* exceptions
169     */
170    public function DeleteFolder($id, $parentid)
171    {
172        return false;
173    }
174
175    /**
176     * Returns a list (array) of messages, each entry being an associative array
177     * with the same entries as StatMessage(). This method should return stable information; ie
178     * if nothing has changed, the items in the array must be exactly the same. The order of
179     * the items within the array is not important though.
180     *
181     * The $cutoffdate is a date in the past, representing the date since which items should be shown.
182     * This cutoffdate is determined by the user's setting of getting 'Last 3 days' of e-mail, etc. If
183     * the cutoffdate is ignored, the user will not be able to select their own cutoffdate, but all
184     * will work OK apart from that.
185     *
186     * @param string        $folderid       id of the parent folder
187     * @param long          $cutoffdate     timestamp in the past from which on messages should be returned
188     *
189     * @access public
190     * @return array/false                  array with messages or false if folder is not available
191     */
192    public function GetMessageList($folderid, $cutoffdate)
193    {
194        $idNumber = (int)str_replace('calendar' , '' , $folderid);
195        $cal_ids = null;
196        $messages = array();
197
198        $sql = 'SELECT calendar_object.last_update , calendar_object.cal_uid FROM calendar_signature , calendar , calendar_to_calendar_object, calendar_object WHERE calendar_signature.id = '.$idNumber.' AND calendar_signature.calendar_id = calendar.id AND calendar_to_calendar_object.calendar_id = calendar.id AND calendar_to_calendar_object.calendar_object_id = calendar_object.id  AND calendar_object.last_update > '. $cutoffdate . '000';
199
200        $rs = Controller::service('PostgreSQL')->execSql($sql);
201
202        if(is_array($rs))
203        {
204            foreach($rs as $v)
205            {
206                $message = array();
207                $message["id"] = $v['cal_uid'];
208                $message["mod"] = substr($v['last_update'], 0, -3);
209                $message["flags"] = 1; // always 'read'
210                $messages[] = $message;
211            }
212        }
213
214        return $messages;
215    }
216
217    /**
218     * Returns the actual SyncXXX object type. The '$folderid' of parent folder can be used.
219     * Mixing item types returned is illegal and will be blocked by the engine; ie returning an Email object in a
220     * Tasks folder will not do anything. The SyncXXX objects should be filled with as much information as possible,
221     * but at least the subject, body, to, from, etc.
222     *
223     * @param string            $folderid           id of the parent folder
224     * @param string            $id                 id of the message
225     * @param ContentParameters $contentparameters  parameters of the requested message (truncation, mimesupport etc)
226     *
227     * @access public
228     * @return object/false                 false if the message could not be retrieved
229     */
230    public function GetMessage($folderid, $id, $contentparameters)
231    {
232        $idNumber = (int)str_replace('calendar' , '' , $folderid);
233        $calendarSignature =  Controller::read( array( 'concept' => 'calendarSignature' , 'id' => $idNumber ));
234
235        $schedulable = Controller::find(array('concept' => 'schedulable'), null , array('filter' => array( '=' , 'uid' , $id)));
236        if( is_array($schedulable) && count($schedulable) > 0 )
237
238            $schedulable = $schedulable[0];
239        else
240            return false;
241
242        $message = new SyncAppointment();
243        $message->uid = $id;
244        $message->dtstamp = (int) substr($schedulable['dtstamp'], 0, -3);
245        $message->starttime =  (int) substr($schedulable['startTime'], 0, -3);
246        $message->endtime = (int) substr($schedulable['endTime'], 0, -3);
247        $message->deleted = 0;
248
249        $message->subject = mb_convert_encoding($schedulable['summary'] , 'UTF-8' , 'UTF-8,ISO-8859-1');
250        $message->location =  mb_convert_encoding($schedulable['location'], 'UTF-8' , 'UTF-8,ISO-8859-1');
251
252        if(isset($schedulable['description']) && $schedulable['description'] != "") {
253            $message->body = mb_convert_encoding($schedulable['description'], 'UTF-8' , 'UTF-8,ISO-8859-1');  // phpgw_cal.description
254            $message->bodysize = strlen($message->body);
255            $message->bodytruncated = 0;
256        }
257
258        $message->sensitivity = 0; // 0 - Normal,
259        $message->alldayevent = (int)$schedulable['allDay']; // (0 - Não(default), 1- Sim)
260        $message->timezone = base64_encode($this->_getSyncBlobFromTZ($this->_getGMTTZ()));
261
262
263        /*
264         * Sincronização de participantes e organizador
265         */
266        $participants = Controller::find(array('concept' => 'participant'), null , array('deepness' => 1 , 'filter' => array( '=' , 'schedulable' , $schedulable['id'] )));
267        if(is_array($participants) && count($participants) > 0)
268        {
269            $message->attendees = array();
270            foreach($participants as $participant)
271            {
272                if($participant['isOrganizer'] == 1) //organizador
273                {
274                    $message->organizername = mb_convert_encoding($participant['user']['name'], 'UTF-8' , 'UTF-8,ISO-8859-1');
275                    $message->organizeremail = mb_convert_encoding($participant['user']['mail'], 'UTF-8' , 'UTF-8,ISO-8859-1');
276                }
277                else
278                {
279                    $attendee = new SyncAttendee();
280                    $attendee->name =  mb_convert_encoding($participant['user']['name'], 'UTF-8' , 'UTF-8,ISO-8859-1');
281                    $attendee->email = mb_convert_encoding($participant['user']['mail'], 'UTF-8' , 'UTF-8,ISO-8859-1');
282                    $message->attendees[] = $attendee;
283                }
284
285                if($participant['user']['id'] == $this->_uidnumber  )
286                {
287                    if($participant['isOrganizer'] == 1 || strpos($participant['acl'] ,'w') !== false) // Caso ele seja organizador ou tenha permisão de editar o evento
288                    {
289                        $message->meetingstatus = 0;
290                    }
291                    else
292                    {
293                        $message->meetingstatus = 3;
294                    }
295
296                    if(isset($participant['alarms'][0]) )
297                    {
298                        switch($participant['alarms'][0]['unit'])
299                        {
300                            case 'h':
301                                $mult = 60;
302                                break;
303                            case 'd':
304                                $mult = 3600;
305                                break;
306                            default:
307                                $mult = 1;
308                                break;
309                        }
310
311                        $message->reminder = $participant['alarms'][0]['time'] * $mult;
312                    }
313
314                    switch($participant['status'])
315                    {
316                        case STATUS_ACCEPTED:
317                            $message->busystatus = 2;
318                            break;
319                        case STATUS_TENTATIVE:
320                            $message->busystatus = 1;
321                            break;
322                        case STATUS_DECLINED:
323                            $message->busystatus = 3;
324                            break;
325                        case STATUS_UNANSWERED:
326                            $message->busystatus = 0;
327                            break;
328                    }
329
330                }
331            }
332        }
333        //------------------------------------------------------------------------------------------------------------//
334
335        /*
336        * Sincronização de Recorrência
337        */
338        $repeats = Controller::find(array('concept' => 'repeat'), null , array( 'filter' => array( 'and' , array( '=' , 'schedulable' , $schedulable['id'] ),array( '!=' , 'frequency' , 'none' )  ) ));
339        if(is_array($repeats) && count($repeats) > 0)
340        {
341            $repeat = $repeats[0];
342            $recur = new SyncRecurrence();
343
344            switch($repeat['frequency'])
345            {
346                case 'daily':
347                    $recur->type = 0;
348                    break;
349                case 'weekly':
350                    $recur->type = 1;
351                    break;
352                case 'monthly':
353                    $recur->type = 2;
354                    break;
355                case 'yearly':
356                    $recur->type = 5;
357                    break;
358            }
359
360            if($repeat['endTime'])
361                $recur->until =  (int) substr($repeat['endTime'], 0, -3);
362
363            $recur->interval = $repeat['interval'] ? $repeat['interval'] : 1;
364
365            if($repeat["count"])
366                $recur->occurrences = (int)$repeat["count"];
367
368            if($repeat["byweekno"])
369                $recur->weekofmonth = (int)$repeat["byweekno"];
370
371            if($repeat["bymonthday"])
372                $recur->dayofmonth = (int)$repeat["bymonthday"];
373
374
375            if($repeat["byday"])
376                $recur->dayofweek = $this->formatDoWeek($repeat["byday"]);
377
378            //$recurrence->monthofyear ; //Não implementado no expresso
379
380            $expetions = Controller::find(array('concept' => 'repeatOccurrence'), null , array( 'filter' => array( 'and' , array( '=' , 'exception' , '1' ),array( '=' , 'repeat' , $repeat['id'] ) )));
381            if(is_array($expetions) && count($expetions) > 0)
382            {
383                $message->exceptions = array();
384                foreach($expetions as $expetion)
385                {
386                    $exception = new SyncAppointmentException();
387                    $exception->exceptionstarttime =  (int) substr($expetion['occurrence'], 0, -3);
388                    $exception->deleted = '1';
389                    $message->exceptions[] = $exception;
390                }
391            }
392
393            $message->recurrence = $recur;
394        }
395
396
397        return $message;
398    }
399
400    /**
401     * Returns message stats, analogous to the folder stats from StatFolder().
402     *
403     * @param string        $folderid       id of the folder
404     * @param string        $id             id of the message
405     *
406     * @access public
407     * @return array or boolean if fails
408     *          Associative array(
409     *              string  "id"            Server unique identifier for the message. Again, try to keep this short (under 20 chars)
410     *              int     "flags"         simply '0' for unread, '1' for read
411     *              long    "mod"           This is the modification signature. It is any arbitrary string which is constant as long as
412     *                                      the message has not changed. As soon as this signature changes, the item is assumed to be completely
413     *                                      changed, and will be sent to the PDA as a whole. Normally you can use something like the modification
414     *                                      time for this field, which will change as soon as the contents have changed.
415     *          )
416     */
417    public function StatMessage($folderid, $id)
418    {
419        $sql = 'SELECT last_update , cal_uid FROM calendar_object WHERE cal_uid = \''.pg_escape_string($id) .'\'';
420        $message = array();
421
422        $rs = Controller::service('PostgreSQL')->execSql($sql);
423        if(is_array($rs))
424        {
425            $message["mod"] = substr($rs[0]['last_update'], 0, -3);
426            $message["id"] = $id;
427            $message["flags"] = 1;
428        }
429        return $message;
430    }
431
432    /**
433     * Called when a message has been changed on the mobile. The new message must be saved to disk.
434     * The return value must be whatever would be returned from StatMessage() after the message has been saved.
435     * This way, the 'flags' and the 'mod' properties of the StatMessage() item may change via ChangeMessage().
436     * This method will never be called on E-mail items as it's not 'possible' to change e-mail items. It's only
437     * possible to set them as 'read' or 'unread'.
438     *
439     * @param string        $folderid       id of the folder
440     * @param string        $id             id of the message
441     * @param SyncXXX       $message        the SyncObject containing a message
442     *
443     * @access public
444     * @return array                        same return value as StatMessage()
445     * @throws StatusException              could throw specific SYNC_STATUS_* exceptions
446     */
447    public function ChangeMessage($folderid, $idMessage, $message)
448    {
449
450        $idNumber = (int)str_replace('calendar' , '' , $folderid);
451        $calendarSignature =  Controller::read( array( 'concept' => 'calendarSignature' , 'id' => $idNumber ));
452        $calendar =  Controller::read( array( 'concept' => 'calendar' , 'id' => $calendarSignature['calendar'] ));
453
454        if($idMessage)
455        {
456            $schedulable = Controller::find(array('concept' => 'schedulable'), null , array('deepness'=> 2 , 'filter' => array( '=' , 'uid' , $idMessage)));
457            $schedulable = $schedulable[0];
458
459
460            foreach($schedulable['participants'] as $i => $v)
461            {
462                if($v['user']['id'] == $this->_uidnumber )
463                {
464                    if(strpos($v['acl'] ,'w') !== false) //Caso o usuario tenha permissão de editar o evento
465                    {
466                        return  $this->updateEvent($folderid, $idMessage, $message , $calendar ,$schedulable);
467                    }
468                    else
469                    {
470                        $interation = array();
471
472                        if(isset($message->reminder) && $message->reminder > 0)
473                        {
474                            $alarm = array();
475                            $alarmID = mt_rand() . '6(Formatter)';
476                            $alarm['type'] = 'alert';
477                            $alarm['time'] = $message->reminder;
478                            $alarm['unit'] = 'm';
479                            $alarm['participant'] = $v['id'];
480                            $alarm['schedulable'] = $schedulable['id'];
481                            $interation['alarm://' . $alarmID ] = $alarm;
482
483                        }
484
485                        $status  = $this->formatBusy($message->busystatus);
486
487                        if($status == STATUS_DECLINED ) //Caso ele não seja dono do evento e recusou o convite deletar o evento da sua agenda.
488                        {
489                            Controller::deleteAll(array('concept' => 'calendarToSchedulable' ) , false , array('filter' => array('AND', array('=','calendar',$calendarSignature['calendar']), array('=','schedulable',$schedulable['id']))));
490                        }
491
492                        $v['status'] = $status;
493
494                        $interation['participant://' . $v['id'] ] = $v;
495
496                        ob_start();
497                        $args = $interation;
498                        include EXPRESSO_PATH.'/prototype/Sync.php';
499                        ob_end_clean();
500
501                    }
502                }
503            }
504            return $this->StatMessage($folderid, $message->uid);
505        }
506        else
507        {
508            if (!$schedulable = $this->_getSchedulable($message->uid))
509                return  $this->createEvent($folderid, $idMessage, $message ,$calendar);
510            else{
511                $links = Controller::read(array('concept' => 'calendarToSchedulable'), array('id'), array('filter' =>
512                array('AND',
513                    array('=', 'calendar', $calendar['id']),
514                    array('=', 'schedulable', $schedulable['id'])
515                )));
516
517                if(!$links &&  !isset($links[0]))
518                    Controller::create(array('concept' => 'calendarToSchedulable'), array('calendar' => $calendar['id'], 'schedulable' => $schedulable['id']));
519
520                foreach($schedulable['participants'] as $i => $v)
521                {
522                    if($v['user']['id'] == $this->_uidnumber)
523                    {
524                        Controller::update(array('concept' => 'participant','id' => $v['id']), array('status' => $this->formatBusy($message->busystatus ) ));
525                    }
526                }
527
528                return $this->StatMessage($folderid, $message->uid);
529            }
530        }
531
532    }
533
534    private function _getSchedulable($uid) {
535        $schedulable = Controller::find(array('concept' => 'schedulable'), false, array('filter' => array('=', 'uid', $uid), 'deepness' => 2));
536        return (isset($schedulable[0])) ? $schedulable[0] : false;
537    }
538
539    private function updateEvent($folderid, $idMessage, $message , $calendar ,$schedulable )
540    {
541
542
543        $tz_CEL = $this->_getTZFromSyncBlob(base64_decode($message->timezone));
544        $GMT_CEL = -(($tz_CEL["bias"] + $tz_CEL["dstbias"]) * 60);
545
546        $interation = array();
547        $eventID = $schedulable['id'];
548        $schedulable['uid'] = $message->uid;
549        $schedulable['summary'] = $message->subject;
550        $schedulable['location'] = $message->location;
551        $schedulable['class'] = 1;
552
553        /// Eliminana o timezone, enviado pelo ceulular e coloca no timezone do calendario.
554        // o celular não manda o nome do timezone apenas o offset dele dae não tem como saber qual foi o timezone selecionado.
555        $calendarSignatureTimezone = new DateTimeZone($calendar['timezone']) ;
556        $schedulable['startTime'] = (($message->starttime + $GMT_CEL) + ($calendarSignatureTimezone->getOffset(new DateTime('@'.($message->starttime + $GMT_CEL), new DateTimeZone('UTC'))) * -1) ) *1000; //$message->starttime  * 1000;
557        $schedulable['endTime'] = (($message->endtime + $GMT_CEL) + ($calendarSignatureTimezone->getOffset(new DateTime('@'.($message->endtime + $GMT_CEL), new DateTimeZone('UTC')))* -1)) *1000;//$message->endtime  * 1000;
558        $schedulable['timezone'] = $calendar['timezone'];
559
560        $schedulable['allDay'] = $message->alldayevent;
561        $schedulable['description'] = $message->body;
562        $schedulable['dtstamp'] = $message->dtstamp;
563        $schedulable['lastUpdate'] = time() * 1000;
564        $schedulable['type'] = '1';
565
566
567        if(isset($message->recurrence))
568        {
569            $repeatID = isset($schedulable['repeat']) ? $schedulable['repeat']['id'] : mt_rand() . '3(Formatter)';
570
571            $repeat = array();
572            $repeat['schedulable'] = $eventID;
573
574            switch( $message->recurrence->type )
575            {
576                case 0:
577                    $repeat['frequency'] = 'daily';
578                    break;
579                case 1:
580                    $repeat['frequency'] = 'weekly';
581                    break;
582                case 2:
583                    $repeat['frequency'] = 'monthly';
584                    break;
585                case 5:
586                    $repeat['frequency'] = 'yearly';
587                    break;
588            }
589
590            if(isset($message->recurrence->until))
591                $repeat['endTime'] =  $message->recurrence->until  * 1000 ;
592            else
593                $repeat['endTime'] = null;
594
595            $repeat['startTime'] =  $message->starttime * 1000 ;
596
597            $repeat['interval'] =  isset($message->recurrence->interval) ? $message->recurrence->interval : 1;
598
599            if(isset($message->recurrence->occurrences) && $message->recurrence->occurrences > 0)
600                $repeat["count"] = $message->recurrence->occurrences;
601            else
602                $repeat["count"] = 0;
603
604            if(isset($message->recurrence->weekofmonth) && $message->recurrence->weekofmonth > 0)
605                $repeat["byweekno"] =  $message->recurrence->weekofmonth;
606            else
607                $repeat["byweekno"] = 0;
608
609            if(isset($message->recurrence->dayofmonth) && $message->recurrence->dayofmonth > 0)
610                $repeat["bymonthday"] = $message->recurrence->dayofmonth;
611            else
612                $repeat["bymonthday"] = 0;
613
614            $day = $message->recurrence->dayofweek;
615            $day_of_week_array = array();
616            if (($day & 1) > 0) $day_of_week_array[] = 'SU';
617            if (($day & 2) > 0) $day_of_week_array[] = 'MO';
618            if (($day & 4) > 0) $day_of_week_array[] = 'TU';
619            if (($day & 8) > 0) $day_of_week_array[] = 'WE';
620            if (($day & 16) > 0) $day_of_week_array[] = 'TH';
621            if (($day & 32) > 0) $day_of_week_array[] = 'FR';
622            if (($day & 64) > 0) $day_of_week_array[] = 'SA';
623
624            $repeat["byday"] = implode(',' ,$day_of_week_array);
625            $interation['repeat://' . $repeatID] = $repeat;
626
627        }
628        else if (isset($schedulable['repeat']) )
629        {
630            $interation['repeat://'.$schedulable['repeat']['id']] = null;
631        }
632
633        $partForDelete = $schedulable['participants'];
634
635        foreach($partForDelete as $partForDeleteIndice => $partForDeleteValue)
636        {
637            if($partForDeleteValue['isOrganizer'] == '1')
638            {
639                if(isset($message->reminder) && $message->reminder > 0)
640                {
641                    $alarm = array();
642                    $alarmID =  isset($partForDeleteValue['alarms'][0]['id']) ? $partForDeleteValue['alarms'][0]['id'] :  mt_rand() . '6(Formatter)';
643                    $alarm['type'] = 'alert';
644                    $alarm['time'] = $message->reminder;
645                    $alarm['unit'] = 'm';
646
647                    foreach ($interation as $iint => &$vint)
648                    {
649                        if(isset($vint['user']) && $vint['user'] == $this->_uidnumber)
650                        {
651                            $alarm['participant'] = str_replace('participant://', '', $iint);
652                            $vint['alarms'][] = $alarmID;
653                        }
654                    }
655
656                    $alarm['schedulable'] = $eventID;
657                    $interation['alarm://' . $alarmID ] = $alarm;
658
659
660                }
661                else if(isset($partForDeleteValue['alarms'][0]['id']))
662                    $interation['alarm://' . $partForDeleteValue['alarms'][0]['id'] ] = false;
663
664                unset($partForDelete[$partForDeleteIndice]);
665                unset($schedulable['participants'][$partForDeleteIndice]['alarms']);
666            }
667        }
668
669        if(isset($message->attendees)  && count($message->attendees) > 0)
670        {
671
672            foreach($message->attendees as $attendee)
673            {
674
675                if($this->_getParticipantByMail($attendee->email, $schedulable['participants']) === false)
676                {
677                    $participantID = mt_rand() . '2(Formatter)';
678                    $participant = array();
679                    $participant['schedulable'] = $eventID;
680                    $participant['isOrganizer'] = '0';
681                    $participant['acl'] = 'r';
682
683                    /* Verifica se este usuario é um usuario interno do ldap */
684                    $intUser = Controller::find(array('concept' => 'user'), array('id', 'isExternal'), array('filter' => array('OR', array('=', 'mail', $attendee->email), array('=', 'mailAlternateAddress', $attendee->email))));
685
686                    $user = null;
687                    if ($intUser && count($intUser) > 0) {
688                        $participant['isExternal'] = isset($intUser[0]['isExternal']) ? $intUser[0]['isExternal'] : 0;
689                        $participant['user'] = $intUser[0]['id'];
690                    } else {
691                        $participant['isExternal'] = 1;
692                        /* Gera um randon id para o contexto formater */
693                        $userID = mt_rand() . '4(Formatter)';
694
695                        $user['mail'] = $attendee->email;
696                        $user['name'] = ( isset($attendee->name) ) ? $attendee->name : '';
697                        $user['participants'] = array($participantID);
698                        $user['isExternal'] = '1';
699                        $participant['user'] = $userID;
700                        $interation['user://' . $userID] = $user;
701                    }
702
703                    $interation['participant://' . $participantID] = $participant;
704                    $schedulable['participants'][] = $participantID;
705                }
706                else
707                    unset($partForDelete[$this->_getParticipantByMail($attendee->email, $schedulable['participants'])]);
708
709            }
710
711        }
712
713        foreach( $partForDelete as $toDelete)
714        {
715            $interation['participant://' . $toDelete['id']] = false;
716            foreach ($schedulable['participants'] as $ipart => $part)
717            {
718                if($part['id'] == $toDelete['id'])
719                {
720                    unset($schedulable['participants'][$ipart]);
721                }
722            }
723
724            $schedulable['participants'] = array_merge($schedulable['participants'] , array());
725
726        }
727
728        foreach($schedulable['participants'] as $i => $v)
729        {
730            if($v['user']['id'] == $this->_uidnumber )
731            {
732                $schedulable['participants'][$i]['status'] = $this->formatBusy($message->busystatus);
733            }
734        }
735
736        unset($schedulable['repeat']);
737
738        $interation['schedulable://' . $eventID] = $schedulable;
739
740        ob_start();
741        $args = $interation;
742        include EXPRESSO_PATH.'/prototype/Sync.php';
743        ob_end_clean();
744
745        return $this->StatMessage($folderid, $message->uid);
746    }
747
748    private function createEvent($folderid, $idMessage, $message , $calendar)
749    {
750        $tz_CEL = $this->_getTZFromSyncBlob(base64_decode($message->timezone));
751        $GMT_CEL = -(($tz_CEL["bias"] + $tz_CEL["dstbias"]) * 60);
752
753
754        $interation = array();
755        $schedulable = array();
756        $eventID = mt_rand() . '(Formatter)';
757
758        $schedulable['calendar'] = $calendar['id'];
759        $schedulable['uid'] = $message->uid;
760        $schedulable['summary'] = $message->subject;
761        $schedulable['location'] = $message->location;
762        $schedulable['class'] = 1;
763
764
765        /// Eliminana o timezone, enviado pelo ceulular e coloca no timezone do calendario.
766        // o celular não manda o nome do timezone apenas o offset dele dae não tem como saber qual foi o timezone selecionado.
767        $calendarSignatureTimezone = new DateTimeZone($calendar['timezone']) ;
768        $schedulable['startTime'] = (($message->starttime + $GMT_CEL) + ($calendarSignatureTimezone->getOffset(new DateTime('@'.($message->starttime + $GMT_CEL), new DateTimeZone('UTC'))) * -1) ) *1000; //$message->starttime  * 1000;
769        $schedulable['endTime'] = (($message->endtime + $GMT_CEL) + ($calendarSignatureTimezone->getOffset(new DateTime('@'.($message->endtime + $GMT_CEL), new DateTimeZone('UTC')))* -1)) *1000;//$message->endtime  * 1000;
770
771        $sv  = new DateTime('@'.($message->starttime + $GMT_CEL), $calendarSignatureTimezone);
772
773        if($sv->format('I') == 0)
774            $schedulable['startTime'] = $schedulable['startTime'] - 3600000;
775
776        $ev  = new DateTime('@'.($message->endtime + $GMT_CEL), $calendarSignatureTimezone);
777
778        if($ev->format('I') == 0)
779            $schedulable['endTime'] = $schedulable['endTime'] - 3600000;
780
781        $schedulable['timezone'] = $calendar['timezone'];
782
783
784        $schedulable['allDay'] = $message->alldayevent;
785        $schedulable['description'] = $message->body;
786        $schedulable['dtstamp'] = $message->dtstamp;
787        // $schedulable['lastUpdate'] = 0;
788        $schedulable['type'] = '1';
789        $participant = array();
790        $participantID = mt_rand() . '2(Formatter)';
791        $participant['schedulable'] = $eventID;
792        $participant['isOrganizer'] = '1';
793        $participant['acl'] = 'rowi';
794        $participant['status'] = '1';
795
796        if($message->organizeremail)
797        {
798            /* Verifica se este usuario é um usuario interno do ldap */
799            $intUser = Controller::find(array('concept' => 'user'), array('id', 'isExternal'), array('filter' => array('OR', array('=', 'mail', $message->organizeremail), array('=', 'mailAlternateAddress', $message->organizeremail))));
800
801            $user = null;
802            if ($intUser && count($intUser) > 0) {
803                $participant['isExternal'] = isset($intUser[0]['isExternal']) ? $intUser[0]['isExternal'] : 0;
804                $participant['user'] = $intUser[0]['id'];
805            } else {
806                $participant['isExternal'] = 1;
807                /* Gera um randon id para o contexto formater */
808                $userID = mt_rand() . '4(Formatter)';
809
810                $user['mail'] = $message->organizeremail;
811                $user['name'] = ( isset($message->organizername) ) ? $message->organizername : '';
812                $user['participants'] = array($participantID);
813                $user['isExternal'] = '1';
814                $participant['user'] = $userID;
815                $interation['user://' . $userID] = $user;
816            }
817        }
818        else
819        {
820            $participant['isExternal'] = 0;
821            $participant['user'] = $this->_uidnumber;
822            $participant['status'] = $this->formatBusy($message->busystatus);
823        }
824
825        //Caso exista recorrencias
826        if(isset($message->recurrence))
827        {
828            /* Gera um randon id para o contexto formater */
829            $repeatID = mt_rand() . '3(Formatter)';
830
831            $repeat = array();
832            $repeat['schedulable'] = $eventID;
833
834            switch( $message->recurrence->type )
835            {
836                case 0:
837                    $repeat['frequency'] = 'daily';
838                    break;
839                case 1:
840                    $repeat['frequency'] = 'weekly';
841                    break;
842                case 2:
843                    $repeat['frequency'] = 'monthly';
844                    break;
845                case 5:
846                    $repeat['frequency'] = 'yearly';
847                    break;
848            }
849
850            if(isset($message->recurrence->until))
851                $repeat['endTime'] =  $message->recurrence->until  * 1000 ;
852
853            $repeat['startTime'] =  $message->starttime * 1000 ;
854
855            $repeat['interval'] =  isset($message->recurrence->interval) ? $message->recurrence->interval : 1;
856
857            if(isset($message->recurrence->occurrences) && $message->recurrence->occurrences > 0)
858                $repeat["count"] = $message->recurrence->occurrences;
859
860            if(isset($message->recurrence->weekofmonth) && $message->recurrence->weekofmonth > 0)
861                $repeat["byweekno"] =  $message->recurrence->weekofmonth;
862
863            if(isset($message->recurrence->dayofmonth) && $message->recurrence->dayofmonth > 0)
864                $repeat["bymonthday"] = $message->recurrence->dayofmonth;
865
866            $day = $message->recurrence->dayofweek;
867            $day_of_week_array = array();
868            if (($day & 1) > 0) $day_of_week_array[] = 'SU';
869            if (($day & 2) > 0) $day_of_week_array[] = 'MO';
870            if (($day & 4) > 0) $day_of_week_array[] = 'TU';
871            if (($day & 8) > 0) $day_of_week_array[] = 'WE';
872            if (($day & 16) > 0) $day_of_week_array[] = 'TH';
873            if (($day & 32) > 0) $day_of_week_array[] = 'FR';
874            if (($day & 64) > 0) $day_of_week_array[] = 'SA';
875
876            $repeat["byday"] = implode(',' ,$day_of_week_array);
877            $interation['repeat://' . $repeatID] = $repeat;
878
879        }
880
881        $interation['participant://' . $participantID] = $participant;
882        $schedulable['participants'][] = $participantID;
883
884
885        if(isset($message->attendees)  && count($message->attendees) > 0)
886        {
887            foreach($message->attendees as $attendee)
888            {
889                $participantID = mt_rand() . '2(Formatter)';
890                $participant = array();
891                $participant['schedulable'] = $eventID;
892                $participant['isOrganizer'] = '0';
893                $participant['acl'] = 'r';
894
895                /* Verifica se este usuario é um usuario interno do ldap */
896                $intUser = Controller::find(array('concept' => 'user'), array('id', 'isExternal'), array('filter' => array('OR', array('=', 'mail', $attendee->email), array('=', 'mailAlternateAddress', $attendee->email))));
897
898                $user = null;
899                if ($intUser && count($intUser) > 0) {
900                    $participant['isExternal'] = isset($intUser[0]['isExternal']) ? $intUser[0]['isExternal'] : 0;
901                    $participant['user'] = $intUser[0]['id'];
902                } else {
903                    $participant['isExternal'] = 1;
904                    /* Gera um randon id para o contexto formater */
905                    $userID = mt_rand() . '4(Formatter)';
906
907                    $user['mail'] = $attendee->email;
908                    $user['name'] = ( isset($attendee->name) ) ? $attendee->name : '';
909                    $user['participants'] = array($participantID);
910                    $user['isExternal'] = '1';
911                    $participant['user'] = $userID;
912                    $interation['user://' . $userID] = $user;
913
914                    if($userID == $this->_uidnumber)
915                    {
916                        $participant['status'] = $this->formatBusy($message->busystatus);
917                    }
918
919                }
920
921                $interation['participant://' . $participantID] = $participant;
922                $schedulable['participants'][] = $participantID;
923
924            }
925
926        }
927
928        if(isset($message->reminder) && $message->reminder > 0)
929        {
930            $alarm = array();
931            $alarmID = mt_rand() . '6(Formatter)';
932            $alarm['type'] = 'alert';
933            $alarm['time'] = $message->reminder;
934            $alarm['unit'] = 'm';
935
936            foreach ($interation as $iint => &$vint)
937            {
938                if(isset($vint['user']) && $vint['user'] == $this->_uidnumber)
939                {
940                    $alarm['participant'] = str_replace('participant://', '', $iint);
941                    $vint['alarms'][] = $alarmID;
942                }
943            }
944
945            $alarm['schedulable'] = $eventID;
946            $interation['alarm://' . $alarmID ] = $alarm;
947
948
949        }
950
951        $interation['schedulable://' . $eventID] = $schedulable;
952
953        ob_start();
954        $args = $interation;
955        include EXPRESSO_PATH.'/prototype/Sync.php';
956        ob_end_clean();
957
958        return $this->StatMessage($folderid, $message->uid);
959    }
960
961
962    /**
963     * Changes the 'read' flag of a message on disk. The $flags
964     * parameter can only be '1' (read) or '0' (unread). After a call to
965     * SetReadFlag(), GetMessageList() should return the message with the
966     * new 'flags' but should not modify the 'mod' parameter. If you do
967     * change 'mod', simply setting the message to 'read' on the mobile will trigger
968     * a full resync of the item from the server.
969     *
970     * @param string        $folderid       id of the folder
971     * @param string        $id             id of the message
972     * @param int           $flags          read flag of the message
973     *
974     * @access public
975     * @return boolean                      status of the operation
976     * @throws StatusException              could throw specific SYNC_STATUS_* exceptions
977     */
978    public function SetReadFlag($folderid, $id, $flags)
979    {
980        return true;
981    }
982
983    /**
984     * Called when the user has requested to delete (really delete) a message. Usually
985     * this means just unlinking the file its in or somesuch. After this call has succeeded, a call to
986     * GetMessageList() should no longer list the message. If it does, the message will be re-sent to the mobile
987     * as it will be seen as a 'new' item. This means that if this method is not implemented, it's possible to
988     * delete messages on the PDA, but as soon as a sync is done, the item will be resynched to the mobile
989     *
990     * @param string        $folderid       id of the folder
991     * @param string        $id             id of the message
992     *
993     * @access public
994     * @return boolean                      status of the operation
995     * @throws StatusException              could throw specific SYNC_STATUS_* exceptions
996     */
997    public function DeleteMessage($folderid, $id)
998    {
999
1000        $idNumber = (int)str_replace('calendar' , '' , $folderid);
1001        $calendarSignature =  Controller::read( array( 'concept' => 'calendarSignature' , 'id' => $idNumber ));
1002        $even = $this->_getSchedulable($id );
1003        $calendar =  Controller::read( array( 'concept' => 'calendar' , 'id' => $calendarSignature['calendar'] ));
1004
1005        $link = Controller::read(array('concept' => 'calendarToSchedulable'), false, array('filter' => array('AND', array('=','calendar',$calendarSignature['calendar']), array('=','schedulable',$even['id']))));
1006
1007        $delete = false;
1008        foreach($even['participants'] as $i => $v)
1009        {
1010            if($v['user']['id'] == $this->_uidnumber && $v['user']['isOrganizer']  == '1')
1011            {
1012                $delete = true;
1013            }
1014        }
1015
1016        if( $delete === true)
1017        {
1018            Controller::delete(array('concept' => 'schedulable' , 'id' => $even['id']));
1019        }
1020        else
1021        {
1022            Controller::delete(array('concept' => 'calendarToSchedulable', 'id' => $link[0]['id']));
1023
1024            foreach($even['participants'] as $i => $v)
1025            {
1026                if($v['user']['id'] == $this->_uidnumber)
1027                {
1028                    Controller::update(array('concept' => 'participant','id' => $v['id']), array('status' => STATUS_CANCELLED ));
1029                }
1030            }
1031
1032        }
1033        return true;
1034    }
1035
1036    /**
1037     * Called when the user moves an item on the PDA from one folder to another. Whatever is needed
1038     * to move the message on disk has to be done here. After this call, StatMessage() and GetMessageList()
1039     * should show the items to have a new parent. This means that it will disappear from GetMessageList()
1040     * of the sourcefolder and the destination folder will show the new message
1041     *
1042     * @param string        $folderid       id of the source folder
1043     * @param string        $id             id of the message
1044     * @param string        $newfolderid    id of the destination folder
1045     *
1046     * @access public
1047     * @return boolean                      status of the operation
1048     * @throws StatusException              could throw specific SYNC_MOVEITEMSSTATUS_* exceptions
1049     */
1050    public function MoveMessage($folderid, $id, $newfolderid)
1051    {
1052        return false;
1053    }
1054
1055    /**
1056     * Authenticates the user
1057     *
1058     * @param string        $username
1059     * @param string        $domain
1060     * @param string        $password
1061     *
1062     * @access public
1063     * @return boolean
1064     * @throws FatalException   e.g. some required libraries are unavailable
1065     */
1066    public function Logon($username, $domain, $password)
1067    {
1068        $ldapConfig = parse_ini_file(EXPRESSO_PATH . '/prototype/config/OpenLDAP.srv' , true );
1069        $ldapConfig =  $ldapConfig['config'];
1070
1071        $sr = ldap_search( $GLOBALS['connections']['ldap'] , $ldapConfig['context'] , "(uid=$username)" , array('uidNumber','uid','mail'), 0 , 1 );
1072        if(!$sr) return false;
1073
1074        $entries = ldap_get_entries( $GLOBALS['connections']['ldap'] , $sr );
1075        $this->_uidnumber = $entries[0]['uidnumber'][0];
1076
1077
1078        //Inicia Variaveis de para API expresso
1079        if(!isset($_SESSION))
1080            session_start();
1081
1082        $userWallet = array();
1083        $userWallet['uidNumber'] = $entries[0]['uidnumber'][0];
1084        $userWallet['uid'] = $entries[0]['uid'][0];
1085        $userWallet['mail'] = $entries[0]['mail'][0];
1086
1087        $_SESSION['wallet'] = array();
1088        $_SESSION['wallet']['user'] = $userWallet;
1089        $_SESSION['flags']['currentapp'] = 'expressoCalendar';
1090
1091        //----------------------------------------------------------------------------------------//
1092
1093        return true;
1094    }
1095
1096    /**
1097     * Logs off
1098     * non critical operations closing the session should be done here
1099     *
1100     * @access public
1101     * @return boolean
1102     */
1103    public function Logoff()
1104    {
1105
1106    }
1107
1108    /**
1109     * Sends an e-mail
1110     * This messages needs to be saved into the 'sent items' folder
1111     *
1112     * Basically two things can be done
1113     *      1) Send the message to an SMTP server as-is
1114     *      2) Parse the message, and send it some other way
1115     *
1116     * @param SyncSendMail        $sm         SyncSendMail object
1117     *
1118     * @access public
1119     * @return boolean
1120     * @throws StatusException
1121     */
1122    public function SendMail($sm)
1123    {
1124        return false;
1125    }
1126
1127    /**
1128     * Returns the waste basket
1129     *
1130     * The waste basked is used when deleting items; if this function returns a valid folder ID,
1131     * then all deletes are handled as moves and are sent to the backend as a move.
1132     * If it returns FALSE, then deletes are handled as real deletes
1133     *
1134     * @access public
1135     * @return string
1136     */
1137    public function GetWasteBasket()
1138    {
1139        return false;
1140    }
1141
1142    /**
1143     * Returns the content of the named attachment as stream. The passed attachment identifier is
1144     * the exact string that is returned in the 'AttName' property of an SyncAttachment.
1145     * Any information necessary to locate the attachment must be encoded in that 'attname' property.
1146     * Data is written directly - 'print $data;'
1147     *
1148     * @param string        $attname
1149     *
1150     * @access public
1151     * @return SyncItemOperationsAttachment
1152     * @throws StatusException
1153     */
1154    public function GetAttachmentData($attname)
1155    {
1156        return false;
1157    }
1158
1159    function _getGMTTZ() {
1160        //$tz = array("bias" => 0, "stdbias" => 0, "dstbias" => 0, "dstendyear" => 0, "dstendmonth" => 2, "dstendday" => 0, "dstendweek" => 2, "dstendhour" => 2, "dstendminute" => 0, "dstendsecond" => 0, "dstendmillis" => 0,
1161        //"dststartyear" => 0, "dststartmonth" =>10, "dststartday" =>0, "dststartweek" => 3, "dststarthour" => 2, "dststartminute" => 0, "dststartsecond" => 0, "dststartmillis" => 0);
1162        $tz = array("bias" => 120, "stdbias" => 0, "dstbias" => -60, "dstendyear" => 0, "dstendmonth" => 2, "dstendday" => 0, "dstendweek" => 2, "dstendhour" => 2, "dstendminute" => 0, "dstendsecond" => 0, "dstendmillis" => 0, "dststartyear" => 0, "dststartmonth" =>10, "dststartday" =>0, "dststartweek" => 3, "dststarthour" => 2, "dststartminute" => 0, "dststartsecond" => 0, "dststartmillis" => 0);
1163
1164        return $tz;
1165    }
1166    function _getSyncBlobFromTZ($tz) {
1167        $packed = pack("la64vvvvvvvv" . "la64vvvvvvvv" . "l",
1168            $tz["bias"], "", 0, $tz["dstendmonth"], $tz["dstendday"], $tz["dstendweek"], $tz["dstendhour"], $tz["dstendminute"], $tz["dstendsecond"], $tz["dstendmillis"],
1169            $tz["stdbias"], "", 0, $tz["dststartmonth"], $tz["dststartday"], $tz["dststartweek"], $tz["dststarthour"], $tz["dststartminute"], $tz["dststartsecond"], $tz["dststartmillis"],
1170            $tz["dstbias"]);
1171
1172        return $packed;
1173    }
1174
1175    function _getTZFromSyncBlob($data) {
1176        $tz = unpack(    "lbias/a64name/vdstendyear/vdstendmonth/vdstendday/vdstendweek/vdstendhour/vdstendminute/vdstendsecond/vdstendmillis/" .
1177            "lstdbias/a64name/vdststartyear/vdststartmonth/vdststartday/vdststartweek/vdststarthour/vdststartminute/vdststartsecond/vdststartmillis/" .
1178            "ldstbias", $data);
1179
1180        // Make the structure compatible with class.recurrence.php
1181        $tz["timezone"] = $tz["bias"];
1182        $tz["timezonedst"] = $tz["dstbias"];
1183
1184        return $tz;
1185    }
1186
1187    private function formatDoWeek($week)
1188    {
1189        $recday = explode(',' , $week);
1190        $nday = 0;
1191        foreach ($recday as $day)
1192        {
1193            switch($day)
1194            {
1195                case 'SU':
1196                    $nday=$nday +1;
1197                    break;
1198                case 'MO':
1199                    $nday=$nday +2;
1200                    break;
1201                case 'TU':
1202                    $nday=$nday +4;
1203                    break;
1204                case 'WE':
1205                    $nday=$nday +8;
1206                    break;
1207                case 'TH':
1208                    $nday=$nday +16;
1209                    break;
1210                case 'FR':
1211                    $nday=$nday +32;
1212                    break;
1213                case 'SA':
1214                    $nday=$nday +64;
1215                    break;
1216
1217            }
1218        }
1219        return $nday;
1220    }
1221
1222    private function _getParticipantByMail($mail, &$participants, $isFull = false) {
1223        if ($participants && $participants != '')
1224            foreach ($participants as $i => $v)
1225                if ((is_array($v) && isset($v['user'])) && ($v['user']['mail'] == $mail || (isset($v['user']['mailAlternateAddress']) && in_array($mail, $v['user']['mailAlternateAddress']))))
1226                    return $i;
1227        return false;
1228    }
1229
1230    private function _getParticipantIDByMail($mail, &$participants, $isFull = false) {
1231        if ($participants && $participants != '')
1232            foreach ($participants as $i => $v)
1233                if ((is_array($v) && isset($v['user'])) && ($v['user']['mail'] == $mail || (isset($v['user']['mailAlternateAddress']) && in_array($mail, $v['user']['mailAlternateAddress']))))
1234                    return !!$isFull ? $v : $v['id'];
1235        return false;
1236    }
1237
1238
1239    private function formatBusy($status)
1240    {
1241        switch($status)
1242        {
1243            case 2:
1244                return STATUS_ACCEPTED;
1245                break;
1246            case 1:
1247                return STATUS_TENTATIVE;
1248                break;
1249            case 3:
1250                return STATUS_DECLINED;
1251                break;
1252            case 0:
1253                return STATUS_UNANSWERED;
1254                break;
1255        }
1256    }
1257
1258
1259
1260}
Note: See TracBrowser for help on using the repository browser.