commit b963d70798422c7c8bd53415097ce02379594d7d Author: Nicholas Novak <34256932+NickyBoy89@users.noreply.github.com> Date: Tue Nov 14 22:35:30 2023 -0800 feat: Added schedule and current course functionality for the initial commit diff --git a/README.md b/README.md new file mode 100644 index 0000000..c832cdf --- /dev/null +++ b/README.md @@ -0,0 +1,3 @@ +# coursed + +`coursed` contains libraries and scripts that manage a locally-defined course syllabus diff --git a/go.mod b/go.mod new file mode 100644 index 0000000..ca16a47 --- /dev/null +++ b/go.mod @@ -0,0 +1,5 @@ +module git.nicholasnovak.io/nnovak/coursed + +go 1.21.4 + +require github.com/BurntSushi/toml v1.3.2 diff --git a/go.sum b/go.sum new file mode 100644 index 0000000..ef0f966 --- /dev/null +++ b/go.sum @@ -0,0 +1,2 @@ +github.com/BurntSushi/toml v1.3.2 h1:o7IhLm0Msx3BaB+n3Ag7L8EVlByGnpq14C4YWiu/gL8= +github.com/BurntSushi/toml v1.3.2/go.mod h1:CxXYINrC8qIiEnFrOxCa7Jy5BFHlXnUU2pbicEuybxQ= diff --git a/schedule.go b/schedule.go new file mode 100644 index 0000000..0cbfeb0 --- /dev/null +++ b/schedule.go @@ -0,0 +1,81 @@ +package main + +import ( + "errors" + "fmt" + "os" + "time" + + "github.com/BurntSushi/toml" +) + +var ( + ErrNoCurrentCourse = errors.New("error: no current course was found") +) + +// `Schedule` represents a set of courses that the user is taking +// +// It stores this as a mapping between the course's short code, and the actual +// information about the course +type Schedule struct { + Courses map[string]CourseConfig +} + +// `CurrentCourse` returns the current course for the user, based on the +// current time, and the schedule that they defined +// +// It is assumed courses cannot overlap, so this will never return multiple +// possible courses +// +// If no course is found, the error will be of type `ErrNoCurrentCourse` +func (s Schedule) CurrentCourse() (string, error) { + currentTime := time.Now() + + for courseName, courseInfo := range s.Courses { + startTime, err := time.Parse(time.Kitchen, courseInfo.StartTime) + if err != nil { + return "", err + } + + endTime, err := time.Parse(time.Kitchen, courseInfo.EndTime) + if err != nil { + return "", err + } + + if currentTime.After(startTime) && currentTime.Before(endTime) { + return courseName, nil + } + } + + return "", ErrNoCurrentCourse +} + +// `CourseConfig` represents all the information that is needed about a single +// course to place it on the schedule +type CourseConfig struct { + StartTime string `toml:"start_time"` + EndTime string `toml:"end_time"` + Days string `toml:"days"` +} + +func (c CourseConfig) String() string { + return fmt.Sprintf("CourseConfig { start: %v, end: %v, days: %v }", c.StartTime, c.EndTime, c.Days) +} + +// `LoadSchedule` loads a course schedule from the given file, and returns a +// `Schdule` object containing the parsed schedule +func LoadSchedule(fileName string) (Schedule, error) { + var v Schedule + + configFile, err := os.Open("schedule.toml") + if err != nil { + return v, err + } + defer configFile.Close() + + if _, err := toml.NewDecoder(configFile).Decode(&v); err != nil { + return v, err + } + + return v, nil +}