Proactive repair

This commit is contained in:
Ben Sarmiento
2024-01-07 19:00:53 +01:00
parent cfb0f12fff
commit 80a1af378a
3 changed files with 60 additions and 6 deletions

View File

@@ -72,7 +72,7 @@ func (t *TorrentManager) RefreshTorrents() []string {
directories = append(directories, directory) directories = append(directories, directory)
} }
}) })
t.log.Debugf("Added %s to %v", accessKey, directories) // t.log.Debugf("Added %s to %v", accessKey, directories)
t.allAccessKeys.Add(accessKey) t.allAccessKeys.Add(accessKey)
return false return false
}) })

View File

@@ -8,6 +8,7 @@ import (
"github.com/debridmediamanager/zurg/internal/config" "github.com/debridmediamanager/zurg/internal/config"
"github.com/debridmediamanager/zurg/pkg/realdebrid" "github.com/debridmediamanager/zurg/pkg/realdebrid"
mapset "github.com/deckarep/golang-set/v2"
cmap "github.com/orcaman/concurrent-map/v2" cmap "github.com/orcaman/concurrent-map/v2"
) )
@@ -23,14 +24,40 @@ func (t *TorrentManager) RepairAll() {
func (t *TorrentManager) repairAll() { func (t *TorrentManager) repairAll() {
allTorrents, _ := t.DirectoryMap.Get(INT_ALL) allTorrents, _ := t.DirectoryMap.Get(INT_ALL)
hashes := make([]string, 0) var hashGroups []mapset.Set[string]
const maxGroupSize = 399
currentGroup := mapset.NewSet[string]()
hashGroups = append(hashGroups, currentGroup)
allTorrents.IterCb(func(_ string, torrent *Torrent) { allTorrents.IterCb(func(_ string, torrent *Torrent) {
if torrent.AnyInProgress() || torrent.Unfixable { if torrent.AnyInProgress() || torrent.Unfixable {
return return
} }
hashes = append(hashes, torrent.Hash) // Check if the current group is full
if currentGroup.Cardinality() >= maxGroupSize {
// Create a new group and add it to the hashGroups
currentGroup = mapset.NewSet[string]()
hashGroups = append(hashGroups, currentGroup)
}
// Add the hash to the current group
currentGroup.Add(torrent.Hash)
}) })
var availabilityChecks = make(map[string]bool)
for i := range hashGroups {
resp, err := t.Api.AvailabilityCheck(hashGroups[i].ToSlice())
if err != nil {
t.log.Warnf("Cannot check availability: %v", err)
continue
}
for hash, hosterHash := range resp {
// Check if HosterHash is a map (Variants field is used)
availabilityChecks[hash] = len(hosterHash.Variants) > 0
}
}
var toRepair []*Torrent var toRepair []*Torrent
allTorrents.IterCb(func(_ string, torrent *Torrent) { allTorrents.IterCb(func(_ string, torrent *Torrent) {
if torrent.AnyInProgress() || torrent.Unfixable { if torrent.AnyInProgress() || torrent.Unfixable {
@@ -38,6 +65,10 @@ func (t *TorrentManager) repairAll() {
} }
// check 1: for cached status // check 1: for cached status
isCached := true
if _, ok := availabilityChecks[torrent.Hash]; !ok || !availabilityChecks[torrent.Hash] {
isCached = false
}
// check 2: for broken files // check 2: for broken files
hasBrokenFiles := false hasBrokenFiles := false
@@ -46,7 +77,8 @@ func (t *TorrentManager) repairAll() {
hasBrokenFiles = true hasBrokenFiles = true
} }
}) })
if hasBrokenFiles {
if !isCached || hasBrokenFiles {
toRepair = append(toRepair, torrent) toRepair = append(toRepair, torrent)
} }
}) })

View File

@@ -1,6 +1,7 @@
package realdebrid package realdebrid
import ( import (
"errors"
"math" "math"
"strings" "strings"
@@ -134,8 +135,11 @@ type User struct {
// key: torrent hash // key: torrent hash
type AvailabilityResponse map[string]HosterHash type AvailabilityResponse map[string]HosterHash
type HosterHash struct {
// key: "rd" // key: "rd"
type HosterHash map[string][]SelectionVariant Variants map[string][]SelectionVariant
Strings []string
}
// key: file id // key: file id
type SelectionVariant map[int]FileData type SelectionVariant map[int]FileData
@@ -144,3 +148,21 @@ type FileData struct {
Filename string `json:"filename"` Filename string `json:"filename"`
Filesize int `json:"filesize"` Filesize int `json:"filesize"`
} }
func (h *HosterHash) UnmarshalJSON(data []byte) error {
// First, try unmarshaling as map[string][]SelectionVariant
var variants map[string][]SelectionVariant
if err := json.Unmarshal(data, &variants); err == nil {
h.Variants = variants
return nil
}
// If that fails, try unmarshaling as []string
var strings []string
if err := json.Unmarshal(data, &strings); err == nil {
h.Strings = strings
return nil
}
return errors.New("availability json data did not match expected formats (map or array)")
}