1 /* 2 * Copyright (C) 2015 Emeric Poupon 3 * 4 * This file is part of LMS. 5 * 6 * LMS is free software: you can redistribute it and/or modify 7 * it under the terms of the GNU General Public License as published by 8 * the Free Software Foundation, either version 3 of the License, or 9 * (at your option) any later version. 10 * 11 * LMS is distributed in the hope that it will be useful, 12 * but WITHOUT ANY WARRANTY; without even the implied warranty of 13 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the 14 * GNU General Public License for more details. 15 * 16 * You should have received a copy of the GNU General Public License 17 * along with LMS. If not, see <http://www.gnu.org/licenses/>. 18 */ 19 20 #pragma once 21 22 #include <optional> 23 #include <set> 24 25 #include <Wt/WDateTime.h> 26 #include <Wt/Dbo/Dbo.h> 27 28 #include "utils/UUID.hpp" 29 #include "Types.hpp" 30 31 namespace Database 32 { 33 34 class Artist; 35 class Cluster; 36 class ClusterType; 37 class Release; 38 class Session; 39 class Track; 40 class User; 41 42 class Release : public Wt::Dbo::Dbo<Release> 43 { 44 public: 45 46 using pointer = Wt::Dbo::ptr<Release>; 47 Release()48 Release() {} 49 Release(const std::string& name, const std::optional<UUID>& MBID = {}); 50 51 // Accessors 52 static std::size_t getCount(Session& session); 53 static pointer getByMBID(Session& session, const UUID& MBID); 54 static std::vector<pointer> getByName(Session& session, const std::string& name); 55 static pointer getById(Session& session, IdType id); 56 static std::vector<pointer> getAllOrphans(Session& session); // no track related 57 static std::vector<pointer> getAll(Session& session, std::optional<Range> range = std::nullopt); 58 static std::vector<IdType> getAllIds(Session& session); 59 static std::vector<pointer> getAllOrderedByArtist(Session& session, std::optional<std::size_t> offset = {}, std::optional<std::size_t> size = {}); 60 static std::vector<pointer> getAllRandom(Session& session, const std::set<IdType>& clusters, std::optional<std::size_t> size = {}); 61 static std::vector<IdType> getAllIdsRandom(Session& session, const std::set<IdType>& clusters, std::optional<std::size_t> size = {}); 62 static std::vector<pointer> getLastWritten(Session& session, std::optional<Wt::WDateTime> after, const std::set<IdType>& clusters, std::optional<Range> range, bool& moreResults); 63 static std::vector<pointer> getByYear(Session& session, int yearFrom, int yearTo, std::optional<Range> range = std::nullopt); 64 static std::vector<pointer> getStarred(Session& session, Wt::Dbo::ptr<User> user, const std::set<IdType>& clusters, std::optional<Range> range, bool& moreResults); 65 66 static std::vector<pointer> getByClusters(Session& session, const std::set<IdType>& clusters); 67 static std::vector<pointer> getByFilter(Session& session, 68 const std::set<IdType>& clusters, // if non empty, at least one release that belongs to these clusters 69 const std::vector<std::string>& keywords, // if non empty, name must match all of these keywords 70 std::optional<Range> range, 71 bool& moreExpected); 72 static std::vector<IdType> getAllIdsWithClusters(Session& session, std::optional<std::size_t> limit = {}); 73 74 std::vector<Wt::Dbo::ptr<Track>> getTracks(const std::set<IdType>& clusters = std::set<IdType>()) const; 75 std::size_t getTracksCount() const; 76 Wt::Dbo::ptr<Track> getFirstTrack() const; 77 78 // Get the cluster of the tracks that belong to this release 79 // Each clusters are grouped by cluster type, sorted by the number of occurence (max to min) 80 // size is the max number of cluster per cluster type 81 std::vector<std::vector<Wt::Dbo::ptr<Cluster>>> getClusterGroups(std::vector<Wt::Dbo::ptr<ClusterType>> clusterTypes, std::size_t size) const; 82 83 // Create 84 static pointer create(Session& session, const std::string& name, const std::optional<UUID>& MBID = {}); 85 86 // Utility functions 87 std::optional<int> getReleaseYear(bool originalDate = false) const; // 0 if unknown or various 88 std::optional<std::string> getCopyright() const; 89 std::optional<std::string> getCopyrightURL() const; 90 91 // Accessors getName() const92 const std::string& getName() const { return _name; } getMBID() const93 std::optional<UUID> getMBID() const { return UUID::fromString(_MBID); } 94 std::optional<std::size_t> getTotalTrack() const; 95 std::optional<std::size_t> getTotalDisc() const; 96 std::chrono::milliseconds getDuration() const; 97 Wt::WDateTime getLastWritten() const; 98 99 // Get the artists of this release 100 std::vector<Wt::Dbo::ptr<Artist> > getArtists(TrackArtistLinkType type = TrackArtistLinkType::Artist) const; getReleaseArtists() const101 std::vector<Wt::Dbo::ptr<Artist> > getReleaseArtists() const { return getArtists(TrackArtistLinkType::ReleaseArtist); } 102 bool hasVariousArtists() const; 103 std::vector<pointer> getSimilarReleases(std::optional<std::size_t> offset = {}, std::optional<std::size_t> count = {}) const; 104 setName(std::string_view name)105 void setName(std::string_view name) { _name = name; } setMBID(const std::optional<UUID> & mbid)106 void setMBID(const std::optional<UUID>& mbid) { _MBID = mbid ? mbid->getAsString() : ""; } 107 108 template<class Action> persist(Action & a)109 void persist(Action& a) 110 { 111 Wt::Dbo::field(a, _name, "name"); 112 Wt::Dbo::field(a, _MBID, "mbid"); 113 114 Wt::Dbo::hasMany(a, _tracks, Wt::Dbo::ManyToOne, "release"); 115 Wt::Dbo::hasMany(a, _starringUsers, Wt::Dbo::ManyToMany, "user_release_starred", "", Wt::Dbo::OnDeleteCascade); 116 } 117 118 private: 119 static const std::size_t _maxNameLength {128}; 120 121 std::string _name; 122 std::string _MBID; 123 124 Wt::Dbo::collection<Wt::Dbo::ptr<Track>> _tracks; // Tracks in the release 125 Wt::Dbo::collection<Wt::Dbo::ptr<User>> _starringUsers; // Users that starred this release 126 }; 127 128 } // namespace Database 129 130 131