package api import ( "encoding/json" "fmt" "html/template" "net/http" "github.com/gorilla/mux" "github.com/gorilla/schema" "gogs.carducci-dante.gov.it/andrea.fazzi/karmen/orm" "gogs.carducci-dante.gov.it/andrea.fazzi/karmen/renderer" ) func saveActivity(r *http.Request, activity *orm.Activity) { var ( class orm.Class subject orm.Subject ) if err := r.ParseForm(); err != nil { panic(err) } decoder := schema.NewDecoder() if err := decoder.Decode(activity, r.PostForm); err != nil { panic(err) } if err := orm.DB().First(&class, activity.ClassID).Error; err != nil { panic(err) } if err := orm.DB().First(&subject, activity.SubjectID).Error; err != nil { panic(err) } activity.Name = fmt.Sprintf("%s %s %dh", class.Name, subject.Name, activity.Hours) if err := orm.DB().Save(activity).Error; err != nil { panic(err) } } func activitiesHandler() http.Handler { fn := func(w http.ResponseWriter, r *http.Request) { var data struct { Activities []orm.Activity } if err := orm.DB().Find(&data.Activities).Error; err != nil { panic(err) } if err := orm.DB().Preload("Subject").Preload("Teacher").Preload("Class").Find(&data.Activities).Error; err != nil { panic(err) } if err := renderer.Render(w, "base", "activities", data); err != nil { panic(err) } } return http.HandlerFunc(fn) } func activitiesAddHandler() http.Handler { fn := func(w http.ResponseWriter, r *http.Request) { if r.Method == "GET" { var data struct { Update bool AllTeachers []orm.Teacher AllClasses []orm.Class AllSubjects []orm.Subject SubmitUrl template.URL } data.SubmitUrl = template.URL(fmt.Sprintf("/activities/add")) if err := orm.DB().Find(&data.AllTeachers).Error; err != nil { panic(err) } if err := orm.DB().Find(&data.AllClasses).Error; err != nil { panic(err) } if err := orm.DB().Find(&data.AllSubjects).Error; err != nil { panic(err) } if err := renderer.Render(w, "base", "activities_add_update", data); err != nil { panic(err) } } else if r.Method == "POST" { var activity orm.Activity if err := orm.DB().Create(&activity).Error; err != nil { panic(err) } saveActivity(r, &activity) http.Redirect(w, r, fmt.Sprintf("/activities"), http.StatusSeeOther) } } return http.HandlerFunc(fn) } func activitiesDeleteHandler() http.Handler { fn := func(w http.ResponseWriter, r *http.Request) { var activity orm.Activity if err := orm.DB().First(&activity, mux.Vars(r)["id"]).Error; err != nil { panic(err) } if err := orm.DB().Delete(&activity).Error; err != nil { panic(err) } var data struct { RedirectUrl string `json:"redirect_url"` } // Handle associations if activity.TeacherID != 0 { var ( class orm.Class subject orm.Class teacher orm.Teacher ) if err := orm.DB().First(&teacher, activity.TeacherID).Error; err != nil { panic(err) } teacher.CalcHours(orm.DB()) orm.DB().Save(&teacher) if err := orm.DB().First(&class, activity.ClassID).Error; err != nil { panic(err) } if err := orm.DB().First(&subject, activity.SubjectID).Error; err != nil { panic(err) } if err := orm.DB().Model(&teacher).Association("Classes").Delete(class).Error; err != nil { panic(err) } if err := orm.DB().Model(&teacher).Association("Subjects").Delete(subject).Error; err != nil { panic(err) } } data.RedirectUrl = "/activities" w.Header().Set("Content-Type", "application/json") json.NewEncoder(w).Encode(data) } return http.HandlerFunc(fn) } func activitiesUpdateHandler() http.Handler { fn := func(w http.ResponseWriter, r *http.Request) { if r.Method == "GET" { var data struct { Update bool SubmitUrl template.URL Activity orm.Activity AllTeachers []orm.Teacher AllSubjects []orm.Subject AllClasses []orm.Class SelectedTeacher map[uint]string SelectedSubject map[uint]string SelectedClass map[uint]string } if err := orm.DB().First(&data.Activity, mux.Vars(r)["id"]).Error; err != nil { panic(err) } if err := orm.DB().Find(&data.AllTeachers).Error; err != nil { panic(err) } if err := orm.DB().Find(&data.AllSubjects).Error; err != nil { panic(err) } if err := orm.DB().Find(&data.AllClasses).Error; err != nil { panic(err) } if id := data.Activity.TeacherID; id != 0 { data.SelectedTeacher = make(map[uint]string) data.SelectedTeacher[id] = "selected" } data.SelectedClass = make(map[uint]string) data.SelectedClass[data.Activity.ClassID] = "selected" data.SelectedSubject = make(map[uint]string) data.SelectedSubject[data.Activity.SubjectID] = "selected" data.Update = true data.SubmitUrl = template.URL(fmt.Sprintf("/activities/%d/update", data.Activity.ID)) if err := renderer.Render(w, "base", "activities_add_update", data); err != nil { panic(err) } } else if r.Method == "POST" { var activity orm.Activity if err := orm.DB().First(&activity, mux.Vars(r)["id"]).Error; err != nil { panic(err) } saveActivity(r, &activity) http.Redirect(w, r, fmt.Sprintf("/activities"), http.StatusSeeOther) } } return http.HandlerFunc(fn) }