mirror of
https://github.com/Dvorinka/swingmusic-extended.git
synced 2026-06-05 13:03:02 +00:00
show toast if album return 204
This commit is contained in:
@@ -49,7 +49,7 @@ def get_album():
|
|||||||
album = instances.album_instance.find_album_by_hash(albumhash)
|
album = instances.album_instance.find_album_by_hash(albumhash)
|
||||||
|
|
||||||
if not album:
|
if not album:
|
||||||
return {"error": "Album not found."}, 404
|
return {"error": "Album not created yet."}, 204
|
||||||
|
|
||||||
album = models.Album(album)
|
album = models.Album(album)
|
||||||
|
|
||||||
|
|||||||
+19
-14
@@ -2,7 +2,6 @@
|
|||||||
This module contains mini functions for the server.
|
This module contains mini functions for the server.
|
||||||
"""
|
"""
|
||||||
import os
|
import os
|
||||||
import random
|
|
||||||
import threading
|
import threading
|
||||||
from datetime import datetime
|
from datetime import datetime
|
||||||
from typing import Dict, Set
|
from typing import Dict, Set
|
||||||
@@ -11,8 +10,8 @@ from typing import List
|
|||||||
import requests
|
import requests
|
||||||
|
|
||||||
from app import models
|
from app import models
|
||||||
from app import settings
|
|
||||||
from app import instances
|
from app import instances
|
||||||
|
from app.lib.albumslib import Thumbnail
|
||||||
|
|
||||||
|
|
||||||
def background(func):
|
def background(func):
|
||||||
@@ -85,12 +84,15 @@ def is_valid_file(filename: str) -> bool:
|
|||||||
return False
|
return False
|
||||||
|
|
||||||
|
|
||||||
|
ill_chars = '/\\:*?"<>|#&'
|
||||||
|
|
||||||
|
|
||||||
def create_album_hash(title: str, artist: str) -> str:
|
def create_album_hash(title: str, artist: str) -> str:
|
||||||
"""
|
"""
|
||||||
Creates a simple hash for an album
|
Creates a simple hash for an album
|
||||||
"""
|
"""
|
||||||
lower = (title + artist).replace(" ", "").lower()
|
lower = (title + artist).replace(" ", "").lower()
|
||||||
hash = "".join([i for i in lower if i not in '/\\:*?"<>|&'])
|
hash = "".join([i for i in lower if i not in ill_chars])
|
||||||
return hash
|
return hash
|
||||||
|
|
||||||
|
|
||||||
@@ -104,7 +106,7 @@ def create_safe_name(name: str) -> str:
|
|||||||
"""
|
"""
|
||||||
Creates a url-safe name from a name.
|
Creates a url-safe name from a name.
|
||||||
"""
|
"""
|
||||||
return "".join([i for i in name if i not in '/\\:*?"<>|#'])
|
return "".join([i for i in name if i not in ill_chars])
|
||||||
|
|
||||||
|
|
||||||
class UseBisection:
|
class UseBisection:
|
||||||
@@ -116,21 +118,20 @@ class UseBisection:
|
|||||||
"""
|
"""
|
||||||
|
|
||||||
def __init__(self, source: List, search_from: str, queries: List[str]) -> None:
|
def __init__(self, source: List, search_from: str, queries: List[str]) -> None:
|
||||||
self.list = source
|
self.source_list = source
|
||||||
self.queries = queries
|
self.queries_list = queries
|
||||||
self.search_from = search_from
|
self.attr = search_from
|
||||||
self.list.sort(key=lambda x: getattr(x, search_from))
|
self.source_list.sort(key=lambda x: getattr(x, search_from))
|
||||||
|
|
||||||
def find(self, query: str):
|
def find(self, query: str):
|
||||||
left = 0
|
left = 0
|
||||||
right = len(self.list) - 1
|
right = len(self.source_list) - 1
|
||||||
|
|
||||||
while left <= right:
|
while left <= right:
|
||||||
mid = (left + right) // 2
|
mid = (left + right) // 2
|
||||||
|
if self.source_list[mid].__getattribute__(self.attr) == query:
|
||||||
if self.list[mid].__getattribute__(self.search_from) == query:
|
return self.source_list[mid]
|
||||||
return self.list[mid]
|
elif self.source_list[mid].__getattribute__(self.attr) > query:
|
||||||
elif self.list[mid].__getattribute__(self.search_from) > query:
|
|
||||||
right = mid - 1
|
right = mid - 1
|
||||||
else:
|
else:
|
||||||
left = mid + 1
|
left = mid + 1
|
||||||
@@ -138,7 +139,11 @@ class UseBisection:
|
|||||||
return None
|
return None
|
||||||
|
|
||||||
def __call__(self) -> List:
|
def __call__(self) -> List:
|
||||||
return [self.find(query) for query in self.queries]
|
if len(self.source_list) == 0:
|
||||||
|
print("🚀🚀🚀🚀🚀🚀🚀")
|
||||||
|
return [None]
|
||||||
|
|
||||||
|
return [self.find(query) for query in self.queries_list]
|
||||||
|
|
||||||
|
|
||||||
class Get:
|
class Get:
|
||||||
|
|||||||
@@ -2,6 +2,7 @@
|
|||||||
This library contains all the functions related to albums.
|
This library contains all the functions related to albums.
|
||||||
"""
|
"""
|
||||||
from concurrent.futures import ThreadPoolExecutor
|
from concurrent.futures import ThreadPoolExecutor
|
||||||
|
from multiprocessing import Manager
|
||||||
from dataclasses import dataclass
|
from dataclasses import dataclass
|
||||||
import os
|
import os
|
||||||
import random
|
import random
|
||||||
@@ -13,7 +14,7 @@ from tqdm import tqdm
|
|||||||
|
|
||||||
from app.settings import THUMBS_PATH
|
from app.settings import THUMBS_PATH
|
||||||
from app import instances
|
from app import instances
|
||||||
|
from app.logger import logg
|
||||||
|
|
||||||
# def get_all_albums() -> List[models.Album]:
|
# def get_all_albums() -> List[models.Album]:
|
||||||
# """
|
# """
|
||||||
@@ -67,7 +68,8 @@ class ValidateThumbs:
|
|||||||
|
|
||||||
for entry in tqdm(entries, desc="Validating thumbnails"):
|
for entry in tqdm(entries, desc="Validating thumbnails"):
|
||||||
e = helpers.UseBisection(thumbs, "filename", [entry.name])()
|
e = helpers.UseBisection(thumbs, "filename", [entry.name])()
|
||||||
if e is not None:
|
|
||||||
|
if e is None:
|
||||||
os.remove(entry.path)
|
os.remove(entry.path)
|
||||||
|
|
||||||
@staticmethod
|
@staticmethod
|
||||||
@@ -76,7 +78,7 @@ class ValidateThumbs:
|
|||||||
Re-rip lost album thumbnails
|
Re-rip lost album thumbnails
|
||||||
"""
|
"""
|
||||||
entries = os.scandir(THUMBS_PATH)
|
entries = os.scandir(THUMBS_PATH)
|
||||||
entries = [Thumbnail(entry) for entry in entries if entry.is_file()]
|
entries = [Thumbnail(entry.name) for entry in entries if entry.is_file()]
|
||||||
|
|
||||||
albums = helpers.Get.get_all_albums()
|
albums = helpers.Get.get_all_albums()
|
||||||
thumbs = [(album.hash + ".webp") for album in albums]
|
thumbs = [(album.hash + ".webp") for album in albums]
|
||||||
@@ -85,13 +87,18 @@ class ValidateThumbs:
|
|||||||
e = helpers.UseBisection(entries, "filename", [t_hash])()[0]
|
e = helpers.UseBisection(entries, "filename", [t_hash])()[0]
|
||||||
|
|
||||||
if e is None:
|
if e is None:
|
||||||
hash = t_hash.split(".")[0]
|
hash = t_hash.replace(".webp", "")
|
||||||
RipAlbumImage(hash)
|
RipAlbumImage(hash)
|
||||||
|
|
||||||
return e
|
logg.info("Ripping lost album thumbnails...")
|
||||||
|
# with ThreadPoolExecutor() as pool:
|
||||||
|
# i = pool.map(rip_image, thumbs)
|
||||||
|
# [a for a in i]
|
||||||
|
# ⚠️ empty lists are sent to the useBisection function as the source list.
|
||||||
|
for thumb in thumbs:
|
||||||
|
rip_image(thumb)
|
||||||
|
|
||||||
with ThreadPoolExecutor() as pool:
|
logg.info("Ripping lost album thumbnails...done")
|
||||||
pool.map(rip_image, thumbs)
|
|
||||||
|
|
||||||
def __init__(self) -> None:
|
def __init__(self) -> None:
|
||||||
self.remove_obsolete()
|
self.remove_obsolete()
|
||||||
|
|||||||
@@ -13,7 +13,7 @@ class CustomFormatter(logging.Formatter):
|
|||||||
# format = (
|
# format = (
|
||||||
# "%(asctime)s - %(name)s - %(levelname)s - %(message)s (%(filename)s:%(lineno)d)"
|
# "%(asctime)s - %(name)s - %(levelname)s - %(message)s (%(filename)s:%(lineno)d)"
|
||||||
# )
|
# )
|
||||||
format = "%(levelname)s: @%(name)s: >>> %(message)s (%(filename)s:%(lineno)d)"
|
format = "[%(asctime)s] [%(levelname)s] [@%(name)s] >>> %(message)s [%(filename)s:%(lineno)d]"
|
||||||
|
|
||||||
FORMATS = {
|
FORMATS = {
|
||||||
logging.DEBUG: grey + format + reset,
|
logging.DEBUG: grey + format + reset,
|
||||||
@@ -25,7 +25,7 @@ class CustomFormatter(logging.Formatter):
|
|||||||
|
|
||||||
def format(self, record):
|
def format(self, record):
|
||||||
log_fmt = self.FORMATS.get(record.levelno)
|
log_fmt = self.FORMATS.get(record.levelno)
|
||||||
formatter = logging.Formatter(log_fmt)
|
formatter = logging.Formatter(log_fmt, "%H:%M:%S")
|
||||||
return formatter.format(record)
|
return formatter.format(record)
|
||||||
|
|
||||||
|
|
||||||
|
|||||||
@@ -26,19 +26,6 @@ DEFAULT_ARTIST_IMG = IMG_ARTIST_URI + "0.webp"
|
|||||||
|
|
||||||
LAST_FM_API_KEY = "762db7a44a9e6fb5585661f5f2bdf23a"
|
LAST_FM_API_KEY = "762db7a44a9e6fb5585661f5f2bdf23a"
|
||||||
|
|
||||||
P_COLORS = [
|
|
||||||
"rgb(4, 40, 196)",
|
|
||||||
"rgb(196, 4, 68)",
|
|
||||||
"rgb(4, 99, 59)",
|
|
||||||
"rgb(161, 87, 1)",
|
|
||||||
"rgb(1, 161, 22)",
|
|
||||||
"rgb(116, 1, 161)",
|
|
||||||
"rgb(0, 0, 0)",
|
|
||||||
"rgb(95, 95, 95)",
|
|
||||||
"rgb(141, 132, 2)",
|
|
||||||
"rgb(141, 11, 2)",
|
|
||||||
]
|
|
||||||
|
|
||||||
CPU_COUNT = multiprocessing.cpu_count()
|
CPU_COUNT = multiprocessing.cpu_count()
|
||||||
|
|
||||||
|
|
||||||
|
|||||||
@@ -1,9 +1,13 @@
|
|||||||
import axios, { AxiosError } from "axios";
|
|
||||||
import state from "../state";
|
import state from "../state";
|
||||||
import { AlbumInfo, Track } from "../../interfaces";
|
import { AlbumInfo, Track } from "../../interfaces";
|
||||||
import useAxios from "../useAxios";
|
import useAxios from "../useAxios";
|
||||||
|
import { NotifType, useNotifStore } from "@/stores/notification";
|
||||||
|
|
||||||
const getAlbumTracks = async (album: string, artist: string) => {
|
const getAlbumData = async (
|
||||||
|
album: string,
|
||||||
|
artist: string,
|
||||||
|
ToastStore: typeof useNotifStore
|
||||||
|
) => {
|
||||||
const url = state.settings.uri + "/album";
|
const url = state.settings.uri + "/album";
|
||||||
|
|
||||||
interface AlbumData {
|
interface AlbumData {
|
||||||
@@ -19,9 +23,13 @@ const getAlbumTracks = async (album: string, artist: string) => {
|
|||||||
},
|
},
|
||||||
});
|
});
|
||||||
|
|
||||||
if (status == 404) {
|
if (status == 204) {
|
||||||
|
ToastStore().showNotification("Album not created yet!", NotifType.Error);
|
||||||
return {
|
return {
|
||||||
info: {},
|
info: {
|
||||||
|
album: album,
|
||||||
|
artist: artist,
|
||||||
|
},
|
||||||
tracks: [],
|
tracks: [],
|
||||||
};
|
};
|
||||||
}
|
}
|
||||||
@@ -63,4 +71,4 @@ const getAlbumBio = async (album: string, albumartist: string) => {
|
|||||||
}
|
}
|
||||||
};
|
};
|
||||||
|
|
||||||
export { getAlbumTracks, getAlbumArtists, getAlbumBio };
|
export { getAlbumData as getAlbumTracks, getAlbumArtists, getAlbumBio };
|
||||||
|
|||||||
@@ -1,4 +1,5 @@
|
|||||||
import { defineStore } from "pinia";
|
import { defineStore } from "pinia";
|
||||||
|
import { useNotifStore } from "../notification";
|
||||||
import { Track, Artist, AlbumInfo } from "../../interfaces";
|
import { Track, Artist, AlbumInfo } from "../../interfaces";
|
||||||
import {
|
import {
|
||||||
getAlbumTracks,
|
getAlbumTracks,
|
||||||
@@ -21,7 +22,7 @@ export default defineStore("album", {
|
|||||||
* @param albumartist artist of the album
|
* @param albumartist artist of the album
|
||||||
*/
|
*/
|
||||||
async fetchTracksAndArtists(title: string, albumartist: string) {
|
async fetchTracksAndArtists(title: string, albumartist: string) {
|
||||||
const tracks = await getAlbumTracks(title, albumartist);
|
const tracks = await getAlbumTracks(title, albumartist, useNotifStore);
|
||||||
const artists = await getAlbumArtists(title, albumartist);
|
const artists = await getAlbumArtists(title, albumartist);
|
||||||
|
|
||||||
this.tracks = tracks.tracks;
|
this.tracks = tracks.tracks;
|
||||||
|
|||||||
Reference in New Issue
Block a user