This commit is contained in:
+148
-8
@@ -2579,6 +2579,9 @@ def register_routes(app, dependencies: dict):
|
||||
print("🔍 Looking up dateadded values from database for missing items...")
|
||||
|
||||
# Enhance episodes with database data
|
||||
episodes_with_dates = 0
|
||||
episodes_missing_db = 0
|
||||
|
||||
for episode in missing_items["episodes"]:
|
||||
if episode["imdb_id"] != "unknown":
|
||||
try:
|
||||
@@ -2595,12 +2598,47 @@ def register_routes(app, dependencies: dict):
|
||||
if result:
|
||||
episode["dateadded"] = result["dateadded"]
|
||||
episode["source"] = result.get("source", "database")
|
||||
episodes_with_dates += 1
|
||||
print(f"✅ Found database date for {episode['imdb_id']} S{episode['season']:02d}E{episode['episode']:02d}: {result['dateadded']}")
|
||||
else:
|
||||
print(f"⚠️ No database entry for {episode['imdb_id']} S{episode['season']:02d}E{episode['episode']:02d}")
|
||||
episodes_missing_db += 1
|
||||
# Try to find other episodes from same series to estimate date
|
||||
cursor.execute("""
|
||||
SELECT dateadded, season, episode
|
||||
FROM episodes
|
||||
WHERE imdb_id = %s AND dateadded IS NOT NULL
|
||||
ORDER BY season DESC, episode DESC
|
||||
LIMIT 3
|
||||
""", (episode["imdb_id"],))
|
||||
|
||||
similar_episodes = cursor.fetchall()
|
||||
if similar_episodes:
|
||||
latest_date = similar_episodes[0]["dateadded"]
|
||||
episode["dateadded"] = latest_date
|
||||
episode["source"] = f"estimated_from_series_latest"
|
||||
print(f"🔮 Estimated date for {episode['imdb_id']} S{episode['season']:02d}E{episode['episode']:02d} from latest episode: {latest_date}")
|
||||
else:
|
||||
# Use NFO file modification time as fallback
|
||||
try:
|
||||
import os
|
||||
from datetime import datetime
|
||||
if os.path.exists(episode["nfo_path"]):
|
||||
file_mtime = os.path.getmtime(episode["nfo_path"])
|
||||
file_date = datetime.fromtimestamp(file_mtime)
|
||||
episode["dateadded"] = file_date
|
||||
episode["source"] = "nfo_file_mtime"
|
||||
print(f"📅 Using NFO file date for {episode['imdb_id']} S{episode['season']:02d}E{episode['episode']:02d}: {file_date}")
|
||||
else:
|
||||
print(f"❌ No fallback date available for {episode['imdb_id']} S{episode['season']:02d}E{episode['episode']:02d}")
|
||||
except Exception as fallback_error:
|
||||
print(f"⚠️ Fallback date lookup failed for {episode['imdb_id']}: {fallback_error}")
|
||||
except Exception as e:
|
||||
print(f"⚠️ Database lookup failed for episode {episode['imdb_id']}: {e}")
|
||||
|
||||
# Enhance movies with database data
|
||||
movies_with_dates = 0
|
||||
movies_missing_db = 0
|
||||
|
||||
for movie in missing_items["movies"]:
|
||||
if movie["imdb_id"] != "unknown":
|
||||
try:
|
||||
@@ -2617,11 +2655,34 @@ def register_routes(app, dependencies: dict):
|
||||
if result:
|
||||
movie["dateadded"] = result["dateadded"]
|
||||
movie["source"] = result.get("source", "database")
|
||||
movies_with_dates += 1
|
||||
print(f"✅ Found database date for movie {movie['imdb_id']}: {result['dateadded']}")
|
||||
else:
|
||||
print(f"⚠️ No database entry for movie {movie['imdb_id']}")
|
||||
movies_missing_db += 1
|
||||
# Use NFO file modification time as fallback for movies
|
||||
try:
|
||||
import os
|
||||
from datetime import datetime
|
||||
if os.path.exists(movie["nfo_path"]):
|
||||
file_mtime = os.path.getmtime(movie["nfo_path"])
|
||||
file_date = datetime.fromtimestamp(file_mtime)
|
||||
movie["dateadded"] = file_date
|
||||
movie["source"] = "nfo_file_mtime"
|
||||
print(f"📅 Using NFO file date for movie {movie['imdb_id']}: {file_date}")
|
||||
else:
|
||||
print(f"❌ No fallback date available for movie {movie['imdb_id']}")
|
||||
except Exception as fallback_error:
|
||||
print(f"⚠️ Fallback date lookup failed for movie {movie['imdb_id']}: {fallback_error}")
|
||||
except Exception as e:
|
||||
print(f"⚠️ Database lookup failed for movie {movie['imdb_id']}: {e}")
|
||||
|
||||
# Print summary statistics
|
||||
total_episodes = len(missing_items["episodes"])
|
||||
total_movies = len(missing_items["movies"])
|
||||
print(f"📊 Database lookup summary:")
|
||||
print(f" Episodes: {episodes_with_dates}/{total_episodes} found in DB, {episodes_missing_db} missing from DB")
|
||||
print(f" Movies: {movies_with_dates}/{total_movies} found in DB, {movies_missing_db} missing from DB")
|
||||
|
||||
total_missing = len(missing_items["episodes"]) + len(missing_items["movies"])
|
||||
print(f"✅ NFO repair scan complete: {total_missing} items missing dateadded elements")
|
||||
|
||||
@@ -2707,6 +2768,14 @@ def register_routes(app, dependencies: dict):
|
||||
# Write back to file
|
||||
tree.write(nfo_path, encoding='utf-8', xml_declaration=True)
|
||||
|
||||
# VERIFY the write was successful by re-reading the file
|
||||
try:
|
||||
verify_tree = ET.parse(nfo_path)
|
||||
verify_root = verify_tree.getroot()
|
||||
verify_dateadded = verify_root.find("dateadded")
|
||||
|
||||
if verify_dateadded is not None and verify_dateadded.text and verify_dateadded.text.strip():
|
||||
# Verification successful
|
||||
fixed_count += 1
|
||||
results.append({
|
||||
"type": "episode",
|
||||
@@ -2715,10 +2784,36 @@ def register_routes(app, dependencies: dict):
|
||||
"episode": episode["episode"],
|
||||
"nfo_path": nfo_path,
|
||||
"dateadded": nfo_dateadded,
|
||||
"status": "fixed"
|
||||
"verified_dateadded": verify_dateadded.text.strip(),
|
||||
"status": "fixed_and_verified"
|
||||
})
|
||||
|
||||
print(f"✅ Fixed episode {episode['imdb_id']} S{episode['season']:02d}E{episode['episode']:02d}")
|
||||
print(f"✅ Fixed and verified episode {episode['imdb_id']} S{episode['season']:02d}E{episode['episode']:02d}")
|
||||
else:
|
||||
# Verification failed - dateadded missing after write
|
||||
failed_count += 1
|
||||
results.append({
|
||||
"type": "episode",
|
||||
"imdb_id": episode["imdb_id"],
|
||||
"season": episode["season"],
|
||||
"episode": episode["episode"],
|
||||
"nfo_path": nfo_path,
|
||||
"dateadded": nfo_dateadded,
|
||||
"status": "write_failed_verification"
|
||||
})
|
||||
print(f"❌ Write verification FAILED for episode {episode['imdb_id']} S{episode['season']:02d}E{episode['episode']:02d} - dateadded not found after write")
|
||||
except Exception as verify_error:
|
||||
# Verification failed due to parse error
|
||||
failed_count += 1
|
||||
results.append({
|
||||
"type": "episode",
|
||||
"imdb_id": episode["imdb_id"],
|
||||
"season": episode["season"],
|
||||
"episode": episode["episode"],
|
||||
"nfo_path": nfo_path,
|
||||
"status": "verification_parse_error",
|
||||
"error": str(verify_error)
|
||||
})
|
||||
print(f"❌ Verification parse error for episode {episode['imdb_id']} S{episode['season']:02d}E{episode['episode']:02d}: {verify_error}")
|
||||
else:
|
||||
failed_count += 1
|
||||
print(f"❌ NFO file not found: {nfo_path}")
|
||||
@@ -2759,6 +2854,14 @@ def register_routes(app, dependencies: dict):
|
||||
# Write back to file
|
||||
tree.write(nfo_path, encoding='utf-8', xml_declaration=True)
|
||||
|
||||
# VERIFY the write was successful by re-reading the file
|
||||
try:
|
||||
verify_tree = ET.parse(nfo_path)
|
||||
verify_root = verify_tree.getroot()
|
||||
verify_dateadded = verify_root.find("dateadded")
|
||||
|
||||
if verify_dateadded is not None and verify_dateadded.text and verify_dateadded.text.strip():
|
||||
# Verification successful
|
||||
fixed_count += 1
|
||||
results.append({
|
||||
"type": "movie",
|
||||
@@ -2766,10 +2869,34 @@ def register_routes(app, dependencies: dict):
|
||||
"title": movie["title"],
|
||||
"nfo_path": nfo_path,
|
||||
"dateadded": nfo_dateadded,
|
||||
"status": "fixed"
|
||||
"verified_dateadded": verify_dateadded.text.strip(),
|
||||
"status": "fixed_and_verified"
|
||||
})
|
||||
|
||||
print(f"✅ Fixed movie {movie['imdb_id']} ({movie['title']})")
|
||||
print(f"✅ Fixed and verified movie {movie['imdb_id']} ({movie['title']})")
|
||||
else:
|
||||
# Verification failed - dateadded missing after write
|
||||
failed_count += 1
|
||||
results.append({
|
||||
"type": "movie",
|
||||
"imdb_id": movie["imdb_id"],
|
||||
"title": movie["title"],
|
||||
"nfo_path": nfo_path,
|
||||
"dateadded": nfo_dateadded,
|
||||
"status": "write_failed_verification"
|
||||
})
|
||||
print(f"❌ Write verification FAILED for movie {movie['imdb_id']} ({movie['title']}) - dateadded not found after write")
|
||||
except Exception as verify_error:
|
||||
# Verification failed due to parse error
|
||||
failed_count += 1
|
||||
results.append({
|
||||
"type": "movie",
|
||||
"imdb_id": movie["imdb_id"],
|
||||
"title": movie["title"],
|
||||
"nfo_path": nfo_path,
|
||||
"status": "verification_parse_error",
|
||||
"error": str(verify_error)
|
||||
})
|
||||
print(f"❌ Verification parse error for movie {movie['imdb_id']} ({movie['title']}): {verify_error}")
|
||||
else:
|
||||
failed_count += 1
|
||||
print(f"❌ NFO file not found: {nfo_path}")
|
||||
@@ -2780,11 +2907,24 @@ def register_routes(app, dependencies: dict):
|
||||
|
||||
print(f"✅ NFO repair fix complete: {fixed_count} fixed, {failed_count} failed")
|
||||
|
||||
# Final summary with detailed statistics
|
||||
verification_summary = {
|
||||
"fixed_and_verified": sum(1 for r in results if r.get("status") == "fixed_and_verified"),
|
||||
"write_failed_verification": sum(1 for r in results if r.get("status") == "write_failed_verification"),
|
||||
"verification_parse_error": sum(1 for r in results if r.get("status") == "verification_parse_error")
|
||||
}
|
||||
|
||||
print(f"📊 Final summary: {fixed_count} fixed, {failed_count} failed")
|
||||
print(f" ✅ Verified successful: {verification_summary['fixed_and_verified']}")
|
||||
print(f" ❌ Write verification failed: {verification_summary['write_failed_verification']}")
|
||||
print(f" ⚠️ Verification parse errors: {verification_summary['verification_parse_error']}")
|
||||
|
||||
return {
|
||||
"status": "success",
|
||||
"total_processed": total_episodes + total_movies,
|
||||
"fixed_count": fixed_count,
|
||||
"failed_count": failed_count,
|
||||
"verification_summary": verification_summary,
|
||||
"results": results[:20] # Show first 20 for UI
|
||||
}
|
||||
|
||||
|
||||
Reference in New Issue
Block a user