flutter: FormatException: Unknown component: BEGIN:VCALENDAR
PRODID:-//E-DIARY//E-DIARY 1.0//EN
VERSION:2.0
METHOD:PUBLISH
X-WR-CALNAME:Formula 1
X-Built-On-Cache-Miss:true
BEGIN:VEVENT
LAST-MODIFIED:20240221T122324Z
DTSTAMP:20240221T122324Z
LOCATION:Monaco
X-ECAL-SCHEDULE:63ed7aff4c410f0d70163027
DTSTART:20240524T113000Z
DTEND:20240524T123000Z
SUMMARY:๐ FORMULA 1 GRAND PRIX DE MONACO 2024 - Practice 1
TRANSP:TRANSPARENT
SEQUENCE:0
UID:65af54f4f4b46e5026018b20
PRIORITY:5
X-MICROSOFT-CDO-IMPORTANCE:1
CLASS:PUBLIC
DESCRIPTION:Follow all the action on F1 TV and F1.com. \n\nUnlock the insid
e world of F1 by signing up to F1 Unlocked at F1.com/F1Unlocked\n\nFollow
on the go with F1 TV\nhttps://cal.f1.com/f/pdgKx/2kxXC\n\nVisit the Race H
ub\nhttps://cal.f1.com/f/pdgKF/2kxXC\n\nFree sign up to F1 Unlocked\nhttps
://cal.f1.com/f/pdgKP/2kxXC\n\nDownload the Official F1 Race Programme App
\nhttps://cal.f1.com/f/pdgL1/2kxXC\n\nWear your favourite teams colours wi
th F1 store\nhttps://cal.f1.com<โฆ>
flutter: #0 VComponent._createComponent (package:enough_icalendar/src/components.dart:278:9)
#1 VComponent.parseLines (package:enough_icalendar/src/components.dart:210:18)
#2 VComponent.parse (package:enough_icalendar/src/components.dart:200:12)
#3 WebCalUtil.parseWebCal (package:impaktfull_f1/util/webcal/webcal_util.dart:90:34)
<asynchronous suspension>
#4 WebCalUtil.syncRacesWithWebCal (package:impaktfull_f1/util/webcal/webcal_util.dart:18:20)
<asynchronous suspension>
#5 _RaceRepository.syncRaces (package:impaktfull_f1/repo/race/race_repository.dart:161:28)
<asynchronous suspension>
#6 AdminViewModel.onSyncRacesTapped (package:impaktfull_f1/viewmodel/admin/admin_viewmodel.dart:29:22)
<asynchronous suspension>
#7 _ImpaktfullListItemState._onAsyncTap (package:impaktfull_ui/src/components/list_item/impaktfull_list_item.dart:70:7)
<asynchronous suspension>
This is my code to parse it.
Future<List<WebCalEvent>> parseWebCal(String url) async {
final httpUrl = url.replaceFirst('webcal://', 'https://');
final data = await dio.get(httpUrl);
if (data.statusCode != 200) {
throw Exception('Failed to load webcal (${data.statusCode})');
}
final icsString = data.data as String;
final icalendar = VComponent.parse(
icsString,
);
if (icalendar is! VCalendar) throw Exception('Failed to parse webcal');
final events = icalendar.children
.map((element) {
if (element is! VEvent) return null;
final summary = element.summary;
final startDate = element.start;
final endDate = element.end;
if (summary == null) return null;
if (startDate == null) return null;
if (endDate == null) return null;
return WebCalEvent(
title: summary,
startDate: startDate,
endDate: endDate,
);
})
.whereType<WebCalEvent>()
.toList();
return events;
}
class WebCalEvent {
final String title;
final DateTime startDate;
final DateTime endDate;
const WebCalEvent({
required this.title,
required this.startDate,
required this.endDate,
});
}