2 * Copyright (c) 2011 Samsung Electronics Co., Ltd All Rights Reserved
4 * Licensed under the Apache License, Version 2.0 (the License);
5 * you may not use this file except in compliance with the License.
6 * You may obtain a copy of the License at
8 * http://www.apache.org/licenses/LICENSE-2.0
10 * Unless required by applicable law or agreed to in writing, software
11 * distributed under the License is distributed on an AS IS BASIS,
12 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
13 * See the License for the specific language governing permissions and
14 * limitations under the License.
18 #include <calendar-svc-provider.h>
19 #include <dpl/log/log.h>
20 #include <dpl/scoped_ptr.h>
22 #include "CalendarManager.h"
23 #include "CalendarQuery.h"
24 #include "CalendarFilter.h"
25 #include "CalendarFilterValidator.h"
26 #include "API/Calendar/OnEventsChanged.h"
27 #include "API/Calendar/IEventWatchChanges.h"
28 #include "API/Calendar/IEventClearWatch.h"
29 #include "API/Calendar/EventId.h"
30 #include <API/Filter/IFilter.h>
31 #include <API/Filter/IFilterVisitor.h>
34 using namespace TizenApis::Api::Calendar;
35 using namespace WrtDeviceApis::Commons;
51 void Calendar::OnRequestReceived(const IEventAddEventPtr &event)
56 if (!event->getEvent()) {
57 ThrowMsg(NullPointerException, "event parameter is NULL");
59 if (event->getEvent()->getIdIsSet()) {
60 LogWarning("adding event that is already added");
61 event->getEvent()->resetId();
63 DPL::ScopedPtr<EventWrapper> eventWrapper(new EventWrapper(event->getEvent(), getType()));
64 event->getEvent()->setCalendarType(getType());
65 eventWrapper->convertAbstractEventToPlatformEvent();
67 // Set the account and calendar id before saving the item.
68 eventWrapper->setCalendarId(getId());
69 eventWrapper->setCalendarAccountId(getAccountId());
70 eventWrapper->saveEvent();
71 event->setResult(true);
75 LogWarning("Exception: "<<_rethrown_exception.GetMessage());
76 event->setResult(false);
77 event->setExceptionCode(ExceptionCodes::UnknownException);
81 void Calendar::OnRequestReceived(const IEventAddEventsPtr &events)
87 if (events->getEvents()->empty()) {
88 ThrowMsg(NullPointerException, "event vector parameter is empty");
91 // Save the vector of events iteratively
92 bool failedAdding = false;
93 for(unsigned int i=0; i<events->getEvents()->size(); i++)
95 if (events->checkCancelled()) {
96 events->setCancelAllowed(true);
97 events->setResult(true);
101 if (events->getEvents()->at(i)->getIdIsSet()) {
102 LogWarning("adding event that is already added: index " << i);
103 events->getEvents()->at(i)->resetId();
105 DPL::ScopedPtr<EventWrapper> eventWrapper(new EventWrapper(events->getEvents()->at(i), getType()));
106 events->getEvents()->at(i)->setCalendarType(getType());
107 eventWrapper->convertAbstractEventToPlatformEvent();
110 // Set the account and calendar id before saving the item.
111 eventWrapper->setCalendarId(getId());
112 eventWrapper->setCalendarAccountId(getAccountId());
113 eventWrapper->saveEvent();
114 } Catch (Exception) {
115 LogWarning("Exception: "<<_rethrown_exception.GetMessage());
118 //getAddEmitter()->emit(eventPtr);
121 if( false==failedAdding ) {
122 events->setResult(true);
124 events->setResult(false);
129 LogWarning("Exception: "<<_rethrown_exception.GetMessage());
130 events->setResult(false);
131 events->setExceptionCode(ExceptionCodes::UnknownException);
133 events->setCancelAllowed(false);
136 void Calendar::OnRequestReceived(const IEventUpdateEventPtr &event)
140 cal_iter *iter = NULL;
143 if (!event->getEvent()) {
144 ThrowMsg(NullPointerException, "Item object is NULL.");
146 if (!event->getEvent()->getIdIsSet()) {
147 ThrowMsg(InvalidArgumentException, "Item id is not set.");
150 DPL::ScopedPtr<EventWrapper> eventWrapper(new EventWrapper(event->getEvent(), getType()));
151 event->getEvent()->setCalendarType(getType());
152 eventWrapper->convertAbstractEventToPlatformEvent();
154 if ( event->getUpdateAllInstances() || 0>=event->getEvent()->getRecurrenceRule()->getFrequency())
156 // Update all parent and child instances with the given uid.
157 int parentId = event->getEvent()->getId();
159 // First, the parent event.
160 eventWrapper->saveEvent();
162 // Next, all the detached instances.
163 cal_struct *platformEvent = NULL;
164 if(CAL_SUCCESS != calendar_svc_find_event_list(getAccountId(), CAL_VALUE_INT_ORIGINAL_EVENT_ID, (void*) parentId, &iter)) {
165 LogInfo("No detached instances found.");
168 while (CAL_SUCCESS == calendar_svc_iter_next(iter)) {
169 platformEvent = NULL;
170 if (CAL_SUCCESS != calendar_svc_iter_get_info(iter, &platformEvent)) {
171 ThrowMsg(PlatformException, "Can't get event info.");
174 int detachedEventId = calendar_svc_struct_get_int(platformEvent, CAL_VALUE_INT_INDEX);
175 std::time_t detachedStartTime = calendar_svc_struct_get_time(platformEvent,
176 CAL_VALUE_GMT_START_DATE_TIME,
178 std::time_t detachedEndTime = calendar_svc_struct_get_time(platformEvent,
179 CAL_VALUE_GMT_END_DATE_TIME,
182 DPL::ScopedPtr<EventWrapper> eventWrapperChild(new EventWrapper(event->getEvent(), getType()));
183 eventWrapperChild->convertAbstractEventToPlatformEvent();
184 if (CAL_SUCCESS != calendar_svc_struct_set_int(eventWrapperChild->getPlatformEvent(),
187 ThrowMsg(PlatformException, "Can't set event Id.");
189 if (CAL_SUCCESS != calendar_svc_struct_set_int(eventWrapperChild->getPlatformEvent(),
190 CAL_VALUE_INT_ORIGINAL_EVENT_ID,
192 ThrowMsg(PlatformException, "Can't set parent Id.");
194 if (CAL_SUCCESS != calendar_svc_struct_set_time(eventWrapperChild->getPlatformEvent(),
195 CAL_VALUE_GMT_START_DATE_TIME,
197 detachedStartTime)) {
198 ThrowMsg(PlatformException, "Can't set start time.");
200 if (CAL_SUCCESS != calendar_svc_struct_set_time(eventWrapperChild->getPlatformEvent(),
201 CAL_VALUE_GMT_END_DATE_TIME,
204 ThrowMsg(PlatformException, "Can't set end time.");
206 if (CAL_SUCCESS != calendar_svc_struct_set_int(eventWrapperChild->getPlatformEvent(),
207 CAL_VALUE_INT_REPEAT_TERM,
209 ThrowMsg(PlatformException, "Can't set repeat term.");
212 eventWrapperChild->saveEvent();
213 LogDebug("Updated a detached event by id: "<<detachedEventId);
218 LogDebug("Update the exception record");
219 DPL::ScopedPtr<EventWrapper> eventWrapperChild(new EventWrapper(event->getEvent(), getType()));
220 eventWrapperChild->convertAbstractEventToPlatformEvent();
221 if ( CAL_SUCCESS!=calendar_svc_struct_set_int(eventWrapperChild->getPlatformEvent(),
222 CAL_VALUE_INT_ORIGINAL_EVENT_ID, event->getEvent()->getId()) ) {
223 ThrowMsg(PlatformException, "cannot save exception event");
225 // Use "CAL_VALUE_GMT_COMPLETED_DATE_TIME" as the recurrence id saving point.
226 if ( CAL_SUCCESS!=calendar_svc_struct_set_time(eventWrapperChild->getPlatformEvent(),
227 CAL_VALUE_GMT_COMPLETED_DATE_TIME, CAL_TZ_FLAG_GMT, event->getEvent()->getRecurrenceId()) ) {
228 ThrowMsg(PlatformException, "cannot save recurrence id");
230 LogInfo("Saved the rid for the child: "<<event->getEvent()->getRecurrenceId());
232 if (CAL_SUCCESS!=calendar_svc_struct_set_int(eventWrapperChild->getPlatformEvent(),
233 CAL_VALUE_INT_REPEAT_TERM, CAL_REPEAT_NONE) ) {
234 ThrowMsg(PlatformException, "cannot save exception event");
236 int childId = calendar_svc_insert(eventWrapperChild->getPlatformEvent());
238 ThrowMsg(PlatformException, "cannot save exception event");
242 cal_value *value = calendar_svc_value_new(CAL_VALUE_LST_EXCEPTION_DATE);
243 if (CAL_SUCCESS!=calendar_svc_value_set_time(value, CAL_VALUE_GMT_EXCEPTION_DATE_TIME, CAL_TZ_FLAG_GMT, event->getEvent()->getRecurrenceId()) ) {
244 ThrowMsg(PlatformException, "cannot save the exception date");
246 LogInfo("Saved the exception date: "<<event->getEvent()->getRecurrenceId());
248 if (CAL_SUCCESS!=calendar_svc_value_set_int(value, CAL_VALUE_INT_EXCEPTION_DATE_ID, childId)) {
249 ThrowMsg(PlatformException, "cannot save the exception parent event");
251 LogInfo("Saved the exception id: "<<childId);
253 eventWrapper->loadEvent(event->getEvent()->getId());
254 calendar_svc_struct_get_list(eventWrapper->getPlatformEvent(), CAL_VALUE_LST_EXCEPTION_DATE, &list);
255 list = g_list_append(list, value);
256 if (CAL_SUCCESS!=calendar_svc_struct_store_list(eventWrapper->getPlatformEvent(), CAL_VALUE_LST_EXCEPTION_DATE, list)) {
257 ThrowMsg(PlatformException, "cannot save the exception parent event");
259 calendar_svc_update(eventWrapper->getPlatformEvent());
261 event->getEvent()->setIsDetached(true);
264 event->setResult(true);
268 LogWarning("Exception: "<<_rethrown_exception.GetMessage());
269 event->setResult(false);
270 event->setExceptionCode(ExceptionCodes::UnknownException);
274 calendar_svc_iter_remove(&iter);
278 void Calendar::OnRequestReceived(const IEventUpdateEventsPtr &events)
282 cal_iter *iter = NULL;
285 if (events->getEvents()->empty()) {
286 ThrowMsg(NullPointerException, "Item vector is empty.");
289 // Update the vector of events iteratively
290 bool failedUpdating = false;
291 for(unsigned int i=0; i<events->getEvents()->size(); i++)
293 if (events->checkCancelled()) {
294 events->setCancelAllowed(true);
295 events->setResult(true);
299 CalendarEventPtr thisEvent = events->getEvents()->at(i);
300 if (!thisEvent->getIdIsSet()) {
301 ThrowMsg(InvalidArgumentException, "Item id is not set.");
303 DPL::ScopedPtr<EventWrapper> eventWrapper(new EventWrapper(thisEvent, getType()));
304 events->getEvents()->at(i)->setCalendarType(getType());
305 eventWrapper->convertAbstractEventToPlatformEvent();
308 if (events->getUpdateAllInstances() || 0>=thisEvent->getRecurrenceRule()->getFrequency())
310 // Update all parent and child instances with the given uid.
311 int parentId = thisEvent->getId();
313 // First, the parent event.
314 eventWrapper->saveEvent();
316 // Next, all the detached instances.
317 cal_struct *platformEvent = NULL;
318 if(CAL_SUCCESS != calendar_svc_find_event_list(getAccountId(), CAL_VALUE_INT_ORIGINAL_EVENT_ID, (void*) parentId, &iter)) {
319 LogInfo("No detached instances found.");
322 while (CAL_SUCCESS == calendar_svc_iter_next(iter)) {
323 platformEvent = NULL;
324 if (CAL_SUCCESS != calendar_svc_iter_get_info(iter, &platformEvent)) {
325 ThrowMsg(PlatformException, "Can't get event info.");
328 int detachedEventId = calendar_svc_struct_get_int(platformEvent, CAL_VALUE_INT_INDEX);
329 std::time_t detachedStartTime = calendar_svc_struct_get_time(platformEvent,
330 CAL_VALUE_GMT_START_DATE_TIME,
332 std::time_t detachedEndTime = calendar_svc_struct_get_time(platformEvent,
333 CAL_VALUE_GMT_END_DATE_TIME,
336 DPL::ScopedPtr<EventWrapper> eventWrapperChild(new EventWrapper(thisEvent, getType()));
337 eventWrapperChild->convertAbstractEventToPlatformEvent();
338 if (CAL_SUCCESS != calendar_svc_struct_set_int(eventWrapperChild->getPlatformEvent(),
341 ThrowMsg(PlatformException, "Can't set event Id.");
343 if (CAL_SUCCESS != calendar_svc_struct_set_time(eventWrapperChild->getPlatformEvent(),
344 CAL_VALUE_GMT_START_DATE_TIME,
346 detachedStartTime)) {
347 ThrowMsg(PlatformException, "Can't set start time.");
349 if (CAL_SUCCESS != calendar_svc_struct_set_time(eventWrapperChild->getPlatformEvent(),
350 CAL_VALUE_GMT_END_DATE_TIME,
353 ThrowMsg(PlatformException, "Can't set end time.");
356 eventWrapper->saveEvent();
357 LogDebug("Updated a detached event by id: "<<detachedEventId);
362 LogDebug("Update the exception record");
363 DPL::ScopedPtr<EventWrapper> eventWrapperChild(new EventWrapper(thisEvent, getType()));
364 eventWrapperChild->convertAbstractEventToPlatformEvent();
366 if ( CAL_SUCCESS!=calendar_svc_struct_set_int(eventWrapperChild->getPlatformEvent(),
367 CAL_VALUE_INT_ORIGINAL_EVENT_ID, thisEvent->getId()) ) {
368 ThrowMsg(PlatformException, "cannot save parent id.");
370 // Use "CAL_VALUE_GMT_COMPLETED_DATE_TIME" as the recurrence id saving point.
371 if ( CAL_SUCCESS!=calendar_svc_struct_set_time(eventWrapperChild->getPlatformEvent(),
372 CAL_VALUE_GMT_COMPLETED_DATE_TIME, CAL_TZ_FLAG_GMT, thisEvent->getRecurrenceId()) ) {
373 ThrowMsg(PlatformException, "cannot save recurrence id.");
375 LogInfo("Saved the rid for the child: "<<thisEvent->getRecurrenceId());
377 if (CAL_SUCCESS!=calendar_svc_struct_set_int(eventWrapperChild->getPlatformEvent(),
378 CAL_VALUE_INT_REPEAT_TERM, CAL_REPEAT_NONE) ) {
379 ThrowMsg(PlatformException, "cannot save repeat term.");
381 int childId = calendar_svc_insert(eventWrapperChild->getPlatformEvent());
383 ThrowMsg(PlatformException, "cannot save exception event");
387 cal_value *value = calendar_svc_value_new(CAL_VALUE_LST_EXCEPTION_DATE);
388 if (CAL_SUCCESS!=calendar_svc_value_set_time(value, CAL_VALUE_GMT_EXCEPTION_DATE_TIME, CAL_TZ_FLAG_GMT, thisEvent->getRecurrenceId()) ) {
389 ThrowMsg(PlatformException, "cannot save the exception parent event");
391 LogInfo("Saved the exception date: "<<thisEvent->getRecurrenceId());
393 if (CAL_SUCCESS!=calendar_svc_value_set_int(value, CAL_VALUE_INT_EXCEPTION_DATE_ID, childId)) {
394 ThrowMsg(PlatformException, "cannot save the exception parent event");
396 LogInfo("Saved the exception id: "<<childId);
398 calendar_svc_struct_get_list(eventWrapper->getPlatformEvent(), CAL_VALUE_LST_EXCEPTION_DATE, &list);
399 list = g_list_append(list, value);
400 if (CAL_SUCCESS!=calendar_svc_struct_store_list(eventWrapper->getPlatformEvent(), CAL_VALUE_LST_EXCEPTION_DATE, list)) {
401 ThrowMsg(PlatformException, "cannot save the exception parent event");
403 calendar_svc_update(eventWrapper->getPlatformEvent());
405 thisEvent->setIsDetached(true);
407 } Catch (Exception) {
408 LogWarning("Exception: "<<_rethrown_exception.GetMessage());
409 failedUpdating = true;
411 //getUpdateEmitter()->emit(eventPtr);
414 if( false==failedUpdating ) {
415 events->setResult(true);
417 events->setResult(false);
422 LogWarning("Exception: "<<_rethrown_exception.GetMessage());
423 events->setResult(false);
424 events->setExceptionCode(ExceptionCodes::UnknownException);
428 calendar_svc_iter_remove(&iter);
430 events->setCancelAllowed(false);
433 void Calendar::OnRequestReceived(const IEventDeleteEventPtr &event)
438 if (!event->getEventId()) {
439 ThrowMsg(NullPointerException, "Item id is not set.");
442 DPL::ScopedPtr<EventWrapper> eventWrapper(new EventWrapper(getType()));
443 event->getEventId()->setCalendarType(getType());
444 std::istringstream stream(event->getEventId()->getUId());
447 eventWrapper->getAbstractEvent()->setId(id);
449 std::stringstream ss(event->getEventId()->getRecurrenceId());
452 eventWrapper->getAbstractEvent()->setRecurrenceId(rid);
454 LogDebug("id: " << id << ", rid: " << rid);
456 eventWrapper->convertAbstractEventToPlatformEvent();
458 eventWrapper->setCalendarId(getId());
459 eventWrapper->setCalendarAccountId(getAccountId());
460 eventWrapper->deleteEvent();
461 event->setResult(true);
463 Catch (NotFoundException)
465 LogWarning("Exception: "<<_rethrown_exception.GetMessage());
466 event->setResult(false);
467 event->setExceptionCode(ExceptionCodes::NotFoundException);
471 LogWarning("Exception: "<<_rethrown_exception.GetMessage());
472 event->setResult(false);
473 event->setExceptionCode(ExceptionCodes::UnknownException);
477 void Calendar::OnRequestReceived(const IEventGetPtr &event)
482 if (!event->getItemId()) {
483 ThrowMsg(NullPointerException, "Id parameter is NULL");
486 DPL::ScopedPtr<EventWrapper> eventWrapper(new EventWrapper(getType()));
487 std::stringstream ss(event->getItemId()->getUId());
490 eventWrapper->loadEvent(id);
492 event->setItem(eventWrapper->convertPlatformEventToAbstractEvent());
493 event->setResult(true);
495 Catch (NotFoundException)
497 LogWarning("Exception: "<<_rethrown_exception.GetMessage());
498 event->setResult(false);
499 event->setExceptionCode(ExceptionCodes::NotFoundException);
503 LogWarning("Exception: "<<_rethrown_exception.GetMessage());
504 event->setResult(false);
505 event->setExceptionCode(ExceptionCodes::UnknownException);
509 void Calendar::OnRequestReceived(const IEventDeleteEventsPtr &events)
514 if (events->getEventIds()->empty()) {
515 ThrowMsg(NullPointerException, "event vector parameter is empty");
518 // Delete the vector of events iteratively considering the recurrenceId
519 bool failedDeleting = false;
520 for(unsigned int i=0; i<events->getEventIds()->size(); i++)
522 DPL::ScopedPtr<EventWrapper> eventWrapper(new EventWrapper(getType()));
523 events->getEventIds()->at(i)->setCalendarType(getType());
524 std::istringstream stream(events->getEventIds()->at(i)->getUId());
527 eventWrapper->getAbstractEvent()->setId(id);
529 std::stringstream ss(events->getEventIds()->at(i)->getRecurrenceId());
532 eventWrapper->getAbstractEvent()->setRecurrenceId(rid);
533 eventWrapper->convertAbstractEventToPlatformEvent();
536 eventWrapper->setCalendarId(getId());
537 eventWrapper->setCalendarAccountId(getAccountId());
538 eventWrapper->deleteEvent();
539 } Catch (NotFoundException) {
540 LogWarning("Exception: "<<_rethrown_exception.GetMessage());
541 events->setExceptionCode(ExceptionCodes::NotFoundException);
542 failedDeleting = true;
543 } Catch (Exception) {
544 LogWarning("Exception: "<<_rethrown_exception.GetMessage());
545 events->setExceptionCode(ExceptionCodes::PlatformException);
546 failedDeleting = true;
550 if( false==failedDeleting ) {
551 events->setResult(true);
554 events->setResult(false);
557 Catch (NotFoundException)
559 LogWarning("Exception: "<<_rethrown_exception.GetMessage());
560 events->setResult(false);
561 events->setExceptionCode(ExceptionCodes::NotFoundException);
565 LogWarning("Exception: "<<_rethrown_exception.GetMessage());
566 events->setResult(false);
567 events->setExceptionCode(ExceptionCodes::UnknownException);
571 void Calendar::OnRequestReceived(const IEventFindEventsPtr &event)
574 event->setResult(true);
580 CalendarFilterPtr calendarFilter( new CalendarFilter() );
582 std::string query (std::string("SELECT ") + CAL_VALUE_INT_INDEX + " FROM schedule_table");
583 LogInfo("Default query statement: "<<query);
585 TizenApis::Api::Tizen::IFilterVisitorPtr filterTraversal = DPL::StaticPointerCast<TizenApis::Api::Tizen::IFilterVisitor>(calendarFilter);
587 std::stringstream ssType;
588 std::stringstream ssAccount;
589 ssAccount<<getAccountId();
590 if (event->getGenericFilterIsSet()) {
591 TizenApis::Api::Tizen::FilterPtr genericFilter = event->getGenericFilter();
593 TizenApis::Api::Tizen::FilterValidatorPtr validator = CalendarFilterValidatorFactory::getCalendarFilterValidator();
594 bool success = genericFilter->validate(validator);
596 ThrowMsg(InvalidArgumentException, "Invalid filter arguments.");
598 LogInfo("Filter validation has passed.");
601 genericFilter->travel(filterTraversal, 0);
602 LogDebug("Traverse string [" << calendarFilter->getResult() << "]");
603 query.append(calendarFilter->getResult());
604 query.append(std::string(" AND ") + CAL_VALUE_INT_ACCOUNT_ID + " = " + ssAccount.str());
605 if (getType()==CalendarEvent::TASK_TYPE) {
606 ssType<<CALS_CALENDAR_TYPE_TODO;
607 query.append(std::string(" AND ") + CAL_VALUE_INT_TYPE + " = " + ssType.str() + " AND " + "is_deleted = 0");
609 ssType<<CALS_CALENDAR_TYPE_EVENT;
610 query.append(std::string(" AND ") + CAL_VALUE_INT_TYPE + " = " + ssType.str() + " AND " + "is_deleted = 0");
613 query.append(std::string(" WHERE ") + CAL_VALUE_INT_ACCOUNT_ID + " = " + ssAccount.str());
614 if (getType()==CalendarEvent::TASK_TYPE) {
615 ssType<<CALS_CALENDAR_TYPE_TODO;
616 query.append(std::string(" AND ") + CAL_VALUE_INT_TYPE + " = " + ssType.str() + " AND " + "is_deleted = 0");
618 ssType<<CALS_CALENDAR_TYPE_EVENT;
619 query.append(std::string(" AND ") + CAL_VALUE_INT_TYPE + " = " + ssType.str() + " AND " + "is_deleted = 0");
623 if (event->getSortModesIsSet()) {
624 query.append(calendarFilter->makeQuerySortMode(event->getSortModes()));
625 query.append(std::string(";"));
628 LogDebug("Filter query [" << query << "]");
630 calendarFilter->executeQuery(query, event->getEvents());
632 LogDebug("Result count [" << event->getEvents()->size() << "]");
634 calendar_db_finish();
636 // Now load the full calendar item using the retrieved id.
637 for( unsigned int i=0; i<event->getEvents()->size(); i++) {
638 // platformEvent is freed when the wrapper destructor is called.
639 DPL::ScopedPtr<EventWrapper> eventWrapper(new EventWrapper(event->getEvents()->at(i), getType()));
640 eventWrapper->loadEvent(event->getEvents()->at(i)->getId());
642 // If it's a detached event, set the saved rid.
643 if (eventWrapper->getAbstractEvent()->getParentId()>0) {
644 LogInfo("Set the saved rid: "<<calendar_svc_struct_get_time(eventWrapper->getPlatformEvent(), CAL_VALUE_GMT_COMPLETED_DATE_TIME, CAL_TZ_FLAG_GMT));
645 event->getEvents()->at(i)->setRecurrenceId(calendar_svc_struct_get_time(eventWrapper->getPlatformEvent(), CAL_VALUE_GMT_COMPLETED_DATE_TIME, CAL_TZ_FLAG_GMT));
649 Catch (InvalidArgumentException)
651 LogWarning("Exception: "<<_rethrown_exception.GetMessage());
652 event->setResult(false);
653 event->setExceptionCode(ExceptionCodes::InvalidArgumentException);
655 Catch (NotFoundException)
657 LogWarning("Exception: "<<_rethrown_exception.GetMessage());
658 event->setResult(false);
659 event->setExceptionCode(ExceptionCodes::NotFoundException);
663 LogWarning("Exception: "<<_rethrown_exception.GetMessage());
664 event->setResult(false);
665 event->setExceptionCode(ExceptionCodes::UnknownException);
669 void Calendar::OnRequestReceived(const IEventCreateEventFromStringPtr &event)
674 DPL::ScopedPtr<EventWrapper> eventWrapper(new EventWrapper(getType()));
675 eventWrapper->createEventFromString(event->getEventString());
676 event->setEvent(eventWrapper->convertPlatformEventToAbstractEvent());
677 event->getEvent()->setCalendarType(getType());
678 event->setResult(true);
680 Catch(PlatformException)
682 LogWarning("Exception: "<<_rethrown_exception.GetMessage());
683 LogInfo("eventString: " + event->getEventString());
684 event->setResult(false);
685 event->setExceptionCode(ExceptionCodes::InvalidArgumentException);
689 LogWarning("Exception: "<<_rethrown_exception.GetMessage());
690 LogInfo("eventString: " + event->getEventString());
691 event->setResult(false);
692 event->setExceptionCode(ExceptionCodes::UnknownException);
696 void Calendar::OnRequestReceived(const IEventExportEventToStringPtr &event)
701 if (!event->getEvent()) {
702 ThrowMsg(NullPointerException, "event parameter is NULL");
705 DPL::ScopedPtr<EventWrapper> eventWrapper(new EventWrapper(event->getEvent(), getType()));
706 event->getEvent()->setCalendarType(getType());
707 eventWrapper->convertAbstractEventToPlatformEvent();
708 event->setEventString(eventWrapper->exportEventToString());
709 event->setResult(true);
713 LogWarning("Exception: "<<_rethrown_exception.GetMessage());
714 event->setResult(false);
715 event->setExceptionCode(ExceptionCodes::UnknownException);
719 static void eventChangedCb(void *user_data)
723 OnEventsChangedPtr eventPtr(new OnEventsChanged());
726 Calendar *thisCalendar = (Calendar*) user_data;
728 // Determine the status of event change.
729 cal_iter *iter = NULL;
730 cal_struct *platformEvent = NULL;
734 if( CAL_SUCCESS != calendar_svc_get_updated_event_list(thisCalendar->getAccountId(),
735 thisCalendar->getLastChangeFetchTime(),
737 ThrowMsg(PlatformException, "Can't get the updated event list.");
739 while( CAL_SUCCESS == calendar_svc_iter_next(iter) )
741 if ( CAL_SUCCESS != calendar_svc_iter_get_info(iter, &platformEvent) ) {
742 ThrowMsg(PlatformException, "Can't get the calendar info.");
745 index = calendar_svc_struct_get_int(platformEvent, CAL_VALUE_INT_INDEX);
746 syncStatus = calendar_svc_struct_get_int(platformEvent, CAL_VALUE_INT_SYNC_STATUS);
747 LogDebug("index "<<index<<" , syncStatus "<<syncStatus);
748 if ( CAL_SYNC_STATUS_NEW==syncStatus ) {
749 eventPtr->setStatus(OnEventsChanged::ON_ADD);
750 } else if ( CAL_SYNC_STATUS_UPDATED==syncStatus ) {
751 eventPtr->setStatus(OnEventsChanged::ON_UPDATE);
752 } else if ( CAL_SYNC_STATUS_DELETED==syncStatus ) {
753 eventPtr->setStatus(OnEventsChanged::ON_DELETE);
755 if( platformEvent ) {
756 calendar_svc_struct_free(&platformEvent);
758 calendar_svc_iter_remove(&iter);
759 ThrowMsg(PlatformException, "Wrong syncStatus.");
762 DPL::ScopedPtr<EventWrapper> eventWrapper(new EventWrapper(thisCalendar->getType()));
764 eventWrapper->loadEvent(index);
765 } Catch (NotFoundException){
766 LogDebug("Handling deleted event with index: "<<index);
768 eventPtr->addEvent(eventWrapper->getAbstractEvent());
770 if ( CAL_SUCCESS != calendar_svc_struct_free(&platformEvent) ) {
771 ThrowMsg(PlatformException, "Can't free the platform event struct.");
775 if ( CAL_SUCCESS != calendar_svc_iter_remove(&iter) ) {
776 ThrowMsg(PlatformException, "Can't remove the iter.");
779 std::time_t localTime = time(NULL);
780 thisCalendar->setLastChangeFetchTime(localTime);
781 LogInfo("Last change fetch time: "<<thisCalendar->getLastChangeFetchTime());
783 eventPtr->setResult(true);
784 eventPtr->setCalendarType(thisCalendar->getType());
786 if( eventPtr->getEventList()->size() > 0 ) {
787 thisCalendar->m_changeEmitters.emit(eventPtr);
789 LogInfo("No actual changes. Skip signal emission.");
794 LogWarning("Exception: "<<_rethrown_exception.GetMessage());
798 void Calendar::OnRequestReceived(const IEventWatchChangesPtr &event)
803 // Subscribe the watch to the platform just once.
804 if( m_changeEmitters.size()==0 )
806 if( CAL_SUCCESS!=calendar_svc_subscribe_change(eventChangedCb, this) ) {
807 ThrowMsg(PlatformException, "Can't subscribe the db change noti.");
809 // Save the last change fetch time to start watching.
810 std::time_t localTime = time(NULL);
811 setLastChangeFetchTime(localTime);
812 LogInfo("Last change fetch time: "<<getLastChangeFetchTime());
816 m_changeEmitters.attach(event->getEmitter());
817 event->setWatchId(event->getEmitter()->getId());
818 event->setResult(true);
822 LogWarning("Exception: "<<_rethrown_exception.GetMessage());
823 event->setResult(false);
824 event->setExceptionCode(ExceptionCodes::UnknownException);
828 void Calendar::OnRequestReceived(const IEventClearWatchPtr &event)
833 m_changeEmitters.detach(event->getWatchId());
835 if( m_changeEmitters.size()==0 ) {
836 if( CAL_SUCCESS!=calendar_svc_unsubscribe_change(eventChangedCb) ) {
837 ThrowMsg(PlatformException, "Can't unsubscribe the db change noti.");
839 LogDebug("Platform watch cleared successfully.");
842 event->setResult(true);
846 LogWarning("Exception: "<<_rethrown_exception.GetMessage());
847 event->setResult(false);
848 event->setExceptionCode(ExceptionCodes::UnknownException);
852 void Calendar::OnRequestReceived(const IEventExpandEventRecurrencePtr &event)
855 const CalendarEventPtr calEvent = event->getEvent();
856 const std::time_t startDate = event->getStartDate();
857 const std::time_t endDate = event->getEndDate();
858 event->setResult(true);
861 if ( 0 >= calEvent->getRecurrenceRule()->getFrequency())
863 ThrowMsg(PlatformException, "This is not a recurring event.");
866 std::time_t nextStartTime = 0;
867 std::time_t nextEndTime = 0;
869 DPL::ScopedPtr<EventWrapper> eventWrapper(new EventWrapper(CalendarEvent::EVENT_TYPE));
870 // We must load the event from the DB in order to get the auto-calculated repeat end time.
871 eventWrapper->loadEvent(event->getEvent()->getId());
872 //eventWrapper->displayPlatformEvent();
874 while ( CAL_SUCCESS==calendar_svc_util_next_valid_event(eventWrapper->getPlatformEvent(), startDate, endDate, &nextStartTime, &nextEndTime) )
876 LogInfo("Found a next valid event: "<<nextStartTime);
877 DPL::ScopedPtr<EventWrapper> recurringEventWrapper(new EventWrapper(getType()));
878 recurringEventWrapper->loadEvent(calEvent->getId());
880 // Set distintive attributes of each instance.
881 recurringEventWrapper->getAbstractEvent()->setRecurrenceId(nextStartTime);
882 recurringEventWrapper->getAbstractEvent()->setStartTime(nextStartTime);
883 recurringEventWrapper->getAbstractEvent()->setEndTime(nextEndTime);
885 event->addExpandedEvent(recurringEventWrapper->getAbstractEvent());
887 LogInfo("Length of expanded events from parent: "<<event->getExpandedEventList()->size());
889 // Consider the detached events also.
890 cal_iter *iter = NULL;
891 cal_struct *platformEvent = NULL;
892 int parentId = event->getEvent()->getId();
893 if(CAL_SUCCESS != calendar_svc_find_event_list(getAccountId(), CAL_VALUE_INT_ORIGINAL_EVENT_ID, (void*) parentId, &iter)) {
894 LogInfo("No detached instances found.");
897 while (CAL_SUCCESS == calendar_svc_iter_next(iter)) {
898 platformEvent = NULL;
899 if (CAL_SUCCESS != calendar_svc_iter_get_info(iter, &platformEvent)) {
900 ThrowMsg(PlatformException, "Can't get event info.");
903 int detachedEventId = calendar_svc_struct_get_int(platformEvent, CAL_VALUE_INT_INDEX);
904 std::time_t detachedStartTime = calendar_svc_struct_get_time(platformEvent, CAL_VALUE_GMT_START_DATE_TIME, CAL_TZ_FLAG_GMT);
905 std::time_t detachedEndTime = calendar_svc_struct_get_time(platformEvent, CAL_VALUE_GMT_END_DATE_TIME, CAL_TZ_FLAG_GMT);
906 if (detachedStartTime>=startDate && detachedStartTime<=endDate) {
907 LogInfo("Found a valid detached event: "<<detachedStartTime);
908 DPL::ScopedPtr<EventWrapper> detachedEventWrapper(new EventWrapper(getType()));
909 detachedEventWrapper->loadEvent(detachedEventId);
911 // Set the same parent uid to each instances
912 detachedEventWrapper->getAbstractEvent()->setId(parentId);
913 // Set distintive attributes of each instance.
914 detachedEventWrapper->getAbstractEvent()->setRecurrenceId(detachedStartTime);
915 detachedEventWrapper->getAbstractEvent()->setStartTime(detachedStartTime);
916 detachedEventWrapper->getAbstractEvent()->setEndTime(detachedEndTime);
918 event->addExpandedEvent(detachedEventWrapper->getAbstractEvent());
922 LogInfo("Length of total expanded events: "<<event->getExpandedEventList()->size());
926 LogWarning("Exception: "<<_rethrown_exception.GetMessage());
927 event->setResult(false);
928 event->setExceptionCode(ExceptionCodes::UnknownException);