mirror of
https://github.com/truewhile/MeBox.git
synced 2026-10-12 00:06:37 +08:00
Fix scraping workflows subscriptions bot and recycle bin
This commit is contained in:
@@ -14,6 +14,7 @@ import (
|
||||
"time"
|
||||
|
||||
"go.uber.org/zap"
|
||||
"gorm.io/gorm"
|
||||
|
||||
"github.com/ShukeBta/MediaStationGo/internal/config"
|
||||
"github.com/ShukeBta/MediaStationGo/internal/model"
|
||||
@@ -239,6 +240,17 @@ func dockerVolumePathCandidates(path string) []string {
|
||||
if strings.HasPrefix(normalized, host+"/") {
|
||||
addCandidate(mapping.container + strings.TrimPrefix(normalized, host))
|
||||
}
|
||||
container := cleanPathForVolumeMapping(mapping.container)
|
||||
if container == "." || container == "" || strings.HasPrefix(container, ".") {
|
||||
continue
|
||||
}
|
||||
if normalized == container {
|
||||
addCandidate(host)
|
||||
continue
|
||||
}
|
||||
if strings.HasPrefix(normalized, container+"/") {
|
||||
addCandidate(host + strings.TrimPrefix(normalized, container))
|
||||
}
|
||||
}
|
||||
|
||||
for _, marker := range []struct {
|
||||
@@ -610,6 +622,8 @@ func (s *MediaService) GetMedia(ctx context.Context, id string) (*model.Media, e
|
||||
return s.repo.Media.FindByID(ctx, id)
|
||||
}
|
||||
|
||||
const maxRecycleBinRecords = 200
|
||||
|
||||
// SoftDelete moves a media row to the recycle bin (gorm soft delete).
|
||||
// The on-disk file is kept; admins can purge it later.
|
||||
func (s *MediaService) SoftDelete(ctx context.Context, id string) error {
|
||||
@@ -626,6 +640,9 @@ func (s *MediaService) SoftDelete(ctx context.Context, id string) error {
|
||||
}
|
||||
err = s.repo.DB.WithContext(ctx).Where("id = ?", id).Delete(&model.Media{}).Error
|
||||
if err == nil {
|
||||
if pruneErr := pruneRecycleBinRows(ctx, s.repo.DB, maxRecycleBinRecords); pruneErr != nil {
|
||||
return pruneErr
|
||||
}
|
||||
s.invalidateMediaCache(ctx)
|
||||
}
|
||||
return err
|
||||
@@ -643,8 +660,11 @@ func (s *MediaService) RestoreDeleted(ctx context.Context, id string) error {
|
||||
|
||||
// ListRecycleBin returns every soft-deleted row, newest first.
|
||||
func (s *MediaService) ListRecycleBin(ctx context.Context, limit int) ([]model.Media, error) {
|
||||
if limit <= 0 || limit > 500 {
|
||||
limit = 100
|
||||
if err := pruneRecycleBinRows(ctx, s.repo.DB, maxRecycleBinRecords); err != nil {
|
||||
return nil, err
|
||||
}
|
||||
if limit <= 0 || limit > maxRecycleBinRecords {
|
||||
limit = maxRecycleBinRecords
|
||||
}
|
||||
var rows []model.Media
|
||||
err := s.repo.DB.Unscoped().
|
||||
@@ -655,6 +675,41 @@ func (s *MediaService) ListRecycleBin(ctx context.Context, limit int) ([]model.M
|
||||
return rows, err
|
||||
}
|
||||
|
||||
func pruneRecycleBinRows(ctx context.Context, db *gorm.DB, keep int) error {
|
||||
if db == nil {
|
||||
return nil
|
||||
}
|
||||
if keep <= 0 {
|
||||
keep = maxRecycleBinRecords
|
||||
}
|
||||
var rows []struct {
|
||||
ID string
|
||||
}
|
||||
if err := db.WithContext(ctx).Unscoped().
|
||||
Model(&model.Media{}).
|
||||
Select("id").
|
||||
Where("deleted_at IS NOT NULL").
|
||||
Order("deleted_at desc").
|
||||
Limit(100000).
|
||||
Offset(keep).
|
||||
Find(&rows).Error; err != nil {
|
||||
return err
|
||||
}
|
||||
if len(rows) == 0 {
|
||||
return nil
|
||||
}
|
||||
ids := make([]string, 0, len(rows))
|
||||
for _, row := range rows {
|
||||
if row.ID != "" {
|
||||
ids = append(ids, row.ID)
|
||||
}
|
||||
}
|
||||
if len(ids) == 0 {
|
||||
return nil
|
||||
}
|
||||
return db.WithContext(ctx).Unscoped().Where("id IN ?", ids).Delete(&model.Media{}).Error
|
||||
}
|
||||
|
||||
// PurgeDeleted permanently removes a soft-deleted row from the database.
|
||||
func (s *MediaService) PurgeDeleted(ctx context.Context, id string) error {
|
||||
err := s.repo.DB.WithContext(ctx).Unscoped().Where("id = ?", id).Delete(&model.Media{}).Error
|
||||
|
||||
Reference in New Issue
Block a user