feat(i18n): add internationalization framework with 10 languages

- Create i18n utility module (app/utils/i18n.py) with translation loading,
  browser language detection, AI fallback, and l10n helpers
- Add JSON translation files for EN, DE, FR, ES, IT, PT, NL, PL, ZH, RU
- Add preferred_language column to UserProfile model with migration
- Register _() translation function as Jinja2 global
- Update base.html with translated navigation, footer, cookie notice
- Add language selector dropdown in nav bar (desktop + mobile)
- Create API endpoints for language preference (POST/GET /api/i18n/)
- Support language detection: user profile > cookie > Accept-Language > default

Co-authored-by: christianlouis <361235+christianlouis@users.noreply.github.com>
This commit is contained in:
copilot-swe-agent[bot]
2026-03-09 23:28:02 +00:00
parent 95f1798908
commit ff76855f29
17 changed files with 2618 additions and 76 deletions
+190
View File
@@ -0,0 +1,190 @@
{
"app.name": "DocuElevate",
"nav.dashboard": "Панель управления",
"nav.upload": "Загрузить",
"nav.files": "Файлы",
"nav.search": "Поиск",
"nav.pipelines": "Конвейеры",
"nav.integrations": "Интеграции",
"nav.help": "Помощь",
"nav.notifications": "Уведомления",
"nav.pricing": "Цены",
"nav.about": "О нас",
"nav.admin": "Админ",
"nav.settings": "Настройки",
"nav.users": "Пользователи",
"nav.plan_designer": "Конструктор планов",
"nav.credentials": "Учётные данные",
"nav.file_manager": "Менеджер файлов",
"nav.duplicates": "Дубликаты",
"nav.similarity": "Сходство",
"nav.queue_monitor": "Монитор очереди",
"nav.scheduled_jobs": "Запланированные задачи",
"nav.backup_restore": "Резервное копирование и восстановление",
"nav.status": "Статус",
"nav.api_docs": "Документация API",
"nav.developer_docs": "Документация для разработчиков",
"nav.dark_mode": "Тёмная тема",
"nav.light_mode": "Светлая тема",
"nav.toggle_dark_mode": "Переключить тёмную тему",
"nav.toggle_nav": "Переключить меню навигации",
"nav.open_main_menu": "Открыть главное меню",
"nav.skip_to_content": "Перейти к основному содержанию",
"nav.main_navigation": "Основная навигация",
"nav.admin_menu": "Меню администратора",
"nav.admin_actions": "Действия администратора",
"nav.help_center": "Центр помощи",
"auth.login": "Войти",
"auth.logout": "Выйти",
"auth.signup": "Регистрация",
"auth.my_account": "Мой аккаунт",
"auth.profile": "Профиль",
"footer.copyright": "DocuElevate {year}",
"footer.privacy": "Конфиденциальность",
"footer.imprint": "Выходные данные",
"footer.terms": "Условия",
"footer.cookies": "Файлы cookie",
"footer.license": "Лицензия",
"footer.attributions": "Атрибуции",
"footer.version": "Версия {version}",
"footer.navigation": "Навигация подвала",
"cookie.notice": "DocuElevate использует только необходимые сессионные файлы cookie для аутентификации и работы сервиса. Файлы cookie для отслеживания и аналитики не используются.",
"cookie.policy_link": "Политика файлов cookie",
"cookie.privacy_link": "Уведомление о конфиденциальности",
"cookie.accept": "Понятно",
"cookie.notice_label": "Уведомление о файлах cookie",
"common.save": "Сохранить",
"common.cancel": "Отмена",
"common.delete": "Удалить",
"common.edit": "Редактировать",
"common.close": "Закрыть",
"common.confirm": "Подтвердить",
"common.back": "Назад",
"common.next": "Далее",
"common.loading": "Загрузка...",
"common.error": "Ошибка",
"common.success": "Успешно",
"common.warning": "Предупреждение",
"common.info": "Информация",
"common.yes": "Да",
"common.no": "Нет",
"common.search": "Поиск",
"common.filter": "Фильтр",
"common.reset": "Сбросить",
"common.refresh": "Обновить",
"common.download": "Скачать",
"common.actions": "Действия",
"common.details": "Подробности",
"common.name": "Название",
"common.description": "Описание",
"common.type": "Тип",
"common.status": "Статус",
"common.date": "Дата",
"common.size": "Размер",
"common.created": "Создано",
"common.updated": "Обновлено",
"common.enabled": "Включено",
"common.disabled": "Отключено",
"common.active": "Активно",
"common.inactive": "Неактивно",
"common.all": "Все",
"common.none": "Нет",
"common.select": "Выбрать",
"common.upload": "Загрузить",
"common.processing": "Обработка",
"common.completed": "Завершено",
"common.failed": "Ошибка",
"common.pending": "В ожидании",
"common.retry": "Повторить",
"common.view": "Просмотр",
"common.copy": "Копировать",
"common.copied": "Скопировано!",
"language.selector": "Язык",
"language.en": "English",
"language.de": "Deutsch",
"language.fr": "Français",
"language.es": "Español",
"language.it": "Italiano",
"language.pt": "Português",
"language.nl": "Nederlands",
"language.pl": "Polski",
"language.zh": "中文",
"language.ru": "Русский",
"language.changed": "Язык изменён на {language}",
"dashboard.title": "Панель управления",
"dashboard.total_files": "Всего файлов",
"dashboard.files_today": "Файлы сегодня",
"dashboard.files_this_month": "Файлы за месяц",
"dashboard.ocr_processed": "OCR обработано",
"dashboard.active_integrations": "Активные интеграции",
"dashboard.storage_targets": "Хранилища",
"dashboard.recent_activity": "Последняя активность",
"dashboard.quick_actions": "Быстрые действия",
"dashboard.welcome": "Добро пожаловать в DocuElevate",
"upload.title": "Загрузить документ",
"upload.drag_drop": "Перетащите файлы сюда или нажмите для выбора",
"upload.select_file": "Выбрать файл",
"upload.uploading": "Загрузка...",
"upload.success": "Файл успешно загружен",
"upload.error": "Ошибка загрузки",
"upload.max_size": "Максимальный размер файла: {size}",
"files.title": "Файлы",
"files.no_files": "Файлы не найдены",
"files.filename": "Имя файла",
"files.document_title": "Название документа",
"files.uploaded": "Загружено",
"files.file_size": "Размер файла",
"files.ocr_status": "Статус OCR",
"files.tags": "Теги",
"search.title": "Поиск документов",
"search.placeholder": "Поиск по имени, содержимому, тегам...",
"search.no_results": "Результаты не найдены",
"search.results_count": "Найдено результатов: {count}",
"settings.title": "Настройки",
"settings.save_success": "Настройка сохранена",
"settings.save_error": "Не удалось сохранить настройку",
"settings.reset_confirm": "Вы уверены, что хотите сбросить эту настройку?",
"integrations.title": "Интеграции",
"integrations.connect": "Подключить",
"integrations.disconnect": "Отключить",
"integrations.connected": "Подключено",
"integrations.not_connected": "Не подключено",
"integrations.configure": "Настроить",
"pipelines.title": "Конвейеры обработки",
"pipelines.create": "Создать конвейер",
"pipelines.edit": "Редактировать конвейер",
"help.title": "Центр помощи",
"help.getting_started": "Начало работы",
"help.faq": "Часто задаваемые вопросы",
"help.documentation": "Документация",
"help.support": "Поддержка",
"error.not_found": "Страница не найдена",
"error.not_found_message": "Запрашиваемая страница не существует.",
"error.server_error": "Внутренняя ошибка сервера",
"error.server_error_message": "Что-то пошло не так. Пожалуйста, попробуйте позже.",
"error.unauthorized": "Не авторизован",
"error.unauthorized_message": "Для доступа к этой странице необходимо войти в систему.",
"error.forbidden": "Доступ запрещён",
"error.forbidden_message": "У вас нет прав для доступа к этой странице.",
"notifications.title": "Уведомления",
"notifications.mark_read": "Отметить как прочитанное",
"notifications.mark_all_read": "Отметить все как прочитанные",
"notifications.no_notifications": "Нет уведомлений",
"notifications.unread_count": "{count} непрочитанных уведомлений"
}