reformat / resolves #32
This commit is contained in:
		| @@ -292,6 +292,7 @@ class ValidRadioQueueRequest(BaseModel): | |||||||
|     start: Optional[int] = 0 |     start: Optional[int] = 0 | ||||||
|     search: Optional[str] = None |     search: Optional[str] = None | ||||||
|  |  | ||||||
|  |  | ||||||
| class ValidRadioQueueShiftRequest(BaseModel): | class ValidRadioQueueShiftRequest(BaseModel): | ||||||
|     """ |     """ | ||||||
|     - **key**: API Key |     - **key**: API Key | ||||||
|   | |||||||
| @@ -84,9 +84,7 @@ class KarmaDB: | |||||||
|             "INSERT INTO karma(keyword, score, last_change) VALUES(?, ?, ?)" |             "INSERT INTO karma(keyword, score, last_change) VALUES(?, ?, ?)" | ||||||
|         ) |         ) | ||||||
|         friendly_flag: str = "++" if not flag else "--" |         friendly_flag: str = "++" if not flag else "--" | ||||||
|         audit_message: str = ( |         audit_message: str = f"{granter} adjusted karma for {keyword} @ {datetime.datetime.now().isoformat()}: {friendly_flag}" | ||||||
|             f"{granter} adjusted karma for {keyword} @ {datetime.datetime.now().isoformat()}: {friendly_flag}" |  | ||||||
|         ) |  | ||||||
|         audit_query: str = ( |         audit_query: str = ( | ||||||
|             "INSERT INTO karma_audit(impacted_keyword, comment) VALUES(?, ?)" |             "INSERT INTO karma_audit(impacted_keyword, comment) VALUES(?, ?)" | ||||||
|         ) |         ) | ||||||
|   | |||||||
| @@ -115,7 +115,7 @@ class LyricSearch(FastAPI): | |||||||
|  |  | ||||||
|         if data.src.upper() not in self.acceptable_request_sources: |         if data.src.upper() not in self.acceptable_request_sources: | ||||||
|             await self.notifier.send( |             await self.notifier.send( | ||||||
|                 f"ERROR @ {__file__.rsplit("/", maxsplit=1)[-1]}", |                 f"ERROR @ {__file__.rsplit('/', maxsplit=1)[-1]}", | ||||||
|                 f"Unknown request source: {data.src}", |                 f"Unknown request source: {data.src}", | ||||||
|             ) |             ) | ||||||
|             return JSONResponse( |             return JSONResponse( | ||||||
|   | |||||||
| @@ -97,8 +97,7 @@ class Radio(FastAPI): | |||||||
|                 }, |                 }, | ||||||
|             ) |             ) | ||||||
|         except Exception as e: |         except Exception as e: | ||||||
|             logging.debug("radio_skip Exception: %s", |             logging.debug("radio_skip Exception: %s", str(e)) | ||||||
|                           str(e)) |  | ||||||
|             traceback.print_exc() |             traceback.print_exc() | ||||||
|             return JSONResponse( |             return JSONResponse( | ||||||
|                 status_code=500, |                 status_code=500, | ||||||
| @@ -122,16 +121,22 @@ class Radio(FastAPI): | |||||||
|         return JSONResponse(content={"ok": True}) |         return JSONResponse(content={"ok": True}) | ||||||
|  |  | ||||||
|     async def radio_get_queue( |     async def radio_get_queue( | ||||||
|         self, request: Request, data: ValidRadioQueueRequest, |         self, | ||||||
|  |         request: Request, | ||||||
|  |         data: ValidRadioQueueRequest, | ||||||
|     ) -> JSONResponse: |     ) -> JSONResponse: | ||||||
|         """ |         """ | ||||||
|         Get current play queue (paged, 20 results per page) |         Get current play queue (paged, 20 results per page) | ||||||
|         """ |         """ | ||||||
|         start: int = int(data.start) |         start: int = int(data.start) | ||||||
|         end: int = start+20 |         end: int = start + 20 | ||||||
|         logging.info("queue request with start pos: %s & end pos: %s", |         search: Optional[str] = data.search | ||||||
|                      start, end) |         logging.info("queue request with start pos: %s & end pos: %s", start, end) | ||||||
|         queue_full: list = self.radio_util.active_playlist |  | ||||||
|  |         if not search: | ||||||
|  |             queue_full: list = self.radio_util.active_playlist | ||||||
|  |         else: | ||||||
|  |             queue_full: list = self.radio_util.datatables_search(data.search) | ||||||
|         queue: list = queue_full[start:end] |         queue: list = queue_full[start:end] | ||||||
|         logging.info("queue length: %s", len(queue)) |         logging.info("queue length: %s", len(queue)) | ||||||
|         queue_out: list[dict] = [] |         queue_out: list[dict] = [] | ||||||
| @@ -152,7 +157,9 @@ class Radio(FastAPI): | |||||||
|         out_json = { |         out_json = { | ||||||
|             "draw": data.draw, |             "draw": data.draw, | ||||||
|             "recordsTotal": len(queue_full), |             "recordsTotal": len(queue_full), | ||||||
|             "recordsFiltered": len(queue_full) if not data.search else len(queue_full), # todo: implement search |             "recordsFiltered": ( | ||||||
|  |                 len(queue_full) if not data.search else len(queue_full) | ||||||
|  |             ),  # todo: implement search | ||||||
|             "items": queue_out, |             "items": queue_out, | ||||||
|         } |         } | ||||||
|         return JSONResponse(content=out_json) |         return JSONResponse(content=out_json) | ||||||
| @@ -239,8 +246,7 @@ class Radio(FastAPI): | |||||||
|                 ) |                 ) | ||||||
|             return Response(content=album_art, media_type="image/png") |             return Response(content=album_art, media_type="image/png") | ||||||
|         except Exception as e: |         except Exception as e: | ||||||
|             logging.debug("album_art_handler Exception: %s", |             logging.debug("album_art_handler Exception: %s", str(e)) | ||||||
|                           str(e)) |  | ||||||
|             traceback.print_exc() |             traceback.print_exc() | ||||||
|             return RedirectResponse( |             return RedirectResponse( | ||||||
|                 url="https://codey.lol/images/radio_art_default.jpg", status_code=302 |                 url="https://codey.lol/images/radio_art_default.jpg", status_code=302 | ||||||
|   | |||||||
| @@ -113,9 +113,7 @@ class Transcriptions(FastAPI): | |||||||
|                 db_path: Union[str, LiteralString] = os.path.join( |                 db_path: Union[str, LiteralString] = os.path.join( | ||||||
|                     "/usr/local/share", "sqlite_dbs", "sp.db" |                     "/usr/local/share", "sqlite_dbs", "sp.db" | ||||||
|                 ) |                 ) | ||||||
|                 db_query: str = ( |                 db_query: str = """SELECT ("S" || Season || "E" || Episode || " " || Title), Character, Line FROM SP_DAT WHERE ID = ?""" | ||||||
|                     """SELECT ("S" || Season || "E" || Episode || " " || Title), Character, Line FROM SP_DAT WHERE ID = ?""" |  | ||||||
|                 ) |  | ||||||
|             case 1: |             case 1: | ||||||
|                 db_path = os.path.join("/usr/local/share", "sqlite_dbs", "futur.db") |                 db_path = os.path.join("/usr/local/share", "sqlite_dbs", "futur.db") | ||||||
|                 db_query = """SELECT ("S" || EP_S || "E" || EP_EP || " " || EP_TITLE || "<br><em>Opener: " || EP_OPENER || "</em>"), EP_LINE_SPEAKER, EP_LINE FROM clean_dialog WHERE EP_ID = ? ORDER BY LINE_ID ASC""" |                 db_query = """SELECT ("S" || EP_S || "E" || EP_EP || " " || EP_TITLE || "<br><em>Opener: " || EP_OPENER || "</em>"), EP_LINE_SPEAKER, EP_LINE FROM clean_dialog WHERE EP_ID = ? ORDER BY LINE_ID ASC""" | ||||||
|   | |||||||
| @@ -78,7 +78,7 @@ class Aggregate: | |||||||
|                     traceback.print_exc() |                     traceback.print_exc() | ||||||
|                     logging.info("Could not increment redis failed counter: %s", str(e)) |                     logging.info("Could not increment redis failed counter: %s", str(e)) | ||||||
|                     self.notifier.send( |                     self.notifier.send( | ||||||
|                         f"ERROR @ {__file__.rsplit("/", maxsplit=1)[-1]}", |                         f"ERROR @ {__file__.rsplit('/', maxsplit=1)[-1]}", | ||||||
|                         f"Could not increment redis failed counter: {str(e)}", |                         f"Could not increment redis failed counter: {str(e)}", | ||||||
|                     ) |                     ) | ||||||
|         return search_result |         return search_result | ||||||
|   | |||||||
| @@ -89,10 +89,8 @@ class Cache: | |||||||
|         logging.debug( |         logging.debug( | ||||||
|             "Checking whether %s is already stored", artistsong.replace("\n", " - ") |             "Checking whether %s is already stored", artistsong.replace("\n", " - ") | ||||||
|         ) |         ) | ||||||
|         check_query: str = ( |         check_query: str = 'SELECT id, artist, song FROM lyrics  WHERE editdist3((lower(artist) || " " || lower(song)), (? || " " || ?))\ | ||||||
|             'SELECT id, artist, song FROM lyrics  WHERE editdist3((lower(artist) || " " || lower(song)), (? || " " || ?))\ |  | ||||||
|                         <= 410 ORDER BY editdist3((lower(artist) || " " || lower(song)), ?) ASC LIMIT 1' |                         <= 410 ORDER BY editdist3((lower(artist) || " " || lower(song)), ?) ASC LIMIT 1' | ||||||
|         ) |  | ||||||
|         artistsong_split = artistsong.split("\n", maxsplit=1) |         artistsong_split = artistsong.split("\n", maxsplit=1) | ||||||
|         artist = artistsong_split[0].lower() |         artist = artistsong_split[0].lower() | ||||||
|         song = artistsong_split[1].lower() |         song = artistsong_split[1].lower() | ||||||
| @@ -132,7 +130,7 @@ class Cache: | |||||||
|                 f"cache::store >> {str(e)}", |                 f"cache::store >> {str(e)}", | ||||||
|             ) |             ) | ||||||
|             await self.notifier.send( |             await self.notifier.send( | ||||||
|                 f"ERROR @ {__file__.rsplit("/", maxsplit=1)[-1]}", |                 f"ERROR @ {__file__.rsplit('/', maxsplit=1)[-1]}", | ||||||
|                 f"cache::store >> `{str(e)}`", |                 f"cache::store >> `{str(e)}`", | ||||||
|             ) |             ) | ||||||
|  |  | ||||||
| @@ -213,8 +211,10 @@ class Cache: | |||||||
|             lyrics = regex.sub(r"(<br>|\n|\r\n)", " / ", lyr_result.lyrics.strip()) |             lyrics = regex.sub(r"(<br>|\n|\r\n)", " / ", lyr_result.lyrics.strip()) | ||||||
|             lyrics = regex.sub(r"\s{2,}", " ", lyrics) |             lyrics = regex.sub(r"\s{2,}", " ", lyrics) | ||||||
|  |  | ||||||
|             insert_query = "INSERT INTO lyrics (src, date_retrieved, artist, song, artistsong, confidence, lyrics)\ |             insert_query = ( | ||||||
|  |                 "INSERT INTO lyrics (src, date_retrieved, artist, song, artistsong, confidence, lyrics)\ | ||||||
|                 VALUES(?, ?, ?, ?, ?, ?, ?)" |                 VALUES(?, ?, ?, ?, ?, ?, ?)" | ||||||
|  |             ) | ||||||
|             params = ( |             params = ( | ||||||
|                 lyr_result.src, |                 lyr_result.src, | ||||||
|                 time.time(), |                 time.time(), | ||||||
| @@ -258,10 +258,8 @@ class Cache: | |||||||
|  |  | ||||||
|             if artist == "!" and song == "!": |             if artist == "!" and song == "!": | ||||||
|                 random_search = True |                 random_search = True | ||||||
|                 search_query: str = ( |                 search_query: str = "SELECT id, artist, song, lyrics, src, confidence\ | ||||||
|                     "SELECT id, artist, song, lyrics, src, confidence\ |  | ||||||
|                 FROM lyrics ORDER BY RANDOM() LIMIT 1" |                 FROM lyrics ORDER BY RANDOM() LIMIT 1" | ||||||
|                 ) |  | ||||||
|  |  | ||||||
|             logging.info("Searching %s - %s on %s", artist, song, self.label) |             logging.info("Searching %s - %s on %s", artist, song, self.label) | ||||||
|  |  | ||||||
| @@ -319,11 +317,9 @@ class Cache: | |||||||
|                     self.cache_pre_query |                     self.cache_pre_query | ||||||
|                 ) as _db_cursor: |                 ) as _db_cursor: | ||||||
|                     if not random_search: |                     if not random_search: | ||||||
|                         search_query: str = ( |                         search_query: str = 'SELECT id, artist, song, lyrics, src, confidence FROM lyrics\ | ||||||
|                             'SELECT id, artist, song, lyrics, src, confidence FROM lyrics\ |  | ||||||
|                         WHERE editdist3((lower(artist) || " " || lower(song)), (? || " " || ?))\ |                         WHERE editdist3((lower(artist) || " " || lower(song)), (? || " " || ?))\ | ||||||
|                         <= 410 ORDER BY editdist3((lower(artist) || " " || lower(song)), ?) ASC LIMIT 10' |                         <= 410 ORDER BY editdist3((lower(artist) || " " || lower(song)), ?) ASC LIMIT 10' | ||||||
|                         ) |  | ||||||
|                         search_params: tuple = ( |                         search_params: tuple = ( | ||||||
|                             artist.strip(), |                             artist.strip(), | ||||||
|                             song.strip(), |                             song.strip(), | ||||||
|   | |||||||
| @@ -31,7 +31,6 @@ class LastFM: | |||||||
|             ] |             ] | ||||||
|  |  | ||||||
|             async with ClientSession() as session: |             async with ClientSession() as session: | ||||||
|  |  | ||||||
|                 async with await session.get( |                 async with await session.get( | ||||||
|                     self.api_base_url, |                     self.api_base_url, | ||||||
|                     params=request_params, |                     params=request_params, | ||||||
|   | |||||||
| @@ -11,9 +11,11 @@ from regex import Pattern | |||||||
| import sqlite3 | import sqlite3 | ||||||
| import gpt | import gpt | ||||||
| import music_tag  # type: ignore | import music_tag  # type: ignore | ||||||
|  | from rapidfuzz import fuzz | ||||||
| from endpoints.constructors import RadioException | from endpoints.constructors import RadioException | ||||||
|  |  | ||||||
| double_space: Pattern = regex.compile(r"\s{2,}") | double_space: Pattern = regex.compile(r"\s{2,}") | ||||||
|  | non_alnum: Pattern = regex.compile(r"[^a-zA-Z0-9]") | ||||||
|  |  | ||||||
| """ | """ | ||||||
| TODO: | TODO: | ||||||
| @@ -110,7 +112,36 @@ class RadioUtil: | |||||||
|             out_result = [str(r["artistsong"]) for r in result] |             out_result = [str(r["artistsong"]) for r in result] | ||||||
|             return out_result |             return out_result | ||||||
|  |  | ||||||
|     async def search_playlist( |     def datatables_search(self, filter: str) -> Optional[list[dict]]: | ||||||
|  |         """DataTables Search | ||||||
|  |  | ||||||
|  |         Args: | ||||||
|  |             filter (str): The filter query to fuzzy match with | ||||||
|  |  | ||||||
|  |         Returns: | ||||||
|  |             list[str]: List of matching playlist items (if any are found) | ||||||
|  |         """ | ||||||
|  |         filter = filter.strip().lower() | ||||||
|  |         matched: list[dict] = [] | ||||||
|  |         for item in self.active_playlist: | ||||||
|  |             artist: str = item.get("artist", None) | ||||||
|  |             song: str = item.get("song", None) | ||||||
|  |             artistsong: str = item.get("artistsong", None) | ||||||
|  |             album: str = item.get("album", None) | ||||||
|  |             if not artist or not song or not artistsong: | ||||||
|  |                 continue | ||||||
|  |             if non_alnum.sub("", filter) in non_alnum.sub("", artistsong).lower(): | ||||||
|  |                 matched.append(item) | ||||||
|  |                 continue | ||||||
|  |             if ( | ||||||
|  |                 fuzz.ratio(filter, artist) >= 85 | ||||||
|  |                 or fuzz.ratio(filter, song) >= 85 | ||||||
|  |                 or fuzz.ratio(filter, album) >= 85 | ||||||
|  |             ): | ||||||
|  |                 matched.append(item) | ||||||
|  |         return matched | ||||||
|  |  | ||||||
|  |     def search_playlist( | ||||||
|         self, |         self, | ||||||
|         artistsong: Optional[str] = None, |         artistsong: Optional[str] = None, | ||||||
|         artist: Optional[str] = None, |         artist: Optional[str] = None, | ||||||
| @@ -130,11 +161,9 @@ class RadioUtil: | |||||||
|         if not artistsong and (not artist or not song): |         if not artistsong and (not artist or not song): | ||||||
|             raise RadioException("No query provided") |             raise RadioException("No query provided") | ||||||
|         try: |         try: | ||||||
|             search_query: str = ( |             search_query: str = 'SELECT id, artist, song, (artist || " - " || song) AS artistsong, album, file_path, duration FROM tracks\ | ||||||
|                 'SELECT id, artist, song, (artist || " - " || song) AS artistsong, album, file_path, duration FROM tracks\ |  | ||||||
|                 WHERE editdist3((lower(artist) || " " || lower(song)), (? || " " || ?))\ |                 WHERE editdist3((lower(artist) || " " || lower(song)), (? || " " || ?))\ | ||||||
|                     <= 410 ORDER BY editdist3((lower(artist) || " " || lower(song)), ?) ASC LIMIT 1' |                     <= 410 ORDER BY editdist3((lower(artist) || " " || lower(song)), ?) ASC LIMIT 1' | ||||||
|             ) |  | ||||||
|             if artistsong: |             if artistsong: | ||||||
|                 artistsong_split: list = artistsong.split(" - ", maxsplit=1) |                 artistsong_split: list = artistsong.split(" - ", maxsplit=1) | ||||||
|                 (search_artist, search_song) = tuple(artistsong_split) |                 (search_artist, search_song) = tuple(artistsong_split) | ||||||
| @@ -153,9 +182,7 @@ class RadioUtil: | |||||||
|                 for ext in self.sqlite_exts: |                 for ext in self.sqlite_exts: | ||||||
|                     db_conn.load_extension(ext) |                     db_conn.load_extension(ext) | ||||||
|                 db_conn.row_factory = sqlite3.Row |                 db_conn.row_factory = sqlite3.Row | ||||||
|                 db_cursor = db_conn.execute( |                 db_cursor = db_conn.execute(search_query, search_params) | ||||||
|                     search_query, search_params |  | ||||||
|                 ) |  | ||||||
|                 result: Optional[sqlite3.Row | bool] = db_cursor.fetchone() |                 result: Optional[sqlite3.Row | bool] = db_cursor.fetchone() | ||||||
|                 if not result or not isinstance(result, sqlite3.Row): |                 if not result or not isinstance(result, sqlite3.Row): | ||||||
|                     return False |                     return False | ||||||
| @@ -178,7 +205,7 @@ class RadioUtil: | |||||||
|             traceback.print_exc() |             traceback.print_exc() | ||||||
|             return False |             return False | ||||||
|  |  | ||||||
|     async def add_genre(self, artist: str, genre: str) -> bool: |     def add_genre(self, artist: str, genre: str) -> bool: | ||||||
|         """ |         """ | ||||||
|         Add artist/genre pairing to DB |         Add artist/genre pairing to DB | ||||||
|         Args: |         Args: | ||||||
| @@ -213,7 +240,7 @@ class RadioUtil: | |||||||
|             traceback.print_exc() |             traceback.print_exc() | ||||||
|             return False |             return False | ||||||
|  |  | ||||||
|     async def add_genres(self, pairs: list[dict[str, str]]) -> bool: |     def add_genres(self, pairs: list[dict[str, str]]) -> bool: | ||||||
|         """ |         """ | ||||||
|         (BATCH) Add artist/genre pairings to DB |         (BATCH) Add artist/genre pairings to DB | ||||||
|         Expects list of dicts comprised of artist name (key), genre (value) |         Expects list of dicts comprised of artist name (key), genre (value) | ||||||
| @@ -228,9 +255,7 @@ class RadioUtil: | |||||||
|                 for pair in pairs: |                 for pair in pairs: | ||||||
|                     try: |                     try: | ||||||
|                         artist, genre = pair |                         artist, genre = pair | ||||||
|                         query: str = ( |                         query: str = "INSERT OR IGNORE INTO artist_genre (artist, genre) VALUES(?, ?)" | ||||||
|                             "INSERT OR IGNORE INTO artist_genre (artist, genre) VALUES(?, ?)" |  | ||||||
|                         ) |  | ||||||
|                         params: tuple[str, str] = (artist, genre) |                         params: tuple[str, str] = (artist, genre) | ||||||
|                         res = _db.execute(query, params) |                         res = _db.execute(query, params) | ||||||
|                         if isinstance(res.lastrowid, int): |                         if isinstance(res.lastrowid, int): | ||||||
| @@ -411,11 +436,13 @@ class RadioUtil: | |||||||
|                 if isinstance(db_cursor.lastrowid, int): |                 if isinstance(db_cursor.lastrowid, int): | ||||||
|                     db_conn.commit() |                     db_conn.commit() | ||||||
|                 else: |                 else: | ||||||
|                     logging.debug("No row inserted for track_id: %s w/ file_path: %s", track_id, |                     logging.debug( | ||||||
|                                   file_path) |                         "No row inserted for track_id: %s w/ file_path: %s", | ||||||
|  |                         track_id, | ||||||
|  |                         file_path, | ||||||
|  |                     ) | ||||||
|         except Exception as e: |         except Exception as e: | ||||||
|             logging.debug("cache_album_art Exception: %s", |             logging.debug("cache_album_art Exception: %s", str(e)) | ||||||
|                           str(e)) |  | ||||||
|             traceback.print_exc() |             traceback.print_exc() | ||||||
|  |  | ||||||
|     async def get_album_art(self, track_id: int) -> Optional[bytes]: |     async def get_album_art(self, track_id: int) -> Optional[bytes]: | ||||||
| @@ -433,15 +460,12 @@ class RadioUtil: | |||||||
|                 query_params: tuple[int] = (track_id,) |                 query_params: tuple[int] = (track_id,) | ||||||
|  |  | ||||||
|                 db_cursor = db_conn.execute(query, query_params) |                 db_cursor = db_conn.execute(query, query_params) | ||||||
|                 result: Optional[Union[sqlite3.Row, bool]] = ( |                 result: Optional[Union[sqlite3.Row, bool]] = db_cursor.fetchone() | ||||||
|                     db_cursor.fetchone() |  | ||||||
|                 ) |  | ||||||
|                 if not result or not isinstance(result, sqlite3.Row): |                 if not result or not isinstance(result, sqlite3.Row): | ||||||
|                     return None |                     return None | ||||||
|                 return result["album_art"] |                 return result["album_art"] | ||||||
|         except Exception as e: |         except Exception as e: | ||||||
|             logging.debug("get_album_art Exception: %s", |             logging.debug("get_album_art Exception: %s", str(e)) | ||||||
|                           str(e)) |  | ||||||
|             traceback.print_exc() |             traceback.print_exc() | ||||||
|             return None |             return None | ||||||
|  |  | ||||||
|   | |||||||
		Reference in New Issue
	
	Block a user