A Crystal library for parsing and generating calendar data with the iCalendar Specification.
DO NOT USE. Still a work in progress, many changes to come.
Add this to your application's shard.yml
:
dependencies:
iCal:
github: HCLarsen/ical_parser.cr
require "iCal"
The ICSStream.read method will read an ICS stream either from a local file, or a remote address. To read a local file, pass in a string of the local filename and path.
filename = File.join(File.dirname(__FILE__), "files", "FIFA_World_Cup_2018.ics")
calendar = ICSStream.read(filename)
calendar.class #=> Calendar
In the case of a remote stream, pass in a URI object with the address of the stream.
address = "https://people.trentu.ca/rloney/files/Canada_Holidays.ics"
uri = URI.parse(address)
calendar = ICSStream.read(uri) #=> #<IcalParser::Calendar:0x10868a5c0>
calendar.class #=> Calendar
In most cases, an iCalendar stream will only contain one calendar object. However, the specification does allow for multiple calendar objects to be sequentially grouped in a single stream. If you are reading such a stream, the ICSStream.read method will only return the first calendar object. If you are working with a stream that may have multiple calendar objects, it's best to use the ICSStream#read_calendars method instead to get an array of Calendar objects.
filename = File.join(File.dirname(__FILE__), "files", "FIFA_World_Cup_2018.ics")
calendars = ICSStream.read_calendars(filename) #=> [#<IcalParser::Calendar:0x10e733100]
calendars.class #=> Array(Calendar)
The Calendar class serves as a container for both the calendar properties and the calendar components. The standard calendar components, EVENT, TODO and so forth are accessed as arrays from the calendar object.
calendar.events #=> [#<IcalParser::Event:0x102776f20...]
calendar.events.first #=> #<IcalParser::Event:0x102776f20>
For both the calendar object and calendar components, standard properties are accessed directly by the name of the property. These methods have names that correspond directly to the name of the property in the RFC5545 specification, with two exceptions. The first being the CLASS property, which is referred to as classification, to avoid conflicting with the Object#class method. The second is any property that may occur more than once in the component, in which case the accessor is the pluralized version of the property name.
# After parsing this event:
# BEGIN:VEVENT
# UID:19970901T130000Z-123401@example.com
# DTSTAMP:19970901T130000Z
# DTSTART:19970903T163000Z
# DTEND:19970903T190000Z
# SUMMARY:Annual Employee Review
# CLASS:PRIVATE
# CATEGORIES:BUSINESS,HUMAN RESOURCES
# END:VEVENT
event.summary #=> "Annual Employee Review"
event.classification #=> "PRIVATE"
event.class #=> IcalParser::Event
event.categories #=> ["BUSINESS", "HUMAN RESOURCES"]
Non-standard and IANA properties are accessed by hash notation.
# After these lines are parsed:
# DRESSCODE:CASUAL
# NON-SMOKING;VALUE=BOOLEAN:TRUE
event["DRESSCODE"] #=> "CASUAL"
event["NON-SMOKING"] #=> True
Where possible, property values are returned as the corresponding Crystal core data type. TEXT values are returned as Strings; Date, Time and Date-Times are returned as Time, Integer is returned as Int32, and so forth.
For values that don't have a corresponding Crystal core class, those types are provided by this module. These include CalAddress, PeriodOfTime, Duration and Recur.
- Fork it ( https://github.com/HCLarsen/ical_parser.cr/fork )
- Create your feature branch (git checkout -b my-new-feature)
- Commit your changes (git commit -am 'Add some feature')
- Push to the branch (git push origin my-new-feature)
- Create a new Pull Request
- HCLarsen Chris Larsen - creator, maintainer