feat: movie also requires suggested dir

This commit is contained in:
Simon Ding
2024-07-30 10:50:40 +08:00
parent ba532d406a
commit 2c8c715540
5 changed files with 71 additions and 65 deletions

View File

@@ -26,10 +26,20 @@ type LocalStorage struct {
dir string
}
func (l *LocalStorage) Move(src, dest string) error {
targetDir := filepath.Join(l.dir, dest)
os.MkdirAll(filepath.Dir(targetDir), os.ModePerm)
err := filepath.Walk(src, func(path string, info fs.FileInfo, err error) error {
func (l *LocalStorage) Move(src, destDir string) error {
os.MkdirAll(filepath.Join(l.dir, destDir), os.ModePerm)
targetBase := filepath.Join(l.dir, destDir, filepath.Base(src)) //文件的场景,要加上文件名, move filename ./dir/
info, err := os.Stat(src)
if err != nil {
return errors.Wrap(err, "read source dir")
}
if info.IsDir() { //如果是路径,则只移动路径里面的文件,不管当前路径, 行为类似 move dirname/* target_dir/
targetBase = filepath.Join(l.dir, destDir)
}
err = filepath.Walk(src, func(path string, info fs.FileInfo, err error) error {
if err != nil {
return err
}
@@ -37,7 +47,7 @@ func (l *LocalStorage) Move(src, dest string) error {
if err != nil {
return errors.Wrapf(err, "relation between %s and %s", src, path)
}
destName := filepath.Join(targetDir, rel)
destName := filepath.Join(targetBase, rel)
if info.IsDir() {
os.Mkdir(destName, os.ModePerm)

View File

@@ -30,13 +30,20 @@ func NewWebdavStorage(url, user, password, path string, changeMediaHash bool) (*
}, nil
}
func (w *WebdavStorage) Move(local, remote string) error {
func (w *WebdavStorage) Move(local, remoteDir string) error {
remoteBase := filepath.Join(w.dir,remote)
remoteBase := filepath.Join(w.dir,remoteDir, filepath.Base(local))
info, err := os.Stat(local)
if err != nil {
return errors.Wrap(err, "read source dir")
}
if info.IsDir() { //如果是路径,则只移动路径里面的文件,不管当前路径, 行为类似 move dirname/* target_dir/
remoteBase = filepath.Join(w.dir, remoteDir)
}
//log.Infof("remove all content in %s", remoteBase)
//w.fs.RemoveAll(remoteBase)
err := filepath.Walk(local, func(path string, info fs.FileInfo, err error) error {
err = filepath.Walk(local, func(path string, info fs.FileInfo, err error) error {
if err != nil {
return errors.Wrapf(err, "read file %v", path)
}

View File

@@ -128,18 +128,10 @@ func (s *Server) moveCompletedTask(id int) (err1 error) {
stImpl = storageImpl
}
if r.EpisodeID == 0 {
//season package download
if err := stImpl.Move(filepath.Join(s.db.GetDownloadDir(), torrent.Name()), r.TargetDir); err != nil {
return errors.Wrap(err, "move file")
}
} else {
if err := stImpl.Move(filepath.Join(s.db.GetDownloadDir(), torrent.Name()), filepath.Join(r.TargetDir, torrent.Name())); err != nil {
return errors.Wrap(err, "move file")
}
//如果种子是路径,则会把路径展开,只移动文件,类似 move dir/* dir2/, 如果种子是文件,则会直接移动文件,类似 move file dir/
if err := stImpl.Move(filepath.Join(s.db.GetDownloadDir(), torrent.Name()), r.TargetDir); err != nil {
return errors.Wrap(err, "move file")
}
log.Infof("move downloaded files to target dir success, file: %v, target dir: %v", torrent.Name(), r.TargetDir)

View File

@@ -60,7 +60,7 @@ 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"`
Folder string `json:"folder" binding:"required"`
DownloadHistoryEpisodes bool `json:"download_history_episodes"` //for tv
}
@@ -187,7 +187,7 @@ func (s *Server) AddMovie2Watchlist(c *gin.Context) (interface{}, error) {
AirDate: detail.ReleaseDate,
Resolution: media.Resolution(in.Resolution),
StorageID: in.StorageID,
TargetDir: "./",
TargetDir: in.Folder,
}, []int{epid})
if err != nil {
return nil, errors.Wrap(err, "add to list")

View File

@@ -30,13 +30,15 @@ class _SearchPageState extends ConsumerState<SearchPage> {
List<Widget> res = searchList.when(
data: (data) {
if (data.isEmpty) {
return [Container(
height: MediaQuery.of(context).size.height * 0.6,
alignment: Alignment.center,
child: const Text(
"啥都没有...",
style: TextStyle(fontSize: 16),
))];
return [
Container(
height: MediaQuery.of(context).size.height * 0.6,
alignment: Alignment.center,
child: const Text(
"啥都没有...",
style: TextStyle(fontSize: 16),
))
];
}
var cards = List<Widget>.empty(growable: true);
for (final item in data) {
@@ -202,44 +204,39 @@ class _SearchPageState extends ConsumerState<SearchPage> {
});
},
),
item.mediaType == "tv"
? name.when(
data: (s) {
return storageSelected == 0
? const Text("")
: () {
final storage = v
.where((e) =>
e.id ==
storageSelected)
.first;
final path = storage
.settings!["tv_path"];
name.when(
data: (s) {
return storageSelected == 0
? const Text("")
: () {
final storage = v
.where((e) =>
e.id == storageSelected)
.first;
final path = item.mediaType ==
"tv"
? storage.settings!["tv_path"]
: storage
.settings!["movie_path"];
pathController.text = s;
return SizedBox(
//width: 300,
child: TextField(
controller:
pathController,
decoration:
InputDecoration(
labelText:
"存储路径",
prefix:
Text(path)),
),
);
}();
},
error: (error, stackTrace) =>
Text("$error"),
loading: () =>
const MyProgressIndicator(
size: 20,
),
)
: Text(""),
pathController.text = s;
return SizedBox(
//width: 300,
child: TextField(
controller: pathController,
decoration: InputDecoration(
labelText: "存储路径",
prefix: Text(path)),
),
);
}();
},
error: (error, stackTrace) =>
Text("$error"),
loading: () => const MyProgressIndicator(
size: 20,
),
),
item.mediaType == "tv"
? SizedBox(
width: 250,