feat(lang): add support for russian languge

pull/228/head
sct 4 years ago
parent 6c7f1cad8b
commit 8d8e750982

@ -9,7 +9,7 @@
"build": "yarn build:next && yarn build:server",
"lint": "eslint \"./server/**/*.{ts,tsx}\" \"./src/**/*.{ts,tsx}\"",
"start": "NODE_ENV=production node dist/index.js",
"i18n:extract": "extract-messages -l=en,ja,fr,nb_NO,de -o src/i18n/locale -d en --flat true --overwriteDefault false './src/**/!(*.test).{ts,tsx}'",
"i18n:extract": "extract-messages -l=en,ja,fr,nb_NO,de,ru -o src/i18n/locale -d en --flat true --overwriteDefault false './src/**/!(*.test).{ts,tsx}'",
"migration:generate": "ts-node --project server/tsconfig.json ./node_modules/.bin/typeorm migration:generate",
"migration:run": "ts-node --project server/tsconfig.json ./node_modules/.bin/typeorm migration:run",
"format": "prettier --write ."

@ -37,6 +37,10 @@ const availableLanguages: AvailableLanguageObject = {
code: 'de',
display: 'German',
},
ru: {
code: 'ru',
display: 'Russian',
},
};
const LanguagePicker: React.FC = () => {
@ -69,10 +73,10 @@ const LanguagePicker: React.FC = () => {
</div>
<Transition
show={isDropdownOpen}
enter="transition ease-out duration-100"
enter="transition ease-out duration-100 opacity-0"
enterFrom="transform opacity-0 scale-95"
enterTo="transform opacity-100 scale-100"
leave="transition ease-in duration-75"
leave="transition ease-in duration-75 opacity-100"
leaveFrom="transform opacity-100 scale-100"
leaveTo="transform opacity-0 scale-95"
>

@ -1,6 +1,6 @@
import React, { ReactNode } from 'react';
export type AvailableLocales = 'en' | 'ja' | 'fr' | 'nb-NO' | 'de';
export type AvailableLocales = 'en' | 'ja' | 'fr' | 'nb-NO' | 'de' | 'ru';
interface LanguageContextProps {
locale: AvailableLocales;

@ -19,7 +19,7 @@ const useClickOutside = (
callback(e);
}
};
document.body.addEventListener('click', handleBodyClick);
document.body.addEventListener('click', handleBodyClick, { capture: true });
return () => {
document.body.removeEventListener('click', handleBodyClick);

@ -1,83 +1,303 @@
{
"components.Settings.SonarrModal.apiKey": "Ключ API",
"components.Settings.SonarrModal.add": "Добавить сервер",
"components.Settings.RadarrModal.validationRootFolderRequired": "Вы должны выбрать корневую папку",
"components.Settings.RadarrModal.validationProfileRequired": "Вы должны выбрать профиль",
"components.Settings.RadarrModal.testing": "Тестирование...",
"components.Settings.RadarrModal.test": "Тест",
"components.Settings.RadarrModal.ssl": "SSL",
"components.Settings.RadarrModal.servername": "Название сервера",
"components.Settings.RadarrModal.selectRootFolder": "Выберите корневую папку",
"components.Settings.RadarrModal.saving": "Сохранение...",
"components.Settings.RadarrModal.save": "Сохранить изменения",
"components.Settings.RadarrModal.rootfolder": "Корневая папка",
"components.Settings.RadarrModal.port": "Порт",
"components.Settings.RadarrModal.hostname": "Имя хоста",
"components.Settings.RadarrModal.defaultserver": "Сервер по умолчанию",
"components.Settings.RadarrModal.apiKey": "Ключ API",
"components.Settings.RadarrModal.add": "Добавить сервер",
"components.Settings.Notifications.saving": "Сохранение...",
"components.Settings.Notifications.save": "Сохранить изменения",
"components.Settings.Notifications.enableSsl": "Включить SSL",
"components.Settings.Notifications.agentenabled": "Агент включен",
"components.Search.searchresults": "Результаты поиска",
"components.RequestModal.selectseason": "Выберите сезон(ы)",
"components.RequestModal.seasonnumber": "Сезон {number}",
"components.RequestModal.season": "Сезон",
"components.RequestModal.requesttitle": "Запрос {title}",
"components.RequestModal.request": "Запрос",
"components.RequestModal.extras": "Дополнительно",
"components.RequestModal.close": "Закрыть",
"components.TvDetails.cancelrequest": "Отменить запрос",
"components.Discover.discovermovies": "Популярные фильмы",
"components.Discover.discovertv": "Популярные серии",
"components.Discover.nopending": "",
"components.Discover.popularmovies": "Популярные фильмы",
"components.Discover.populartv": "Популярные серии",
"components.Discover.recentlyAdded": "Недавно добавленные",
"components.Discover.recentrequests": "Последние запросы",
"components.Discover.trending": "Тренды",
"components.Discover.upcoming": "Предстоящие фильмы",
"components.Discover.upcomingmovies": "Предстоящие фильмы",
"components.Layout.LanguagePicker.changelanguage": "Изменить язык",
"components.Layout.SearchInput.searchPlaceholder": "Поиск фильмов и сериалов",
"components.Layout.Sidebar.dashboard": "",
"components.Layout.Sidebar.requests": "Запросы",
"components.Layout.Sidebar.settings": "Настройки",
"components.Layout.Sidebar.users": "Пользователи",
"components.Layout.UserDropdown.signout": "Выход",
"components.Layout.alphawarning": "",
"components.Login.signinplex": "Войдите, чтобы продолжить",
"components.MovieDetails.approve": "Одобрить",
"components.MovieDetails.available": "Доступно",
"components.MovieDetails.budget": "Бюджет",
"components.MovieDetails.cancelrequest": "Отменить запрос",
"components.MovieDetails.cast": "В ролях",
"components.MovieDetails.decline": "",
"components.MovieDetails.manageModalClearMedia": "Очистить все медиаданные",
"components.MovieDetails.manageModalClearMediaWarning": "",
"components.MovieDetails.manageModalNoRequests": "Нет запросов",
"components.MovieDetails.manageModalRequests": "Запросы",
"components.MovieDetails.manageModalTitle": "",
"components.MovieDetails.originallanguage": "Оригинальный язык",
"components.MovieDetails.overview": "Обзор",
"components.MovieDetails.overviewunavailable": "",
"components.MovieDetails.pending": "В ожидании",
"components.MovieDetails.recommendations": "Рекомендации",
"components.MovieDetails.recommendationssubtext": "",
"components.MovieDetails.releasedate": "Дата выпуска",
"components.MovieDetails.request": "Запрос",
"components.MovieDetails.revenue": "Доход",
"components.MovieDetails.runtime": "{minutes} минут",
"components.MovieDetails.similar": "",
"components.MovieDetails.similarsubtext": "",
"components.MovieDetails.status": "Статус",
"components.MovieDetails.unavailable": "Недоступен",
"components.MovieDetails.userrating": "Пользовательский рейтинг",
"components.MovieDetails.viewrequest": "Просмотр запроса",
"components.PlexLoginButton.loading": "Загрузка...",
"components.PlexLoginButton.loggingin": "",
"components.PlexLoginButton.loginwithplex": "Войти через Plex",
"components.RequestBlock.seasons": "Сезонов",
"components.RequestCard.all": "",
"components.RequestCard.requestedby": "По запросу {username}",
"components.RequestCard.seasons": "Сезонов",
"components.RequestList.RequestItem.notavailable": "",
"components.RequestList.RequestItem.requestedby": "По запросу {username}",
"components.RequestList.RequestItem.seasons": "Сезонов",
"components.RequestList.mediaInfo": "",
"components.RequestList.modifiedBy": "Автор последнего изменения",
"components.RequestList.next": "Следующий",
"components.RequestList.previous": "Предыдущий",
"components.RequestList.requestedAt": "",
"components.RequestList.requests": "Запросы",
"components.RequestList.showingresults": "",
"components.RequestList.status": "Статус",
"components.RequestModal.cancel": "Отменить запрос",
"components.RequestModal.cancelling": "",
"components.RequestModal.cancelrequest": "",
"components.RequestModal.close": "Закрыть",
"components.RequestModal.extras": "Дополнительно",
"components.RequestModal.notrequested": "",
"components.RequestModal.numberofepisodes": "",
"components.RequestModal.pendingrequest": "",
"components.RequestModal.request": "Запрос",
"components.RequestModal.requestCancel": "",
"components.RequestModal.requestSuccess": "",
"components.RequestModal.requestadmin": "",
"components.RequestModal.requestfrom": "",
"components.RequestModal.requesting": "",
"components.RequestModal.requestseasons": "",
"components.RequestModal.requesttitle": "Запрос {title}",
"components.RequestModal.season": "Сезон",
"components.RequestModal.seasonnumber": "Сезон {number}",
"components.RequestModal.selectseason": "Выберите сезон(ы)",
"components.RequestModal.status": "Статус",
"components.Search.searchresults": "Результаты поиска",
"components.Settings.Notifications.agentenabled": "Агент включен",
"components.Settings.Notifications.authPass": "",
"components.Settings.Notifications.authUser": "",
"components.Settings.Notifications.emailsender": "",
"components.Settings.Notifications.enableSsl": "Включить SSL",
"components.Settings.Notifications.save": "Сохранить изменения",
"components.Settings.Notifications.saving": "Сохранение...",
"components.Settings.Notifications.smtpHost": "",
"components.Settings.Notifications.smtpPort": "",
"components.Settings.Notifications.validationFromRequired": "",
"components.Settings.Notifications.validationSmtpHostRequired": "",
"components.Settings.Notifications.validationSmtpPortRequired": "",
"components.Settings.Notifications.validationWebhookUrlRequired": "",
"components.Settings.Notifications.webhookUrl": "",
"components.Settings.Notifications.webhookUrlPlaceholder": "",
"components.Settings.RadarrModal.add": "Добавить сервер",
"components.Settings.RadarrModal.apiKey": "Ключ API",
"components.Settings.RadarrModal.apiKeyPlaceholder": "",
"components.Settings.RadarrModal.baseUrl": "",
"components.Settings.RadarrModal.baseUrlPlaceholder": "",
"components.Settings.RadarrModal.createradarr": "",
"components.Settings.RadarrModal.defaultserver": "Сервер по умолчанию",
"components.Settings.RadarrModal.editradarr": "",
"components.Settings.RadarrModal.hostname": "Имя хоста",
"components.Settings.RadarrModal.minimumAvailability": "",
"components.Settings.RadarrModal.port": "Порт",
"components.Settings.RadarrModal.qualityprofile": "",
"components.Settings.RadarrModal.rootfolder": "Корневая папка",
"components.Settings.RadarrModal.save": "Сохранить изменения",
"components.Settings.RadarrModal.saving": "Сохранение...",
"components.Settings.RadarrModal.selectMinimumAvailability": "",
"components.Settings.RadarrModal.selectQualityProfile": "",
"components.Settings.RadarrModal.selectRootFolder": "Выберите корневую папку",
"components.Settings.RadarrModal.server4k": "",
"components.Settings.RadarrModal.servername": "Название сервера",
"components.Settings.RadarrModal.servernamePlaceholder": "",
"components.Settings.RadarrModal.ssl": "SSL",
"components.Settings.RadarrModal.test": "Тест",
"components.Settings.RadarrModal.testing": "Тестирование...",
"components.Settings.RadarrModal.toastRadarrTestFailure": "",
"components.Settings.RadarrModal.toastRadarrTestSuccess": "",
"components.Settings.RadarrModal.validationApiKeyRequired": "",
"components.Settings.RadarrModal.validationHostnameRequired": "",
"components.Settings.RadarrModal.validationPortRequired": "",
"components.Settings.RadarrModal.validationProfileRequired": "Вы должны выбрать профиль",
"components.Settings.RadarrModal.validationRootFolderRequired": "Вы должны выбрать корневую папку",
"components.Settings.SonarrModal.add": "Добавить сервер",
"components.Settings.SonarrModal.apiKey": "Ключ API",
"components.Settings.SonarrModal.apiKeyPlaceholder": "",
"components.Settings.SonarrModal.baseUrl": "",
"components.Settings.SonarrModal.baseUrlPlaceholder": "",
"components.Settings.SonarrModal.createsonarr": "",
"components.Settings.SonarrModal.defaultserver": "",
"components.Settings.SonarrModal.editsonarr": "",
"components.Settings.SonarrModal.hostname": "",
"components.Settings.SonarrModal.port": "",
"components.Settings.SonarrModal.qualityprofile": "",
"components.Settings.SonarrModal.rootfolder": "",
"components.Settings.SonarrModal.save": "",
"components.Settings.SonarrModal.saving": "",
"components.Settings.SonarrModal.seasonfolders": "",
"components.Settings.SonarrModal.selectQualityProfile": "",
"components.Settings.SonarrModal.selectRootFolder": "",
"components.Settings.SonarrModal.server4k": "",
"components.Settings.SonarrModal.servername": "",
"components.Settings.SonarrModal.servernamePlaceholder": "",
"components.Settings.SonarrModal.ssl": "",
"components.Settings.SonarrModal.test": "",
"components.Settings.SonarrModal.testing": "",
"components.Settings.SonarrModal.toastRadarrTestFailure": "",
"components.Settings.SonarrModal.toastRadarrTestSuccess": "",
"components.Settings.SonarrModal.validationApiKeyRequired": "",
"components.Settings.SonarrModal.validationHostnameRequired": "",
"components.Settings.SonarrModal.validationPortRequired": "",
"components.Settings.SonarrModal.validationProfileRequired": "",
"components.Settings.SonarrModal.validationRootFolderRequired": "",
"components.Settings.activeProfile": "",
"components.Settings.addradarr": "",
"components.Settings.address": "",
"components.Settings.addsonarr": "",
"components.Settings.apikey": "",
"components.Settings.applicationurl": "",
"components.Settings.cancelscan": "",
"components.Settings.copied": "",
"components.Settings.currentlibrary": "",
"components.Settings.default": "",
"components.Settings.default4k": "",
"components.Settings.delete": "",
"components.Settings.deleteserverconfirm": "",
"components.Settings.edit": "",
"components.Settings.generalsettings": "",
"components.Settings.generalsettingsDescription": "",
"components.Settings.hostname": "",
"components.Settings.jobname": "",
"components.Settings.librariesRemaining": "",
"components.Settings.manualscan": "",
"components.Settings.manualscanDescription": "",
"components.Settings.menuAbout": "",
"components.Settings.menuGeneralSettings": "",
"components.Settings.menuJobs": "",
"components.Settings.menuLogs": "",
"components.Settings.menuNotifications": "",
"components.Settings.menuPlexSettings": "",
"components.Settings.menuServices": "",
"components.Settings.nextexecution": "",
"components.Settings.notificationsettings": "",
"components.Settings.notificationsettingsDescription": "",
"components.Settings.notrunning": "",
"components.Settings.plexlibraries": "",
"components.Settings.plexlibrariesDescription": "",
"components.Settings.plexsettings": "",
"components.Settings.plexsettingsDescription": "",
"components.Settings.port": "",
"components.Settings.radarrSettingsDescription": "",
"components.Settings.radarrsettings": "",
"components.Settings.runnow": "",
"components.Settings.save": "",
"components.Settings.saving": "",
"components.Settings.servername": "",
"components.Settings.servernamePlaceholder": "",
"components.Settings.sonarrSettingsDescription": "",
"components.Settings.sonarrsettings": "",
"components.Settings.ssl": "",
"components.Settings.startscan": "",
"components.Settings.sync": "",
"components.Settings.syncing": "",
"components.Setup.configureplex": "",
"components.Setup.configureservices": "",
"components.Setup.continue": "",
"components.Setup.finish": "",
"components.Setup.finishing": "",
"components.Setup.loginwithplex": "",
"components.Setup.signinMessage": "",
"components.Setup.welcome": "",
"components.Slider.noresults": "",
"components.TitleCard.movie": "",
"components.TitleCard.tvshow": "",
"components.TvDetails.approve": "",
"components.TvDetails.approverequests": "",
"components.TvDetails.available": "",
"components.TvDetails.cancelrequest": "Отменить запрос",
"components.TvDetails.cast": "",
"components.TvDetails.decline": "",
"components.TvDetails.declinerequests": "",
"components.TvDetails.manageModalClearMedia": "",
"components.TvDetails.manageModalClearMediaWarning": "",
"components.TvDetails.manageModalNoRequests": "",
"components.TvDetails.manageModalRequests": "",
"components.TvDetails.manageModalTitle": "",
"components.TvDetails.originallanguage": "",
"components.TvDetails.overview": "",
"components.TvDetails.overviewunavailable": "",
"components.TvDetails.pending": "",
"components.TvDetails.recommendations": "",
"components.TvDetails.recommendationssubtext": "",
"components.TvDetails.request": "",
"components.TvDetails.requestmore": "",
"components.TvDetails.similar": "",
"components.TvDetails.similarsubtext": "",
"components.TvDetails.status": "Статус",
"components.RequestList.status": "Статус",
"components.RequestList.requests": "Запросы",
"components.RequestList.previous": "Предыдущий",
"components.RequestList.next": "Следующий",
"components.RequestList.modifiedBy": "Автор последнего изменения",
"components.RequestList.RequestItem.seasons": "Сезонов",
"components.RequestList.RequestItem.requestedby": "По запросу {username}",
"components.RequestCard.seasons": "Сезонов",
"components.RequestCard.requestedby": "По запросу {username}",
"components.RequestBlock.seasons": "Сезонов",
"components.PlexLoginButton.loginwithplex": "Войти через Plex",
"components.PlexLoginButton.loading": "Загрузка...",
"components.MovieDetails.viewrequest": "Просмотр запроса",
"components.MovieDetails.userrating": "Пользовательский рейтинг",
"components.MovieDetails.unavailable": "Недоступен",
"components.MovieDetails.status": "Статус",
"components.MovieDetails.runtime": "{minutes} минут",
"components.MovieDetails.revenue": "Доход",
"components.MovieDetails.request": "Запрос",
"components.MovieDetails.releasedate": "Дата выпуска",
"components.MovieDetails.recommendations": "Рекомендации",
"components.MovieDetails.pending": "В ожидании",
"components.MovieDetails.overview": "Обзор",
"components.MovieDetails.originallanguage": "Оригинальный язык",
"components.MovieDetails.manageModalRequests": "Запросы",
"components.MovieDetails.manageModalNoRequests": "Нет запросов",
"components.MovieDetails.manageModalClearMedia": "Очистить все медиаданные",
"components.MovieDetails.cast": "В ролях",
"components.MovieDetails.cancelrequest": "Отменить запрос",
"components.MovieDetails.budget": "Бюджет",
"components.MovieDetails.available": "Доступно",
"components.MovieDetails.approve": "Одобрить",
"components.Login.signinplex": "Войдите, чтобы продолжить",
"components.Layout.UserDropdown.signout": "Выход",
"components.Layout.Sidebar.users": "Пользователи",
"components.Layout.Sidebar.settings": "Настройки",
"components.Layout.Sidebar.requests": "Запросы",
"components.Layout.SearchInput.searchPlaceholder": "Поиск фильмов и сериалов",
"components.Layout.LanguagePicker.changelanguage": "Изменить язык",
"components.Discover.upcomingmovies": "Предстоящие фильмы",
"components.Discover.upcoming": "Предстоящие фильмы",
"components.Discover.trending": "Тренды",
"components.Discover.recentrequests": "Последние запросы",
"components.Discover.recentlyAdded": "Недавно добавленные",
"components.Discover.populartv": "Популярные серии",
"components.Discover.popularmovies": "Популярные фильмы",
"components.Discover.discovertv": "Популярные серии",
"components.Discover.discovermovies": "Популярные фильмы"
"components.TvDetails.unavailable": "",
"components.TvDetails.userrating": "",
"components.UserEdit.admin": "",
"components.UserEdit.adminDescription": "",
"components.UserEdit.autoapprove": "",
"components.UserEdit.autoapproveDescription": "",
"components.UserEdit.avatar": "",
"components.UserEdit.edituser": "",
"components.UserEdit.email": "",
"components.UserEdit.managerequests": "",
"components.UserEdit.managerequestsDescription": "",
"components.UserEdit.permissions": "",
"components.UserEdit.request": "",
"components.UserEdit.requestDescription": "",
"components.UserEdit.save": "",
"components.UserEdit.saving": "",
"components.UserEdit.settings": "",
"components.UserEdit.settingsDescription": "",
"components.UserEdit.userfail": "",
"components.UserEdit.username": "",
"components.UserEdit.users": "",
"components.UserEdit.usersDescription": "",
"components.UserEdit.usersaved": "",
"components.UserEdit.vote": "",
"components.UserEdit.voteDescription": "",
"components.UserList.admin": "",
"components.UserList.created": "",
"components.UserList.delete": "",
"components.UserList.edit": "",
"components.UserList.lastupdated": "",
"components.UserList.plexuser": "",
"components.UserList.role": "",
"components.UserList.totalrequests": "",
"components.UserList.user": "",
"components.UserList.userlist": "",
"components.UserList.username": "",
"components.UserList.usertype": "",
"i18n.approve": "",
"i18n.approved": "",
"i18n.available": "",
"i18n.cancel": "",
"i18n.decline": "",
"i18n.declined": "",
"i18n.delete": "",
"i18n.movies": "",
"i18n.partiallyavailable": "",
"i18n.pending": "",
"i18n.processing": "",
"i18n.tvshows": "",
"i18n.unavailable": "",
"pages.internalServerError": "",
"pages.oops": "",
"pages.pageNotFound": "",
"pages.returnHome": "",
"pages.serviceUnavailable": "",
"pages.somethingWentWrong": ""
}

@ -24,6 +24,8 @@ const loadLocaleData = (locale: string): Promise<any> => {
return import('../i18n/locale/nb_NO.json');
case 'de':
return import('../i18n/locale/de.json');
case 'ru':
return import('../i18n/locale/ru.json');
default:
return import('../i18n/locale/en.json');
}

Loading…
Cancel
Save