jens-maus / node-ical

NodeJS class for parsing iCalendar/ICS files
Apache License 2.0
120 stars 51 forks source link

added parsing for alarms #299

Closed jonnytest1 closed 8 months ago

jonnytest1 commented 9 months ago

note1: test2.ics has a VALARM outside of any events (which might be invalid)

result:

{
   type: 'VEVENT'
   ...
   alarms:{
      type:VALARM
      ...
   }
}
  type Task = {
      type:"VEVENT"
      alarms?:Array<Alarm>
  }
jonnytest1 commented 9 months ago

(if note 1 is solved by addressing the test data i can remove te par.type=="VEVENT" check

jens-maus commented 9 months ago

(if note 1 is solved by addressing the test data i can remove te par.type=="VEVENT" check

Please adapt test2.ics yourself as being part of this PR.

jonnytest1 commented 9 months ago

one second ill quickly chekc the other files

jonnytest1 commented 9 months ago

ok - i wonder if i should also add some "calender" methods for alarms 🤔 I did write a parser for it after all (mostly just integrating the "trigger" property a bit)

oh judging from the example data my implementation would be missing some cases 🤔

class EventAlarm implements AlarmProvider {

  type: "VALARM"
  trigger: string

  action: "DISPLAY"

  timeOffset: number

  relative: boolean

  constructor(alarmConfig) {
    Object.assign(this, alarmConfig)

    this.calculateTimeOffset()
  }
  calculateTimeOffset() {
    const triggerMAtch = this.trigger.match(/(?<relative>-)?P(?<days>\d+)D.*?T?((?<hours>\d+)H)?((?<minutes>\d+)M)?((?<seconds>\d+)S)?/)
    if (!triggerMAtch) {
      console.error("invalid regex parsing TRIGGER for alarm ", this.trigger)
      return
    }

    this.relative = !!triggerMAtch.groups.relative
    const days = +triggerMAtch.groups.days
    const hours = +(triggerMAtch.groups.hours ?? 0)
    const minutes = +(triggerMAtch.groups.minutes ?? 0)
    const seconds = +(triggerMAtch.groups.seconds ?? 0)

    this.timeOffset = 0
    this.timeOffset += seconds * SECOND
    this.timeOffset += minutes * MINUTE
    this.timeOffset += hours * HOUR
    this.timeOffset += days * DAY
  }

  getDateForEventInstance(start_or_rrule_date: Date) {
    if (!this.relative) {
      const copy = new Date(start_or_rrule_date);
      copy.setHours(0)
      copy.setMinutes(0)
      copy.setSeconds(0)

      const absoulte = new Date(+copy + this.timeOffset)
      return absoulte
    }
    return new Date(start_or_rrule_date.valueOf() - this.timeOffset);
  }

}
jens-maus commented 9 months ago

one second ill quickly chekc the other files

Are you sure that VALARM outside VEVENT is invalid? I wonder because all these test.ics files are certainly not made/generated by hand. Thus, there might be ical applications out there having generated these ics files and I wonder who is wrong? They or you?

jonnytest1 commented 9 months ago

i foudn spec - https://www.kanzaki.com/docs/ical/valarm.html 🤔 so i guess i should add a VTODO case as well image

titanism commented 8 months ago

This would be amazing to have!

jonnytest1 commented 8 months ago

i noticed the event alarm class is missing a few trigger formats so i dont think it should be part of this pr

jonnytest1 commented 8 months ago

oh i missed the d.ts file 🥲

jens-maus commented 8 months ago

then please go ahead and submit another PR because I did not yet release a new node-ical version.

jonnytest1 commented 8 months ago

https://github.com/jens-maus/node-ical/pull/308/files