- Реструктуризация: src/ разбит на middleware/, utils/, repositories/ (удалены), routes/ (удалены) - Добавлен src/original-html.ts — полный HTML с reportModal - Добавлен src/index.tsx.backup — React-компонент с reportModal - Миграции переименованы (0001_initial_schema.sql) - Добавлена миграция 0018 (удалена позже) - Docker: multi-stage build, wrangler.toml - Frontend: public/static/app.js + style.css - seed.sql добавлен - Документация: CHANGELOG, CHANGES_v4.1.0-4.1.9, PROJECT_STRUCTURE
8.1 KiB
8.1 KiB
🔧 HOTFIX v4.1.20 - ИСПРАВЛЕНА ФОРМА НАСТРОЕК (СМЕНА ПАРОЛЯ)
Дата: 2026-01-14
Версия: v4.1.20 FINAL
Приоритет: HIGH (Критическая ошибка - невозможно использовать настройки)
📋 ПРОБЛЕМА
Форма настроек не работала
Симптомы:
- Ошибка 400 при попытке сохранить настройки
- Консоль:
PATCH /api/users/profile [HTTP/2 400 153ms] - Невозможно изменить ни имя, ни пароль
Причины:
- Несоответствие форматов полей: Frontend отправлял
full_name,current_password,new_password(snake_case), а backend ожидалfullName,currentPassword,newPassword(camelCase) - Обязательный currentPassword: Backend требовал текущий пароль ВСЕГДА, даже если пользователь только меняет имя
- Frontend валидация: Требовал
currentPasswordвсегда, даже если пароль не меняется
✅ ИСПРАВЛЕНИЯ
1. Backend: Поддержка обоих форматов + опциональный пароль
Файл: src/index.tsx, строки 63-93
app.patch('/api/users/profile', authMiddleware, async (c) => {
try {
const body = await c.req.json()
// Support both snake_case and camelCase
const fullName = body.full_name || body.fullName
const currentPassword = body.current_password || body.currentPassword
const newPassword = body.new_password || body.newPassword
const userId = c.get('userId')
console.log('[PROFILE UPDATE]', { userId, fullName, hasCurrentPwd: !!currentPassword, hasNewPwd: !!newPassword })
// Get user from database
const user = await c.env.DB.prepare(
'SELECT password_hash, full_name FROM users WHERE id = ?'
).bind(userId).first()
if (!user) {
return c.json({ error: 'Kasutajat ei leitud' }, 404)
}
// If changing password
if (newPassword) {
// Verify current password is provided
if (!currentPassword) {
return c.json({ error: 'Praegune parool on kohustuslik parooli muutmiseks' }, 400)
}
// Verify current password
if (!await verifyPassword(currentPassword, user.password_hash as string)) {
return c.json({ error: 'Vale praegune parool' }, 400)
}
// Update password and full name
const newHash = await hashPassword(newPassword)
await c.env.DB.prepare(
'UPDATE users SET password_hash = ?, full_name = ?, updated_at = CURRENT_TIMESTAMP WHERE id = ?'
).bind(newHash, fullName, userId).run()
} else {
// Only update full name (no password change)
await c.env.DB.prepare(
'UPDATE users SET full_name = ?, updated_at = CURRENT_TIMESTAMP WHERE id = ?'
).bind(fullName, userId).run()
}
return c.json({
success: true,
message: 'Profiil uuendatud',
user: {
full_name: fullName
}
})
} catch (error) {
console.error('Profile update error:', error)
return c.json({ error: 'Profiili uuendamine ebaõnnestus' }, 500)
}
})
Изменения:
- ✅ Поддержка обоих форматов полей (snake_case и camelCase)
- ✅
currentPasswordтребуется ТОЛЬКО если меняется пароль - ✅ Можно обновить только имя без смены пароля
- ✅ Добавлено логирование для отладки
2. Frontend: Опциональный currentPassword
Файл: public/static/app.js, строки 1458-1476
// Validation
if (!fullName.trim()) {
errorDiv.textContent = 'Nimi ei saa olla tühi';
errorDiv.classList.remove('hidden');
return;
}
// If changing password, current password is required
if (newPassword && !currentPassword) {
errorDiv.textContent = 'Praegune parool on kohustuslik parooli muutmiseks';
errorDiv.classList.remove('hidden');
return;
}
// Check if passwords match (only if new password is provided)
if (newPassword && newPassword !== confirmPassword) {
errorDiv.textContent = 'Uued paroolid ei kattu';
errorDiv.classList.remove('hidden');
return;
}
Изменения:
- ✅
currentPasswordтребуется ТОЛЬКО если указанnewPassword - ✅ Можно оставить поле "Praegune parool" пустым если не меняется пароль
- ✅ Более понятное сообщение об ошибке
🧪 ТЕСТИРОВАНИЕ
Test 1: Изменить только имя (БЕЗ пароля) ✅
curl -X PATCH /api/users/profile \
-d '{"full_name":"New Name","current_password":"","new_password":""}'
# Результат: {"success":true,"message":"Profiil uuendatud"}
Test 2: Изменить имя + пароль ✅
curl -X PATCH /api/users/profile \
-d '{"full_name":"Name","current_password":"demo123","new_password":"demo123"}'
# Результат: {"success":true,"message":"Profiil uuendatud"}
Test 3: Попытка сменить пароль без currentPassword ✅
curl -X PATCH /api/users/profile \
-d '{"full_name":"Name","current_password":"","new_password":"newpass"}'
# Результат: {"error":"Praegune parool on kohustuslik parooli muutmiseks"}
Test 4: Неверный текущий пароль ✅
curl -X PATCH /api/users/profile \
-d '{"full_name":"Name","current_password":"wrong","new_password":"newpass"}'
# Результат: {"error":"Vale praegune parool"}
📦 ФАЙЛЫ
Изменённые файлы:
src/index.tsx- endpoint/api/users/profilepublic/static/app.js- функцияupdateSettings()
Версия:
public/original.html- обновлена до v4.1.20
🚀 РАЗВЁРТЫВАНИЕ
# 1. Распаковать архив
unzip aknaproff_production_v4.1.20_FINAL.zip
# 2. Запустить
cd backend
docker-compose up -d --build
# 3. Проверить форму настроек
# Открыть веб-интерфейс → Seaded → изменить имя → сохранить
📝 СЦЕНАРИИ ИСПОЛЬЗОВАНИЯ
Сценарий 1: Изменить только имя
- Открыть форму "Seaded"
- Изменить "Nimi"
- Оставить поля паролей ПУСТЫМИ
- Нажать "Salvesta"
- ✅ Имя обновлено
Сценарий 2: Изменить пароль
- Открыть форму "Seaded"
- Ввести "Praegune parool"
- Ввести "Uus parool"
- Ввести "Kinnita uus parool"
- Нажать "Salvesta"
- ✅ Пароль изменён
Сценарий 3: Изменить имя + пароль
- Открыть форму "Seaded"
- Изменить "Nimi"
- Ввести все поля паролей
- Нажать "Salvesta"
- ✅ Имя и пароль обновлены
✅ РЕЗУЛЬТАТ
- ✅ Форма настроек работает корректно
- ✅ Можно изменить только имя (без пароля)
- ✅ Можно изменить пароль (с проверкой текущего)
- ✅ Правильная валидация на frontend и backend
- ✅ Понятные сообщения об ошибках на эстонском языке
🔄 ИСТОРИЯ ВЕРСИЙ
| Версия | Изменения |
|---|---|
| v4.1.19 | Документирована логика блокировки VALMIS/VÄLJAS |
| v4.1.20 | Исправлена форма настроек (смена пароля) |
Статус: ✅ ГОТОВО
Тестирование: ✅ ПРОЙДЕНО
Развёртывание: ГОТОВО К ИСПОЛЬЗОВАНИЮ