import { modalManager } from '../managers/ModalManager.js';
import { getModelApiClient, resetAndReload } from '../api/modelApiFactory.js';
import { showActionToast } from './uiHelpers.js';
import { translate } from './i18nHelpers.js';
import { handleUndoDelete } from './undoHelpers.js';
import { state } from '../state/index.js';
import { formatFileSize } from '../components/shared/utils.js';
const DELETE_BUTTON_ARM_DELAY_MS = 1500;
let pendingDeletePath = null;
let pendingDeleteName = null;
let pendingExcludePath = null;
let pendingDeleteArmTimer = null;
// Delay-activates every delete button inside a delete-confirmation modal so a
// misclick in the first moments after opening cannot confirm the deletion.
// Returns the pending timeout id so callers can cancel it when the modal closes early.
export function armDeleteButton(modalElement, delayMs = DELETE_BUTTON_ARM_DELAY_MS) {
if (!modalElement) return null;
const deleteButtons = modalElement.querySelectorAll('.delete-btn');
if (!deleteButtons.length) return null;
deleteButtons.forEach((button) => { button.disabled = true; });
return setTimeout(() => {
deleteButtons.forEach((button) => { button.disabled = false; });
}, delayMs);
}
export function showDeleteModal(filePath) {
pendingDeletePath = filePath;
const escapedPath = window.CSS && typeof window.CSS.escape === 'function'
? window.CSS.escape(filePath)
: filePath.replace(/["\\]/g, '\\$&');
const card = document.querySelector(`.model-card[data-filepath="${escapedPath}"]`);
const modelName = card ? card.dataset.name : filePath.split('/').pop();
pendingDeleteName = modelName;
const modal = modalManager.getModal('deleteModal').element;
const modelInfo = modal.querySelector('.delete-model-info');
const undoEnabled = state.global?.settings?.delete_undo_enabled;
const warningKey = undoEnabled
? 'modals.deleteModel.recoverableWarning'
: 'modals.deleteModel.permanentWarning';
const fileSize = card?.dataset.file_size;
const sizeLine = fileSize
? `
${translate('modals.deleteModel.freesSpace', { size: formatFileSize(parseInt(fileSize, 10)) })}`
: '';
modelInfo.innerHTML = `
Model: ${modelName}
File: ${filePath}
${translate(warningKey)}${sizeLine}
`;
modalManager.showModal('deleteModal');
pendingDeleteArmTimer = armDeleteButton(modal);
}
export async function confirmDelete() {
if (!pendingDeletePath) return;
try {
const modelName = pendingDeleteName;
const result = await getModelApiClient().deleteModel(pendingDeletePath);
closeDeleteModal();
if (result?.batch_id) {
const batchId = result.batch_id;
showActionToast('toast.undo.deleted', { name: modelName }, 'success', {
actionText: translate('toast.undo.action'),
onAction: () => handleUndoDelete(batchId, () => resetAndReload(true)),
});
}
if (window.modelDuplicatesManager) {
window.modelDuplicatesManager.updateDuplicatesBadgeAfterRefresh();
}
} catch (error) {
console.error('Error deleting model:', error);
alert(`Error deleting model: ${error}`);
}
}
export function closeDeleteModal() {
modalManager.closeModal('deleteModal');
if (pendingDeleteArmTimer) {
clearTimeout(pendingDeleteArmTimer);
pendingDeleteArmTimer = null;
}
pendingDeletePath = null;
pendingDeleteName = null;
}
// Functions for the exclude modal
export function showExcludeModal(filePath) {
pendingExcludePath = filePath;
const escapedPath = window.CSS && typeof window.CSS.escape === 'function'
? window.CSS.escape(filePath)
: filePath.replace(/["\\]/g, '\\$&');
const card = document.querySelector(`.model-card[data-filepath="${escapedPath}"]`);
const modelName = card ? card.dataset.name : filePath.split('/').pop();
const modal = modalManager.getModal('excludeModal').element;
const modelInfo = modal.querySelector('.exclude-model-info');
modelInfo.innerHTML = `
Model: ${modelName}
File: ${filePath}
`;
modalManager.showModal('excludeModal');
}
export function closeExcludeModal() {
modalManager.closeModal('excludeModal');
pendingExcludePath = null;
}
export async function confirmExclude() {
if (!pendingExcludePath) return;
try {
await getModelApiClient().excludeModel(pendingExcludePath);
closeExcludeModal();
if (window.modelDuplicatesManager) {
window.modelDuplicatesManager.updateDuplicatesBadgeAfterRefresh();
}
} catch (error) {
console.error('Error excluding model:', error);
}
}