Add retain_folder_name_extension option
This commit is contained in:
@@ -11,6 +11,7 @@ enable_repair: true # BEWARE! THERE CAN ONLY BE 1 INSTANCE OF ZURG THAT SHOULD R
|
||||
on_library_update: |
|
||||
echo "hook"
|
||||
network_buffer_size: 32768 # 32KB
|
||||
retain_folder_name_extension: false # if true, the folder name will contain the file extension when it is a torrent for a single file
|
||||
|
||||
# List of directory definitions and their filtering rules
|
||||
directories:
|
||||
|
||||
@@ -22,6 +22,7 @@ type ConfigInterface interface {
|
||||
GetOnLibraryUpdate() string
|
||||
GetNetworkBufferSize() int
|
||||
GetMountPoint() string
|
||||
EnableRetainFolderNameExtension() bool
|
||||
}
|
||||
|
||||
func LoadZurgConfig(filename string) (ConfigInterface, error) {
|
||||
|
||||
@@ -1,17 +1,18 @@
|
||||
package config
|
||||
|
||||
type ZurgConfig struct {
|
||||
Version string `yaml:"zurg"`
|
||||
Token string `yaml:"token"`
|
||||
Host string `yaml:"host"`
|
||||
Port string `yaml:"port"`
|
||||
NumOfWorkers int `yaml:"concurrent_workers"`
|
||||
RefreshEverySeconds int `yaml:"check_for_changes_every_secs"`
|
||||
CacheTimeHours int `yaml:"info_cache_time_hours"`
|
||||
CanRepair bool `yaml:"enable_repair"`
|
||||
OnLibraryUpdate string `yaml:"on_library_update"`
|
||||
NetworkBufferSize int `yaml:"network_buffer_size"`
|
||||
MountPoint string `yaml:"mount_point"`
|
||||
Version string `yaml:"zurg"`
|
||||
Token string `yaml:"token"`
|
||||
Host string `yaml:"host"`
|
||||
Port string `yaml:"port"`
|
||||
NumOfWorkers int `yaml:"concurrent_workers"`
|
||||
RefreshEverySeconds int `yaml:"check_for_changes_every_secs"`
|
||||
CacheTimeHours int `yaml:"info_cache_time_hours"`
|
||||
CanRepair bool `yaml:"enable_repair"`
|
||||
OnLibraryUpdate string `yaml:"on_library_update"`
|
||||
NetworkBufferSize int `yaml:"network_buffer_size"`
|
||||
MountPoint string `yaml:"mount_point"`
|
||||
RetainFolderNameExtension bool `yaml:"retain_folder_name_extension"`
|
||||
}
|
||||
|
||||
func (z *ZurgConfig) GetToken() string {
|
||||
@@ -68,3 +69,7 @@ func (z *ZurgConfig) GetNetworkBufferSize() int {
|
||||
func (z *ZurgConfig) GetMountPoint() string {
|
||||
return z.MountPoint
|
||||
}
|
||||
|
||||
func (z *ZurgConfig) EnableRetainFolderNameExtension() bool {
|
||||
return z.RetainFolderNameExtension
|
||||
}
|
||||
|
||||
@@ -49,14 +49,13 @@ func createSingleTorrentResponse(basePath string, torrents []torrent.Torrent) (*
|
||||
for _, torrent := range torrents {
|
||||
for _, file := range torrent.SelectedFiles {
|
||||
if file.Link == "" {
|
||||
// TODO: fix the file?
|
||||
// log.Println("File has no link, skipping (repairing links take time)", file.Path)
|
||||
continue
|
||||
}
|
||||
|
||||
filename := filepath.Base(file.Path)
|
||||
if finalName[filename] {
|
||||
// fragment := davextra.GetLinkFragment(file.Link)
|
||||
// filename = davextra.InsertLinkFragment(filename, fragment)
|
||||
continue
|
||||
}
|
||||
finalName[filename] = true
|
||||
|
||||
@@ -40,14 +40,13 @@ func createSingleTorrentResponse(basePath string, torrents []torrent.Torrent) (s
|
||||
for _, torrent := range torrents {
|
||||
for _, file := range torrent.SelectedFiles {
|
||||
if file.Link == "" {
|
||||
// TODO: fix the file?
|
||||
// log.Println("File has no link, skipping", file.Path)
|
||||
continue
|
||||
}
|
||||
|
||||
filename := filepath.Base(file.Path)
|
||||
if finalName[filename] {
|
||||
// fragment := davextra.GetLinkFragment(file.Link)
|
||||
// filename = davextra.InsertLinkFragment(filename, fragment)
|
||||
continue
|
||||
}
|
||||
finalName[filename] = true
|
||||
|
||||
@@ -35,7 +35,7 @@ type TorrentManager struct {
|
||||
// and store them in-memory; it is called only once at startup
|
||||
func NewTorrentManager(config config.ConfigInterface, cache *expirable.LRU[string, string]) *TorrentManager {
|
||||
t := &TorrentManager{
|
||||
requiredVersion: "4.11.2023",
|
||||
requiredVersion: fmt.Sprintf("4.11.2023 - retain:%v", config.EnableRetainFolderNameExtension()),
|
||||
config: config,
|
||||
cache: cache,
|
||||
workerPool: make(chan bool, config.GetNumOfWorkers()),
|
||||
@@ -256,7 +256,7 @@ func (t *TorrentManager) addMoreInfo(torrent *Torrent) {
|
||||
// see if api data and file data still match
|
||||
// then it means data is still usable
|
||||
if len(torrentFromFile.Links) == len(torrent.Links) {
|
||||
torrent.Name = getName(torrentFromFile)
|
||||
torrent.Name = t.getName(torrentFromFile)
|
||||
torrent.ForRepair = torrentFromFile.ForRepair
|
||||
torrent.SelectedFiles = torrentFromFile.SelectedFiles[:]
|
||||
return
|
||||
@@ -323,7 +323,7 @@ func (t *TorrentManager) addMoreInfo(torrent *Torrent) {
|
||||
}
|
||||
// update file cache
|
||||
torrent.OriginalName = info.OriginalName
|
||||
torrent.Name = getName(torrent)
|
||||
torrent.Name = t.getName(torrent)
|
||||
if len(selectedFiles) > 0 {
|
||||
// update the torrent with more data!
|
||||
torrent.SelectedFiles = selectedFiles
|
||||
@@ -332,16 +332,17 @@ func (t *TorrentManager) addMoreInfo(torrent *Torrent) {
|
||||
}
|
||||
}
|
||||
|
||||
func getName(torrent *Torrent) string {
|
||||
ret := ""
|
||||
if torrent.OriginalName != "" {
|
||||
ret = torrent.OriginalName
|
||||
func (t *TorrentManager) getName(torrent *Torrent) string {
|
||||
// drop the extension from the name
|
||||
t.log.Debugf("Original name: %s", torrent.OriginalName)
|
||||
t.log.Debugf("Name: %s", torrent.Name)
|
||||
if t.config.EnableRetainFolderNameExtension() && strings.Contains(torrent.Name, torrent.OriginalName) {
|
||||
return torrent.Name
|
||||
} else {
|
||||
ret = torrent.Name
|
||||
ret := strings.TrimSuffix(torrent.OriginalName, ".mp4")
|
||||
ret = strings.TrimSuffix(ret, ".mkv")
|
||||
return ret
|
||||
}
|
||||
ret = strings.TrimSuffix(ret, ".mkv")
|
||||
ret = strings.TrimSuffix(ret, ".mp4")
|
||||
return ret
|
||||
}
|
||||
|
||||
// mapToDirectories maps torrents to directories
|
||||
|
||||
@@ -11,7 +11,6 @@ import (
|
||||
"github.com/debridmediamanager.com/zurg/internal/dav"
|
||||
intHttp "github.com/debridmediamanager.com/zurg/internal/http"
|
||||
"github.com/debridmediamanager.com/zurg/internal/torrent"
|
||||
"github.com/debridmediamanager.com/zurg/pkg/davextra"
|
||||
"github.com/debridmediamanager.com/zurg/pkg/logutil"
|
||||
"github.com/debridmediamanager.com/zurg/pkg/realdebrid"
|
||||
"github.com/hashicorp/golang-lru/v2/expirable"
|
||||
@@ -58,8 +57,7 @@ func HandleGetRequest(w http.ResponseWriter, r *http.Request, t *torrent.Torrent
|
||||
return
|
||||
}
|
||||
|
||||
filenameV2, linkFragment := davextra.ExtractLinkFragment(filename)
|
||||
torrent, file := getFile(torrents, filenameV2, linkFragment)
|
||||
torrent, file := getFile(torrents, filename)
|
||||
if file == nil {
|
||||
log.Errorf("Cannot find file from path %s", requestPath)
|
||||
http.Error(w, "File not found", http.StatusNotFound)
|
||||
@@ -79,20 +77,20 @@ func HandleGetRequest(w http.ResponseWriter, r *http.Request, t *torrent.Torrent
|
||||
resp := realdebrid.RetryUntilOk(unrestrictFn)
|
||||
if resp == nil {
|
||||
if !file.Unavailable {
|
||||
log.Errorf("Cannot unrestrict file %s %s", filenameV2, link)
|
||||
log.Errorf("Cannot unrestrict file %s %s", filename, link)
|
||||
t.HideTheFile(torrent, file)
|
||||
}
|
||||
streamErrorVideo("https://www.youtube.com/watch?v=gea_FJrtFVA", w, r, c, log)
|
||||
return
|
||||
} else if resp.Filename != filenameV2 {
|
||||
} else if resp.Filename != filename {
|
||||
actualExt := filepath.Ext(resp.Filename)
|
||||
expectedExt := filepath.Ext(filenameV2)
|
||||
expectedExt := filepath.Ext(filename)
|
||||
if actualExt != expectedExt && resp.Streamable != 1 {
|
||||
log.Errorf("File extension mismatch: %s and %s", filenameV2, resp.Filename)
|
||||
log.Errorf("File extension mismatch: %s and %s", filename, resp.Filename)
|
||||
streamErrorVideo("https://www.youtube.com/watch?v=t9VgOriBHwE", w, r, c, log)
|
||||
return
|
||||
} else {
|
||||
log.Errorf("Filename mismatch: %s and %s", filenameV2, resp.Filename)
|
||||
log.Errorf("Filename mismatch: %s and %s", filename, resp.Filename)
|
||||
}
|
||||
}
|
||||
cache.Add(requestPath, resp.Download)
|
||||
|
||||
@@ -9,7 +9,6 @@ import (
|
||||
|
||||
"github.com/debridmediamanager.com/zurg/internal/config"
|
||||
"github.com/debridmediamanager.com/zurg/internal/torrent"
|
||||
"github.com/debridmediamanager.com/zurg/pkg/davextra"
|
||||
"github.com/debridmediamanager.com/zurg/pkg/logutil"
|
||||
"github.com/hashicorp/golang-lru/v2/expirable"
|
||||
)
|
||||
@@ -53,8 +52,7 @@ func HandleHeadRequest(w http.ResponseWriter, r *http.Request, t *torrent.Torren
|
||||
return
|
||||
}
|
||||
|
||||
filenameV2, linkFragment := davextra.ExtractLinkFragment(filename)
|
||||
_, file := getFile(torrents, filenameV2, linkFragment)
|
||||
_, file := getFile(torrents, filename)
|
||||
if file == nil {
|
||||
log.Errorf("Cannot find file from path %s", requestPath)
|
||||
http.Error(w, "Cannot find file", http.StatusNotFound)
|
||||
|
||||
@@ -2,17 +2,16 @@ package universal
|
||||
|
||||
import (
|
||||
"path/filepath"
|
||||
"strings"
|
||||
|
||||
"github.com/debridmediamanager.com/zurg/internal/torrent"
|
||||
)
|
||||
|
||||
// getFile finds a link by a fragment, it might be wrong
|
||||
func getFile(torrents []torrent.Torrent, filename, fragment string) (*torrent.Torrent, *torrent.File) {
|
||||
func getFile(torrents []torrent.Torrent, filename string) (*torrent.Torrent, *torrent.File) {
|
||||
for t := range torrents {
|
||||
for f, file := range torrents[t].SelectedFiles {
|
||||
fname := filepath.Base(file.Path)
|
||||
if filename == fname && strings.Contains(file.Link, fragment) {
|
||||
if filename == fname {
|
||||
return &torrents[t], &torrents[t].SelectedFiles[f]
|
||||
}
|
||||
}
|
||||
|
||||
@@ -1,11 +1,7 @@
|
||||
package davextra
|
||||
|
||||
import (
|
||||
"fmt"
|
||||
"net/url"
|
||||
"path/filepath"
|
||||
"regexp"
|
||||
"strings"
|
||||
)
|
||||
|
||||
// GetLinkFragment returns the longest alphanumeric string from a link
|
||||
@@ -20,33 +16,3 @@ func GetLinkFragment(link string) string {
|
||||
}
|
||||
return longestMatch[:4]
|
||||
}
|
||||
|
||||
// InsertLinkFragment inserts the link ID into a filename
|
||||
// returns the new filename
|
||||
func InsertLinkFragment(filename, dupeID string) string {
|
||||
ext := filepath.Ext(filename)
|
||||
name := strings.TrimSuffix(filename, ext)
|
||||
return fmt.Sprintf("%s DMM%s%s", name, dupeID, ext)
|
||||
}
|
||||
|
||||
// ExtractLinkFragment extracts the link ID from a filename
|
||||
// returns the original filename and the link ID
|
||||
func ExtractLinkFragment(filename string) (string, string) {
|
||||
filenameV2, err := url.PathUnescape(filename)
|
||||
if err != nil {
|
||||
filenameV2 = filename
|
||||
}
|
||||
ext := filepath.Ext(filenameV2)
|
||||
name := strings.TrimSuffix(filenameV2, ext)
|
||||
|
||||
r := regexp.MustCompile(`\sDMM(\w+)`)
|
||||
matches := r.FindStringSubmatch(name)
|
||||
if len(matches) < 2 {
|
||||
// No ID found
|
||||
return filenameV2, ""
|
||||
}
|
||||
|
||||
// Remove ID from filename
|
||||
originalName := strings.Replace(name, matches[0], "", 1)
|
||||
return originalName + ext, matches[1]
|
||||
}
|
||||
|
||||
Reference in New Issue
Block a user