- Dashboard com 5 gráficos Chart.js (execuções, status, custo, agentes, pipelines) - Sistema de notificações com polling, badge e Browser Notification API - Relatórios MD automáticos para execuções de agentes e pipelines (data/reports/) - Lucide local (v0.475.0) com nomes de ícones atualizados e refreshIcons centralizado - Correção de ícones icon-only (padding CSS sobrescrito por btn-sm) - Cards de agentes e pipelines com botões alinhados na base (flex column) - Terminal com busca, download, cópia e auto-scroll toggle - Histórico com export CSV, retry, paginação e truncamento de texto - Webhooks com edição e teste inline - Duplicação de agentes e export/import JSON - Rate limiting, CORS, correlação de requests e health check no backend - Escrita atômica em JSON (temp + rename) e store de notificações - Tema claro/escuro com toggle e persistência em localStorage - Atalhos de teclado 1-9 para navegação entre seções
65 lines
1.7 KiB
JavaScript
65 lines
1.7 KiB
JavaScript
const Toast = {
|
|
iconMap: {
|
|
success: 'circle-check',
|
|
error: 'circle-x',
|
|
info: 'info',
|
|
warning: 'triangle-alert',
|
|
},
|
|
|
|
colorMap: {
|
|
success: 'toast-success',
|
|
error: 'toast-error',
|
|
info: 'toast-info',
|
|
warning: 'toast-warning',
|
|
},
|
|
|
|
show(message, type = 'info', duration = 4000) {
|
|
const container = document.getElementById('toast-container');
|
|
if (!container) return;
|
|
|
|
const toast = document.createElement('div');
|
|
toast.className = `toast toast-${type}`;
|
|
|
|
const iconName = Toast.iconMap[type] || 'info';
|
|
|
|
toast.innerHTML = `
|
|
<span class="toast-icon" data-lucide="${iconName}"></span>
|
|
<span class="toast-message">${message}</span>
|
|
<button class="toast-close" aria-label="Fechar notificação">
|
|
<i data-lucide="x"></i>
|
|
</button>
|
|
`;
|
|
|
|
const closeBtn = toast.querySelector('.toast-close');
|
|
closeBtn.addEventListener('click', () => Toast.dismiss(toast));
|
|
|
|
container.appendChild(toast);
|
|
|
|
Utils.refreshIcons(toast);
|
|
|
|
requestAnimationFrame(() => {
|
|
toast.classList.add('toast-show');
|
|
});
|
|
|
|
if (duration > 0) {
|
|
setTimeout(() => Toast.dismiss(toast), duration);
|
|
}
|
|
|
|
return toast;
|
|
},
|
|
|
|
dismiss(toast) {
|
|
toast.classList.remove('toast-show');
|
|
toast.classList.add('removing');
|
|
toast.addEventListener('animationend', () => toast.remove(), { once: true });
|
|
setTimeout(() => toast.remove(), 400);
|
|
},
|
|
|
|
success(message, duration) { return Toast.show(message, 'success', duration); },
|
|
error(message, duration) { return Toast.show(message, 'error', duration); },
|
|
info(message, duration) { return Toast.show(message, 'info', duration); },
|
|
warning(message, duration) { return Toast.show(message, 'warning', duration); },
|
|
};
|
|
|
|
window.Toast = Toast;
|