package view import ( "net/http" "strconv" "strings" "git.sr.ht/~gabrielgio/img/pkg/database/repository" "git.sr.ht/~gabrielgio/img/pkg/ext" "git.sr.ht/~gabrielgio/img/templates" ) type ( MediaView struct { mediaRepository repository.MediaRepository userRepository repository.UserRepository settingsRepository repository.SettingsRepository } ) func getPagination(r *http.Request) *repository.Pagination { var ( size int page int albumID *uint sizeStr = r.FormValue("size") pageStr = r.FormValue("page") albumIDStr = r.FormValue("albumId") ) if sizeStr == "" { size = 100 } else if s, err := strconv.Atoi(sizeStr); err != nil { size = 100 } else { size = s } if pageStr == "" { page = 0 } else if p, err := strconv.Atoi(pageStr); err != nil { page = 0 } else { page = p } if albumIDStr == "" { albumID = nil } else if p, err := strconv.Atoi(albumIDStr); err == nil { id := uint(p) albumID = &id } return &repository.Pagination{ Page: page, Size: size, AlbumID: albumID, } } func NewMediaView( mediaRepository repository.MediaRepository, userRepository repository.UserRepository, settingsRepository repository.SettingsRepository, ) *MediaView { return &MediaView{ mediaRepository: mediaRepository, userRepository: userRepository, settingsRepository: settingsRepository, } } func (self *MediaView) Index(w http.ResponseWriter, r *http.Request) error { p := getPagination(r) user := ext.GetUserFromCtx(r) userPath, err := self.userRepository.GetPathFromUserID(r.Context(), user.ID) if err != nil { return err } p.Path = userPath medias, err := self.mediaRepository.List(r.Context(), p) if err != nil { return err } settings, err := self.settingsRepository.Load(r.Context()) if err != nil { return err } page := &templates.MediaPage{ Medias: medias, Next: &repository.Pagination{ Size: p.Size, Page: p.Page + 1, }, Settings: settings, } templates.WritePageTemplate(w, page, user.IsAdmin) return nil } func (self *MediaView) Detail(w http.ResponseWriter, r *http.Request) error { user := ext.GetUserFromCtx(r) userPath, err := self.userRepository.GetPathFromUserID(r.Context(), user.ID) if err != nil { return err } pathHash := r.FormValue("path_hash") media, err := self.mediaRepository.Get(r.Context(), pathHash) if err != nil { return err } if !strings.Contains(media.Path, userPath) { ext.NotFound(w) return nil } settings, err := self.settingsRepository.Load(r.Context()) if err != nil { return err } page := &templates.DetailPage{ Settings: settings, Media: media, } templates.WritePageTemplate(w, page, user.IsAdmin) return nil } func (self *MediaView) GetImage(w http.ResponseWriter, r *http.Request) error { pathHash := r.FormValue("path_hash") media, err := self.mediaRepository.Get(r.Context(), pathHash) if err != nil { return err } w.Header().Set("Content-Type", media.MIMEType) http.ServeFile(w, r, media.Path) return nil } func (self *MediaView) GetThumbnail(w http.ResponseWriter, r *http.Request) error { pathHash := r.FormValue("path_hash") path, err := self.mediaRepository.GetThumbnailPath(r.Context(), pathHash) if err != nil { http.Redirect(w, r, "/media/image?path_hash="+pathHash, http.StatusTemporaryRedirect) // nolint: nilerr return nil } w.Header().Set("Content-Type", "image/jpeg") http.ServeFile(w, r, path) return nil } func (self *MediaView) SetMyselfIn(r *ext.Router) { r.GET("/media", self.Index) r.POST("/media", self.Index) r.GET("/detail", self.Detail) r.POST("/detail", self.Detail) r.GET("/media/image", self.GetImage) r.GET("/media/thumbnail", self.GetThumbnail) }