This feature was introduced in 2.10 but results a lot of data being
overwritten with (potentially) incorrect data the next time a user runs
`mbsync` over their library.
To make this less of a "breaking" change, make this feature opt-in. The
users who want this large change can enable the functionality.
When album art is being moved to the destination folder, a PermissionError (or
other OSError) can occur if the file is locked by another process (e.g. a media
player scanning the folder). Previously this caused an unhandled traceback crash.
Wrap album.set_art() in a try/except OSError block in _set_art, log a warning,
and return False so callers can handle the failure gracefully.
Fixes#6193
Replace defensive .get("aliases", []) with recording["aliases"] now that
"aliases" is in BROWSE_INCLUDES. Swap the graceful-fallback test for one
that asserts aliases from browse results take priority over the track title.
When a release exceeds BROWSE_MAXTRACKS tracks, _ensure_complete_recordings
fetches recordings via browse_recordings. BROWSE_INCLUDES was missing "aliases",
so the API never returned alias data, causing a KeyError in get_tracks_from_medium.
Add "aliases" to BROWSE_INCLUDES and defensively use .get("aliases", []) at the
access site, consistent with all other alias lookups in the file.
Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com>
Update all references in core, plugins, and tests to import UserError
from the new location. This centralizes exception handling and improves
code organization.
if import.from_scratch was set in the config, runnning mbsync would
clear any metadata not provided by MBz (replay gain, lyrics, genres...).
we now ignore this setting when running mbsync to preserve metadata.
Fixes: #6613
* the pugin used an empty format string unless --count was provided,
resulting in outputs like `: 1`. it now correctly displays duplicated
items.
* --count was ignored (aside from above bug), and item count was always
appended to output.