2011-04-30 15 views
5

estoy trabajando en la aplicación que analiza el Calendario de Google a través de Google API para DDay.iCalcalendario de análisis de Google para DDay.iCal

Los principales atributos, propiedades se manejan fácilmente ... ev.Summary = evt.Title. Texto;

El problema es cuando tengo una recurrentes evento, el XML contiene un campo como:

<gd:recurrence> 
    DTSTART;VALUE=DATE:20100916 
    DTEND;VALUE=DATE:20100917 
    RRULE:FREQ=YEARLY 
</gd:recurrence> 

o

<gd:recurrence> 
    DTSTART:20100915T220000Z 
    DTEND:20100916T220000Z 
    RRULE:FREQ=YEARLY;BYMONTH=9;WKST=SU" 
</gd:recurrence> 

usando el siguiente código:

String[] lines = 
evt.Recurrence.Value.Split(new char[] { '\n', '\r' }, StringSplitOptions.RemoveEmptyEntries); 

        foreach (String line in lines) 
        { 

         if (line.StartsWith("R")) 
         { 
          RecurrencePattern rp = new RecurrencePattern(line); 
          ev.RecurrenceRules.Add(rp); 
         } 
         else 
         { 
          ISerializationContext ctx = new SerializationContext(); 
          ISerializerFactory factory = new DDay.iCal.Serialization.iCalendar.SerializerFactory(); 

          ICalendarProperty property = new CalendarProperty(); 

          IStringSerializer serializer = factory.Build(property.GetType(), ctx) as IStringSerializer; 

          property = (ICalendarProperty)serializer.Deserialize(new StringReader(line)); 

          ev.Properties.Add(property); 
          Console.Out.WriteLine(property.Name + " - " + property.Value); 
         } 

        } 

Las RRULE se analizan correctamente, pero el problema es que otra propiedad (d atetimes) los valores están vacíos ...

+0

Quizás quiso decir utilizar dos puntos después de DTSTART y dtend en su primer ejemplo? ¿Y se supone que hay una comilla doble después de SU en el segundo ejemplo? –

Respuesta

4

Aquí está el punto de partida de lo que estoy haciendo, saliendo de the RFC-5545 spec's recurrence rule. No está completo para la especificación y puede romperse dada cierta información, pero debería hacerlo funcionar. Creo que esto debería ser factible usando RegEx, y algo tan pesado como un analizador decente recursivo sería exagerado.

RRULE:(?:FREQ=(DAILY|WEEKLY|SECONDLY|MINUTELY|HOURLY|DAILY|WEEKLY|MONTHLY|YEARLY);)?(?:COUNT=([0-9]+);)?(?:INTERVAL=([0-9]+);)?(?:BYDAY=([A-Z,]+);)?(?:UNTIL=([0-9]+);)?

estoy construyendo esta usando http://regexstorm.net/tester.

La entrada de prueba que estoy usando es:

DTSTART; TZID = America/Chicago: 20140711T133000 \ nDTEND; TZID = America/Chicago: 20140711T163000 \ nRRULE: FREC = Semanal; INTERVALO = 8; BYDAY = FR; HASTA = 20141101

DTSTART; TZID = America/Chicago: 20140711T133000 \ nDTEND; TZID = America/Chicago: 20140711T163000 \ nRRULE: FREC = WEEKLY; COUNT = 5, intervalo = 8; BYDAY = FR; HASTA = 20141101

DTSTART; TZID = América/Chicago: 20140711T133000 \ nDTEND; TZID = América/Chicago: 20140711T163000 \ nRRULE: FREQ = WEEKLY; BYDAY = FR; UNTIL = 20141101

resultados que coinciden con la muestra se vería así:

Index Position Matched String             $1  $2 $3 $4 $5 
0  90   RRULE:FREQ=WEEKLY;INTERVAL=8;BYDAY=FR;UNTIL=20141101   WEEKLY  8 FR 20141101 
1  236   RRULE:FREQ=WEEKLY;COUNT=5;INTERVAL=8;BYDAY=FR;UNTIL=20141101 WEEKLY 5 8 FR 20141101 
2  390   RRULE:FREQ=WEEKLY;BYDAY=FR;UNTIL=20141101      WEEKLY   FR 20141101 

uso es como:

string freqPattern = @"RRULE:(?:FREQ=(DAILY|WEEKLY|SECONDLY|MINUTELY|HOURLY|DAILY|WEEKLY|MONTHLY|YEARLY);?)?(?:COUNT=([0-9]+);?)?(?:INTERVAL=([0-9]+);?)?(?:BYDAY=([A-Z,]+);?)?(?:UNTIL=([0-9]+);?)?"; 
MatchCollection mc = Regex.Matches(rule, freqPattern, System.Text.RegularExpressions.RegexOptions.IgnoreCase); 
foreach (Match m in mc) 
{ 
    string frequency = m.Groups[1].ToString(); 
    string count = m.Groups[2].ToString(); 
    string interval = m.Groups[3].ToString(); 
    string byday = m.Groups[4].ToString(); 
    string until = m.Groups[5].ToString(); 
    System.Console.WriteLine("recurrence => frequency: \"{0}\", count: \"{1}\", interval: \"{2}\", byday: \"{3}\", until: \"{4}\"", frequency, count, interval, byday, until); 
} 
-1

Este es un gran ejemplo de cuándo usar expresiones regulares. Pruébelo para el análisis general:

\s*(\w+):((\w+=\w+;)+(\w+=\w+)?|\w+) 

O puede decidir tener algo más específico del esquema.

\s*(?:DTSTART:)(?'Start'\w+) 
\s*(?:DTEND:)(?'End'\w+) 
\s*(?:RRULE:)(?'Rule'(\w+=\w+;)+(\w+=\w+)?) 
Cuestiones relacionadas