from dataclasses import dataclass, field from app.utils.auth import get_current_userid @dataclass(slots=True) class Track: """ Track class """ id: int album: str albumartists: list[dict[str, str]] albumhash: str artisthashes: list[str] artists: list[dict[str, str]] bitrate: int copyright: str date: int disc: int duration: int filepath: str folder: str genres: list[dict[str, str]] genrehashes: list[str] last_mod: int og_album: str og_title: str title: str track: int trackhash: str extra: dict lastplayed: int playcount: int playduration: int _pos: int = 0 _ati: str = "" image: str = "" fav_userids: set = field(default_factory=set) @property def is_favorite(self): return get_current_userid() in self.fav_userids def __post_init__(self): self.image = self.albumhash + ".webp" self.extra = { "disc_total": self.extra.get("disc_total", 0), "track_total": self.extra.get("track_total", 0), "samplerate": self.extra.get("samplerate", -1), } # album: str # albumartists: str | list[ArtistMinimal] # albumhash: str # artists: str | list[ArtistMinimal] # bitrate: int # copyright: str # date: int # disc: int # duration: int # filepath: str # folder: str # genre: str | list[str] # title: str # track: int # trackhash: str # last_mod: str | int # image: str = "" # artist_hashes: str = "" # """ # A string of user ids separated by commas. # """ # # is_favorite: bool = False # # temporary attributes # _pos: int = 0 # for sorting tracks by disc and track number # _ati: str = ( # "" # (album track identifier) for removing duplicates when merging album versions # ) # og_title: str = "" # og_album: str = "" # created_date: float = 0.0 # def set_created_date(self): # try: # self.created_date = Path(self.filepath).stat().st_ctime # except FileNotFoundError: # pass # def __post_init__(self): # self.og_title = self.title # self.og_album = self.album # self.last_mod = int(self.last_mod) # self.date = int(self.date) # # add a trailing slash to the folder path # # to avoid matching a folder starting with the same name as the root path # # eg. .../Music and .../Music Videos # self.folder = os.path.join(self.folder, "") # if self.artists is not None: # artists = split_artists(self.artists) # new_title = self.title # if get_flag(SessionVarKeys.EXTRACT_FEAT): # featured, new_title = parse_feat_from_title(self.title) # original_lower = "-".join([create_hash(a) for a in artists]) # artists.extend( # a for a in featured if create_hash(a) not in original_lower # ) # self.artist_hashes = "-".join(create_hash(a, decode=True) for a in artists) # self.artists = [ArtistMinimal(a) for a in artists] # albumartists = split_artists(self.albumartists) # if not albumartists: # self.albumartists = self.artists[:1] # else: # self.albumartists = [ArtistMinimal(a) for a in albumartists] # if get_flag(SessionVarKeys.REMOVE_PROD): # new_title = remove_prod(new_title) # if track is a single # if self.og_title == self.album: # self.rename_album(new_title) # if get_flag(SessionVarKeys.REMOVE_REMASTER_FROM_TRACK): # new_title = clean_title(new_title) # self.title = new_title # if get_flag(SessionVarKeys.CLEAN_ALBUM_TITLE): # self.album, _ = get_base_title_and_versions( # self.album, get_versions=False # ) # if get_flag(SessionVarKeys.MERGE_ALBUM_VERSIONS): # self.recreate_albumhash() # self.image = self.albumhash + ".webp" # if self.genre is not None and self.genre != "": # self.genre = self.genre.lower() # separators = {"/", ";", "&"} # contains_rnb = "r&b" in self.genre # contains_rock = "rock & roll" in self.genre # if contains_rnb: # self.genre = self.genre.replace("r&b", "RnB") # if contains_rock: # self.genre = self.genre.replace("rock & roll", "rock") # for s in separators: # self.genre: str = self.genre.replace(s, ",") # self.genre = self.genre.split(",") # self.genre = [g.strip() for g in self.genre] # self.recreate_hash() # self.set_created_date() # def recreate_hash(self): # """ # Recreates a track hash if the track title was altered # to prevent duplicate tracks having different hashes. # """ # if self.og_title == self.title and self.og_album == self.album: # return # self.trackhash = create_hash( # ", ".join(a.name for a in self.artists), self.og_album, self.title # ) # def recreate_artists_hash(self): # """ # Recreates a track's artist hashes if the artist list was altered # """ # self.artist_hashes = "-".join(a.artisthash for a in self.artists) # def recreate_albumhash(self): # """ # Recreates an albumhash of a track to merge all versions of an album. # """ # albumartists = (a.name for a in self.albumartists) # self.albumhash = create_hash(self.album, *albumartists) # def rename_album(self, new_album: str): # """ # Renames an album # """ # self.album = new_album # def add_artists(self, artists: list[str], new_album_title: str): # for artist in artists: # if create_hash(artist, decode=True) not in self.artist_hashes: # self.artists.append(ArtistMinimal(artist)) # self.recreate_artists_hash() # self.rename_album(new_album_title)