// js/init.js document.addEventListener('DOMContentLoaded', () => { const DOMElements = { initForm: document.getElementById('init-form'), initButton: null, toastContainer: document.getElementById('toast-container'), usernameInput: document.getElementById('username'), passwordInput: document.getElementById('password'), confirmPasswordInput: document.getElementById('confirm_password'), }; const INIT_API_URL = '/v0/api/auth/init'; const PASSWORD_MIN_LENGTH = 8; const TOAST_DEFAULT_DURATION = 3000; const REDIRECT_DELAY_SUCCESS = 1500; const theme = { init: () => { const storedTheme = localStorage.getItem('theme'); const systemPrefersDark = window.matchMedia('(prefers-color-scheme: dark)').matches; const currentTheme = storedTheme || (systemPrefersDark ? 'dark' : 'light'); document.documentElement.dataset.theme = currentTheme; } }; const toast = { _container: null, _icons: { success: 'fa-check-circle', error: 'fa-times-circle', info: 'fa-info-circle' }, init: (containerElement) => { if (!containerElement) { console.error('Toast container element not found.'); return; } toast._container = containerElement; toast._container.addEventListener('click', (e) => { if (e.target.dataset.toastClose !== undefined) { toast._hideToast(e.target.closest('.toast')); } }); }, show: (message, type = 'info', duration = TOAST_DEFAULT_DURATION) => { if (!toast._container) { console.error('Toast module not initialized. Container is missing.'); return; } const iconClass = toast._icons[type] || 'fa-info-circle'; const toastElement = document.createElement('div'); toastElement.className = `toast ${type}`; toastElement.innerHTML = `

${message}

`; toast._container.appendChild(toastElement); requestAnimationFrame(() => toastElement.classList.add('show')); setTimeout(() => toast._hideToast(toastElement), duration); }, _hideToast: (toastElement) => { if (!toastElement) return; toastElement.classList.remove('show'); toastElement.addEventListener('transitionend', () => toastElement.remove(), { once: true }); } }; async function handleInitSubmit(e) { e.preventDefault(); // 1. 获取并修剪输入值 const username = DOMElements.usernameInput.value.trim(); // 获取用户名并去除前后空格 const password = DOMElements.passwordInput.value.trim(); const confirmPassword = DOMElements.confirmPasswordInput.value.trim(); // 2. 添加用户名输入框的空值验证 if (username === '') { toast.show('管理员用户名不能为空', 'error'); DOMElements.usernameInput.focus(); return; } // 其他密码验证逻辑不变 if (password === '') { toast.show('密码不能为空', 'error'); DOMElements.passwordInput.focus(); return; } if (confirmPassword === '') { toast.show('确认密码不能为空', 'error'); DOMElements.confirmPasswordInput.focus(); return; } if (password !== confirmPassword) { toast.show('两次输入的密码不匹配', 'error'); DOMElements.passwordInput.focus(); return; } if (password.length < PASSWORD_MIN_LENGTH) { toast.show(`密码长度至少为 ${PASSWORD_MIN_LENGTH} 位`, 'error'); DOMElements.passwordInput.focus(); return; } DOMElements.initButton.disabled = true; DOMElements.initButton.querySelector('span').textContent = '设置中...'; try { const formData = new FormData(DOMElements.initForm); formData.set('username', username); // 确保发送的是修剪过的用户名 formData.set('password', password); // 确保发送的是修剪过的密码 formData.delete('confirm_password'); const response = await fetch(INIT_API_URL, { method: 'POST', body: new URLSearchParams(formData) }); const result = await response.json(); if (response.ok) { toast.show('管理员账户创建成功!正在跳转到登录页面...', 'success'); setTimeout(() => { window.location.href = '/login.html'; }, REDIRECT_DELAY_SUCCESS); } else { throw new Error(result.error || `初始化失败: ${response.status}`); } } catch (error) { toast.show(error.message, 'error'); DOMElements.initButton.disabled = false; DOMElements.initButton.querySelector('span').textContent = '完成设置'; } } function initApp() { theme.init(); if (DOMElements.initForm) { DOMElements.initButton = DOMElements.initForm.querySelector('button[type="submit"]'); toast.init(DOMElements.toastContainer); DOMElements.initForm.addEventListener('submit', handleInitSubmit); } else { console.error('Init form element not found. Script may not function correctly.'); } } initApp(); });