Feature: Historial, DELETE de movimientos y sistema de modales

- Nueva pantalla historial.html con movimientos agrupados por mes
- Botón eliminar en cada movimiento con modal de confirmación
- js/ui.js: sistema de modales y toasts reutilizables (reemplaza alert/confirm nativos)
- API: endpoint GET ?view=historial y método DELETE en movimientos.php
- add.html: categorías cargadas dinámicamente desde la API
- index.html: "Ver todo" e ícono de nav apuntan a historial.html
- Docker: eliminado volumen nombrado db_data para evitar problemas de permisos

Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com>
This commit is contained in:
Ricardo Monla
2026-06-03 16:06:28 -03:00
co-authored by Claude Sonnet 4.6
parent 5a54fdcfde
commit 1db200343d
8 changed files with 356 additions and 32 deletions
+17 -4
View File
@@ -12,6 +12,19 @@ document.addEventListener('DOMContentLoaded', () => {
// Default a hoy
iptFecha.valueAsDate = new Date();
// Cargar categorías desde la API
fetch('api/movimientos.php')
.then(r => r.json())
.then(data => {
if (data.categorias) {
const sel = document.getElementById('ui-categoria');
sel.innerHTML = data.categorias.map(c =>
`<option value="${c.id}">${c.nombre}</option>`
).join('');
}
})
.catch(() => {});
// Tipo selector
const updateTipoUI = () => {
if (selectedTipo === 'gasto') {
@@ -62,7 +75,7 @@ document.addEventListener('DOMContentLoaded', () => {
};
if (isNaN(payload.monto) || payload.monto <= 0) {
alert('Por favor ingrese un monto mayor a 0');
rmModal.alert('Ingresá un monto mayor a 0.', 'Monto inválido');
return;
}
@@ -79,15 +92,15 @@ document.addEventListener('DOMContentLoaded', () => {
const data = await r.json();
if (data.status === 'success') {
window.location.href = 'index.html'; // Redirige al inicio tras guardar
window.location.href = 'index.html';
} else {
alert('Error al guardar: ' + data.message);
await rmModal.alert(data.message, 'Error al guardar');
btnSave.innerHTML = btnOriginal;
btnSave.disabled = false;
}
} catch (err) {
console.error(err);
alert('Fallo en la comunicación');
await rmModal.alert('No se pudo conectar con el servidor.', 'Error de conexión');
btnSave.disabled = false;
}
});