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