5

我正在尝试使用Ical4j.ics创建一个文件。 但是当我尝试添加重复时它失败了,抛出一个:
ValidationException

net.fortuna.ical4j.model.ValidationException: Invalid property: RRULE at
        net.fortuna.ical4j.model.Calendar.validate(Calendar.java:297) at  
        net.fortuna.ical4j.model.Calendar.validate(Calendar.java:257) at 
        net.fortuna.ical4j.data.CalendarOutputter.output(CalendarOutputter.java:96) at 
        net.fortuna.ical4j.data.CalendarOutputter.output(CalendarOutputter.java:83)

我添加重复的代码是:

Recur recur = new Recur(Recur.WEEKLY,null);
recur.setUntil( new DateTime(dateTo.getTime()) );

RRule rule = new RRule(recur);
cal.getProperties().add(rule);

如果没有这条规则,它可以正常工作,但我想在每个星期一添加这个事件,
直到12 December 2011(返回的日期dateTo)。有任何想法吗?

4

3 回答 3

5

必须将重复规则 (RRULE) 属性添加到日历中的特定事件 (VEVENT),而不是日历本身。例如

myEvent.getProperties().add(rule);

此外,如果您希望事件在星期一发生,您可能应该使用如下规则:

FREQ=WEEKLY;BYDAY=MO;UNTIL=<date>

这不是我的想法,所以最好检查 RFC 以确保:

https://www.rfc-editor.org/rfc/rfc5545#section-3.3.10

于 2011-10-17T22:54:02.840 回答
0

这是我的相同 每周重复规则的重复规则示例

RRULE:FREQ=MONTHLY;INTERVAL=1;BYDAY=MO;UNTIL=20161222T000000Z
RRULE:FREQ=MONTHLY;INTERVAL=<Every month/with some interval>;BYDAY=<Day of week>;UNTIL=<Until Date>

所以按照这个你的规则将是: "RRULE:FREQ=MONTHLY;INTERVAL=1;BYDAY=MO;UNTIL=20111212T000000Z"

给出的是创建重复规则和日期的代码

class CreateRule{

    static {
        weekMap.put(Short.valueOf("0"), "SU");
        weekMap.put(Short.valueOf("1"), "MO");
        weekMap.put(Short.valueOf("2"), "TU");
        weekMap.put(Short.valueOf("3"), "WE");
        weekMap.put(Short.valueOf("4"), "TH");
        weekMap.put(Short.valueOf("5"), "FR");
        weekMap.put(Short.valueOf("6"), "SA");
    }

    Short repeatCountMonthly = repeatCount != null ? repeatCount : 0;
    String weekDay = weekMap.get(<repeatMonthWeek>);
    //Create recurrence Rule    
    String monthlyRecurrenceRule = DateUtils.getMonthlyRecurrenceRule(repeatCountMonthly,endsNever,                             endsAfterOccurrences,endTime,repeatMonthDay,weekDay);
    //Create recurrence Dates
    Set<LocalDate> monthlyStartDates = CalendarUtils.getRecurrenceDates(monthlyRecurrenceRule,
                    LocalDate.fromDateFields(startDate));

}

类将具有创建规则和生成日期的方法:

class DateUtils{

            public static String getMonthlyRecurrenceRule(Short interval,boolean endsNever,Integer occurrences, StringBuilder endTime,Short dayOfMonth,String dayOfWeek){
                StringBuilder monthlyRecurrenceRule = new StringBuilder("RRULE:FREQ=MONTHLY");

                if(interval!=null&&interval.intValue()>0)
                    monthlyRecurrenceRule.append(";INTERVAL=").append(interval.toString());

                if(dayOfMonth!=null && dayOfMonth>0)
                    monthlyRecurrenceRule.append(";BYMONTHDAY=").append(dayOfMonth.toString());
                else
                    monthlyRecurrenceRule.append(";BYDAY=").append(dayOfWeek);

                if(endsNever){
                    //set endtime as startdate+10 years
                    monthlyRecurrenceRule.append(";UNTIL=").append("20271231T090000Z");
                }
                else{
                    if(occurrences!=null&&occurrences.intValue()>0)
                        monthlyRecurrenceRule.append(";COUNT=").append(occurrences.toString());
                    else
                        monthlyRecurrenceRule.append(";UNTIL=").append(endTime.toString());
                }

                return monthlyRecurrenceRule.toString();
            }

            public static Set<LocalDate> getRecurrenceDates(String rRule,LocalDate startDate) throws ParseException{
                Set<LocalDate> recurrenceDates = new HashSet<LocalDate>();

                for (LocalDate date : LocalDateIteratorFactory.createLocalDateIterable(rRule, startDate, true)) {
                     recurrenceDates.add(date);
                    }

                return recurrenceDates;
            }   

        }
于 2016-09-23T08:41:09.680 回答
-1

I had similar problem with this API. Unfortunately I do not have the code right now but I remember that problem was that some properties are "optional". There is an API that allows their registration. I'd recommend you to download the source code and check out what does method validate do. You will see that it verifies that the property is in collection (or map). Then just find that method that adds properties to this collection.

If you have troubles with achieving the source code just decompile the class files. I personally did this with this package. I used plugin to eclipse that decompiles every class that does not have associated source code: http://java.decompiler.free.fr/?q=jdeclipse

I am sorry that my answer is not concrete enough but I hope it is helpful anyway. Good luck.

于 2011-10-16T16:25:00.600 回答