refactor: update and remove anything to do with NFO files
Local Docker Build (Dev) / build-dev (push) Successful in 35s
Local Docker Build (Dev) / build-dev (push) Successful in 35s
moving to an all DB approach since radarr overwrites .nfo files
This commit is contained in:
@@ -382,6 +382,39 @@
|
||||
<i class="fas fa-sync"></i> Refresh Stats
|
||||
</button>
|
||||
</div>
|
||||
|
||||
<div class="tool-card">
|
||||
<h3><i class="fas fa-upload"></i> Populate Database</h3>
|
||||
<p>Bulk import data from Radarr/Sonarr into NFOGuard database</p>
|
||||
<form id="populate-form">
|
||||
<div class="form-group">
|
||||
<label>Media Type:</label>
|
||||
<select id="populate-media-type" required>
|
||||
<option value="both">Movies & TV Shows</option>
|
||||
<option value="movies">Movies Only</option>
|
||||
<option value="tv">TV Shows Only</option>
|
||||
</select>
|
||||
</div>
|
||||
<button type="submit" class="btn btn-primary">
|
||||
<i class="fas fa-play"></i> Start Population
|
||||
</button>
|
||||
</form>
|
||||
<div id="populate-status" class="scan-status" style="display: none;">
|
||||
<div class="scan-progress">
|
||||
<div class="progress-bar">
|
||||
<div class="progress-fill" id="populate-progress-bar"></div>
|
||||
</div>
|
||||
<div class="scan-info">
|
||||
<span id="populate-current-operation">Running...</span>
|
||||
<span id="populate-progress-text">In Progress</span>
|
||||
</div>
|
||||
</div>
|
||||
<div id="populate-results" class="stats-display" style="margin-top: 10px;"></div>
|
||||
<button class="btn btn-secondary btn-sm" onclick="stopPopulatePolling()">
|
||||
<i class="fas fa-times"></i> Hide Status
|
||||
</button>
|
||||
</div>
|
||||
</div>
|
||||
</div>
|
||||
</div>
|
||||
</main>
|
||||
|
||||
@@ -77,6 +77,7 @@ function initializeEventListeners() {
|
||||
document.getElementById('edit-form').addEventListener('submit', handleEditSubmit);
|
||||
document.getElementById('bulk-update-form').addEventListener('submit', handleBulkUpdate);
|
||||
document.getElementById('manual-scan-form').addEventListener('submit', handleManualScan);
|
||||
document.getElementById('populate-form').addEventListener('submit', handlePopulateDatabase);
|
||||
}
|
||||
|
||||
// API calls
|
||||
@@ -1742,3 +1743,186 @@ async function bulkDeleteSelected() {
|
||||
showToast(`❌ Failed to delete ${failCount} episode(s)`, 'error');
|
||||
}
|
||||
}
|
||||
|
||||
// ---------------------------
|
||||
// Database Population Functions
|
||||
// ---------------------------
|
||||
|
||||
async function handlePopulateDatabase(event) {
|
||||
event.preventDefault();
|
||||
|
||||
const mediaType = document.getElementById('populate-media-type').value;
|
||||
|
||||
// Validate input
|
||||
if (!mediaType) {
|
||||
showToast('❌ Please select media type', 'error');
|
||||
return;
|
||||
}
|
||||
|
||||
// Confirm with user
|
||||
const confirmMsg = `Are you sure you want to populate the database with ${mediaType}? This will query Radarr/Sonarr and may take several minutes.`;
|
||||
if (!confirm(confirmMsg)) {
|
||||
return;
|
||||
}
|
||||
|
||||
try {
|
||||
// Show populate status
|
||||
showPopulateStatus();
|
||||
|
||||
// Start the population
|
||||
showToast('🚀 Starting database population...', 'info');
|
||||
const response = await fetch(`/admin/populate-database?media_type=${mediaType}`, {
|
||||
method: 'POST',
|
||||
credentials: 'include'
|
||||
});
|
||||
|
||||
if (!response.ok) {
|
||||
throw new Error(`HTTP ${response.status}: ${response.statusText}`);
|
||||
}
|
||||
|
||||
const result = await response.json();
|
||||
|
||||
if (result.status === 'started') {
|
||||
showToast('✅ Population started successfully', 'success');
|
||||
// Start polling for status
|
||||
startPopulatePolling();
|
||||
} else {
|
||||
showToast(`ℹ️ ${result.message || 'Population completed'}`, 'info');
|
||||
hidePopulateStatus();
|
||||
}
|
||||
|
||||
} catch (error) {
|
||||
console.error('Database population failed:', error);
|
||||
showToast(`❌ Population failed: ${error.message}`, 'error');
|
||||
hidePopulateStatus();
|
||||
}
|
||||
}
|
||||
|
||||
function showPopulateStatus() {
|
||||
const populateStatus = document.getElementById('populate-status');
|
||||
const progressBar = document.getElementById('populate-progress-bar');
|
||||
const operationText = document.getElementById('populate-current-operation');
|
||||
const progressText = document.getElementById('populate-progress-text');
|
||||
const resultsDiv = document.getElementById('populate-results');
|
||||
|
||||
populateStatus.style.display = 'block';
|
||||
progressBar.style.width = '0%';
|
||||
operationText.textContent = 'Initializing...';
|
||||
progressText.textContent = '0%';
|
||||
resultsDiv.innerHTML = '';
|
||||
}
|
||||
|
||||
function hidePopulateStatus() {
|
||||
const populateStatus = document.getElementById('populate-status');
|
||||
if (populateStatus) {
|
||||
populateStatus.style.display = 'none';
|
||||
}
|
||||
}
|
||||
|
||||
function startPopulatePolling() {
|
||||
// Poll every 2 seconds for populate status
|
||||
window.populatePollingInterval = setInterval(async () => {
|
||||
try {
|
||||
const response = await fetch('/api/populate/status');
|
||||
if (!response.ok) {
|
||||
throw new Error('Failed to get populate status');
|
||||
}
|
||||
|
||||
const status = await response.json();
|
||||
updatePopulateProgress(status);
|
||||
|
||||
// Stop polling if population is complete
|
||||
if (!status.running && status.completed) {
|
||||
stopPopulatePolling();
|
||||
showToast('✅ Database population completed!', 'success');
|
||||
}
|
||||
|
||||
} catch (error) {
|
||||
console.error('Failed to poll populate status:', error);
|
||||
// Don't show error toast repeatedly, just stop polling
|
||||
stopPopulatePolling();
|
||||
}
|
||||
}, 2000);
|
||||
}
|
||||
|
||||
function stopPopulatePolling() {
|
||||
if (window.populatePollingInterval) {
|
||||
clearInterval(window.populatePollingInterval);
|
||||
window.populatePollingInterval = null;
|
||||
}
|
||||
}
|
||||
|
||||
function updatePopulateProgress(status) {
|
||||
const progressBar = document.getElementById('populate-progress-bar');
|
||||
const operationText = document.getElementById('populate-current-operation');
|
||||
const progressText = document.getElementById('populate-progress-text');
|
||||
const resultsDiv = document.getElementById('populate-results');
|
||||
|
||||
if (status.error) {
|
||||
progressBar.style.width = '100%';
|
||||
progressBar.style.backgroundColor = '#e74c3c';
|
||||
operationText.textContent = 'Error occurred';
|
||||
progressText.textContent = 'Failed';
|
||||
resultsDiv.innerHTML = `<p style="color: #e74c3c;">Error: ${status.error}</p>`;
|
||||
return;
|
||||
}
|
||||
|
||||
if (!status.running && status.completed) {
|
||||
progressBar.style.width = '100%';
|
||||
operationText.textContent = 'Population completed';
|
||||
progressText.textContent = '100%';
|
||||
|
||||
// Display results
|
||||
let resultsHTML = '<h4>Population Results:</h4>';
|
||||
|
||||
if (status.movies && status.movies.stats) {
|
||||
const m = status.movies.stats;
|
||||
resultsHTML += `
|
||||
<div style="margin: 10px 0;">
|
||||
<strong>Movies:</strong><br>
|
||||
Total: ${m.total || 0} | Added: ${m.added || 0} | Skipped: ${m.skipped || 0} | Errors: ${m.errors || 0}<br>
|
||||
Duration: ${m.duration ? m.duration.toFixed(2) : 0}s
|
||||
</div>
|
||||
`;
|
||||
}
|
||||
|
||||
if (status.tv && status.tv.stats) {
|
||||
const t = status.tv.stats;
|
||||
resultsHTML += `
|
||||
<div style="margin: 10px 0;">
|
||||
<strong>TV Shows:</strong><br>
|
||||
Series: ${t.total_series || 0} | Episodes: ${t.total_episodes || 0}<br>
|
||||
Added: ${t.added || 0} | Skipped: ${t.skipped || 0} | Errors: ${t.errors || 0}<br>
|
||||
Duration: ${t.duration ? t.duration.toFixed(2) : 0}s
|
||||
</div>
|
||||
`;
|
||||
}
|
||||
|
||||
resultsDiv.innerHTML = resultsHTML;
|
||||
return;
|
||||
}
|
||||
|
||||
// Update progress based on status
|
||||
let totalProgress = 0;
|
||||
let progressDetails = '';
|
||||
|
||||
if (status.movies && status.movies.status === 'running') {
|
||||
totalProgress = 50;
|
||||
progressDetails = 'Processing movies...';
|
||||
} else if (status.movies && status.movies.status === 'completed') {
|
||||
totalProgress = 50;
|
||||
progressDetails = 'Movies completed, processing TV...';
|
||||
}
|
||||
|
||||
if (status.tv && status.tv.status === 'running') {
|
||||
totalProgress = 75;
|
||||
progressDetails = 'Processing TV shows...';
|
||||
} else if (status.tv && status.tv.status === 'completed') {
|
||||
totalProgress = 100;
|
||||
progressDetails = 'Completed';
|
||||
}
|
||||
|
||||
progressBar.style.width = `${totalProgress}%`;
|
||||
operationText.textContent = progressDetails;
|
||||
progressText.textContent = `${totalProgress}%`;
|
||||
}
|
||||
|
||||
Reference in New Issue
Block a user