package polochons import ( "encoding/json" "fmt" "net/http" "git.quimbo.fr/odwrtw/canape/backend/auth" "git.quimbo.fr/odwrtw/canape/backend/models" "git.quimbo.fr/odwrtw/canape/backend/web" "github.com/gorilla/mux" polochon "github.com/odwrtw/polochon/lib" "github.com/sirupsen/logrus" ) // GetPublicPolochonsHandler returns the public list of polochons func GetPublicPolochonsHandler(env *web.Env, w http.ResponseWriter, r *http.Request) error { log := env.Log.WithFields(logrus.Fields{ "function": "polochons.GetPublicPolochonsHandler", }) log.Debug("Getting public polochons") polochons, err := models.GetAllPolochons(env.Database) if err != nil { return env.RenderError(w, err) } type MinimalPolochon struct { ID string `json:"id"` Name string `json:"name"` URL string `json:"url"` } mPolochons := []*MinimalPolochon{} for _, p := range polochons { mPolochons = append(mPolochons, &MinimalPolochon{ ID: p.ID, Name: p.Name, URL: p.URL, }) } return env.RenderJSON(w, mPolochons) } // GetPolochonsHandler returns the list of polochons and their users func GetPolochonsHandler(env *web.Env, w http.ResponseWriter, r *http.Request) error { log := env.Log.WithFields(logrus.Fields{ "function": "polochons.GetPolochonsHandler", }) user := auth.GetCurrentUser(r, env.Log) log.Debug("Getting polochons") polochons, err := models.GetAllPolochonsByUser(env.Database, user.ID) if err != nil { return env.RenderError(w, err) } for _, p := range polochons { users, err := models.GetPolochonUsers(env.Database, p.ID) if err != nil { return env.RenderError(w, err) } p.Users = users } return env.RenderJSON(w, polochons) } // NewPolochonHandler handles the creation of a new polochon func NewPolochonHandler(env *web.Env, w http.ResponseWriter, r *http.Request) error { log := env.Log.WithFields(logrus.Fields{ "function": "polochons.NewPolochonHandler", }) user := auth.GetCurrentUser(r, env.Log) var data struct { Name string `json:"name"` URL string `json:"url"` Token string `json:"token"` } if err := json.NewDecoder(r.Body).Decode(&data); err != nil { return env.RenderError(w, err) } for _, c := range []string{ data.Name, data.URL, data.Token, } { if c == "" { return env.RenderError(w, fmt.Errorf("name, url and token are mandatory fields")) } } log.Debugf("creating new polochon ...") p := models.Polochon{ Name: data.Name, URL: data.URL, Token: data.Token, AdminID: user.ID, } if err := p.Add(env.Database); err != nil { return env.RenderError(w, err) } log.Debugf("new polochon %s created ...", data.Name) return env.RenderOK(w, "Polochon created") } // EditPolochonHandler handles the edit of a polochon func EditPolochonHandler(env *web.Env, w http.ResponseWriter, r *http.Request) error { log := env.Log.WithFields(logrus.Fields{ "function": "polochons.EditPolochonHandler", }) log.Debugf("editing polochon ...") user := auth.GetCurrentUser(r, env.Log) // Get the polochon vars := mux.Vars(r) id := vars["id"] p, err := models.GetPolochonByID(env.Database, id) if err != nil { return env.RenderError(w, err) } // Check that the logged-in user is the polochon admin if p.AdminID != user.ID { return env.RenderError(w, fmt.Errorf("forbidden")) } var data struct { Name string `json:"name"` URL string `json:"url"` Token string `json:"token"` } if err := json.NewDecoder(r.Body).Decode(&data); err != nil { return env.RenderError(w, err) } for _, c := range []string{ data.Name, data.URL, data.Token, } { if c == "" { return env.RenderError(w, fmt.Errorf("name, url and token are mandatory fields")) } } p.Name = data.Name p.URL = data.URL p.Token = data.Token err = p.Update(env.Database) if err != nil { return env.RenderError(w, err) } return env.RenderOK(w, "Polochon updated") } // PolochonUserHandler edit a user's polochon config func PolochonUserHandler(env *web.Env, w http.ResponseWriter, r *http.Request) error { log := env.Log.WithFields(logrus.Fields{ "function": "polochons.PolochonUserHandler", }) log.Debugf("editing polochon user") var data struct { Activated bool `json:"activated"` Token string `json:"token"` } if err := json.NewDecoder(r.Body).Decode(&data); err != nil { return err } user := auth.GetCurrentUser(r, env.Log) // Get the polochon vars := mux.Vars(r) id := vars["id"] p, err := models.GetPolochonByID(env.Database, id) if err != nil { return env.RenderError(w, err) } // Check that the logged-in user is the polochon admin if p.AdminID != user.ID { return env.RenderError(w, fmt.Errorf("forbidden")) } // Get the user userID := vars["user_id"] u, err := models.GetUserByID(env.Database, userID) if err != nil { return env.RenderError(w, err) } u.PolochonActivated = data.Activated u.Token = data.Token err = u.Update(env.Database) if err != nil { return env.RenderError(w, err) } return env.RenderOK(w, "Polochon user updated") } // DeletePolochonHandler deletes a polochon func DeletePolochonHandler(env *web.Env, w http.ResponseWriter, r *http.Request) error { log := env.Log.WithFields(logrus.Fields{ "function": "polochons.DeletePolochonHandler", }) log.Debugf("deleting polochon user") user := auth.GetCurrentUser(r, env.Log) // Get the polochon vars := mux.Vars(r) id := vars["id"] p, err := models.GetPolochonByID(env.Database, id) if err != nil { return env.RenderError(w, err) } // Check that the logged-in user is the polochon admin if p.AdminID != user.ID { return env.RenderError(w, fmt.Errorf("forbidden")) } err = p.Delete(env.Database) if err != nil { return env.RenderError(w, err) } return env.RenderOK(w, "Polochon deleted") } // GetMovieWishlistHandler returns the movie wishlist of all of the polochon's // users combined func GetMovieWishlistHandler(env *web.Env, w http.ResponseWriter, r *http.Request) error { log := env.Log.WithFields(logrus.Fields{ "function": "polochons.GetMovieWishlistHandler", }) log.Debugf("getting polochon movie wishlist") p, err := getPolochon(env, r) if err != nil { return env.RenderError(w, err) } // Get the polochon's users users, err := models.GetPolochonUsers(env.Database, p.ID) if err != nil { return env.RenderError(w, err) } wishlist := polochon.Wishlist{} for _, u := range users { // Get the user's wishlisted movies moviesWishlist, err := models.GetMovieWishlist(env.Database, u.ID) if err != nil { return env.RenderError(w, err) } // Add the movie to the wishlist for _, imdbID := range moviesWishlist.List() { err := wishlist.AddMovie(&polochon.WishedMovie{ImdbID: imdbID}) if err != nil { return env.RenderError(w, err) } } } return env.RenderJSON(w, wishlist.Movies) } // GetShowWishlistHandler returns the show wishlist of all of the polochon's // users combined func GetShowWishlistHandler(env *web.Env, w http.ResponseWriter, r *http.Request) error { log := env.Log.WithFields(logrus.Fields{ "function": "polochons.GetShowWishlistHandler", }) log.Debugf("getting polochon show wishlist") p, err := getPolochon(env, r) if err != nil { return env.RenderError(w, err) } // Get the polochon's users users, err := models.GetPolochonUsers(env.Database, p.ID) if err != nil { return env.RenderError(w, err) } wishlist := polochon.Wishlist{} for _, u := range users { // Get the user's wishlisted shows moviesWishlist, err := models.GetShowWishlist(env.Database, u.ID) if err != nil { return env.RenderError(w, err) } // Add the show to the wishlist for _, show := range moviesWishlist.List() { err := wishlist.AddShow(&polochon.WishedShow{ ImdbID: show.ImdbID, Season: show.Season, Episode: show.Episode, }) if err != nil { return env.RenderError(w, err) } } } return env.RenderJSON(w, wishlist.Shows) } // Small helper to retrieve and check the polochon's credentials // TODO: Put this code in a middleware func getPolochon(env *web.Env, r *http.Request) (*models.Polochon, error) { vars := mux.Vars(r) id := vars["id"] token := r.URL.Query().Get("token") // Get the polochon associated p, err := models.GetPolochonByID(env.Database, id) if err != nil { return nil, err } // Check the auth if token != p.AuthToken { return nil, fmt.Errorf("forbidden") } return p, nil }