add files to lib return value debug

This commit is contained in:
billy 2025-04-08 15:57:34 -04:00
parent 47ec08ec15
commit 40d78066c6
4 changed files with 98 additions and 89 deletions

View File

@ -8,12 +8,11 @@ from logging import debug
class DebugWindow(QDialog):
def __init__(self, song_filepath: str, text: str):
def __init__(self, text: str):
super(DebugWindow, self).__init__()
self.setWindowTitle("debug")
self.setMinimumSize(400, 400)
self.text: str = text
self.song_filepath: str = song_filepath
layout = QVBoxLayout()
# Labels & input fields

View File

@ -124,7 +124,7 @@ class MusicTable(QTableView):
self.selected_song_filepath = ""
self.current_song_filepath = ""
self.current_song_db_id = None
self.current_song_qmodelindex = None
self.current_song_qmodelindex: QModelIndex
# Properties
self.setAcceptDrops(True)
@ -265,7 +265,7 @@ class MusicTable(QTableView):
if directories:
worker = Worker(self.get_audio_files_recursively, directories)
worker.signals.signal_progress.connect(self.handle_progress)
worker.signals.signal_result.connect(self.on_recursive_search_finished)
worker.signals.signal_result.connect(self.on_get_audio_files_recursively_finished)
worker.signals.signal_finished.connect(self.load_music_table)
if self.qapp:
threadpool = self.qapp.threadpool
@ -399,49 +399,29 @@ class MusicTable(QTableView):
update_song_in_database(song_id, edited_column_name, user_input_data)
return
def on_recursive_search_finished(self, result):
"""file search completion handler"""
if result:
self.add_files_to_library(result)
def handle_progress(self, data):
"""Emits data to main"""
self.handleProgressSignal.emit(data)
# ____________________
# | |
# | |
# | Connection Mgmt |
# | |
# |____________________|
def on_get_audio_files_recursively_finished(self, result):
"""file search completion handler"""
if result:
self.add_files_to_library(result)
def disconnect_data_changed(self):
"""Disconnects the dataChanged signal from QTableView.model"""
try:
self.model2.dataChanged.disconnect()
except Exception:
pass
def on_add_files_to_database_finished(self, *args):
"""
Shows failed to import files and reasons
Runs after worker process signal_finished for add_files_to_database()
def connect_data_changed(self):
"""Connects the dataChanged signal from QTableView.model"""
try:
self.model2.dataChanged.connect(self.on_cell_data_changed)
except Exception:
pass
def disconnect_layout_changed(self):
"""Disconnects the layoutChanged signal from QTableView.model"""
try:
self.model2.layoutChanged.disconnect()
except Exception:
pass
def connect_layout_changed(self):
"""Connects the layoutChanged signal from QTableView.model"""
try:
self.model2.layoutChanged.connect(self.restore_scroll_position)
except Exception:
pass
Args:
- args: ((return_data),)
- data returned from the original worker process function are returned here
as the first item in a tuple
"""
# TODO: make this prettier, show a table in a window instead of raw text probably
_, details = args[0][:2]
window = DebugWindow(details)
window.exec_()
# ____________________
# | |
@ -458,6 +438,7 @@ class MusicTable(QTableView):
"""
worker = Worker(add_files_to_database, files)
worker.signals.signal_progress.connect(self.qapp.handle_progress)
worker.signals.signal_result.connect(self.on_add_files_to_database_finished)
worker.signals.signal_finished.connect(self.load_music_table)
if self.qapp:
threadpool = self.qapp.threadpool
@ -539,12 +520,9 @@ class MusicTable(QTableView):
def show_id3_tags_debug_menu(self):
"""Shows ID3 tags for a specific .mp3 file"""
selected_song_filepath = self.get_selected_song_filepath()
if selected_song_filepath is None:
return
current_song = self.get_selected_song_metadata()
lyrics_window = DebugWindow(selected_song_filepath, str(current_song))
lyrics_window.exec_()
if self.get_selected_song_filepath() is not None:
window = DebugWindow(str(self.get_selected_song_metadata()))
window.exec_()
def show_lyrics_menu(self):
"""Shows the lyrics for the currently selected song"""
@ -601,6 +579,8 @@ class MusicTable(QTableView):
debug("reorganizing files")
# FIXME: batch update, instead of doing 1 file at a time
# DBAccess is being instantiated for every file, boo
# NOTE:
# is that even possible with move file function?
# Get target directory
target_dir = str(self.config["directories"]["reorganize_destination"])
@ -618,10 +598,8 @@ class MusicTable(QTableView):
if progress_callback:
progress_callback.emit(f"Organizing: {filepath}")
# Create the directories if they dont exist
debug("make dirs")
os.makedirs(os.path.dirname(new_path), exist_ok=True)
# Move the file to the new directory
debug(f"{filepath} > {new_path}")
shutil.move(filepath, new_path)
# Update the db
with DBA.DBAccess() as db:
@ -629,7 +607,7 @@ class MusicTable(QTableView):
"UPDATE song SET filepath = ? WHERE filepath = ?",
(new_path, filepath),
)
debug(f"reorganize_files() | Moved: {filepath} -> {new_path}")
# debug(f"reorganize_files() | Moved: {filepath} -> {new_path}")
except Exception as e:
error(f"reorganize_files() | Error moving file: {filepath} | {e}")
# Draw the rest of the owl
@ -757,7 +735,7 @@ class MusicTable(QTableView):
def restore_scroll_position(self) -> None:
"""Restores the scroll position"""
debug("restore_scroll_position")
debug("restore_scroll_position (inactive)")
# QTimer.singleShot(
# 100,
# lambda: self.verticalScrollBar().setValue(self.vertical_scroll_position),
@ -845,6 +823,40 @@ class MusicTable(QTableView):
"""Necessary for using members and methods of main application window"""
self.qapp = qapp
# ____________________
# | |
# | |
# | Connection Mgmt |
# | |
# |____________________|
def disconnect_data_changed(self):
"""Disconnects the dataChanged signal from QTableView.model"""
try:
self.model2.dataChanged.disconnect()
except Exception:
pass
def connect_data_changed(self):
"""Connects the dataChanged signal from QTableView.model"""
try:
self.model2.dataChanged.connect(self.on_cell_data_changed)
except Exception:
pass
def disconnect_layout_changed(self):
"""Disconnects the layoutChanged signal from QTableView.model"""
try:
self.model2.layoutChanged.disconnect()
except Exception:
pass
def connect_layout_changed(self):
"""Connects the layoutChanged signal from QTableView.model"""
try:
self.model2.layoutChanged.connect(self.restore_scroll_position)
except Exception:
pass
# QT Roles

View File

@ -1,4 +1,5 @@
from PyQt5.QtWidgets import QMessageBox
from mutagen.id3 import ID3
import DBA
from logging import debug
from utils import get_id3_tags, convert_id3_timestamp_to_datetime
@ -21,25 +22,21 @@ def add_files_to_database(files, progress_callback=None):
Path(user_config_dir(appname="musicpom", appauthor="billypom")) / "config.ini"
)
config.read(cfg_file)
if not files:
return False
return False, {'Failure': 'All operations failed in add_files_to_database()'}
extensions = config.get("settings", "extensions").split(",")
failed_dict = {}
insert_data = [] # To store data for batch insert
for filepath in files:
if any(filepath.lower().endswith(ext) for ext in extensions):
if progress_callback:
progress_callback.emit(filepath)
filename = filepath.split("/")[-1]
audio = get_id3_tags(filepath)
if not audio:
QMessageBox.error(
"Error",
f"Could not retrieve ID3 tags for {filepath}",
QMessageBox.Ok,
QMessageBox.Ok,
)
return
audio, details = get_id3_tags(filepath)
if not isinstance(audio, ID3):
failed_dict[filepath] = details
continue
try:
title = audio["TIT2"].text[0]
@ -105,7 +102,7 @@ def add_files_to_database(files, progress_callback=None):
"INSERT OR IGNORE INTO song (filepath, title, album, artist, track_number, genre, codec, album_date, bitrate) VALUES (?, ?, ?, ?, ?, ?, ?, ?, ?)",
insert_data,
)
return True
return True, failed_dict
# id int unsigned auto_increment,

View File

@ -5,13 +5,11 @@ from mutagen.id3._frames import TIT2
from mutagen.id3._util import ID3NoHeaderError
def get_id3_tags(filename: str):
def get_id3_tags(filename: str) -> tuple[object, str]:
"""Get the ID3 tags for an audio file"""
# debug(filename)
if filename.endswith(".flac"):
return
if filename.endswith(".mp3"):
try:
# Open the MP3 file and read its content
audio = ID3(filename)
@ -29,14 +27,17 @@ def get_id3_tags(filename: str):
list_of_id3_tags = list(audio.keys())
if "TIT2" in list_of_id3_tags:
audio.save()
return audio
return audio, ""
else:
tit2_tag = TIT2(encoding=3, text=[title])
audio["TIT2"] = tit2_tag
# Save the updated tags
audio.save()
return audio, ""
except Exception as e:
error(f"Could not assign file ID3 tag: {e}")
return None, f"Could not assign ID3 tag to file: {e}"
return None, "non mp3 file"
return audio