package fetch import ( "net/http" "strings" "time" "git.newty.dev/uofgsync/auth" ics "github.com/arran4/golang-ical" "github.com/charmbracelet/log" cron "github.com/go-co-op/gocron/v2" "golang.org/x/oauth2/google" "google.golang.org/api/calendar/v3" ) const calendar_url = "https://frontdoor.spa.gla.ac.uk/spacett/download/uogtimetable.ics" var Scheduler *cron.Scheduler func StartScheduler() { // fetch credentials config, err := google.ConfigFromJSON(auth.GoogleOAuthCreds, calendar.CalendarReadonlyScope) if err != nil { log.Fatal(err) } credentials, err := auth.GetCredentials(config) if err != nil { log.Fatal(err) } // create scheduler Scheduler, err := cron.NewScheduler() if err != nil { log.Fatal(err) } j, err := Scheduler.NewJob( // every 24 hours cron.DurationJob( 24*time.Hour, ), // update the calendar cron.NewTask( update_calendar, auth.GetHeader(credentials.GUID, credentials.UofgPass), auth.GetGoogleClient(config, credentials.GoogleToken), ), ) if err != nil { log.Fatal(err) } // run job and start scheduler go j.RunNow() Scheduler.Start() } func update_calendar(authorization string, google *http.Client) { // create request req, err := http.NewRequest("GET", calendar_url, nil) if err != nil { log.Fatal(err) } req.Header.Set("Authorization", authorization) // send request resp, err := http.DefaultClient.Do(req) if err != nil { log.Fatal(err) } defer resp.Body.Close() // check if authentication failed if resp.StatusCode == 401 { log.Fatal("authentication failed") } // parse ics file calendar, err := ics.ParseCalendar(resp.Body) if err != nil { log.Fatal(err) } for _, event := range calendar.Events() { name := event.GetProperty(ics.ComponentPropertySummary).Value location := strings.TrimSpace(strings.Replace(event.GetProperty(ics.ComponentPropertyLocation).Value, "ON CAMPUS:", "", 1)) log.Infof("%s: %s", name, location) } }