Skip to content

Commit

Permalink
feat: download per media feature
Browse files Browse the repository at this point in the history
  • Loading branch information
simon-ding committed Aug 12, 2024
1 parent 3c37948 commit 09ff67f
Show file tree
Hide file tree
Showing 7 changed files with 109 additions and 56 deletions.
4 changes: 2 additions & 2 deletions pkg/metadata/movie.go
Original file line number Diff line number Diff line change
Expand Up @@ -57,13 +57,13 @@ func ParseMovie(name string) *MovieMetadata {

// https://en.wikipedia.org/wiki/Pirated_movie_release_types
func isQiangban(name string) bool {
qiangbanFilter := []string{"CAM-Rip", "CAM", "HDCAM", "TS", "HDTS", "TELESYNC", "PDVD", "PreDVDRip", "TC", "HDTC", "TELECINE", "WP", "WORKPRINT"}
qiangbanFilter := []string{"CAMRip","CAM-Rip", "CAM", "HDCAM", "TS","TSRip", "HDTS", "TELESYNC", "PDVD", "PreDVDRip", "TC", "HDTC", "TELECINE", "WP", "WORKPRINT"}
re := regexp.MustCompile(`\W`)
name = re.ReplaceAllString(strings.ToLower(name), " ")
fields := strings.Fields(name)
for _, q := range qiangbanFilter {
for _, f := range fields {
if strings.ToLower(q) == strings.ToLower(f) {
if strings.EqualFold(q, f) {
return true
}
}
Expand Down
120 changes: 69 additions & 51 deletions server/core/scheduler.go
Original file line number Diff line number Diff line change
Expand Up @@ -19,8 +19,8 @@ import (
func (c *Client) addSysCron() {
c.mustAddCron("@every 1m", c.checkTasks)
c.mustAddCron("0 0 * * * *", func() {
c.downloadTvSeries()
c.downloadMovie()
c.downloadAllTvSeries()
c.downloadAllMovies()
})
c.mustAddCron("0 0 */12 * * *", c.checkAllSeriesNewSeason)
c.cron.Start()
Expand Down Expand Up @@ -206,79 +206,97 @@ type Task struct {
pkg.Torrent
}

func (c *Client) downloadTvSeries() {
log.Infof("begin check all tv series resources")
allSeries := c.db.GetMediaWatchlist(media.MediaTypeTv)
for _, series := range allSeries {
tvDetail := c.db.GetMediaDetails(series.ID)
m := make(map[int][]*ent.Episode)
for _, ep := range tvDetail.Episodes {
m[ep.SeasonNumber] = append(m[ep.SeasonNumber], ep)
func (c *Client) DownloadSeriesAllEpisodes(id int) ([]string, error) {
tvDetail := c.db.GetMediaDetails(id)
m := make(map[int][]*ent.Episode)
for _, ep := range tvDetail.Episodes {
m[ep.SeasonNumber] = append(m[ep.SeasonNumber], ep)
}
var allNames []string
for seasonNum, epsides := range m {
wantedSeasonPack := true
for _, ep := range epsides {
if !ep.Monitored {
wantedSeasonPack = false
}
if ep.Status != episode.StatusMissing {
wantedSeasonPack = false
}
}
for seasonNum, epsides := range m {
wantedSeasonPack := true
if wantedSeasonPack {
name, err := c.SearchAndDownload(id, seasonNum, -1)
if err != nil {
return nil, errors.Wrap(err, "find resource")
} else {
allNames = append(allNames, *name)
log.Infof("begin download torrent resource: %v", name)
}

} else {
for _, ep := range epsides {
if !ep.Monitored {
wantedSeasonPack = false
continue
}
if ep.Status != episode.StatusMissing {
wantedSeasonPack = false
continue
}
}
if wantedSeasonPack {
name, err := c.SearchAndDownload(series.ID, seasonNum, -1)
name, err := c.SearchAndDownload(id, ep.SeasonNumber, ep.EpisodeNumber)
if err != nil {
log.Infof("cannot find resource to download : %v", err)
return nil, errors.Wrap(err, "find resource to download")
} else {
allNames = append(allNames, *name)
log.Infof("begin download torrent resource: %v", name)
}
}

} else {
for _, ep := range epsides {
if !ep.Monitored {
continue
}
if ep.Status != episode.StatusMissing {
continue
}
name, err := c.SearchAndDownload(series.ID, ep.SeasonNumber, ep.EpisodeNumber)
if err != nil {
log.Infof("cannot find resource to download for %s: %v", ep.Title, err)
} else {
log.Infof("begin download torrent resource: %v", name)
}
}
}

}
}
return allNames, nil
}

func (c *Client) downloadAllTvSeries() {
log.Infof("begin check all tv series resources")
allSeries := c.db.GetMediaWatchlist(media.MediaTypeTv)
for _, series := range allSeries {
if _, err := c.DownloadSeriesAllEpisodes(series.ID); err != nil {
return
}
}
}

func (c *Client) downloadMovie() {
func (c *Client) downloadAllMovies() {
log.Infof("begin check all movie resources")
allSeries := c.db.GetMediaWatchlist(media.MediaTypeMovie)

for _, series := range allSeries {
detail := c.db.GetMediaDetails(series.ID)
if len(detail.Episodes) == 0 {
log.Errorf("no related dummy episode: %v", detail.NameEn)
continue
}
ep := detail.Episodes[0]
if ep.Status != episode.StatusMissing {
continue
}

if err := c.downloadMovieSingleEpisode(ep, series.TargetDir); err != nil {
if _, err := c.DownloadMovieByID(series.ID); err != nil {
log.Errorf("download movie error: %v", err)
}
}
}

func (c *Client) downloadMovieSingleEpisode(ep *ent.Episode, targetDir string) error {
func (c *Client) DownloadMovieByID(id int) (string, error) {
detail := c.db.GetMediaDetails(id)
if len(detail.Episodes) == 0 {
return "", fmt.Errorf("no related dummy episode: %v", detail.NameEn)
}
ep := detail.Episodes[0]
if ep.Status != episode.StatusMissing {
return "", nil
}

if name, err := c.downloadMovieSingleEpisode(ep, detail.TargetDir); err != nil {
return "", errors.Wrap(err, "download movie")
} else {
return name, nil
}
}

func (c *Client) downloadMovieSingleEpisode(ep *ent.Episode, targetDir string) (string, error) {
trc, dlc, err := c.getDownloadClient()
if err != nil {
return errors.Wrap(err, "connect transmission")
return "", errors.Wrap(err, "connect transmission")
}
qiangban := c.db.GetSetting(db.SettingAllowQiangban)
allowQiangban := false
Expand All @@ -294,13 +312,13 @@ func (c *Client) downloadMovieSingleEpisode(ep *ent.Episode, targetDir string) e
})
if err != nil {

return errors.Wrap(err, "search movie")
return "", errors.Wrap(err, "search movie")
}
r1 := res[0]
log.Infof("begin download torrent resource: %v", r1.Name)
torrent, err := trc.Download(r1.Link, c.db.GetDownloadDir())
if err != nil {
return errors.Wrap(err, "downloading")
return "", errors.Wrap(err, "downloading")
}
torrent.Start()

Expand All @@ -322,7 +340,7 @@ func (c *Client) downloadMovieSingleEpisode(ep *ent.Episode, targetDir string) e
c.tasks[history.ID] = &Task{Torrent: torrent}

c.db.SetEpisodeStatus(ep.ID, episode.StatusDownloading)
return nil
return r1.Name, nil
}

func (c *Client) checkAllSeriesNewSeason() {
Expand Down
19 changes: 19 additions & 0 deletions server/resources.go
Original file line number Diff line number Diff line change
Expand Up @@ -7,6 +7,7 @@ import (
"polaris/log"
"polaris/pkg/torznab"
"polaris/server/core"
"strconv"

"github.com/gin-gonic/gin"
"github.com/pkg/errors"
Expand Down Expand Up @@ -167,3 +168,21 @@ func (s *Server) DownloadTorrent(c *gin.Context) (interface{}, error) {
}

}

func (s *Server) DownloadAll(c *gin.Context) (interface{}, error) {
ids := c.Param("id")
id, err := strconv.Atoi(ids)
if err != nil {
return nil, errors.Wrap(err, "convert")
}
m, err := s.db.GetMedia(id)
if err != nil {
return nil, errors.Wrap(err, "get media")
}
if m.MediaType == media.MediaTypeTv {
return s.core.DownloadSeriesAllEpisodes(m.ID)
}
name, err := s.core.DownloadMovieByID(m.ID)

return []string{name}, err
}
1 change: 1 addition & 0 deletions server/server.go
Original file line number Diff line number Diff line change
Expand Up @@ -91,6 +91,7 @@ func (s *Server) Serve() error {
tv.DELETE("/record/:id", HttpHandler(s.DeleteFromWatchlist))
tv.GET("/suggest/tv/:tmdb_id", HttpHandler(s.SuggestedSeriesFolderName))
tv.GET("/suggest/movie/:tmdb_id", HttpHandler(s.SuggestedMovieFolderName))
tv.GET("/downloadall/:id", HttpHandler(s.DownloadAll))
}
indexer := api.Group("/indexer")
{
Expand Down
1 change: 1 addition & 0 deletions ui/lib/providers/APIs.dart
Original file line number Diff line number Diff line change
Expand Up @@ -8,6 +8,7 @@ class APIs {
static final _baseUrl = baseUrl();
static final searchUrl = "$_baseUrl/api/v1/media/search";
static final editMediaUrl = "$_baseUrl/api/v1/media/edit";
static final downloadAllUrl = "$_baseUrl/api/v1/media/downloadall/";
static final settingsUrl = "$_baseUrl/api/v1/setting/do";
static final settingsGeneralUrl = "$_baseUrl/api/v1/setting/general";
static final watchlistTvUrl = "$_baseUrl/api/v1/media/tv/watchlist";
Expand Down
10 changes: 10 additions & 0 deletions ui/lib/providers/series_details.dart
Original file line number Diff line number Diff line change
Expand Up @@ -81,6 +81,16 @@ class SeriesDetailData
}
ref.invalidateSelf();
}

Future<void> downloadall() async {
final dio = APIs.getDio();
var resp = await dio.get(APIs.downloadAllUrl + id!);
var sp = ServerResponse.fromJson(resp.data);
if (sp.code != 0) {
throw sp.message;
}
ref.invalidateSelf();
}
}

class SeriesDetails {
Expand Down
10 changes: 7 additions & 3 deletions ui/lib/widgets/detail_card.dart
Original file line number Diff line number Diff line change
Expand Up @@ -303,9 +303,13 @@ class _DetailCardState extends ConsumerState<DetailCard> {
}

Widget downloadButton() {
return IconButton(
return LoadingIconButton(
tooltip: widget.details.mediaType == "tv" ? "查找并下载所有监控剧集" : "查找并下载此电影",
onPressed: () {},
icon: const Icon(Icons.download_rounded));
onPressed: () async{
await ref
.read(mediaDetailsProvider(widget.details.id.toString()).notifier)
.downloadall();
},
icon: Icons.download_rounded);
}
}

0 comments on commit 09ff67f

Please sign in to comment.