Fall back to rm when a fuzzy-dedup delete target isn't tracked in beets
A handful of confirmed candidates reference files that are no longer in the beets DB (removed by some other pass, or never re-imported after a move) but are still sitting on disk -- beet remove can't match them by id or path either way, so they failed forever. If the file still exists after a "No matching items found" error, remove it directly instead of counting it as a failure. Applies to both --apply and --apply-pairs.
This commit is contained in:
@@ -180,9 +180,22 @@ def _apply_pairs(pairs_file: str, emit_json: bool) -> int:
|
||||
capture_output=True, text=True,
|
||||
)
|
||||
if result.returncode != 0:
|
||||
print(f" FAILED: {delete_path} — {result.stderr.strip()}", file=sys.stderr)
|
||||
failed += 1
|
||||
continue
|
||||
if "No matching items found" in result.stderr and os.path.exists(delete_path):
|
||||
# Not tracked in beets at all (e.g. it was already removed
|
||||
# from the DB by some other pass, or never re-imported after
|
||||
# a move) but the duplicate file itself is still sitting on
|
||||
# disk -- `beet remove` can never match it by id or path
|
||||
# either way, so just remove the file directly.
|
||||
try:
|
||||
os.remove(delete_path)
|
||||
except OSError as exc:
|
||||
print(f" FAILED: {delete_path} — not in beets, then rm failed: {exc}", file=sys.stderr)
|
||||
failed += 1
|
||||
continue
|
||||
else:
|
||||
print(f" FAILED: {delete_path} — {result.stderr.strip()}", file=sys.stderr)
|
||||
failed += 1
|
||||
continue
|
||||
print(f" DELETE {delete_path}")
|
||||
deleted += 1
|
||||
if emit_json:
|
||||
@@ -372,8 +385,18 @@ def main() -> int:
|
||||
capture_output=True, text=True,
|
||||
)
|
||||
if result.returncode != 0:
|
||||
print(f" FAILED: {path} — {result.stderr.strip()}", file=sys.stderr)
|
||||
failed += 1
|
||||
if "No matching items found" in result.stderr and os.path.exists(path):
|
||||
# Item was already gone from beets by the time we got here
|
||||
# (e.g. removed by an earlier pass) but the file is still on
|
||||
# disk -- remove it directly instead of counting it failed.
|
||||
try:
|
||||
os.remove(path)
|
||||
except OSError as exc:
|
||||
print(f" FAILED: {path} — not in beets, then rm failed: {exc}", file=sys.stderr)
|
||||
failed += 1
|
||||
else:
|
||||
print(f" FAILED: {path} — {result.stderr.strip()}", file=sys.stderr)
|
||||
failed += 1
|
||||
deleted = len(delete_targets) - failed - skipped_unconfirmed
|
||||
print(f"[fuzzy-dupes] done. {deleted} deleted, {failed} failed, {skipped_unconfirmed} skipped (unconfirmed).")
|
||||
return 1 if failed else 0
|
||||
|
||||
Reference in New Issue
Block a user