1
19
20 package com.liferay.portlet.calendar.service.impl;
21
22 import com.liferay.portal.PortalException;
23 import com.liferay.portal.SystemException;
24 import com.liferay.portal.im.AIMConnector;
25 import com.liferay.portal.im.ICQConnector;
26 import com.liferay.portal.im.MSNConnector;
27 import com.liferay.portal.im.YMConnector;
28 import com.liferay.portal.kernel.cal.DayAndPosition;
29 import com.liferay.portal.kernel.cal.Recurrence;
30 import com.liferay.portal.kernel.cal.TZSRecurrence;
31 import com.liferay.portal.kernel.log.Log;
32 import com.liferay.portal.kernel.log.LogFactoryUtil;
33 import com.liferay.portal.kernel.mail.MailMessage;
34 import com.liferay.portal.kernel.search.BooleanClauseOccur;
35 import com.liferay.portal.kernel.search.BooleanQuery;
36 import com.liferay.portal.kernel.search.BooleanQueryFactoryUtil;
37 import com.liferay.portal.kernel.search.Field;
38 import com.liferay.portal.kernel.search.Hits;
39 import com.liferay.portal.kernel.search.SearchEngineUtil;
40 import com.liferay.portal.kernel.search.SearchException;
41 import com.liferay.portal.kernel.util.ArrayUtil;
42 import com.liferay.portal.kernel.util.CalendarFactoryUtil;
43 import com.liferay.portal.kernel.util.CalendarUtil;
44 import com.liferay.portal.kernel.util.DateFormats;
45 import com.liferay.portal.kernel.util.GetterUtil;
46 import com.liferay.portal.kernel.util.LocaleUtil;
47 import com.liferay.portal.kernel.util.ReleaseInfo;
48 import com.liferay.portal.kernel.util.StringPool;
49 import com.liferay.portal.kernel.util.StringUtil;
50 import com.liferay.portal.kernel.util.Time;
51 import com.liferay.portal.kernel.util.TimeZoneUtil;
52 import com.liferay.portal.kernel.util.UnmodifiableList;
53 import com.liferay.portal.kernel.util.Validator;
54 import com.liferay.portal.kernel.uuid.PortalUUIDUtil;
55 import com.liferay.portal.model.Company;
56 import com.liferay.portal.model.Contact;
57 import com.liferay.portal.model.ModelHintsUtil;
58 import com.liferay.portal.model.ResourceConstants;
59 import com.liferay.portal.model.User;
60 import com.liferay.portal.service.ServiceContext;
61 import com.liferay.portal.util.PortalUtil;
62 import com.liferay.portal.util.PortletKeys;
63 import com.liferay.portlet.calendar.EventDurationException;
64 import com.liferay.portlet.calendar.EventEndDateException;
65 import com.liferay.portlet.calendar.EventStartDateException;
66 import com.liferay.portlet.calendar.EventTitleException;
67 import com.liferay.portlet.calendar.job.CheckEventJob;
68 import com.liferay.portlet.calendar.model.CalEvent;
69 import com.liferay.portlet.calendar.model.impl.CalEventImpl;
70 import com.liferay.portlet.calendar.service.base.CalEventLocalServiceBaseImpl;
71 import com.liferay.portlet.calendar.social.CalendarActivityKeys;
72 import com.liferay.portlet.calendar.util.CalUtil;
73 import com.liferay.portlet.calendar.util.Indexer;
74 import com.liferay.portlet.expando.model.ExpandoBridge;
75 import com.liferay.util.TimeZoneSensitive;
76 import com.liferay.util.servlet.ServletResponseUtil;
77
78 import java.io.BufferedOutputStream;
79 import java.io.File;
80 import java.io.FileOutputStream;
81 import java.io.FileReader;
82 import java.io.IOException;
83 import java.io.OutputStream;
84
85 import java.text.DateFormat;
86
87 import java.util.ArrayList;
88 import java.util.Calendar;
89 import java.util.Date;
90 import java.util.Iterator;
91 import java.util.List;
92 import java.util.Locale;
93 import java.util.Map;
94 import java.util.TimeZone;
95
96 import javax.mail.internet.InternetAddress;
97
98 import javax.portlet.PortletPreferences;
99
100 import net.fortuna.ical4j.data.CalendarBuilder;
101 import net.fortuna.ical4j.data.CalendarOutputter;
102 import net.fortuna.ical4j.data.ParserException;
103 import net.fortuna.ical4j.model.Component;
104 import net.fortuna.ical4j.model.DateTime;
105 import net.fortuna.ical4j.model.Dur;
106 import net.fortuna.ical4j.model.Parameter;
107 import net.fortuna.ical4j.model.Property;
108 import net.fortuna.ical4j.model.PropertyList;
109 import net.fortuna.ical4j.model.Recur;
110 import net.fortuna.ical4j.model.WeekDay;
111 import net.fortuna.ical4j.model.component.VEvent;
112 import net.fortuna.ical4j.model.parameter.Value;
113 import net.fortuna.ical4j.model.property.CalScale;
114 import net.fortuna.ical4j.model.property.Comment;
115 import net.fortuna.ical4j.model.property.DateProperty;
116 import net.fortuna.ical4j.model.property.Description;
117 import net.fortuna.ical4j.model.property.DtEnd;
118 import net.fortuna.ical4j.model.property.DtStart;
119 import net.fortuna.ical4j.model.property.Duration;
120 import net.fortuna.ical4j.model.property.ProdId;
121 import net.fortuna.ical4j.model.property.RRule;
122 import net.fortuna.ical4j.model.property.Summary;
123 import net.fortuna.ical4j.model.property.Uid;
124 import net.fortuna.ical4j.model.property.Version;
125
126
136 public class CalEventLocalServiceImpl extends CalEventLocalServiceBaseImpl {
137
138 public CalEvent addEvent(
139 long userId, String title, String description, int startDateMonth,
140 int startDateDay, int startDateYear, int startDateHour,
141 int startDateMinute, int endDateMonth, int endDateDay,
142 int endDateYear, int durationHour, int durationMinute,
143 boolean allDay, boolean timeZoneSensitive, String type,
144 boolean repeating, TZSRecurrence recurrence, int remindBy,
145 int firstReminder, int secondReminder,
146 ServiceContext serviceContext)
147 throws PortalException, SystemException {
148
149 return addEvent(
150 null, userId, title, description, startDateMonth, startDateDay,
151 startDateYear, startDateHour, startDateMinute, endDateMonth,
152 endDateDay, endDateYear, durationHour, durationMinute, allDay,
153 timeZoneSensitive, type, repeating, recurrence, remindBy,
154 firstReminder, secondReminder, serviceContext);
155 }
156
157 public CalEvent addEvent(
158 String uuid, long userId, String title, String description,
159 int startDateMonth, int startDateDay, int startDateYear,
160 int startDateHour, int startDateMinute, int endDateMonth,
161 int endDateDay, int endDateYear, int durationHour,
162 int durationMinute, boolean allDay, boolean timeZoneSensitive,
163 String type, boolean repeating, TZSRecurrence recurrence,
164 int remindBy, int firstReminder, int secondReminder,
165 ServiceContext serviceContext)
166 throws PortalException, SystemException {
167
168
170 User user = userPersistence.findByPrimaryKey(userId);
171 long groupId = serviceContext.getScopeGroupId();
172 Date now = new Date();
173
174 Locale locale = null;
175 TimeZone timeZone = null;
176
177 if (timeZoneSensitive) {
178 locale = user.getLocale();
179 timeZone = user.getTimeZone();
180 }
181 else {
182 locale = LocaleUtil.getDefault();
183 timeZone = TimeZoneUtil.getDefault();
184 }
185
186 Calendar startDate = CalendarFactoryUtil.getCalendar(timeZone, locale);
187
188 startDate.set(Calendar.MONTH, startDateMonth);
189 startDate.set(Calendar.DATE, startDateDay);
190 startDate.set(Calendar.YEAR, startDateYear);
191 startDate.set(Calendar.HOUR_OF_DAY, startDateHour);
192 startDate.set(Calendar.MINUTE, startDateMinute);
193 startDate.set(Calendar.SECOND, 0);
194 startDate.set(Calendar.MILLISECOND, 0);
195
196 Calendar endDate = CalendarFactoryUtil.getCalendar(timeZone, locale);
197
198 endDate.set(Calendar.MONTH, endDateMonth);
199 endDate.set(Calendar.DATE, endDateDay);
200 endDate.set(Calendar.YEAR, endDateYear);
201 endDate.set(Calendar.HOUR_OF_DAY, 23);
202 endDate.set(Calendar.MINUTE, 59);
203 endDate.set(Calendar.SECOND, 59);
204 endDate.set(Calendar.MILLISECOND, 999);
205
206 if (allDay) {
207 startDate.set(Calendar.HOUR_OF_DAY, 0);
208 startDate.set(Calendar.MINUTE, 0);
209
210 durationHour = 24;
211 durationMinute = 0;
212 }
213
214 validate(
215 title, startDateMonth, startDateDay, startDateYear, endDateMonth,
216 endDateDay, endDateYear, durationHour, durationMinute, allDay,
217 repeating);
218
219 long eventId = counterLocalService.increment();
220
221 CalEvent event = calEventPersistence.create(eventId);
222
223 event.setUuid(uuid);
224 event.setGroupId(groupId);
225 event.setCompanyId(user.getCompanyId());
226 event.setUserId(user.getUserId());
227 event.setUserName(user.getFullName());
228 event.setCreateDate(now);
229 event.setModifiedDate(now);
230 event.setTitle(title);
231 event.setDescription(description);
232 event.setStartDate(startDate.getTime());
233 event.setEndDate(endDate.getTime());
234 event.setDurationHour(durationHour);
235 event.setDurationMinute(durationMinute);
236 event.setAllDay(allDay);
237 event.setTimeZoneSensitive(timeZoneSensitive);
238 event.setType(type);
239 event.setRepeating(repeating);
240 event.setRecurrenceObj(recurrence);
241 event.setRemindBy(remindBy);
242 event.setFirstReminder(firstReminder);
243 event.setSecondReminder(secondReminder);
244
245 calEventPersistence.update(event, false);
246
247
249 if (serviceContext.getAddCommunityPermissions() ||
250 serviceContext.getAddGuestPermissions()) {
251
252 addEventResources(
253 event, serviceContext.getAddCommunityPermissions(),
254 serviceContext.getAddGuestPermissions());
255 }
256 else {
257 addEventResources(
258 event, serviceContext.getCommunityPermissions(),
259 serviceContext.getGuestPermissions());
260 }
261
262
264 ExpandoBridge expandoBridge = event.getExpandoBridge();
265
266 expandoBridge.setAttributes(serviceContext);
267
268
270 socialActivityLocalService.addActivity(
271 userId, groupId, CalEvent.class.getName(), eventId,
272 CalendarActivityKeys.ADD_EVENT, StringPool.BLANK, 0);
273
274
276 reIndex(event);
277
278
280 CalEventLocalUtil.clearEventsPool(event.getGroupId());
281
282 return event;
283 }
284
285 public void addEventResources(
286 long eventId, boolean addCommunityPermissions,
287 boolean addGuestPermissions)
288 throws PortalException, SystemException {
289
290 CalEvent event = calEventPersistence.findByPrimaryKey(eventId);
291
292 addEventResources(
293 event, addCommunityPermissions, addGuestPermissions);
294 }
295
296 public void addEventResources(
297 CalEvent event, boolean addCommunityPermissions,
298 boolean addGuestPermissions)
299 throws PortalException, SystemException {
300
301 resourceLocalService.addResources(
302 event.getCompanyId(), event.getGroupId(), event.getUserId(),
303 CalEvent.class.getName(), event.getEventId(), false,
304 addCommunityPermissions, addGuestPermissions);
305 }
306
307 public void addEventResources(
308 long eventId, String[] communityPermissions,
309 String[] guestPermissions)
310 throws PortalException, SystemException {
311
312 CalEvent event = calEventPersistence.findByPrimaryKey(eventId);
313
314 addEventResources(event, communityPermissions, guestPermissions);
315 }
316
317 public void addEventResources(
318 CalEvent event, String[] communityPermissions,
319 String[] guestPermissions)
320 throws PortalException, SystemException {
321
322 resourceLocalService.addModelResources(
323 event.getCompanyId(), event.getGroupId(), event.getUserId(),
324 CalEvent.class.getName(), event.getEventId(), communityPermissions,
325 guestPermissions);
326 }
327
328 public void checkEvents() throws PortalException, SystemException {
329 Iterator<CalEvent> itr = calEventPersistence.findByRemindBy(
330 CalEventImpl.REMIND_BY_NONE).iterator();
331
332 while (itr.hasNext()) {
333 CalEvent event = itr.next();
334
335 User user = userPersistence.fetchByPrimaryKey(event.getUserId());
336
337 if (user == null) {
338 deleteEvent(event);
339
340 continue;
341 }
342
343 Calendar now = CalendarFactoryUtil.getCalendar(
344 user.getTimeZone(), user.getLocale());
345
346 if (!event.isTimeZoneSensitive()) {
347 Calendar temp = CalendarFactoryUtil.getCalendar();
348
349 temp.setTime(Time.getDate(now));
350
351 now = temp;
352 }
353
354 Calendar startDate = null;
355
356 if (event.isTimeZoneSensitive()) {
357 startDate = CalendarFactoryUtil.getCalendar(
358 user.getTimeZone(), user.getLocale());
359 }
360 else {
361 startDate = CalendarFactoryUtil.getCalendar();
362 }
363
364 if (event.isRepeating()) {
365 double daysToCheck = Math.ceil(
366 CalEventImpl.REMINDERS[CalEventImpl.REMINDERS.length - 1] /
367 Time.DAY);
368
369 Calendar cal = (Calendar)now.clone();
370
371 for (int i = 0; i <= daysToCheck; i++) {
372 Recurrence recurrence = event.getRecurrenceObj();
373
374 Calendar tzICal = CalendarFactoryUtil.getCalendar(
375 cal.get(Calendar.YEAR), cal.get(Calendar.MONTH),
376 cal.get(Calendar.DATE));
377
378 Calendar recurrenceCal = getRecurrenceCal(
379 cal, tzICal, event);
380
381 if (recurrence.isInRecurrence(recurrenceCal)) {
382 remindUser(event, user, recurrenceCal, now);
383 }
384
385 cal.add(Calendar.DAY_OF_YEAR, 1);
386 }
387 }
388 else {
389 startDate.setTime(event.getStartDate());
390
391 remindUser(event, user, startDate, now);
392 }
393 }
394 }
395
396 public void deleteEvent(long eventId)
397 throws PortalException, SystemException {
398
399 CalEvent event = calEventPersistence.findByPrimaryKey(eventId);
400
401 deleteEvent(event);
402 }
403
404 public void deleteEvent(CalEvent event)
405 throws PortalException, SystemException {
406
407
409 CalEventLocalUtil.clearEventsPool(event.getGroupId());
410
411
413 socialActivityLocalService.deleteActivities(
414 CalEvent.class.getName(), event.getEventId());
415
416
418 expandoValueLocalService.deleteValues(
419 CalEvent.class.getName(), event.getEventId());
420
421
423 resourceLocalService.deleteResource(
424 event.getCompanyId(), CalEvent.class.getName(),
425 ResourceConstants.SCOPE_INDIVIDUAL, event.getEventId());
426
427
429 calEventPersistence.remove(event);
430 }
431
432 public void deleteEvents(long groupId)
433 throws PortalException, SystemException {
434
435 Iterator<CalEvent> itr = calEventPersistence.findByGroupId(
436 groupId).iterator();
437
438 while (itr.hasNext()) {
439 CalEvent event = itr.next();
440
441 deleteEvent(event);
442 }
443 }
444
445 public File exportEvent(long userId, long eventId)
446 throws PortalException, SystemException {
447
448 List<CalEvent> events = new ArrayList<CalEvent>();
449
450 CalEvent event = calEventPersistence.findByPrimaryKey(eventId);
451
452 events.add(event);
453
454 return exportICal4j(toICalCalendar(userId, events), null);
455 }
456
457 public File exportGroupEvents(long userId, long groupId, String fileName)
458 throws PortalException, SystemException {
459
460 List<CalEvent> events = calEventPersistence.findByGroupId(groupId);
461
462 return exportICal4j(toICalCalendar(userId, events), fileName);
463 }
464
465 public CalEvent getEvent(long eventId)
466 throws PortalException, SystemException {
467
468 return calEventPersistence.findByPrimaryKey(eventId);
469 }
470
471 public List<CalEvent> getEvents(
472 long groupId, String type, int start, int end)
473 throws SystemException {
474
475 if (Validator.isNull(type)) {
476 return calEventPersistence.findByGroupId(groupId, start, end);
477 }
478 else {
479 return calEventPersistence.findByG_T(groupId, type, start, end);
480 }
481 }
482
483 public List<CalEvent> getEvents(long groupId, Calendar cal)
484 throws SystemException {
485
486 Map<String, List<CalEvent>> eventsPool =
487 CalEventLocalUtil.getEventsPool(groupId);
488
489 String key = CalUtil.toString(cal);
490
491 List<CalEvent> events = eventsPool.get(key);
492
493 if (events == null) {
494
495
497 List<CalEvent> events1 = calEventFinder.findByG_SD(
498 groupId, CalendarUtil.getGTDate(cal),
499 CalendarUtil.getLTDate(cal), true);
500
501
503 Calendar tzICal = CalendarFactoryUtil.getCalendar(
504 cal.get(Calendar.YEAR), cal.get(Calendar.MONTH),
505 cal.get(Calendar.DATE));
506
507 List<CalEvent> events2 = calEventFinder.findByG_SD(
508 groupId, CalendarUtil.getGTDate(tzICal),
509 CalendarUtil.getLTDate(tzICal), false);
510
511
513 events = new ArrayList<CalEvent>();
514
515 events.addAll(events1);
516 events.addAll(events2);
517
518
520 Iterator<CalEvent> itr = getRepeatingEvents(groupId).iterator();
521
522 while (itr.hasNext()) {
523 CalEvent event = itr.next();
524
525 TZSRecurrence recurrence = event.getRecurrenceObj();
526
527 try {
528
529
531 if ((recurrence.getFrequency() !=
532 Recurrence.NO_RECURRENCE) &&
533 (recurrence.getInterval() <= 0)) {
534
535 recurrence.setInterval(1);
536
537 event.setRecurrenceObj(recurrence);
538
539 event = calEventPersistence.update(event, false);
540
541 recurrence = event.getRecurrenceObj();
542 }
543
544 if (recurrence.isInRecurrence(
545 getRecurrenceCal(cal, tzICal, event))) {
546
547 events.add(event);
548 }
549 }
550 catch (Exception e) {
551 _log.error(e.getMessage());
552 }
553 }
554
555 events = new UnmodifiableList<CalEvent>(events);
556
557 eventsPool.put(key, events);
558 }
559
560 return events;
561 }
562
563 public List<CalEvent> getEvents(long groupId, Calendar cal, String type)
564 throws SystemException {
565
566 List<CalEvent> events = getEvents(groupId, cal);
567
568 if (Validator.isNull(type)) {
569 return events;
570 }
571 else {
572 events = new ArrayList<CalEvent>(events);
573
574 Iterator<CalEvent> itr = events.iterator();
575
576 while (itr.hasNext()) {
577 CalEvent event = itr.next();
578
579 if (!event.getType().equals(type)) {
580 itr.remove();
581 }
582 }
583
584 return events;
585 }
586 }
587
588 public int getEventsCount(long groupId, String type)
589 throws SystemException {
590
591 if (Validator.isNull(type)) {
592 return calEventPersistence.countByGroupId(groupId);
593 }
594 else {
595 return calEventPersistence.countByG_T(groupId, type);
596 }
597 }
598
599 public List<CalEvent> getRepeatingEvents(long groupId)
600 throws SystemException {
601
602 Map<String, List<CalEvent>> eventsPool =
603 CalEventLocalUtil.getEventsPool(groupId);
604
605 String key = "recurrence";
606
607 List<CalEvent> events = eventsPool.get(key);
608
609 if (events == null) {
610 events = calEventPersistence.findByG_R(groupId, true);
611
612 events = new UnmodifiableList<CalEvent>(events);
613
614 eventsPool.put(key, events);
615 }
616
617 return events;
618 }
619
620 public boolean hasEvents(long groupId, Calendar cal)
621 throws SystemException {
622
623 return hasEvents(groupId, cal, null);
624 }
625
626 public boolean hasEvents(long groupId, Calendar cal, String type)
627 throws SystemException {
628
629 if (getEvents(groupId, cal, type).size() > 0) {
630 return true;
631 }
632 else {
633 return false;
634 }
635 }
636
637 public void importICal4j(long userId, long groupId, File file)
638 throws PortalException, SystemException {
639
640 FileReader fileReader = null;
641
642 try {
643 fileReader = new FileReader(file);
644
645 CalendarBuilder builder = new CalendarBuilder();
646
647 net.fortuna.ical4j.model.Calendar calendar = builder.build(
648 fileReader);
649
650 Iterator<VEvent> itr = calendar.getComponents(
651 Component.VEVENT).iterator();
652
653 while (itr.hasNext()) {
654 VEvent vEvent = itr.next();
655
656 importICal4j(userId, groupId, vEvent);
657 }
658 }
659 catch (IOException ioe) {
660 throw new SystemException(ioe.getMessage());
661 }
662 catch (ParserException pe) {
663 throw new SystemException(pe.getMessage());
664 }
665 finally {
666 try {
667 fileReader.close();
668 }
669 catch (IOException ioe) {
670 _log.error(ioe);
671 }
672 }
673 }
674
675 public void reIndex(long eventId) throws SystemException {
676 if (SearchEngineUtil.isIndexReadOnly()) {
677 return;
678 }
679
680 CalEvent event = calEventPersistence.fetchByPrimaryKey(eventId);
681
682 if (event == null) {
683 return;
684 }
685
686 reIndex(event);
687 }
688
689 public void reIndex(CalEvent event) throws SystemException {
690 long companyId = event.getCompanyId();
691 long groupId = event.getGroupId();
692 long userId = event.getUserId();
693 long eventId = event.getEventId();
694 String userName = event.getUserName();
695 String title = event.getTitle();
696 String description = event.getDescription();
697 Date modifiedDate = event.getModifiedDate();
698
699 String[] tagsEntries = tagsEntryLocalService.getEntryNames(
700 CalEvent.class.getName(), eventId);
701
702 ExpandoBridge expandoBridge = event.getExpandoBridge();
703
704 try {
705 Indexer.updateEvent(
706 companyId, groupId, userId, userName, eventId, title,
707 description, modifiedDate, tagsEntries, expandoBridge);
708 }
709 catch (SearchException se) {
710 _log.error("Reindexing " + eventId, se);
711 }
712 }
713
714 public void reIndex(String[] ids) throws SystemException {
715 if (SearchEngineUtil.isIndexReadOnly()) {
716 return;
717 }
718
719 long companyId = GetterUtil.getLong(ids[0]);
720
721 try {
722 reIndexEvents(companyId);
723 }
724 catch (SystemException se) {
725 throw se;
726 }
727 catch (Exception e) {
728 throw new SystemException(e);
729 }
730 }
731
732 public Hits search(
733 long companyId, long groupId, long userId, long ownerUserId,
734 String keywords, int start, int end)
735 throws SystemException {
736
737 try {
738 BooleanQuery contextQuery = BooleanQueryFactoryUtil.create();
739
740 contextQuery.addRequiredTerm(Field.PORTLET_ID, Indexer.PORTLET_ID);
741
742 if (groupId > 0) {
743 contextQuery.addRequiredTerm(Field.GROUP_ID, groupId);
744 }
745
746 if (ownerUserId > 0) {
747 contextQuery.addRequiredTerm(Field.USER_ID, ownerUserId);
748 }
749
750 BooleanQuery searchQuery = BooleanQueryFactoryUtil.create();
751
752 if (Validator.isNotNull(keywords)) {
753 searchQuery.addTerm(Field.USER_NAME, keywords);
754 searchQuery.addTerm(Field.TITLE, keywords);
755 searchQuery.addTerm(Field.DESCRIPTION, keywords);
756 searchQuery.addTerm(Field.TAGS_ENTRIES, keywords);
757 }
758
759 BooleanQuery fullQuery = BooleanQueryFactoryUtil.create();
760
761 fullQuery.add(contextQuery, BooleanClauseOccur.MUST);
762
763 if (searchQuery.clauses().size() > 0) {
764 fullQuery.add(searchQuery, BooleanClauseOccur.MUST);
765 }
766
767 return SearchEngineUtil.search(
768 companyId, groupId, userId, CalEvent.class.getName(), fullQuery,
769 start, end);
770 }
771 catch (Exception e) {
772 throw new SystemException(e);
773 }
774 }
775
776 public CalEvent updateEvent(
777 long userId, long eventId, String title, String description,
778 int startDateMonth, int startDateDay, int startDateYear,
779 int startDateHour, int startDateMinute, int endDateMonth,
780 int endDateDay, int endDateYear, int durationHour,
781 int durationMinute, boolean allDay, boolean timeZoneSensitive,
782 String type, boolean repeating, TZSRecurrence recurrence,
783 int remindBy, int firstReminder, int secondReminder,
784 ServiceContext serviceContext)
785 throws PortalException, SystemException {
786
787
789 User user = userPersistence.findByPrimaryKey(userId);
790
791 Locale locale = null;
792 TimeZone timeZone = null;
793
794 if (timeZoneSensitive) {
795 locale = user.getLocale();
796 timeZone = user.getTimeZone();
797 }
798 else {
799 locale = LocaleUtil.getDefault();
800 timeZone = TimeZoneUtil.getDefault();
801 }
802
803 Calendar startDate = CalendarFactoryUtil.getCalendar(timeZone, locale);
804
805 startDate.set(Calendar.MONTH, startDateMonth);
806 startDate.set(Calendar.DATE, startDateDay);
807 startDate.set(Calendar.YEAR, startDateYear);
808 startDate.set(Calendar.HOUR_OF_DAY, startDateHour);
809 startDate.set(Calendar.MINUTE, startDateMinute);
810 startDate.set(Calendar.SECOND, 0);
811 startDate.set(Calendar.MILLISECOND, 0);
812
813 Calendar endDate = CalendarFactoryUtil.getCalendar(timeZone, locale);
814
815 endDate.set(Calendar.MONTH, endDateMonth);
816 endDate.set(Calendar.DATE, endDateDay);
817 endDate.set(Calendar.YEAR, endDateYear);
818 endDate.set(Calendar.HOUR_OF_DAY, 23);
819 endDate.set(Calendar.MINUTE, 59);
820 endDate.set(Calendar.SECOND, 59);
821 endDate.set(Calendar.MILLISECOND, 999);
822
823 if (allDay) {
824 startDate.set(Calendar.HOUR_OF_DAY, 0);
825 startDate.set(Calendar.MINUTE, 0);
826
827 durationHour = 24;
828 durationMinute = 0;
829 }
830
831 validate(
832 title, startDateMonth, startDateDay, startDateYear, endDateMonth,
833 endDateDay, endDateYear, durationHour, durationMinute, allDay,
834 repeating);
835
836 CalEvent event = calEventPersistence.findByPrimaryKey(eventId);
837
838 event.setModifiedDate(new Date());
839 event.setTitle(title);
840 event.setDescription(description);
841 event.setStartDate(startDate.getTime());
842 event.setEndDate(endDate.getTime());
843 event.setDurationHour(durationHour);
844 event.setDurationMinute(durationMinute);
845 event.setAllDay(allDay);
846 event.setTimeZoneSensitive(timeZoneSensitive);
847 event.setType(type);
848 event.setRepeating(repeating);
849 event.setRecurrenceObj(recurrence);
850 event.setRemindBy(remindBy);
851 event.setFirstReminder(firstReminder);
852 event.setSecondReminder(secondReminder);
853
854 calEventPersistence.update(event, false);
855
856
858 ExpandoBridge expandoBridge = event.getExpandoBridge();
859
860 expandoBridge.setAttributes(serviceContext);
861
862
864 socialActivityLocalService.addActivity(
865 userId, event.getGroupId(), CalEvent.class.getName(), eventId,
866 CalendarActivityKeys.UPDATE_EVENT, StringPool.BLANK, 0);
867
868
870 reIndex(event);
871
872
874 CalEventLocalUtil.clearEventsPool(event.getGroupId());
875
876 return event;
877 }
878
879 protected File exportICal4j(
880 net.fortuna.ical4j.model.Calendar cal, String fileName)
881 throws SystemException {
882
883 OutputStream os = null;
884
885 try {
886 String extension = ".ics";
887
888 if (Validator.isNull(fileName)) {
889 fileName = "liferay.";
890 }
891 else {
892 int pos = fileName.lastIndexOf(StringPool.PERIOD);
893
894 if (pos != -1) {
895 extension = fileName.substring(pos);
896 fileName = fileName.substring(0, pos);
897 }
898 }
899
900 File file = File.createTempFile(fileName, extension);
901
902 os = new BufferedOutputStream(new FileOutputStream(file.getPath()));
903
904 CalendarOutputter calOutput = new CalendarOutputter();
905
906 if (cal.getComponents().isEmpty()) {
907 calOutput.setValidating(false);
908 }
909
910 calOutput.output(cal, os);
911
912 return file;
913 }
914 catch (Exception e) {
915 _log.error(e, e);
916
917 throw new SystemException(e);
918 }
919 finally {
920 ServletResponseUtil.cleanUp(os);
921 }
922 }
923
924 protected Calendar getRecurrenceCal(
925 Calendar cal, Calendar tzICal, CalEvent event) {
926
927 Calendar eventCal = CalendarFactoryUtil.getCalendar();
928 eventCal.setTime(event.getStartDate());
929
930 Calendar recurrenceCal = (Calendar)tzICal.clone();
931 recurrenceCal.set(
932 Calendar.HOUR_OF_DAY, eventCal.get(Calendar.HOUR_OF_DAY));
933 recurrenceCal.set(
934 Calendar.MINUTE, eventCal.get(Calendar.MINUTE));
935 recurrenceCal.set(Calendar.SECOND, 0);
936 recurrenceCal.set(Calendar.MILLISECOND, 0);
937
938 if (event.isTimeZoneSensitive()) {
939 int gmtDate = eventCal.get(Calendar.DATE);
940 long gmtMills = eventCal.getTimeInMillis();
941
942 eventCal.setTimeZone(cal.getTimeZone());
943
944 int tziDate = eventCal.get(Calendar.DATE);
945 long tziMills = Time.getDate(eventCal).getTime();
946
947 if (gmtDate != tziDate) {
948 int diffDate = 0;
949
950 if (gmtMills > tziMills) {
951 diffDate = (int)Math.ceil(
952 (double)(gmtMills - tziMills) / Time.DAY);
953 }
954 else {
955 diffDate = (int)Math.floor(
956 (double)(gmtMills - tziMills) / Time.DAY);
957 }
958
959 recurrenceCal.add(Calendar.DATE, diffDate);
960 }
961 }
962
963 return recurrenceCal;
964 }
965
966 protected void importICal4j(
967 long userId, long groupId, VEvent event)
968 throws PortalException, SystemException {
969
970 User user = userPersistence.findByPrimaryKey(userId);
971
972 TimeZone timeZone = user.getTimeZone();
973
974
976 Property timeZoneXProperty = event.getProperty(
977 TimeZoneSensitive.PROPERTY_NAME);
978
979 boolean timeZoneXPropertyValue = true;
980
981 if (Validator.isNotNull(timeZoneXProperty) &&
982 timeZoneXProperty.getValue().equals("FALSE")) {
983
984 timeZoneXPropertyValue = false;
985 }
986
987
989 String title = StringPool.BLANK;
990
991 if (event.getSummary() != null) {
992 title = ModelHintsUtil.trimString(
993 CalEvent.class.getName(), "title",
994 event.getSummary().getValue());
995 }
996
997
999 String description = StringPool.BLANK;
1000
1001 if (event.getDescription() != null) {
1002 description = event.getDescription().getValue();
1003 }
1004
1005
1007 DtStart dtStart = event.getStartDate();
1008
1009 Calendar startDate = toCalendar(
1010 dtStart, timeZone, timeZoneXPropertyValue);
1011
1012 startDate.setTime(dtStart.getDate());
1013
1014
1016 Calendar endDate = null;
1017
1018 DtEnd dtEnd = event.getEndDate(true);
1019
1020 RRule rrule = (RRule)event.getProperty(Property.RRULE);
1021
1022 if (Validator.isNotNull(dtEnd)) {
1023 endDate = toCalendar(dtEnd, timeZone, timeZoneXPropertyValue);
1024
1025 endDate.setTime(dtEnd.getDate());
1026 }
1027 else {
1028 endDate = (Calendar)startDate.clone();
1029 endDate.add(Calendar.DATE, 1);
1030 }
1031
1032
1034 long diffMillis = 0;
1035 long durationHours = 24;
1036 long durationMins = 0;
1037 boolean multiDayEvent = false;
1038
1039 if (Validator.isNotNull(dtEnd)) {
1040 diffMillis =
1041 dtEnd.getDate().getTime() - startDate.getTimeInMillis();
1042 durationHours = diffMillis / Time.HOUR;
1043 durationMins = (diffMillis / Time.MINUTE) - (durationHours * 60);
1044
1045 if ((durationHours > 24) ||
1046 ((durationHours == 24) && (durationMins > 0))) {
1047
1048 durationHours = 24;
1049 durationMins = 0;
1050 multiDayEvent = true;
1051 }
1052 }
1053
1054
1056 boolean allDay = false;
1057
1058 if (isICal4jDateOnly(event.getStartDate()) || multiDayEvent) {
1059 allDay = true;
1060 }
1061
1062
1064 boolean timeZoneSensitive = true;
1065
1066 if (allDay || !timeZoneXPropertyValue) {
1067 timeZoneSensitive = false;
1068 }
1069
1070
1072 String type = StringPool.BLANK;
1073
1074 Property comment = event.getProperty(Property.COMMENT);
1075
1076 if (Validator.isNotNull(comment) &&
1077 ArrayUtil.contains(CalEventImpl.TYPES, comment.getValue())) {
1078
1079 type = comment.getValue();
1080 }
1081
1082
1084 boolean repeating = false;
1085 TZSRecurrence recurrence = null;
1086
1087 if (multiDayEvent) {
1088 repeating = true;
1089
1090 Calendar recStartCal = CalendarFactoryUtil.getCalendar(timeZone);
1091
1092 recStartCal.setTime(startDate.getTime());
1093
1094 com.liferay.portal.kernel.cal.Duration duration =
1095 new com.liferay.portal.kernel.cal.Duration(1, 0, 0, 0);
1096
1097 recurrence = new TZSRecurrence(
1098 recStartCal, duration, Recurrence.DAILY);
1099
1100 Calendar until = (Calendar) startDate.clone();
1101
1102 until.setTimeInMillis(until.getTimeInMillis() + diffMillis);
1103
1104 recurrence.setUntil(until);
1105
1106 endDate = recurrence.getUntil();
1107 }
1108 else if (rrule != null) {
1109 repeating = true;
1110 recurrence = toRecurrence(rrule, timeZone, startDate);
1111
1112 if (recurrence.getUntil() != null) {
1113 endDate = recurrence.getUntil();
1114 }
1115 }
1116
1117
1119 int remindBy = CalEventImpl.REMIND_BY_NONE;
1120 int firstReminder = 300000;
1121 int secondReminder = 300000;
1122
1123
1125 ServiceContext serviceContext = new ServiceContext();
1126
1127 serviceContext.setAddCommunityPermissions(true);
1128 serviceContext.setAddGuestPermissions(true);
1129 serviceContext.setScopeGroupId(groupId);
1130
1131 addEvent(
1132 userId, title, description, startDate.get(Calendar.MONTH),
1133 startDate.get(Calendar.DAY_OF_MONTH), startDate.get(Calendar.YEAR),
1134 startDate.get(Calendar.HOUR_OF_DAY),
1135 startDate.get(Calendar.MINUTE), endDate.get(Calendar.MONTH),
1136 endDate.get(Calendar.DAY_OF_MONTH), endDate.get(Calendar.YEAR),
1137 (int)durationHours, (int)durationMins, allDay,
1138 timeZoneSensitive, type, repeating, recurrence, remindBy,
1139 firstReminder, secondReminder, serviceContext);
1140
1141 }
1142
1143 protected boolean isICal4jDateOnly(DateProperty date) {
1144 if (Validator.isNotNull(date.getParameter(Parameter.VALUE)) &&
1145 date.getParameter(Parameter.VALUE).getValue().equals("DATE")) {
1146
1147 return true;
1148 }
1149
1150 return false;
1151 }
1152
1153 protected void reIndexEvents(long companyId) throws SystemException {
1154 int count = calEventPersistence.countByCompanyId(companyId);
1155
1156 int pages = count / Indexer.DEFAULT_INTERVAL;
1157
1158 for (int i = 0; i <= pages; i++) {
1159 int start = (i * Indexer.DEFAULT_INTERVAL);
1160 int end = start + Indexer.DEFAULT_INTERVAL;
1161
1162 reIndexEvents(companyId, start, end);
1163 }
1164 }
1165
1166 protected void reIndexEvents(long companyId, int start, int end)
1167 throws SystemException {
1168
1169 List<CalEvent> events = calEventPersistence.findByCompanyId(
1170 companyId, start, end);
1171
1172 for (CalEvent event : events) {
1173 reIndex(event);
1174 }
1175 }
1176
1177 protected void remindUser(CalEvent event, User user, Calendar startDate) {
1178 int remindBy = event.getRemindBy();
1179
1180 if (remindBy == CalEventImpl.REMIND_BY_NONE) {
1181 return;
1182 }
1183
1184 try {
1185 long ownerId = event.getGroupId();
1186 int ownerType = PortletKeys.PREFS_OWNER_TYPE_GROUP;
1187 long plid = PortletKeys.PREFS_PLID_SHARED;
1188 String portletId = PortletKeys.CALENDAR;
1189
1190 PortletPreferences preferences =
1191 portletPreferencesLocalService.getPreferences(
1192 event.getCompanyId(), ownerId, ownerType, plid, portletId);
1193
1194 Company company = companyPersistence.findByPrimaryKey(
1195 user.getCompanyId());
1196
1197 Contact contact = user.getContact();
1198
1199 String portletName = PortalUtil.getPortletTitle(
1200 PortletKeys.CALENDAR, user);
1201
1202 String fromName = CalUtil.getEmailFromName(preferences);
1203 String fromAddress = CalUtil.getEmailFromAddress(preferences);
1204
1205 String toName = user.getFullName();
1206 String toAddress = user.getEmailAddress();
1207
1208 if (remindBy == CalEventImpl.REMIND_BY_SMS) {
1209 toAddress = contact.getSmsSn();
1210 }
1211
1212 String subject = CalUtil.getEmailEventReminderSubject(preferences);
1213 String body = CalUtil.getEmailEventReminderBody(preferences);
1214
1215 DateFormat dateFormatDateTime = DateFormats.getDateTime(
1216 user.getLocale(), user.getTimeZone());
1217
1218 subject = StringUtil.replace(
1219 subject,
1220 new String[] {
1221 "[$EVENT_START_DATE$]",
1222 "[$EVENT_TITLE$]",
1223 "[$FROM_ADDRESS$]",
1224 "[$FROM_NAME$]",
1225 "[$PORTAL_URL$]",
1226 "[$PORTLET_NAME$]",
1227 "[$TO_ADDRESS$]",
1228 "[$TO_NAME$]"
1229 },
1230 new String[] {
1231 dateFormatDateTime.format(startDate.getTime()),
1232 event.getTitle(),
1233 fromAddress,
1234 fromName,
1235 company.getVirtualHost(),
1236 portletName,
1237 toAddress,
1238 toName,
1239 });
1240
1241 body = StringUtil.replace(
1242 body,
1243 new String[] {
1244 "[$EVENT_START_DATE$]",
1245 "[$EVENT_TITLE$]",
1246 "[$FROM_ADDRESS$]",
1247 "[$FROM_NAME$]",
1248 "[$PORTAL_URL$]",
1249 "[$PORTLET_NAME$]",
1250 "[$TO_ADDRESS$]",
1251 "[$TO_NAME$]"
1252 },
1253 new String[] {
1254 dateFormatDateTime.format(startDate.getTime()),
1255 event.getTitle(),
1256 fromAddress,
1257 fromName,
1258 company.getVirtualHost(),
1259 portletName,
1260 toAddress,
1261 toName,
1262 });
1263
1264 if ((remindBy == CalEventImpl.REMIND_BY_EMAIL) ||
1265 (remindBy == CalEventImpl.REMIND_BY_SMS)) {
1266
1267 InternetAddress from = new InternetAddress(
1268 fromAddress, fromName);
1269
1270 InternetAddress to = new InternetAddress(toAddress, toName);
1271
1272 MailMessage message = new MailMessage(
1273 from, to, subject, body, true);
1274
1275 mailService.sendEmail(message);
1276 }
1277 else if ((remindBy == CalEventImpl.REMIND_BY_AIM) &&
1278 (Validator.isNotNull(contact.getAimSn()))) {
1279
1280 AIMConnector.send(contact.getAimSn(), body);
1281 }
1282 else if ((remindBy == CalEventImpl.REMIND_BY_ICQ) &&
1283 (Validator.isNotNull(contact.getIcqSn()))) {
1284
1285 ICQConnector.send(contact.getIcqSn(), body);
1286 }
1287 else if ((remindBy == CalEventImpl.REMIND_BY_MSN) &&
1288 (Validator.isNotNull(contact.getMsnSn()))) {
1289
1290 MSNConnector.send(contact.getMsnSn(), body);
1291 }
1292 else if ((remindBy == CalEventImpl.REMIND_BY_YM) &&
1293 (Validator.isNotNull(contact.getYmSn()))) {
1294
1295 YMConnector.send(contact.getYmSn(), body);
1296 }
1297 }
1298 catch (Exception e) {
1299 _log.error(e);
1300 }
1301 }
1302
1303 protected void remindUser(
1304 CalEvent event, User user, Calendar startDate, Calendar now) {
1305
1306 long diff =
1307 (startDate.getTime().getTime() - now.getTime().getTime()) /
1308 CheckEventJob.INTERVAL;
1309
1310 if ((diff == (event.getFirstReminder() / CheckEventJob.INTERVAL)) ||
1311 (diff ==
1312 (event.getSecondReminder() / CheckEventJob.INTERVAL))) {
1313
1314 remindUser(event, user, startDate);
1315 }
1316 }
1317
1318 protected Calendar toCalendar(
1319 DateProperty date, TimeZone timeZone, boolean timeZoneSensitive) {
1320
1321 Calendar cal = null;
1322
1323 if (isICal4jDateOnly(date)) {
1324 cal = Calendar.getInstance();
1325 }
1326 else if (!timeZoneSensitive) {
1327 cal = Calendar.getInstance(TimeZone.getTimeZone(StringPool.UTC));
1328 }
1329 else {
1330 cal = Calendar.getInstance(timeZone);
1331 }
1332
1333 return cal;
1334 }
1335
1336 protected int toCalendarWeekDay(WeekDay weekDay) {
1337 int dayOfWeeek = 0;
1338
1339 if (weekDay.getDay().equals(WeekDay.SU.getDay())) {
1340 dayOfWeeek = Calendar.SUNDAY;
1341 }
1342 else if (weekDay.getDay().equals(WeekDay.MO.getDay())) {
1343 dayOfWeeek = Calendar.MONDAY;
1344 }
1345 else if (weekDay.getDay().equals(WeekDay.TU.getDay())) {
1346 dayOfWeeek = Calendar.TUESDAY;
1347 }
1348 else if (weekDay.getDay().equals(WeekDay.WE.getDay())) {
1349 dayOfWeeek = Calendar.WEDNESDAY;
1350 }
1351 else if (weekDay.getDay().equals(WeekDay.TH.getDay())) {
1352 dayOfWeeek = Calendar.THURSDAY;
1353 }
1354 else if (weekDay.getDay().equals(WeekDay.FR.getDay())) {
1355 dayOfWeeek = Calendar.FRIDAY;
1356 }
1357 else if (weekDay.getDay().equals(WeekDay.SA.getDay())) {
1358 dayOfWeeek = Calendar.SATURDAY;
1359 }
1360
1361 return dayOfWeeek;
1362 }
1363
1364 protected net.fortuna.ical4j.model.Calendar toICalCalendar(
1365 long userId, List<CalEvent> events)
1366 throws PortalException, SystemException {
1367
1368 net.fortuna.ical4j.model.Calendar iCal =
1369 new net.fortuna.ical4j.model.Calendar();
1370
1371 ProdId prodId = new ProdId(
1372 "-//Liferay Inc//Liferay Portal " + ReleaseInfo.getVersion() +
1373 "//EN");
1374
1375 PropertyList props = iCal.getProperties();
1376
1377 props.add(prodId);
1378 props.add(Version.VERSION_2_0);
1379 props.add(CalScale.GREGORIAN);
1380
1381 User user = userPersistence.findByPrimaryKey(userId);
1382 TimeZone timeZone = user.getTimeZone();
1383
1384 List<VEvent> components = iCal.getComponents();
1385
1386 Iterator<CalEvent> itr = events.iterator();
1387
1388 while (itr.hasNext()) {
1389 CalEvent event = itr.next();
1390
1391 components.add(toICalVEvent(event, timeZone));
1392 }
1393
1394 return iCal;
1395 }
1396
1397 protected Recur toICalRecurrence(TZSRecurrence recurrence) {
1398 Recur recur = null;
1399
1400 int recurrenceType = recurrence.getFrequency();
1401
1402 int interval = recurrence.getInterval();
1403
1404 if (recurrenceType == Recurrence.DAILY) {
1405 recur = new Recur(Recur.DAILY, -1);
1406
1407 if (interval >= 1) {
1408 recur.setInterval(interval);
1409 }
1410
1411 DayAndPosition[] byDay = recurrence.getByDay();
1412
1413 if (byDay != null) {
1414 for (int i = 0; i < byDay.length; i++) {
1415 WeekDay weekDay = toICalWeekDay(byDay[i].getDayOfWeek());
1416
1417 recur.getDayList().add(weekDay);
1418 }
1419 }
1420
1421 }
1422 else if (recurrenceType == Recurrence.WEEKLY) {
1423 recur = new Recur(Recur.WEEKLY, -1);
1424
1425 recur.setInterval(interval);
1426
1427 DayAndPosition[] byDay = recurrence.getByDay();
1428
1429 if (byDay != null) {
1430 for (int i = 0; i < byDay.length; i++) {
1431 WeekDay weekDay = toICalWeekDay(byDay[i].getDayOfWeek());
1432
1433 recur.getDayList().add(weekDay);
1434 }
1435 }
1436 }
1437 else if (recurrenceType == Recurrence.MONTHLY) {
1438 recur = new Recur(Recur.MONTHLY, -1);
1439
1440 recur.setInterval(interval);
1441
1442 int[] byMonthDay = recurrence.getByMonthDay();
1443
1444 if (byMonthDay != null) {
1445 Integer monthDay = new Integer(byMonthDay[0]);
1446
1447 recur.getMonthDayList().add(monthDay);
1448 }
1449 else if (recurrence.getByDay() != null) {
1450 DayAndPosition[] byDay = recurrence.getByDay();
1451
1452 WeekDay weekDay = toICalWeekDay(byDay[0].getDayOfWeek());
1453
1454 recur.getDayList().add(weekDay);
1455
1456 Integer position = new Integer(byDay[0].getDayPosition());
1457
1458 recur.getSetPosList().add(position);
1459 }
1460 }
1461 else if (recurrenceType == Recurrence.YEARLY) {
1462 recur = new Recur(Recur.YEARLY, -1);
1463
1464 recur.setInterval(interval);
1465 }
1466
1467 Calendar until = recurrence.getUntil();
1468
1469 if (until != null) {
1470 DateTime dateTime = new DateTime(until.getTime());
1471
1472 recur.setUntil(dateTime);
1473 }
1474
1475 return recur;
1476 }
1477
1478 protected VEvent toICalVEvent(CalEvent event, TimeZone timeZone) {
1479 VEvent vEvent = new VEvent();
1480
1481 PropertyList eventProps = vEvent.getProperties();
1482
1483
1485 Uid uid = new Uid(PortalUUIDUtil.generate());
1486
1487 eventProps.add(uid);
1488
1489 if (event.isAllDay()) {
1490
1491
1493 DtStart dtStart = new DtStart(
1494 new net.fortuna.ical4j.model.Date(event.getStartDate()));
1495
1496 eventProps.add(dtStart);
1497
1498 Property dtStartProperty = eventProps.getProperty(Property.DTSTART);
1499
1500 dtStartProperty.getParameters().add(Value.DATE);
1501 }
1502 else {
1503
1504
1506 DtStart dtStart = new DtStart(new DateTime(event.getStartDate()));
1507
1508 eventProps.add(dtStart);
1509
1510
1512 Duration duration = new Duration(
1513 new Dur(
1514 0, event.getDurationHour(), event.getDurationMinute(), 0));
1515
1516 eventProps.add(duration);
1517 }
1518
1519
1521 Summary summary = new Summary(event.getTitle());
1522
1523 eventProps.add(summary);
1524
1525
1527 Description description = new Description(event.getDescription());
1528
1529 eventProps.add(description);
1530
1531
1533 Comment comment = new Comment(event.getType());
1534
1535 eventProps.add(comment);
1536
1537
1539 if (event.isRepeating()) {
1540 Recur recur = toICalRecurrence(event.getRecurrenceObj());
1541
1542 RRule rRule = new RRule(recur);
1543
1544 eventProps.add(rRule);
1545 }
1546
1547
1549 if (!event.getTimeZoneSensitive()) {
1550 eventProps.add(new TimeZoneSensitive("FALSE"));
1551 }
1552
1553 return vEvent;
1554 }
1555
1556 protected WeekDay toICalWeekDay(int dayOfWeek) {
1557 WeekDay weekDay = null;
1558
1559 if (dayOfWeek == Calendar.SUNDAY) {
1560 weekDay = WeekDay.SU;
1561 }
1562 else if (dayOfWeek == Calendar.MONDAY) {
1563 weekDay = WeekDay.MO;
1564 }
1565 else if (dayOfWeek == Calendar.TUESDAY) {
1566 weekDay = WeekDay.TU;
1567 }
1568 else if (dayOfWeek == Calendar.WEDNESDAY) {
1569 weekDay = WeekDay.WE;
1570 }
1571 else if (dayOfWeek == Calendar.THURSDAY) {
1572 weekDay = WeekDay.TH;
1573 }
1574 else if (dayOfWeek == Calendar.FRIDAY) {
1575 weekDay = WeekDay.FR;
1576 }
1577 else if (dayOfWeek == Calendar.SATURDAY) {
1578 weekDay = WeekDay.SA;
1579 }
1580
1581 return weekDay;
1582 }
1583
1584 protected TZSRecurrence toRecurrence(
1585 RRule rRule, TimeZone timeZone, Calendar startDate) {
1586
1587 Recur recur = rRule.getRecur();
1588
1589 Calendar recStartCal = CalendarFactoryUtil.getCalendar(timeZone);
1590
1591 recStartCal.setTime(startDate.getTime());
1592
1593 TZSRecurrence recurrence = new TZSRecurrence(
1594 recStartCal,
1595 new com.liferay.portal.kernel.cal.Duration(1, 0, 0, 0));
1596
1597 recurrence.setWeekStart(Calendar.SUNDAY);
1598
1599 if (recur.getInterval() > 1) {
1600 recurrence.setInterval(recur.getInterval());
1601 }
1602
1603 Calendar until = Calendar.getInstance(timeZone);
1604
1605 String frequency = recur.getFrequency();
1606
1607 if (Validator.isNotNull(recur.getUntil())) {
1608 until.setTime(recur.getUntil());
1609
1610 recurrence.setUntil(until);
1611 }
1612 else if (rRule.getValue().indexOf("COUNT") >= 0) {
1613 until.setTimeInMillis(startDate.getTimeInMillis());
1614
1615 int addField = 0;
1616
1617 if (Recur.DAILY.equals(frequency)) {
1618 addField = Calendar.DAY_OF_YEAR;
1619 }
1620 else if (Recur.WEEKLY.equals(frequency)) {
1621 addField = Calendar.WEEK_OF_YEAR;
1622 }
1623 else if (Recur.MONTHLY.equals(frequency)) {
1624 addField = Calendar.MONTH;
1625 }
1626 else if (Recur.YEARLY.equals(frequency)) {
1627 addField = Calendar.YEAR;
1628 }
1629
1630 int addAmount = recurrence.getInterval() * recur.getCount();
1631
1632 until.add(addField, addAmount);
1633 until.add(Calendar.DAY_OF_YEAR, -1);
1634
1635 recurrence.setUntil(until);
1636 }
1637
1638 if (Recur.DAILY.equals(frequency)) {
1639 recurrence.setFrequency(Recurrence.DAILY);
1640
1641 List<DayAndPosition> dayPosList = new ArrayList<DayAndPosition>();
1642
1643 Iterator<WeekDay> itr = recur.getDayList().iterator();
1644
1645 while (itr.hasNext()) {
1646 WeekDay weekDay = itr.next();
1647
1648 dayPosList.add(
1649 new DayAndPosition(toCalendarWeekDay(weekDay), 0));
1650 }
1651
1652 if (!dayPosList.isEmpty()) {
1653 recurrence.setByDay(
1654 dayPosList.toArray(new DayAndPosition[dayPosList.size()]));
1655 }
1656 }
1657 else if (Recur.WEEKLY.equals(frequency)) {
1658 recurrence.setFrequency(Recurrence.WEEKLY);
1659
1660 List<DayAndPosition> dayPosList = new ArrayList<DayAndPosition>();
1661
1662 Iterator<WeekDay> itr = recur.getDayList().iterator();
1663
1664 while (itr.hasNext()) {
1665 WeekDay weekDay = itr.next();
1666
1667 dayPosList.add(
1668 new DayAndPosition(toCalendarWeekDay(weekDay), 0));
1669 }
1670
1671 if (!dayPosList.isEmpty()) {
1672 recurrence.setByDay(
1673 dayPosList.toArray(new DayAndPosition[dayPosList.size()]));
1674 }
1675 }
1676 else if (Recur.MONTHLY.equals(frequency)) {
1677 recurrence.setFrequency(Recurrence.MONTHLY);
1678
1679 Iterator<Integer> monthDayListItr =
1680 recur.getMonthDayList().iterator();
1681
1682 if (monthDayListItr.hasNext()) {
1683 Integer monthDay = monthDayListItr.next();
1684
1685 recurrence.setByMonthDay(new int[] {monthDay.intValue()});
1686 }
1687
1688 Iterator<WeekDay> dayListItr = recur.getDayList().iterator();
1689
1690 if (dayListItr.hasNext()) {
1691 WeekDay weekDay = dayListItr.next();
1692
1693 DayAndPosition[] dayPos = {
1694 new DayAndPosition(toCalendarWeekDay(weekDay),
1695 weekDay.getOffset())
1696 };
1697
1698 recurrence.setByDay(dayPos);
1699 }
1700 }
1701 else if (Recur.YEARLY.equals(frequency)) {
1702 recurrence.setFrequency(Recurrence.YEARLY);
1703 }
1704
1705 return recurrence;
1706 }
1707
1708 protected void validate(
1709 String title, int startDateMonth, int startDateDay,
1710 int startDateYear, int endDateMonth, int endDateDay,
1711 int endDateYear, int durationHour, int durationMinute,
1712 boolean allDay, boolean repeating)
1713 throws PortalException {
1714
1715 if (Validator.isNull(title)) {
1716 throw new EventTitleException();
1717 }
1718 else if (!Validator.isDate(
1719 startDateMonth, startDateDay, startDateYear)) {
1720
1721 throw new EventStartDateException();
1722 }
1723 else if (!Validator.isDate(endDateMonth, endDateDay, endDateYear)) {
1724 throw new EventEndDateException();
1725 }
1726
1727 if (!allDay && durationHour <= 0 && durationMinute <= 0) {
1728 throw new EventDurationException();
1729 }
1730
1731 Calendar startDate = CalendarFactoryUtil.getCalendar(
1732 startDateYear, startDateMonth, startDateDay);
1733
1734 Calendar endDate = CalendarFactoryUtil.getCalendar(
1735 endDateYear, endDateMonth, endDateDay);
1736
1737 if (repeating && startDate.after(endDate)) {
1738 throw new EventEndDateException();
1739 }
1740 }
1741
1742 private static Log _log =
1743 LogFactoryUtil.getLog(CalEventLocalServiceImpl.class);
1744
1745}