Handle artist display names

This commit is contained in:
emeric
2023-10-14 19:22:13 +02:00
parent 76290768bb
commit d2956df4cc
20 changed files with 389 additions and 309 deletions
+3
View File
@@ -210,6 +210,7 @@ getRelease(const TagMap& tags)
release.emplace();
release->name = std::move(*releaseName);
release->artistDisplayName = getPropertyValueAs<std::string_view>(tags, "ALBUMARTIST").value_or("");
release->mbid = getPropertyValueFirstMatchAs<UUID>(tags, {"MUSICBRAINZ_ALBUMID", "MUSICBRAINZ ALBUM ID", "MUSICBRAINZ/ALBUM ID"});
release->artists = getArtists(tags, {"ALBUMARTISTS", "ALBUMARTIST"}, {"ALBUMARTISTSSORT", "ALBUMARTISTSORT"}, {"MUSICBRAINZ_ALBUMARTISTID", "MUSICBRAINZ ALBUM ARTIST ID", "MUSICBRAINZ/ALBUM ARTIST ID"});
release->mediumCount = getPropertyValueAs<std::size_t>(tags, "DISCTOTAL");
@@ -353,6 +354,8 @@ TagLibParser::processTag(Track& track, const std::string& tag, const std::vector
track.copyrightURL = value;
else if (tag == "REPLAYGAIN_TRACK_GAIN")
track.replayGain = StringUtils::readAs<float>(value);
else if (tag == "ARTIST")
track.artistDisplayName = value;
else if (_clusterTypeNames.find(tag) != _clusterTypeNames.end())
{
std::set<std::string> clusterNames;
@@ -79,6 +79,7 @@ namespace MetaData
std::optional<UUID> mbid;
std::string name;
std::string artistDisplayName;
std::vector<Artist> artists;
std::optional<std::size_t> mediumCount;
std::optional<PrimaryType> primaryType;
@@ -117,6 +118,7 @@ namespace MetaData
std::string copyright;
std::string copyrightURL;
std::optional<float> replayGain;
std::string artistDisplayName;
std::vector<Artist> artists;
std::vector<Artist> conductorArtists;
std::vector<Artist> composerArtists;
@@ -665,6 +665,18 @@ CREATE TABLE IF NOT EXISTS "track_backup" (
ScanSettings::get(session).modify()->incScanVersion();
}
static
void
migrateFromV40(Session& session)
{
// add artist_display_name in Release and Track
session.getDboSession().execute("ALTER TABLE release ADD artist_display_name TEXT");
session.getDboSession().execute("ALTER TABLE track ADD artist_display_name TEXT");
// Just increment the scan version of the settings to make the next scheduled scan rescan everything
ScanSettings::get(session).modify()->incScanVersion();
}
void
doDbMigration(Session& session)
{
@@ -711,6 +723,7 @@ CREATE TABLE IF NOT EXISTS "track_backup" (
{37, migrateFromV37},
{38, migrateFromV38},
{39, migrateFromV39},
{40, migrateFromV40},
};
while (1)
@@ -26,7 +26,7 @@ namespace Database
class Session;
using Version = std::size_t;
static constexpr Version LMS_DATABASE_VERSION {40};
static constexpr Version LMS_DATABASE_VERSION {41};
class VersionInfo
{
public:
@@ -113,6 +113,7 @@ namespace Database
Wt::WDateTime getLastWritten() const;
std::optional<ReleaseTypePrimary> getPrimaryType() const { return _primaryType; }
EnumSet<ReleaseTypeSecondary> getSecondaryTypes() const { return _secondaryTypes; }
std::string_view getArtistDisplayName() const { return _artistDisplayName; }
std::size_t getTracksCount() const;
// Setters
@@ -121,6 +122,7 @@ namespace Database
void setTotalDisc(std::optional<int> totalDisc) { _totalDisc = totalDisc; }
void setPrimaryType(std::optional<ReleaseTypePrimary> type) { _primaryType = type; }
void setSecondaryTypes(EnumSet<ReleaseTypeSecondary> types) { _secondaryTypes = types; }
void setArtistDisplayName(std::string_view name) { _artistDisplayName = name; }
// Get the artists of this release
std::vector<ObjectPtr<Artist>> getArtists(TrackArtistLinkType type = TrackArtistLinkType::Artist) const;
@@ -137,7 +139,7 @@ namespace Database
Wt::Dbo::field(a, _totalDisc, "total_disc");
Wt::Dbo::field(a, _primaryType, "primary_type");
Wt::Dbo::field(a, _secondaryTypes, "secondary_types");
Wt::Dbo::field(a, _artistDisplayName, "artist_display_name");
Wt::Dbo::hasMany(a, _tracks, Wt::Dbo::ManyToOne, "release");
}
@@ -155,6 +157,7 @@ namespace Database
std::optional<int> _totalDisc{};
std::optional<ReleaseTypePrimary> _primaryType;
EnumSet<ReleaseTypeSecondary> _secondaryTypes;
std::string _artistDisplayName;
Wt::Dbo::collection<Wt::Dbo::ptr<Track>> _tracks; // Tracks in the release
};
@@ -138,6 +138,7 @@ class Track final : public Object<Track, TrackId>
void setCopyrightURL(const std::string& copyrightURL) { _copyrightURL = std::string(copyrightURL, 0, _maxCopyrightURLLength); }
void setTrackReplayGain(std::optional<float> replayGain) { _trackReplayGain = replayGain; }
void setReleaseReplayGain(std::optional<float> replayGain) { _releaseReplayGain = replayGain; } // may be by disc!
void setArtistDisplayName(std::string_view name) { _artistDisplayName = name; }
void clearArtistLinks();
void addArtistLink(const ObjectPtr<TrackArtistLink>& artistLink);
void setRelease(ObjectPtr<Release> release) { _release = getDboPtr(release); }
@@ -163,6 +164,7 @@ class Track final : public Object<Track, TrackId>
std::optional<std::string> getCopyrightURL() const;
std::optional<float> getTrackReplayGain() const { return _trackReplayGain; }
std::optional<float> getReleaseReplayGain() const { return _releaseReplayGain; }
std::string_view getArtistDisplayName() const { return _artistDisplayName; }
// no artistLinkTypes means get all
std::vector<ObjectPtr<Artist>> getArtists(EnumSet<TrackArtistLinkType> artistLinkTypes) const; // no type means all
std::vector<ArtistId> getArtistIds(EnumSet<TrackArtistLinkType> artistLinkTypes) const; // no type means all
@@ -195,6 +197,7 @@ class Track final : public Object<Track, TrackId>
Wt::Dbo::field(a, _copyrightURL, "copyright_url");
Wt::Dbo::field(a, _trackReplayGain, "track_replay_gain");
Wt::Dbo::field(a, _releaseReplayGain, "release_replay_gain"); // here in Track since Release does not have concept of "disc" (yet?)
Wt::Dbo::field(a, _artistDisplayName, "artist_display_name");
Wt::Dbo::belongsTo(a, _release, "release", Wt::Dbo::OnDeleteCascade);
Wt::Dbo::hasMany(a, _trackArtistLinks, Wt::Dbo::ManyToOne, "track");
Wt::Dbo::hasMany(a, _clusters, Wt::Dbo::ManyToMany, "track_cluster", "", Wt::Dbo::OnDeleteCascade);
@@ -228,6 +231,7 @@ class Track final : public Object<Track, TrackId>
std::string _copyrightURL;
std::optional<float> _trackReplayGain;
std::optional<float> _releaseReplayGain;
std::string _artistDisplayName;
Wt::Dbo::ptr<Release> _release;
Wt::Dbo::collection<Wt::Dbo::ptr<TrackArtistLink>> _trackArtistLinks;
@@ -189,9 +189,11 @@ namespace
if (release->getPrimaryType() != primaryType)
release.modify()->setPrimaryType(primaryType);
}
const EnumSet<ReleaseTypeSecondary> secondaryTypes {convertReleaseTypesSecondary(releaseInfo.secondaryTypes)};
const EnumSet<ReleaseTypeSecondary> secondaryTypes{ convertReleaseTypesSecondary(releaseInfo.secondaryTypes) };
if (release->getSecondaryTypes() != secondaryTypes)
release.modify()->setSecondaryTypes(secondaryTypes);
if (release->getArtistDisplayName() != releaseInfo.artistDisplayName)
release.modify()->setArtistDisplayName(releaseInfo.artistDisplayName);
}
Release::pointer
@@ -525,5 +527,6 @@ namespace Scanner
track.modify()->setCopyright(trackInfo->copyright);
track.modify()->setCopyrightURL(trackInfo->copyrightURL);
track.modify()->setTrackReplayGain(trackInfo->replayGain);
track.modify()->setArtistDisplayName(trackInfo->artistDisplayName);
}
}
@@ -186,6 +186,8 @@ namespace API::Subsonic
for (const Artist::pointer& artist : release->getReleaseArtists())
albumNode.addArrayChild("artists", createArtistNode(artist));
albumNode.setAttribute("displayArtist", release->getArtistDisplayName());
{
const Wt::WDate originalReleaseDate{ release->getOriginalReleaseDate() };
albumNode.setAttribute("originalReleaseDate", originalReleaseDate.isValid() ? StringUtils::toISO8601String(originalReleaseDate) : "");
+9 -4
View File
@@ -134,11 +134,12 @@ namespace API::Subsonic
trackResponse.setAttribute("artistId", idToString(artists.front()->getId()));
}
if (track->getRelease())
Release::pointer release{ track->getRelease() };
if (release)
{
trackResponse.setAttribute("album", track->getRelease()->getName());
trackResponse.setAttribute("albumId", idToString(track->getRelease()->getId()));
trackResponse.setAttribute("parent", idToString(track->getRelease()->getId()));
trackResponse.setAttribute("album", release->getName());
trackResponse.setAttribute("albumId", idToString(release->getId()));
trackResponse.setAttribute("parent", idToString(release->getId()));
}
trackResponse.setAttribute("duration", std::chrono::duration_cast<std::chrono::seconds>(track->getDuration()).count());
@@ -195,7 +196,11 @@ namespace API::Subsonic
} };
addArtistLinks("artists", TrackArtistLinkType::Artist);
trackResponse.setAttribute("displayArtist", track->getArtistDisplayName());
addArtistLinks("albumartists", TrackArtistLinkType::ReleaseArtist);
if (release)
trackResponse.setAttribute("displayAlbumArtist", release->getArtistDisplayName());
auto addClusters{ [&](std::string_view field, std::string_view clusterTypeName)
{