Automated emailing of .ics appointments
February 2, 2006 1:02 AM

I have a .ics (iCal) calendar file hosted on webdav on a linux server. I need a script to run on the server as a cron job and email me any upcoming appointments. Does anyone know of such a thing?
posted by blacksky to Computers & Internet (7 answers total)
planzo has a service that will email you about events... perhaps your iCal file could be linked with a planzo calendar?

A hack, I know, but it seems simpler than searching for a perl/php/shell script and taking the time to test it.
posted by Wild_Eep at 5:19 AM on February 2, 2006


It should be relatively easy to code a quick Perl script using the CPAN modules Data::ICal and Mail::Sender to do what you want.

In fact, this is simple enough that I went ahead and coded you a quick example in Perl that reads an iCal file and sends an e-mail describing the upcoming events in the next 24 hours. To use it you'll first have to adjust the constants at the top of the script to point to your .ics file and to correctly specify the details needed to send outgoing mail. The code assumes the server is in the same time zone as the time in the calendar.
posted by RichardP at 5:56 AM on February 2, 2006


Is there a reason that iCal's built-in email reminders won't work for you?
posted by mwhybark at 6:27 AM on February 2, 2006


RichardP: You are a lovely man - thank you very much! I'll give that a try and report back.

mwhybark: I'm using Mozilla Sunbird (but that also does email reminders). The problem is, that if Sunbird isn't running, the reminders aren't sent. It would be nice to be able to check my webmail from where ever I might be, and see an email containing a list of events for today.
posted by blacksky at 7:15 AM on February 2, 2006


RichardP: Works like a charm! Best Answer goodness for you :)
posted by blacksky at 7:54 AM on February 2, 2006


RichardP: This script is great! It's just what I needed. However,
there seems to be an issue with parsing VALARM (as generated by sunbird). This issue causes the perl script to abort with no email :(. Here is a working and a not-working example. My guess is that VALARMs need to be ignored but I'm not a perl programmer, so can you help?

Working:
physio# ./mailappointments
physio# cat mycal.ics
BEGIN:VCALENDAR
VERSION:2.0
PRODID:-//Mozilla.org/NONSGML Mozilla Calendar V1.0//EN
BEGIN:VEVENT
CREATED:20060316T045825Z
LAST-MODIFIED:20060316T045911Z
DTSTAMP:20060316T045825Z
UID:uuid1142485151365
SUMMARY:Egmond Workshop
PRIORITY:0
STATUS:
CLASS:PUBLIC
DTSTART;VALUE=DATE:20060910
DTEND;VALUE=DATE:20060919
CATEGORIES:Travel
END:VEVENT
END:VCALENDAR


... Edit to not working form (i.e. add back in the 3 line VALARM section originally generated by sunbird):

physio# ./mailappointments
Use of uninitialized value in exists at /usr/lib/perl5/site_perl/5.8.5/Data/ICal/Entry.pm line 440.
Use of uninitialized value in concatenation (.) or string at /usr/lib/perl5/site_perl/5.8.5/Data/ICal/Entry.pm line 440.
Can't parse VALARM with action at /usr/lib/perl5/site_perl/5.8.5/Data/ICal/Entry.pm line 440.

physio# cat mycal.ics
BEGIN:VCALENDAR
VERSION:2.0
PRODID:-//Mozilla.org/NONSGML Mozilla Calendar V1.0//EN
BEGIN:VEVENT
CREATED:20060316T045825Z
LAST-MODIFIED:20060316T045911Z
DTSTAMP:20060316T045825Z
UID:uuid1142485151365
SUMMARY:Egmond Workshop
PRIORITY:0
STATUS:
CLASS:PUBLIC
DTSTART;VALUE=DATE:20060910
DTEND;VALUE=DATE:20060919
CATEGORIES:Travel
BEGIN:VALARM
TRIGGER;VALUE=DURATION:-PT15H
END:VALARM
END:VEVENT
END:VCALENDAR
posted by mcneale at 6:48 AM on March 17, 2006


I guess I answered my own comment. Sed can be used to delete
blocks of text; in this case we want to strip everything between BEGIN VALARM and END VALARM. However, it would be more elegant to have the perl script work all by itself, without this hack.

#!/bin/sh
# sed script to delete a block
:t
/BEGIN:VALARM/,/END:VALARM/ { # For each line between these block markers..
/END:VALARM/!{ # If we are not at the /end/ marker
$!{ # nor the last line of the file,
N; # add the Next line to the pattern space
bt
} # and branch (loop back) to the :t label.
} # This line matches the /end/ marker.
d; # If /regex/ matches, delete the block.
} # Otherwise, the block will be printed.
#---end of script---
posted by mcneale at 6:38 AM on March 20, 2006


« Older So, what could opened, exposed processed cheese do...   |   Have any good Valentine's Day mix songs? Newer »
This thread is closed to new comments.