I have made a few mentions to valarmd
, a project of mine which is paused for
the moment. It is a daemon used to show desktop notifications for alarms in
calendar entries. This is its specification. I hope to continue working on it
after completing my current work on vdirsyncer
.
Specification for valarmd
The basic usage is:
valarmd --socket /path/to/socket --vdir /path/to/vdir
valarmd
shall read icalendar components (both events and todos) from a local
file-system directory, extracting their respective dates, alarms and summaries.
It will also monitor the directory for any changes to these files and load any
changes.
At the time of each alarm, valarmd
will write a single event into its socket.
An event is a JSON object, encoded into a single line:
{"summary": "Meeting with Alice", "alarm": 1700811229, "type": "event", "start": 1700813029}
Programs that read events from this socket can perform all kind of actions:
- Show a notification via a notification daemon.
- Play an audible notification
- Read the event summary via text-to-speech.
- Send an email, print job or fax with the details of the alarm.
- Emit a D-Bus signal.
Clearly, anything can be done with the information. How these alarms are presented is up to end users.
Development status
The current work in progress is written in Rust. Parsing icalendar timezones and recurrence rules is a bit not trivial, and existing Rust libraries have some limitations that need to be addressed:
chrono
: It is not possible to create aVec<DateTime>
where datetimes have a different timezones. There is an issue for this upstream. This is required to properly handle all form of recurring events.rrule
: Doesn’t support using custom timezone implementations. A custom timezone implementation is needed to represent data read from icalendar components. I attempted to address the issue but it’s more complicated that it seems.
The current (incomplete and broken) implementation is in the valarmd
repository. There is also a short thread covering its status in
further detail.
Given limitations of existing libraries (and being focused elsewhere), this project remains paused. A few workarounds have been mentioned, but they only work for some events in my personal calendar. Missing some alarms is not a reasonable compromise.
Considering for golang
I had considered golang before using Rust, but its timezone implementation is
annoying to work with. Golang’s timezone implementation is represented by the
Location
type. Creating a new Location
instance cannot be done directly;
it can only be done by providing IANA Time Zone database-formatted data as
input.
So in order to create a Location
instance from an icalendar VTIMEZONE
, it
needs to be converted into IANA Time Zone database-format first, and then
into Location
.
This is an awful API (which won’t be fixed), and only a single example. In general, I don’t consider golang’s datetime and timezone interfaces flexible enough for tools that need to interoperate with icalendar data.