mirror of
https://github.com/simon-ding/polaris.git
synced 2026-02-06 23:21:00 +08:00
209 lines
5.3 KiB
Go
209 lines
5.3 KiB
Go
package server
|
|
|
|
import (
|
|
"os"
|
|
"path/filepath"
|
|
"polaris/db"
|
|
"polaris/ent"
|
|
"polaris/ent/episode"
|
|
"polaris/ent/media"
|
|
"polaris/log"
|
|
"polaris/server/core"
|
|
"strconv"
|
|
"strings"
|
|
|
|
"github.com/gin-gonic/gin"
|
|
"github.com/pkg/errors"
|
|
)
|
|
|
|
type searchTvParam struct {
|
|
Query string `form:"query"`
|
|
Page int `form:"page"`
|
|
}
|
|
|
|
func (s *Server) SearchTvSeries(c *gin.Context) (interface{}, error) {
|
|
var q searchTvParam
|
|
if err := c.ShouldBindQuery(&q); err != nil {
|
|
return nil, errors.Wrap(err, "bind query")
|
|
}
|
|
log.Infof("search tv series with keyword: %v", q.Query)
|
|
r, err := s.MustTMDB().SearchTvShow(q.Query, "")
|
|
if err != nil {
|
|
return nil, errors.Wrap(err, "search tv")
|
|
}
|
|
return r, nil
|
|
}
|
|
|
|
func (s *Server) SearchMedia(c *gin.Context) (interface{}, error) {
|
|
var q searchTvParam
|
|
if err := c.ShouldBindQuery(&q); err != nil {
|
|
return nil, errors.Wrap(err, "bind query")
|
|
}
|
|
log.Infof("search media with keyword: %v", q.Query)
|
|
tmdb, err := s.TMDB()
|
|
if err != nil {
|
|
return nil, err
|
|
}
|
|
r, err := tmdb.SearchMedia(q.Query, s.language, q.Page)
|
|
if err != nil {
|
|
return nil, errors.Wrap(err, "search tv")
|
|
}
|
|
for i, res := range r.Results {
|
|
if s.db.TmdbIdInWatchlist(int(res.ID)) {
|
|
r.Results[i].InWatchlist = true
|
|
}
|
|
}
|
|
return r, nil
|
|
|
|
}
|
|
|
|
type addWatchlistIn struct {
|
|
TmdbID int `json:"tmdb_id" binding:"required"`
|
|
StorageID int `json:"storage_id" `
|
|
Resolution string `json:"resolution" binding:"required"`
|
|
Folder string `json:"folder" binding:"required"`
|
|
DownloadHistoryEpisodes bool `json:"download_history_episodes"` //for tv
|
|
SizeMin int `json:"size_min"`
|
|
SizeMax int `json:"size_max"`
|
|
}
|
|
|
|
func (s *Server) AddTv2Watchlist(c *gin.Context) (interface{}, error) {
|
|
var in core.AddWatchlistIn
|
|
if err := c.ShouldBindJSON(&in); err != nil {
|
|
return nil, errors.Wrap(err, "bind query")
|
|
}
|
|
return s.core.AddTv2Watchlist(in)
|
|
}
|
|
|
|
func (s *Server) AddMovie2Watchlist(c *gin.Context) (interface{}, error) {
|
|
var in core.AddWatchlistIn
|
|
if err := c.ShouldBindJSON(&in); err != nil {
|
|
return nil, errors.Wrap(err, "bind query")
|
|
}
|
|
return s.core.AddMovie2Watchlist(in)
|
|
}
|
|
|
|
type MediaWithStatus struct {
|
|
*ent.Media
|
|
MonitoredNum int `json:"monitored_num"`
|
|
DownloadedNum int `json:"downloaded_num"`
|
|
}
|
|
|
|
//missing: episode aired missing
|
|
//downloaded: all monitored episode downloaded
|
|
//monitoring: episode aired downloaded, but still has not aired episode
|
|
//for movie, only monitoring/downloaded
|
|
|
|
func (s *Server) GetTvWatchlist(c *gin.Context) (interface{}, error) {
|
|
list := s.db.GetMediaWatchlist(media.MediaTypeTv)
|
|
res := make([]MediaWithStatus, len(list))
|
|
for i, item := range list {
|
|
var ms = MediaWithStatus{
|
|
Media: item,
|
|
MonitoredNum: 0,
|
|
DownloadedNum: 0,
|
|
}
|
|
mon, ok1 := s.monitorNumCache.Get(item.ID)
|
|
dow, ok2 := s.downloadNumCache.Get(item.ID)
|
|
if ok1 && ok2 {
|
|
ms.MonitoredNum = mon
|
|
ms.DownloadedNum = dow
|
|
} else {
|
|
details, err := s.db.GetMediaDetails(item.ID)
|
|
if err != nil {
|
|
return nil, errors.Wrap(err, "get details")
|
|
}
|
|
for _, ep := range details.Episodes {
|
|
if ep.Monitored {
|
|
ms.MonitoredNum++
|
|
if ep.Status == episode.StatusDownloaded {
|
|
ms.DownloadedNum++
|
|
}
|
|
}
|
|
}
|
|
s.monitorNumCache.Set(item.ID, ms.MonitoredNum)
|
|
s.downloadNumCache.Set(item.ID, ms.DownloadedNum)
|
|
}
|
|
|
|
res[i] = ms
|
|
}
|
|
return res, nil
|
|
}
|
|
|
|
func (s *Server) GetMovieWatchlist(c *gin.Context) (interface{}, error) {
|
|
list := s.db.GetMediaWatchlist(media.MediaTypeMovie)
|
|
res := make([]MediaWithStatus, len(list))
|
|
for i, item := range list {
|
|
var ms = MediaWithStatus{
|
|
Media: item,
|
|
MonitoredNum: 1,
|
|
DownloadedNum: 0,
|
|
}
|
|
dummyEp, err := s.db.GetMovieDummyEpisode(item.ID)
|
|
if err != nil {
|
|
log.Errorf("get dummy episode: %v", err)
|
|
} else {
|
|
if dummyEp.Status == episode.StatusDownloaded {
|
|
ms.DownloadedNum++
|
|
}
|
|
}
|
|
res[i] = ms
|
|
}
|
|
return res, nil
|
|
}
|
|
|
|
type MediaDetails struct {
|
|
*db.MediaDetails
|
|
Storage *ent.Storage `json:"storage"`
|
|
}
|
|
|
|
func (s *Server) GetMediaDetails(c *gin.Context) (interface{}, error) {
|
|
ids := c.Param("id")
|
|
id, err := strconv.Atoi(ids)
|
|
if err != nil {
|
|
return nil, errors.Wrap(err, "convert")
|
|
}
|
|
detail, err := s.db.GetMediaDetails(id)
|
|
if err != nil {
|
|
return nil, errors.Wrap(err, "get details")
|
|
}
|
|
st := s.db.GetStorage(detail.StorageID)
|
|
return MediaDetails{MediaDetails: detail, Storage: &st.Storage}, nil
|
|
}
|
|
|
|
func (s *Server) DeleteFromWatchlist(c *gin.Context) (interface{}, error) {
|
|
ids := c.Param("id")
|
|
id, err := strconv.Atoi(ids)
|
|
if err != nil {
|
|
return nil, errors.Wrap(err, "convert")
|
|
}
|
|
|
|
deleteFiles := c.Query("delete_files")
|
|
if strings.ToLower(deleteFiles) == "true" {
|
|
//will delete local media file
|
|
log.Infof("will delete local media files for %d", id)
|
|
m, err := s.db.GetMedia(id)
|
|
if err != nil {
|
|
log.Warnf("get media: %v", err)
|
|
} else {
|
|
st, err := s.core.GetStorage(m.StorageID, m.MediaType)
|
|
if err != nil {
|
|
log.Warnf("get storage error: %v", err)
|
|
} else {
|
|
if err := st.RemoveAll(m.TargetDir); err != nil {
|
|
log.Warnf("remove all : %v", err)
|
|
} else {
|
|
log.Infof("delete media files success: %v", m.TargetDir)
|
|
}
|
|
}
|
|
}
|
|
}
|
|
|
|
if err := s.db.DeleteMedia(id); err != nil {
|
|
return nil, errors.Wrap(err, "delete db")
|
|
}
|
|
os.RemoveAll(filepath.Join(db.ImgPath, ids)) //delete image related
|
|
|
|
return "success", nil
|
|
}
|