gsd 8 months ago
parent
commit
4fb11d9dba
  1. 26
      Dockerfile.web
  2. 71
      packages/web/public/i18n/locales/ru-RU/channels.json
  3. 51
      packages/web/public/i18n/locales/ru-RU/commandPalette.json
  4. 123
      packages/web/public/i18n/locales/ru-RU/common.json
  5. 12
      packages/web/public/i18n/locales/ru-RU/dashboard.json
  6. 428
      packages/web/public/i18n/locales/ru-RU/deviceConfig.json
  7. 221
      packages/web/public/i18n/locales/ru-RU/dialog.json
  8. 38
      packages/web/public/i18n/locales/ru-RU/map.json
  9. 39
      packages/web/public/i18n/locales/ru-RU/messages.json
  10. 448
      packages/web/public/i18n/locales/ru-RU/moduleConfig.json
  11. 59
      packages/web/public/i18n/locales/ru-RU/nodes.json
  12. 221
      packages/web/public/i18n/locales/ru-RU/ui.json
  13. 2
      packages/web/src/i18n-config.ts

26
Dockerfile.web

@ -0,0 +1,26 @@
FROM node:20-slim AS base
ENV PNPM_HOME="/pnpm"
ENV PATH="$PNPM_HOME:$PATH"
RUN corepack enable
FROM base AS prod
WORKDIR /app
COPY pnpm-lock.yaml /app
RUN pnpm fetch --prod
WORKDIR /app/packages/web
COPY . /app
RUN pnpm build
####################################
FROM nginx:1.29.1-alpine-slim as web
RUN rm -r /usr/share/nginx/html \
&& mkdir -p /usr/share/nginx/html \
&& mkdir -p /etc/nginx/conf.d
WORKDIR /usr/share/nginx/html
COPY --from=prod /app/packages/web/dist ./
#ADD ./packages/web/dist .
COPY --from=prod /app/packages/web/infra/default.conf /etc/nginx/conf.d/default.conf
EXPOSE 8080
CMD ["nginx", "-g", "daemon off;"]

71
packages/web/public/i18n/locales/ru-RU/channels.json

@ -0,0 +1,71 @@
{
"page": {
"sectionLabel": "Каналы",
"channelName": "Канал: {{channelName}}",
"broadcastLabel": "Основной",
"channelIndex": "Кан {{index}}",
"import": "Импорт",
"export": "Экспорт"
},
"validation": {
"pskInvalid": "Пожалуйста, введите корректный {{bits}}-битный PSK."
},
"settings": {
"label": "Настройки канала",
"description": "Шифрование, MQTT и прочие настройки"
},
"role": {
"label": "Роль",
"description": "Телеметрия устройства отправляется через ОСНОВНОЙ канал. Разрешён только один ОСНОВНОЙ канал",
"options": {
"primary": "ОСНОВНОЙ",
"disabled": "ОТКЛЮЧЁН",
"secondary": "ВТОРИЧНЫЙ"
}
},
"psk": {
"label": "Предварительный общий ключ (PSK)",
"description": "Поддерживаемые длины PSK: 256-бит, 128-бит, 8-бит, Пустой (0-бит)",
"generate": "Сгенерировать"
},
"name": {
"label": "Название",
"description": "Уникальное имя канала <12 байт, оставьте пустым для значения по умолчанию"
},
"uplinkEnabled": {
"label": "Восходящая связь включена",
"description": "Отправлять сообщения из локальной сети в MQTT"
},
"downlinkEnabled": {
"label": "Нисходящая связь включена",
"description": "Отправлять сообщения из MQTT в локальную сеть"
},
"positionPrecision": {
"label": "Локация",
"description": "Точность передаваемой локации в канале. Можно отключить.",
"options": {
"none": "Не передавать локацию",
"precise": "Точная локация",
"metric_km23": "В радиусе 23 километров",
"metric_km12": "В радиусе 12 километров",
"metric_km5_8": "В радиусе 5,8 километров",
"metric_km2_9": "В радиусе 2,9 километров",
"metric_km1_5": "В радиусе 1,5 километров",
"metric_m700": "В радиусе 700 метров",
"metric_m350": "В радиусе 350 метров",
"metric_m200": "В радиусе 200 метров",
"metric_m90": "В радиусе 90 метров",
"metric_m50": "В радиусе 50 метров",
"imperial_mi15": "В радиусе 15 миль",
"imperial_mi7_3": "В радиусе 7,3 миль",
"imperial_mi3_6": "В радиусе 3,6 миль",
"imperial_mi1_8": "В радиусе 1,8 миль",
"imperial_mi0_9": "В радиусе 0,9 миль",
"imperial_mi0_5": "В радиусе 0,5 миль",
"imperial_mi0_2": "В радиусе 0,2 миль",
"imperial_ft600": "В радиусе 600 футов",
"imperial_ft300": "В радиусе 300 футов",
"imperial_ft150": "В радиусе 150 футов"
}
}
}

51
packages/web/public/i18n/locales/ru-RU/commandPalette.json

@ -0,0 +1,51 @@
{
"emptyState": "Ничего не найдено.",
"page": {
"title": "Меню команд"
},
"pinGroup": {
"label": "Закрепить группу команд"
},
"unpinGroup": {
"label": "Открепить группу команд"
},
"goto": {
"label": "Перейти",
"command": {
"messages": "Сообщения",
"map": "Карта",
"config": "Настройки",
"nodes": "Узлы"
}
},
"manage": {
"label": "Управление",
"command": {
"switchNode": "Сменить узел",
"connectNewNode": "Подключить новый узел"
}
},
"contextual": {
"label": "Контекстные",
"command": {
"qrCode": "QR-код",
"qrGenerator": "Генератор",
"qrImport": "Импорт",
"scheduleShutdown": "Запланировать выключение",
"scheduleReboot": "Перезагрузить устройство",
"resetNodeDb": "Сбросить базу узлов",
"dfuMode": "Режим DFU",
"factoryResetDevice": "Сброс устройства к заводским",
"factoryResetConfig": "Сброс конфигурации к заводским",
"disconnect": "Отключиться"
}
},
"debug": {
"label": "Отладка",
"command": {
"reconfigure": "Переконфигурировать",
"clearAllStoredMessages": "Очистить все сохранённые сообщения",
"clearAllStores": "Очистить всё локальное хранилище"
}
}
}

123
packages/web/public/i18n/locales/ru-RU/common.json

@ -0,0 +1,123 @@
{
"button": {
"apply": "Применить",
"backupKey": "Сохранить ключ",
"cancel": "Отмена",
"clearMessages": "Очистить сообщения",
"close": "Закрыть",
"confirm": "Подтвердить",
"delete": "Удалить",
"dismiss": "Отклонить",
"download": "Скачать",
"export": "Экспортировать",
"generate": "Сгенерировать",
"regenerate": "Перегенерировать",
"import": "Импортировать",
"message": "Сообщение",
"now": "Сейчас",
"ok": "ОК",
"print": "Печать",
"remove": "Удалить",
"requestNewKeys": "Запросить новые ключи",
"requestPosition": "Запросить позицию",
"reset": "Сбросить",
"save": "Сохранить",
"scanQr": "Сканировать QR-код",
"traceRoute": "Трассировка маршрута",
"submit": "Отправить"
},
"app": {
"title": "Meshtastic",
"fullTitle": "Meshtastic Веб-клиент"
},
"loading": "Загрузка...",
"unit": {
"cps": "симв/с",
"dbm": "дБм",
"hertz": "Гц",
"hop": {
"one": "Передача",
"plural": "Передачи"
},
"hopsAway": {
"one": "{{count}} передача",
"plural": "{{count}} передач",
"unknown": "Неизвестное количество передач"
},
"megahertz": "МГц",
"raw": "исх.",
"meter": { "one": "Метр", "plural": "Метра", "suffix": "м" },
"kilometer": { "one": "Километр", "plural": "Километров", "suffix": "км" },
"minute": { "one": "Минута", "plural": "Минут" },
"hour": { "one": "Час", "plural": "Часов" },
"millisecond": {
"one": "Миллисекунда",
"plural": "Миллисекунд",
"suffix": "мс"
},
"second": { "one": "Секунда", "plural": "Секунд" },
"day": {
"one": "День",
"plural": "Дней",
"today": "Сегодня",
"yesterday": "Вчера"
},
"month": { "one": "Месяц", "plural": "Месяцев" },
"year": { "one": "Год", "plural": "Лет" },
"snr": "ОСШ",
"volt": { "one": "Вольт", "plural": "Вольт", "suffix": "В" },
"record": { "one": "Запись", "plural": "Записи" },
"degree": { "one": "Градус", "plural": "Градусов", "suffix": "°" }
},
"security": {
"0bit": "Пусто",
"8bit": "8 бит",
"128bit": "128 бит",
"256bit": "256 бит"
},
"unknown": {
"longName": "Неизвестно",
"shortName": "НЕИЗВ",
"notAvailable": "Н/Д",
"num": "??"
},
"nodeUnknownPrefix": "!",
"unset": "НЕ ЗАДАНО",
"fallbackName": "Meshtastic {{last4}}",
"node": "Узел",
"formValidation": {
"unsavedChanges": "Несохранённые изменения",
"tooBig": {
"string": "Слишком длинное, ожидалось не более {{maximum}} символов.",
"number": "Слишком большое, ожидалось число не более {{maximum}}.",
"bytes": "Слишком большой размер, ожидалось не более {{params.maximum}} байт."
},
"tooSmall": {
"string": "Слишком короткое, ожидалось не менее {{minimum}} символов.",
"number": "Слишком маленькое, ожидалось число не менее {{minimum}}."
},
"invalidFormat": {
"ipv4": "Неверный формат, ожидался IPv4-адрес.",
"key": "Неверный формат, ожидался ключ в формате Base64 (PSK)."
},
"invalidType": {
"number": "Неверный тип, ожидалось число."
},
"pskLength": {
"0bit": "Ключ должен быть пустым.",
"8bit": "Ключ должен быть 8-битным предварительно разделённым ключом (PSK).",
"128bit": "Ключ должен быть 128-битным предварительно разделённым ключом (PSK).",
"256bit": "Ключ должен быть 256-битным предварительно разделённым ключом (PSK)."
},
"required": {
"generic": "Это поле обязательно для заполнения.",
"managed": "Требуется хотя бы один административный ключ, если узел управляемый.",
"key": "Ключ обязателен."
},
"invalidOverrideFreq": {
"number": "Неверный формат, ожидалось значение в диапазоне 410–930 МГц или 0 (по умолчанию)."
}
},
"yes": "Да",
"no": "Нет"
}

12
packages/web/public/i18n/locales/ru-RU/dashboard.json

@ -0,0 +1,12 @@
{
"dashboard": {
"title": "Подключённые устройства",
"description": "Управление вашими подключёнными устройствами Meshtastic.",
"connectionType_ble": "BLE",
"connectionType_serial": "Последовательный порт",
"connectionType_network": "Сеть",
"noDevicesTitle": "Нет подключённых устройств",
"noDevicesDescription": "Подключите новое устройство, чтобы начать.",
"button_newConnection": "Новое подключение"
}
}

428
packages/web/public/i18n/locales/ru-RU/deviceConfig.json

@ -0,0 +1,428 @@
{
"page": {
"title": "Конфигурация",
"tabBluetooth": "Bluetooth",
"tabDevice": "Устройство",
"tabDisplay": "Дисплей",
"tabLora": "LoRa",
"tabNetwork": "Сеть",
"tabPosition": "Позиция",
"tabPower": "Питание",
"tabSecurity": "Безопасность"
},
"sidebar": {
"label": "Модули"
},
"device": {
"title": "Настройки устройства",
"description": "Параметры устройства",
"buttonPin": {
"description": "Переопределение контакта кнопки",
"label": "Контакт кнопки"
},
"buzzerPin": {
"description": "Переопределение контакта зуммера",
"label": "Контакт зуммера"
},
"disableTripleClick": {
"description": "Отключить тройное нажатие",
"label": "Отключить тройное нажатие"
},
"doubleTapAsButtonPress": {
"description": "Рассматривать двойное касание как нажатие кнопки",
"label": "Двойное касание как нажатие"
},
"ledHeartbeatDisabled": {
"description": "Отключить мигание светодиода по умолчанию",
"label": "Отключить мигание светодиода"
},
"nodeInfoBroadcastInterval": {
"description": "Как часто транслировать информацию об узле",
"label": "Интервал трансляции информации об узле"
},
"posixTimezone": {
"description": "Строка временной зоны POSIX для устройства",
"label": "Временная зона POSIX"
},
"rebroadcastMode": {
"description": "Как обрабатывать ретрансляцию",
"label": "Режим ретрансляции"
},
"role": {
"description": "Роль устройства в сети",
"label": "Роль"
}
},
"bluetooth": {
"title": "Настройки Bluetooth",
"description": "Параметры модуля Bluetooth",
"note": "Примечание: Некоторые устройства (ESP32) не могут использовать Bluetooth и Wi-Fi одновременно.",
"enabled": {
"description": "Включить или отключить Bluetooth",
"label": "Включено"
},
"pairingMode": {
"description": "Поведение при выборе PIN-кода.",
"label": "Режим сопряжения"
},
"pin": {
"description": "PIN-код для сопряжения",
"label": "PIN-код"
}
},
"display": {
"description": "Параметры дисплея устройства",
"title": "Настройки дисплея",
"headingBold": {
"description": "Выделение текста заголовка жирным",
"label": "Жирный заголовок"
},
"carouselDelay": {
"description": "Скорость переключения между окнами",
"label": "Задержка карусели"
},
"compassNorthTop": {
"description": "Фиксировать север вверху компаса",
"label": "Север вверху компаса"
},
"displayMode": {
"description": "Вариант компоновки экрана",
"label": "Режим отображения"
},
"displayUnits": {
"description": "Отображение метрических или имперских единиц",
"label": "Единицы измерения"
},
"flipScreen": {
"description": "Повернуть экран на 180 градусов",
"label": "Перевернуть экран"
},
"gpsDisplayUnits": {
"description": "Формат отображения координат",
"label": "Единицы отображения GPS"
},
"oledType": {
"description": "Тип OLED-экрана, подключённого к устройству",
"label": "Тип OLED"
},
"screenTimeout": {
"description": "Выключать дисплей через указанное время",
"label": "Таймаут экрана"
},
"twelveHourClock": {
"description": "Использовать 12-часовой формат времени",
"label": "12-часовой формат"
},
"wakeOnTapOrMotion": {
"description": "Пробуждать устройство по касанию или движению",
"label": "Пробуждение по касанию или движению"
}
},
"lora": {
"title": "Настройки сети LoRa",
"description": "Параметры сети LoRa",
"bandwidth": {
"description": "Полоса пропускания канала в МГц",
"label": "Полоса пропускания"
},
"boostedRxGain": {
"description": "Усиленное усиление приёма",
"label": "Усиленное усиление RX"
},
"codingRate": {
"description": "Знаменатель кодовой скорости",
"label": "Кодовая скорость"
},
"frequencyOffset": {
"description": "Смещение частоты для коррекции ошибок калибровки кварца",
"label": "Смещение частоты"
},
"frequencySlot": {
"description": "Номер частотного канала LoRa",
"label": "Частотный слот"
},
"hopLimit": {
"description": "Максимальное количество переприёмов",
"label": "Лимит переприёмов"
},
"ignoreMqtt": {
"description": "Не передавать MQTT-сообщения по сети",
"label": "Игнорировать MQTT"
},
"modemPreset": {
"description": "Используемый пресет модема",
"label": "Пресет модема"
},
"okToMqtt": {
"description": "Если установлено \"true\", это означает, что пользователь разрешает загрузку пакетов в MQTT. Если \"false\", удалённые узлы не должны передавать пакеты в MQTT",
"label": "Разрешить MQTT"
},
"overrideDutyCycle": {
"description": "Переопределение рабочего цикла",
"label": "Переопределить рабочий цикл"
},
"overrideFrequency": {
"description": "Переопределение частоты",
"label": "Переопределить частоту"
},
"region": {
"description": "Регион для вашего узла",
"label": "Регион"
},
"spreadingFactor": {
"description": "Количество чирпов на символ",
"label": "Коэффициент расширения"
},
"transmitEnabled": {
"description": "Включить/отключить передачу (TX) по радио LoRa",
"label": "Передача включена"
},
"transmitPower": {
"description": "Максимальная мощность передачи",
"label": "Мощность передачи"
},
"usePreset": {
"description": "Использовать один из заранее определённых пресетов модема",
"label": "Использовать пресет"
},
"meshSettings": {
"description": "Параметры сети LoRa",
"label": "Настройки сети"
},
"waveformSettings": {
"description": "Параметры формы сигнала LoRa",
"label": "Настройки формы сигнала"
},
"radioSettings": {
"label": "Настройки радио",
"description": "Параметры радио LoRa"
}
},
"network": {
"title": "Конфигурация Wi-Fi",
"description": "Настройки радиомодуля Wi-Fi",
"note": "Примечание: Некоторые устройства (ESP32) не могут использовать Bluetooth и Wi-Fi одновременно.",
"addressMode": {
"description": "Выбор способа назначения адреса",
"label": "Режим адресации"
},
"dns": {
"description": "DNS-сервер",
"label": "DNS"
},
"ethernetEnabled": {
"description": "Включить или отключить Ethernet-порт",
"label": "Включено"
},
"gateway": {
"description": "Основной шлюз",
"label": "Шлюз"
},
"ip": {
"description": "IP-адрес",
"label": "IP"
},
"psk": {
"description": "Пароль сети",
"label": "Пароль"
},
"ssid": {
"description": "Имя сети",
"label": "SSID"
},
"subnet": {
"description": "Маска подсети",
"label": "Подсеть"
},
"wifiEnabled": {
"description": "Включить или отключить радиомодуль Wi-Fi",
"label": "Включено"
},
"meshViaUdp": {
"label": "Сеть через UDP"
},
"ntpServer": {
"label": "NTP-сервер"
},
"rsyslogServer": {
"label": "Rsyslog-сервер"
},
"ethernetConfigSettings": {
"description": "Настройки Ethernet-порта",
"label": "Конфигурация Ethernet"
},
"ipConfigSettings": {
"description": "Конфигурация IP",
"label": "Конфигурация IP"
},
"ntpConfigSettings": {
"description": "Конфигурация NTP",
"label": "Конфигурация NTP"
},
"rsyslogConfigSettings": {
"description": "Конфигурация Rsyslog",
"label": "Конфигурация Rsyslog"
},
"udpConfigSettings": {
"description": "Конфигурация UDP через сеть",
"label": "Конфигурация UDP"
}
},
"position": {
"title": "Настройки позиции",
"description": "Параметры модуля позиции",
"broadcastInterval": {
"description": "Как часто ваша позиция отправляется по сети",
"label": "Интервал трансляции"
},
"enablePin": {
"description": "Переопределение контакта включения GPS-модуля",
"label": "Контакт включения"
},
"fixedPosition": {
"description": "Не передавать данные GPS, а использовать заданную вручную позицию",
"label": "Фиксированная позиция"
},
"gpsMode": {
"description": "Настройка режима GPS: включён, отключён или отсутствует",
"label": "Режим GPS"
},
"gpsUpdateInterval": {
"description": "Как часто обновлять данные GPS",
"label": "Интервал обновления GPS"
},
"positionFlags": {
"description": "Дополнительные поля для включения в сообщения о позиции. Чем больше полей выбрано, тем больше размер сообщения, что увеличивает время передачи и риск потери пакетов.",
"label": "Флаги позиции"
},
"receivePin": {
"description": "Переопределение контакта RX GPS-модуля",
"label": "Контакт приёма"
},
"smartPositionEnabled": {
"description": "Отправлять позицию только при значительном изменении местоположения",
"label": "Умная позиция"
},
"smartPositionMinDistance": {
"description": "Минимальное расстояние (в метрах), которое должно быть пройдено перед отправкой обновления позиции",
"label": "Минимальное расстояние"
},
"smartPositionMinInterval": {
"description": "Минимальный интервал (в секундах), который должен пройти перед отправкой обновления позиции",
"label": "Минимальный интервал"
},
"transmitPin": {
"description": "Переопределение контакта TX GPS-модуля",
"label": "Контакт передачи"
},
"intervalsSettings": {
"description": "Как часто отправлять обновления позиции",
"label": "Интервалы"
},
"flags": {
"placeholder": "Выберите флаги позиции...",
"altitude": "Высота",
"altitudeGeoidalSeparation": "Разделение высоты по геоиду",
"altitudeMsl": "Высота над уровнем моря",
"dop": "Показатель точности (DOP), по умолчанию PDOP",
"hdopVdop": "Если выбран DOP, использовать значения HDOP/VDOP вместо PDOP",
"numSatellites": "Количество спутников",
"sequenceNumber": "Порядковый номер",
"timestamp": "Временная метка",
"unset": "Сбросить",
"vehicleHeading": "Направление движения",
"vehicleSpeed": "Скорость движения"
}
},
"power": {
"adcMultiplierOverride": {
"description": "Используется для корректировки показаний напряжения батареи",
"label": "Коэффициент пересчёта АЦП"
},
"ina219Address": {
"description": "Адрес монитора батареи INA219",
"label": "Адрес INA219"
},
"lightSleepDuration": {
"description": "Продолжительность лёгкого сна устройства",
"label": "Длительность лёгкого сна"
},
"minimumWakeTime": {
"description": "Минимальное время бодрствования устройства после получения пакета",
"label": "Минимальное время бодрствования"
},
"noConnectionBluetoothDisabled": {
"description": "Если устройство не получает подключение по Bluetooth, модуль BLE будет отключён через указанное время",
"label": "Отключить Bluetooth при отсутствии подключения"
},
"powerSavingEnabled": {
"description": "Выберите, если устройство питается от источника с низким током (например, солнечная батарея), чтобы минимизировать потребление энергии.",
"label": "Включить режим энергосбережения"
},
"shutdownOnBatteryDelay": {
"description": "Автоматическое выключение узла через указанное время при питании от батареи, 0 — без ограничения",
"label": "Задержка выключения на батарее"
},
"superDeepSleepDuration": {
"description": "Продолжительность сверхглубокого сна устройства",
"label": "Длительность сверхглубокого сна"
},
"powerConfigSettings": {
"description": "Параметры модуля питания",
"label": "Конфигурация питания"
},
"sleepSettings": {
"description": "Настройки сна для модуля питания",
"label": "Настройки сна"
}
},
"security": {
"description": "Параметры конфигурации безопасности",
"title": "Настройки безопасности",
"button_backupKey": "Резервное копирование ключа",
"adminChannelEnabled": {
"description": "Разрешить входящее управление устройством через небезопасный устаревший административный канал",
"label": "Разрешить устаревший административный канал"
},
"enableDebugLogApi": {
"description": "Выводить живой отладочный лог через последовательный порт, просматривать и экспортировать логи устройства (без данных о позиции) через Bluetooth",
"label": "Включить API отладочного лога"
},
"managed": {
"description": "Если включено, параметры конфигурации устройства могут изменяться только удалённо узлом Remote Admin через административные сообщения. Не включайте эту опцию, если не настроен хотя бы один подходящий узел Remote Admin и его публичный ключ не сохранён в одном из полей выше.",
"label": "Управляемый режим"
},
"privateKey": {
"description": "Используется для создания общего ключа с удалённым устройством",
"label": "Закрытый ключ"
},
"publicKey": {
"description": "Отправляется другим узлам сети для вычисления общего секретного ключа",
"label": "Открытый ключ"
},
"primaryAdminKey": {
"description": "Основной публичный ключ, авторизованный для отправки административных сообщений на этот узел",
"label": "Основной административный ключ"
},
"secondaryAdminKey": {
"description": "Вторичный публичный ключ, авторизованный для отправки административных сообщений на этот узел",
"label": "Вторичный административный ключ"
},
"serialOutputEnabled": {
"description": "Серийная консоль через Stream API",
"label": "Вывод через последовательный порт"
},
"tertiaryAdminKey": {
"description": "Третичный публичный ключ, авторизованный для отправки административных сообщений на этот узел",
"label": "Третичный административный ключ"
},
"adminSettings": {
"description": "Параметры администратора",
"label": "Настройки администратора"
},
"loggingSettings": {
"description": "Параметры ведения лога",
"label": "Настройки лога"
}
}
}

221
packages/web/public/i18n/locales/ru-RU/dialog.json

@ -0,0 +1,221 @@
{
"deleteMessages": {
"description": "Это действие удалит всю историю сообщений. Отменить это будет невозможно. Вы уверены, что хотите продолжить?",
"title": "Очистить все сообщения"
},
"deviceName": {
"description": "Устройство перезагрузится после сохранения настроек.",
"longName": "Длинное имя",
"shortName": "Короткое имя",
"title": "Изменить имя устройства",
"validation": {
"longNameMax": "Длинное имя не должно превышать 40 символов",
"shortNameMax": "Короткое имя не должно превышать 4 символов",
"longNameMin": "Длинное имя должно содержать хотя бы 1 символ",
"shortNameMin": "Короткое имя должно содержать хотя бы 1 символ"
}
},
"import": {
"description": "Импортировать набор каналов из Meshtastic URL. <br />Допустимые URL Meshtastic начинаются с \"<italic>https://meshtastic.org/e/...</italic>\"",
"error": {
"invalidUrl": "Некорректный Meshtastic URL"
},
"channelPrefix": "Канал ",
"primary": "Основной ",
"doNotImport": "Не импортировать",
"channelName": "Имя",
"channelSlot": "Слот",
"channelSetUrl": "URL набора каналов/QR-кода",
"useLoraConfig": "Импортировать конфигурацию LoRa",
"presetDescription": "Текущая конфигурация LoRa будет заменена.",
"title": "Импорт каналов"
},
"locationResponse": {
"title": "Местоположение: {{identifier}}",
"altitude": "Высота: ",
"coordinates": "Координаты: ",
"noCoordinates": "Координаты отсутствуют"
},
"pkiRegenerateDialog": {
"title": "Перегенерировать предварительно разделённый ключ?",
"description": "Вы уверены, что хотите перегенерировать предварительно разделённый ключ?",
"regenerate": "Перегенерировать"
},
"newDeviceDialog": {
"title": "Подключить новое устройство",
"https": "https",
"http": "http",
"tabHttp": "HTTP",
"tabBluetooth": "Bluetooth",
"tabSerial": "Последовательный порт",
"useHttps": "Использовать HTTPS",
"connecting": "Подключение...",
"connect": "Подключиться",
"connectionFailedAlert": {
"title": "Ошибка подключения",
"descriptionPrefix": "Не удалось подключиться к устройству. ",
"httpsHint": "При использовании HTTPS может потребоваться принять самоподписанный сертификат. ",
"openLinkPrefix": "Пожалуйста, откройте ",
"openLinkSuffix": " в новой вкладке",
"acceptTlsWarningSuffix": ", примите все предупреждения TLS, если они появятся, затем повторите попытку",
"learnMoreLink": "Узнать больше"
},
"httpConnection": {
"label": "IP-адрес/Имя хоста",
"placeholder": "000.000.000.000 / meshtastic.local"
},
"serialConnection": {
"noDevicesPaired": "Ещё нет сопряжённых устройств.",
"newDeviceButton": "Новое устройство",
"deviceIdentifier": "# {{index}} - {{vendorId}} - {{productId}}"
},
"bluetoothConnection": {
"noDevicesPaired": "Ещё нет сопряжённых устройств.",
"newDeviceButton": "Новое устройство",
"connectionFailed": "Ошибка подключения",
"deviceDisconnected": "Устройство отключено",
"unknownDevice": "Неизвестное устройство",
"errorLoadingDevices": "Ошибка загрузки устройств",
"unknownErrorLoadingDevices": "Неизвестная ошибка загрузки устройств"
},
"validation": {
"requiresWebBluetooth": "Этот тип подключения требует <0>Web Bluetooth</0>. Пожалуйста, используйте поддерживаемый браузер, например Chrome или Edge.",
"requiresWebSerial": "Этот тип подключения требует <0>Web Serial</0>. Пожалуйста, используйте поддерживаемый браузер, например Chrome или Edge.",
"requiresSecureContext": "Это приложение требует <0>защищённого контекста</0>. Пожалуйста, подключайтесь по HTTPS или через localhost.",
"additionallyRequiresSecureContext": "Кроме того, требуется <0>защищённый контекст</0>. Пожалуйста, подключайтесь по HTTPS или через localhost."
}
},
"nodeDetails": {
"message": "Сообщение",
"requestPosition": "Запросить местоположение",
"traceRoute": "Трассировка маршрута",
"airTxUtilization": "Использование эфира (TX)",
"allRawMetrics": "Все исходные метрики:",
"batteryLevel": "Уровень заряда батареи",
"channelUtilization": "Использование канала",
"details": "Детали:",
"deviceMetrics": "Метрики устройства:",
"hardware": "Оборудование: ",
"lastHeard": "Последний сигнал: ",
"nodeHexPrefix": "Hex-адрес узла: ",
"nodeNumber": "Номер узла: ",
"position": "Позиция:",
"role": "Роль: ",
"uptime": "Время работы: ",
"voltage": "Напряжение",
"title": "Детали узла для {{identifier}}",
"ignoreNode": "Игнорировать узел",
"removeNode": "Удалить узел",
"unignoreNode": "Перестать игнорировать узел",
"security": "Безопасность:",
"publicKey": "Публичный ключ: ",
"messageable": "Доступен для сообщений: ",
"KeyManuallyVerifiedTrue": "Публичный ключ подтверждён вручную",
"KeyManuallyVerifiedFalse": "Публичный ключ не подтверждён вручную"
},
"pkiBackup": {
"loseKeysWarning": "Если вы потеряете ключи, вам потребуется сбросить устройство.",
"secureBackup": "Важно сделать резервную копию ваших публичных и приватных ключей и хранить её в безопасности!",
"footer": "=== КОНЕЦ КЛЮЧЕЙ ===",
"header": "=== КЛЮЧИ MESHTASTIC ДЛЯ {{longName}} ({{shortName}}) ===",
"privateKey": "Приватный ключ:",
"publicKey": "Публичный ключ:",
"fileName": "meshtastic_keys_{{longName}}_{{shortName}}.txt",
"title": "Резервное копирование ключей"
},
"pkiBackupReminder": {
"description": "Рекомендуем регулярно делать резервную копию ключей. Хотите сделать резервную копию сейчас?",
"title": "Напоминание о резервном копировании",
"remindLaterPrefix": "Напомнить через",
"remindNever": "Больше не напоминать",
"backupNow": "Сделать резервную копию сейчас"
},
"pkiRegenerate": {
"description": "Вы уверены, что хотите перегенерировать пару ключей?",
"title": "Перегенерировать пару ключей"
},
"qr": {
"addChannels": "Добавить каналы",
"replaceChannels": "Заменить каналы",
"description": "Текущая конфигурация LoRa также будет включена.",
"sharableUrl": "Ссылка для совместного доступа",
"title": "Сгенерировать QR-код"
},
"reboot": {
"title": "Перезагрузка устройства",
"description": "Перезагрузить устройство сейчас или запланировать перезагрузку подключённого узла. При желании можно перезагрузиться в режим OTA (по воздуху).",
"ota": "Перезагрузиться в режим OTA",
"enterDelay": "Введите задержку",
"scheduled": "Перезагрузка запланирована",
"schedule": "Запланировать перезагрузку",
"now": "Перезагрузить сейчас",
"cancel": "Отменить запланированную перезагрузку"
},
"refreshKeys": {
"description": {
"acceptNewKeys": "Это удалит узел с устройства и запросит новые ключи.",
"keyMismatchReasonSuffix": ". Это связано с тем, что текущий публичный ключ удалённого узла не совпадает с ранее сохранённым ключом для этого узла.",
"unableToSendDmPrefix": "Ваш узел не может отправить прямое сообщение узлу: "
},
"acceptNewKeys": "Принять новые ключи",
"title": "Несовпадение ключей — {{identifier}}"
},
"removeNode": {
"description": "Вы уверены, что хотите удалить этот узел?",
"title": "Удалить узел?"
},
"shutdown": {
"title": "Запланировать выключение",
"description": "Выключить подключённый узел через X минут."
},
"traceRoute": {
"routeToDestination": "Маршрут до места назначения:",
"routeBack": "Обратный маршрут:"
},
"tracerouteResponse": {
"title": "Трассировка: {{identifier}}"
},
"unsafeRoles": {
"confirmUnderstanding": "Да, я знаю, что делаю",
"conjunction": " и статью в блоге о ",
"postamble": " и понимаю последствия изменения роли.",
"preamble": "Я прочитал ",
"choosingRightDeviceRole": "Выбор правильной роли устройства",
"deviceRoleDocumentation": "Документация по ролям устройств",
"title": "Вы уверены?"
},
"managedMode": {
"confirmUnderstanding": "Да, я знаю, что делаю",
"title": "Вы уверены?",
"description": "Включение управляемого режима блокирует клиентским приложениям (включая веб-клиент) возможность записывать конфигурации в радио. После включения конфигурации радио можно изменять только через сообщения удалённого администратора. Эта настройка не обязательна для удалённого администрирования узлов."
},
"clientNotification": {
"title": "Уведомление клиента",
"TraceRoute can only be sent once every 30 seconds": "TraceRoute можно отправлять не чаще одного раза в 30 секунд",
"Compromised keys were detected and regenerated.": "Обнаружены скомпрометированные ключи и они были перегенерарованы."
},
"resetNodeDb": {
"title": "Сбросить базу данных узлов",
"description": "Это удалит все узлы из базы данных подключённого устройства и очистит всю историю сообщений в клиенте. Это действие нельзя отменить. Вы уверены, что хотите продолжить?",
"confirm": "Сбросить базу данных узлов",
"failedTitle": "Произошла ошибка при сбросе базы данных узлов. Пожалуйста, попробуйте ещё раз."
},
"clearAllStores": {
"title": "Очистить всё локальное хранилище",
"description": "Это удалит все локально сохранённые данные, включая историю сообщений и базы данных узлов для всех ранее подключённых устройств. После этого вам потребуется заново подключиться к узлу. Это действие нельзя отменить. Вы уверены, что хотите продолжить?",
"confirm": "Очистить всё локальное хранилище",
"failedTitle": "Произошла ошибка при очистке локального хранилища. Пожалуйста, попробуйте ещё раз."
},
"factoryResetDevice": {
"title": "Сброс устройства к заводским настройкам",
"description": "Это выполнит сброс подключённого устройства к заводским настройкам, удалив все конфигурации и данные на устройстве, а также все узлы и сообщения, сохранённые в клиенте. Это действие нельзя отменить. Вы уверены, что хотите продолжить?",
"confirm": "Сбросить устройство к заводским настройкам",
"failedTitle": "Произошла ошибка при сбросе устройства. Пожалуйста, попробуйте ещё раз."
},
"factoryResetConfig": {
"title": "Сброс конфигурации к заводским настройкам",
"description": "Это выполнит сброс конфигурации подключённого устройства к заводским настройкам, удалив все конфигурации на устройстве. Это действие нельзя отменить. Вы уверены, что хотите продолжить?",
"confirm": "Сбросить конфигурацию к заводским настройкам",
"failedTitle": "Произошла ошибка при сбросе конфигурации. Пожалуйста, попробуйте ещё раз."
}
}

38
packages/web/public/i18n/locales/ru-RU/map.json

@ -0,0 +1,38 @@
{
"maplibre": {
"GeolocateControl.FindMyLocation": "Найти моё местоположение",
"NavigationControl.ZoomIn": "Увеличить",
"NavigationControl.ZoomOut": "Уменьшить",
"CooperativeGesturesHandler.WindowsHelpText": "Используйте Ctrl + прокрутку для масштабирования карты",
"CooperativeGesturesHandler.MacHelpText": "Используйте ⌘ + прокрутку для масштабирования карты",
"CooperativeGesturesHandler.MobileHelpText": "Используйте два пальца для перемещения по карте"
},
"layerTool": {
"nodeMarkers": "Показать узлы",
"directNeighbors": "Показать прямые соединения",
"remoteNeighbors": "Показать удалённые соединения",
"positionPrecision": "Показать точность позиции",
"traceroutes": "Показать маршруты",
"waypoints": "Показать точки маршрута"
},
"mapMenu": {
"locateAria": "Найти мой узел",
"layersAria": "Изменить стиль карты"
},
"waypointDetail": {
"edit": "Редактировать",
"description": "Описание:",
"createdBy": "Отредактировано:",
"createdDate": "Создано:",
"updated": "Обновлено:",
"expires": "Истекает:",
"distance": "Расстояние:",
"bearing": "Абсолютный азимут:",
"lockedTo": "Заблокировано:",
"latitude": "Широта:",
"longitude": "Долгота:"
},
"myNode": {
"tooltip": "Это устройство"
}
}

39
packages/web/public/i18n/locales/ru-RU/messages.json

@ -0,0 +1,39 @@
{
"page": {
"title": "Сообщения: {{chatName}}",
"placeholder": "Введите сообщение"
},
"emptyState": {
"title": "Выберите чат",
"text": "Сообщений пока нет."
},
"selectChatPrompt": {
"text": "Выберите канал или узел, чтобы начать обмен сообщениями."
},
"sendMessage": {
"placeholder": "Введите ваше сообщение здесь...",
"sendButton": "Отправить"
},
"actionsMenu": {
"addReactionLabel": "Добавить реакцию",
"replyLabel": "Ответить"
},
"deliveryStatus": {
"delivered": {
"label": "Сообщение доставлено",
"displayText": "Доставлено"
},
"failed": {
"label": "Не удалось доставить сообщение",
"displayText": "Доставка не удалась"
},
"unknown": {
"label": "Статус сообщения неизвестен",
"displayText": "Неизвестный статус"
},
"waiting": {
"label": "Отправка сообщения",
"displayText": "Ожидание доставки"
}
}
}

448
packages/web/public/i18n/locales/ru-RU/moduleConfig.json

@ -0,0 +1,448 @@
{
"page": {
"tabAmbientLighting": "Подсветка",
"tabAudio": "Аудио",
"tabCannedMessage": "Шаблоны",
"tabDetectionSensor": "Датчик обнаружения",
"tabExternalNotification": "Внешние уведомления",
"tabMqtt": "MQTT",
"tabNeighborInfo": "Информация о соседах",
"tabPaxcounter": "Счётчик людей",
"tabRangeTest": "Тест дальности",
"tabSerial": "Последовательный порт",
"tabStoreAndForward": "Хранение и пересылка",
"tabTelemetry": "Телеметрия"
},
"ambientLighting": {
"title": "Настройки подсветки",
"description": "Настройки модуля подсветки",
"ledState": {
"label": "Состояние LED",
"description": "Включить или выключить LED"
},
"current": {
"label": "Ток",
"description": "Устанавливает ток для выхода LED. По умолчанию 10"
},
"red": {
"label": "Красный",
"description": "Уровень красного LED. Значения от 0 до 255"
},
"green": {
"label": "Зелёный",
"description": "Уровень зелёного LED. Значения от 0 до 255"
},
"blue": {
"label": "Синий",
"description": "Уровень синего LED. Значения от 0 до 255"
}
},
"audio": {
"title": "Настройки аудио",
"description": "Настройки модуля аудио",
"codec2Enabled": {
"label": "Codec 2 включён",
"description": "Включить кодирование аудио Codec 2"
},
"pttPin": {
"label": "PTT контакт",
"description": "Контакт GPIO для PTT"
},
"bitrate": {
"label": "Битрейт",
"description": "Битрейт для кодирования аудио"
},
"i2sWs": {
"label": "i2S WS",
"description": "Контакт GPIO для i2S WS"
},
"i2sSd": {
"label": "i2S SD",
"description": "Контакт GPIO для i2S SD"
},
"i2sDin": {
"label": "i2S DIN",
"description": "Контакт GPIO для i2S DIN"
},
"i2sSck": {
"label": "i2S SCK",
"description": "Контакт GPIO для i2S SCK"
}
},
"cannedMessage": {
"title": "Настройки шаблонов сообщений",
"description": "Настройки модуля шаблонов сообщений",
"moduleEnabled": {
"label": "Модуль включён",
"description": "Включить шаблоны сообщений"
},
"rotary1Enabled": {
"label": "Энкодер #1 включён",
"description": "Включить поворотный энкодер"
},
"inputbrokerPinA": {
"label": "Контакт энкодера A",
"description": "Значение контакта GPIO (1-39) для порта A энкодера"
},
"inputbrokerPinB": {
"label": "Контакт энкодера B",
"description": "Значение контакта GPIO (1-39) для порта B энкодера"
},
"inputbrokerPinPress": {
"label": "Контакт нажатия энкодера",
"description": "Значение контакта GPIO (1-39) для нажатия энкодера"
},
"inputbrokerEventCw": {
"label": "Событие по часовой",
"description": "Выберите событие."
},
"inputbrokerEventCcw": {
"label": "Событие против часовой",
"description": "Выберите событие."
},
"inputbrokerEventPress": {
"label": "Событие нажатия",
"description": "Выберите событие"
},
"updown1Enabled": {
"label": "Вверх/вниз включено",
"description": "Включить энкодер вверх/вниз"
},
"allowInputSource": {
"label": "Разрешить источник ввода",
"description": "Выберите из: '_any', 'rotEnc1', 'upDownEnc1', 'cardkb'"
},
"sendBell": {
"label": "Отправлять звонок",
"description": "Отправлять символ звонка с каждым сообщением"
}
},
"detectionSensor": {
"title": "Настройки датчика обнаружения",
"description": "Настройки модуля датчика обнаружения",
"enabled": {
"label": "Включено",
"description": "Включить или отключить модуль датчика обнаружения"
},
"minimumBroadcastSecs": {
"label": "Минимальный интервал передачи (сек)",
"description": "Интервал в секундах, как часто отправлять сообщение в сеть при обнаружении изменения состояния"
},
"stateBroadcastSecs": {
"label": "Интервал передачи состояния (сек)",
"description": "Интервал в секундах, как часто отправлять сообщение в сеть с текущим состоянием, независимо от изменений"
},
"sendBell": {
"label": "Отправлять звонок",
"description": "Отправлять ASCII-звонок с сообщением об оповещении"
},
"name": {
"label": "Дружественное имя",
"description": "Используется для форматирования сообщения, отправляемого в сеть, максимум 20 символов"
},
"monitorPin": {
"label": "Контакт мониторинга",
"description": "Контакт GPIO для мониторинга изменений состояния"
},
"detectionTriggerType": {
"label": "Тип триггера обнаружения",
"description": "Тип события триггера, который будет использоваться"
},
"usePullup": {
"label": "Использовать подтяжку",
"description": "Использовать режим INPUT_PULLUP для контакта GPIO"
}
},
"externalNotification": {
"title": "Настройки внешних уведомлений",
"description": "Настройка модуля внешних уведомлений",
"enabled": {
"label": "Модуль включён",
"description": "Включить внешние уведомления"
},
"outputMs": {
"label": "Длительность выхода (мс)",
"description": "Длительность выхода в миллисекундах"
},
"output": {
"label": "Выход",
"description": "Выход"
},
"outputVibra": {
"label": "Вибрационный выход",
"description": "Вибрационный выход"
},
"outputBuzzer": {
"label": "Звуковой выход",
"description": "Звуковой выход"
},
"active": {
"label": "Активен",
"description": "Активен"
},
"alertMessage": {
"label": "Сообщение оповещения",
"description": "Сообщение оповещения"
},
"alertMessageVibra": {
"label": "Вибрационное оповещение",
"description": "Вибрационное оповещение"
},
"alertMessageBuzzer": {
"label": "Звуковое оповещение",
"description": "Звуковое оповещение"
},
"alertBell": {
"label": "Оповещение звонком",
"description": "Следует ли срабатывать оповещение при получении входящего звонка?"
},
"alertBellVibra": {
"label": "Вибрация при звонке",
"description": "Вибрация при звонке"
},
"alertBellBuzzer": {
"label": "Звук при звонке",
"description": "Звук при звонке"
},
"usePwm": {
"label": "Использовать ШИМ",
"description": "Использовать ШИМ"
},
"nagTimeout": {
"label": "Таймаут напоминания",
"description": "Таймаут напоминания"
},
"useI2sAsBuzzer": {
"label": "Использовать I²S как зуммер",
"description": "Назначить контакт I²S как выход зуммера"
}
},
"mqtt": {
"title": "Настройки MQTT",
"description": "Настройки модуля MQTT",
"enabled": {
"label": "Включено",
"description": "Включить или отключить MQTT"
},
"address": {
"label": "Адрес сервера MQTT",
"description": "Адрес сервера MQTT для стандартных/пользовательских серверов"
},
"username": {
"label": "Имя пользователя MQTT",
"description": "Имя пользователя MQTT для стандартных/пользовательских серверов"
},
"password": {
"label": "Пароль MQTT",
"description": "Пароль MQTT для стандартных/пользовательских серверов"
},
"encryptionEnabled": {
"label": "Шифрование включено",
"description": "Включить или отключить шифрование MQTT. Примечание: все сообщения отправляются на брокер MQTT незашифрованными, если эта опция не включена, даже если ваши каналы связи зашифрованы. Это включает данные о местоположении."
},
"jsonEnabled": {
"label": "JSON включён",
"description": "Отправлять/принимать JSON-пакеты по MQTT"
},
"tlsEnabled": {
"label": "TLS включён",
"description": "Включить или отключить TLS"
},
"root": {
"label": "Корневой топик",
"description": "Корневой топик MQTT для стандартных/пользовательских серверов"
},
"proxyToClientEnabled": {
"label": "Прокси MQTT для клиента включено",
"description": "Использует сетевое подключение для проксирования сообщений MQTT клиенту."
},
"mapReportingEnabled": {
"label": "Отправка данных на карту включена",
"description": "Ваш узел будет периодически отправлять незашифрованный пакет отчёта на карту на настроенный сервер MQTT, это включает ID, короткое и длинное имя, приблизительное местоположение, модель оборудования, роль, версию прошивки, регион LoRa, пресет модема и имя основного канала."
},
"mapReportSettings": {
"publishIntervalSecs": {
"label": "Интервал публикации отчёта (сек)",
"description": "Интервал в секундах для публикации отчётов на карте"
},
"positionPrecision": {
"label": "Приблизительное местоположение",
"description": "Разделяемая позиция будет точной в пределах этого расстояния",
"options": {
"metric_km23": "В пределах 23 км",
"metric_km12": "В пределах 12 км",
"metric_km5_8": "В пределах 5,8 км",
"metric_km2_9": "В пределах 2,9 км",
"metric_km1_5": "В пределах 1,5 км",
"metric_m700": "В пределах 700 м",
"metric_m350": "В пределах 350 м",
"metric_m200": "В пределах 200 м",
"metric_m90": "В пределах 90 м",
"metric_m50": "В пределах 50 м",
"imperial_mi15": "В пределах 15 миль",
"imperial_mi7_3": "В пределах 7,3 миль",
"imperial_mi3_6": "В пределах 3,6 миль",
"imperial_mi1_8": "В пределах 1,8 миль",
"imperial_mi0_9": "В пределах 0,9 миль",
"imperial_mi0_5": "В пределах 0,5 миль",
"imperial_mi0_2": "В пределах 0,2 миль",
"imperial_ft600": "В пределах 600 футов",
"imperial_ft300": "В пределах 300 футов",
"imperial_ft150": "В пределах 150 футов"
}
}
}
},
"neighborInfo": {
"title": "Настройки информации о соседах",
"description": "Настройки модуля информации о соседах",
"enabled": {
"label": "Включено",
"description": "Включить или отключить модуль информации о соседах"
},
"updateInterval": {
"label": "Интервал обновления",
"description": "Интервал в секундах, как часто пытаться отправлять информацию о соседах в сеть"
}
},
"paxcounter": {
"title": "Настройки счётчика людей",
"description": "Настройки модуля счётчика людей",
"enabled": {
"label": "Модуль включён",
"description": "Включить счётчик людей"
},
"paxcounterUpdateInterval": {
"label": "Интервал обновления (сек)",
"description": "Как долго ждать между отправкой пакетов счётчика"
},
"wifiThreshold": {
"label": "Порог RSSI Wi-Fi",
"description": "При каком уровне RSSI Wi-Fi счётчик должен увеличиваться. По умолчанию -80."
},
"bleThreshold": {
"label": "Порог RSSI BLE",
"description": "При каком уровне RSSI BLE счётчик должен увеличиваться. По умолчанию -80."
}
},
"rangeTest": {
"title": "Настройки теста дальности",
"description": "Настройки модуля теста дальности",
"enabled": {
"label": "Модуль включён",
"description": "Включить тест дальности"
},
"sender": {
"label": "Интервал сообщений",
"description": "Как долго ждать между отправкой тестовых пакетов"
},
"save": {
"label": "Сохранить CSV в память",
"description": "Только для ESP32"
}
},
"serial": {
"title": "Настройки последовательного порта",
"description": "Настройки модуля последовательного порта",
"enabled": {
"label": "Модуль включён",
"description": "Включить вывод через последовательный порт"
},
"echo": {
"label": "Эхо",
"description": "Все отправленные пакеты будут возвращаться обратно на ваше устройство"
},
"rxd": {
"label": "Контакт приёма",
"description": "Установите контакт GPIO как RXD."
},
"txd": {
"label": "Контакт передачи",
"description": "Установите контакт GPIO как TXD."
},
"baud": {
"label": "Скорость (бод)",
"description": "Скорость передачи данных"
},
"timeout": {
"label": "Таймаут",
"description": "Время ожидания в секундах, после которого пакет считается завершённым"
},
"mode": {
"label": "Режим",
"description": "Выберите режим"
},
"overrideConsoleSerialPort": {
"label": "Переопределить консольный порт",
"description": "Если у вас подключён последовательный порт к консоли, это переопределит его."
}
},
"storeForward": {
"title": "Настройки хранения и пересылки",
"description": "Настройки модуля хранения и пересылки",
"enabled": {
"label": "Модуль включён",
"description": "Включить хранение и пересылку"
},
"heartbeat": {
"label": "Heartbeat включён",
"description": "Включить heartbeat для хранения и пересылки"
},
"records": {
"label": "Количество записей",
"description": "Количество записей для хранения"
},
"historyReturnMax": {
"label": "Максимум возвращаемых записей",
"description": "Максимальное количество возвращаемых записей"
},
"historyReturnWindow": {
"label": "Окно возвращаемых записей",
"description": "Максимальное количество возвращаемых записей"
}
},
"telemetry": {
"title": "Настройки телеметрии",
"description": "Настройки модуля телеметрии",
"deviceUpdateInterval": {
"label": "Интервал обновления устройства",
"description": "Интервал обновления метрик устройства (сек)"
},
"environmentUpdateInterval": {
"label": "Интервал обновления окружающей среды (сек)",
"description": ""
},
"environmentMeasurementEnabled": {
"label": "Модуль включён",
"description": "Включить телеметрию окружающей среды"
},
"environmentScreenEnabled": {
"label": "Отображать на экране",
"description": "Показывать модуль телеметрии на OLED"
},
"environmentDisplayFahrenheit": {
"label": "Отображать в Фаренгейтах",
"description": "Отображать температуру в Фаренгейтах"
},
"airQualityEnabled": {
"label": "Качество воздуха включено",
"description": "Включить телеметрию качества воздуха"
},
"airQualityInterval": {
"label": "Интервал обновления качества воздуха",
"description": "Как часто отправлять данные о качестве воздуха в сеть"
},
"powerMeasurementEnabled": {
"label": "Измерение мощности включено",
"description": "Включить телеметрию измерения мощности"
},
"powerUpdateInterval": {
"label": "Интервал обновления мощности",
"description": "Как часто отправлять данные о мощности в сеть"
},
"powerScreenEnabled": {
"label": "Экран мощности включён",
"description": "Включить экран телеметрии мощности"
}
}
}

59
packages/web/public/i18n/locales/ru-RU/nodes.json

@ -0,0 +1,59 @@
{
"nodeDetail": {
"publicKeyEnabled": {
"label": "Публичный ключ включён"
},
"noPublicKey": {
"label": "Нет публичного ключа"
},
"directMessage": {
"label": "Прямое сообщение {{shortName}}"
},
"favorite": {
"label": "Избранное",
"tooltip": "Добавить или убрать этот узел из избранного"
},
"notFavorite": {
"label": "Не в избранном"
},
"error": {
"label": "Ошибка",
"text": "Произошла ошибка при получении данных об узле. Пожалуйста, попробуйте позже."
},
"status": {
"heard": "Услышан",
"mqtt": "MQTT"
},
"elevation": {
"label": "Высота"
},
"channelUtil": {
"label": "Использование канала"
},
"airtimeUtil": {
"label": "Использование эфирного времени"
}
},
"nodesTable": {
"headings": {
"longName": "Полное имя",
"connection": "Подключение",
"lastHeard": "Последний контакт",
"encryption": "Шифрование",
"model": "Модель",
"macAddress": "MAC-адрес"
},
"connectionStatus": {
"direct": "Прямое",
"away": "недоступен",
"viaMqtt": ", через MQTT"
}
},
"actions": {
"added": "Добавлено",
"removed": "Удалено",
"ignoreNode": "Игнорировать узел",
"unignoreNode": "Перестать игнорировать узел",
"requestPosition": "Запросить позицию"
}
}

221
packages/web/public/i18n/locales/ru-RU/ui.json

@ -0,0 +1,221 @@
{
"navigation": {
"title": "Навигация",
"messages": "Сообщения",
"map": "Карта",
"config": "Настройки",
"channels": "Каналы",
"radioConfig": "Настройки радио",
"moduleConfig": "Настройки модуля",
"channelConfig": "Настройки канала",
"nodes": "Узлы"
},
"app": {
"title": "Meshtastic",
"logo": "Логотип Meshtastic"
},
"sidebar": {
"collapseToggle": {
"button": {
"open": "Открыть боковую панель",
"close": "Закрыть боковую панель"
}
},
"deviceInfo": {
"volts": "{{voltage}} вольт",
"firmware": {
"title": "Прошивка",
"version": "в{{version}}",
"buildDate": "Дата сборки: {{date}}"
},
"deviceName": {
"title": "Имя устройства",
"changeName": "Изменить имя устройства",
"placeholder": "Введите имя устройства"
},
"editDeviceName": "Редактировать имя устройства"
}
},
"batteryStatus": {
"charging": "{{level}}% зарядки",
"pluggedIn": "Подключено к сети",
"title": "Аккумулятор"
},
"search": {
"nodes": "Поиск узлов...",
"channels": "Поиск каналов...",
"commandPalette": "Поиск команд..."
},
"toast": {
"positionRequestSent": { "title": "Запрос позиции отправлен." },
"requestingPosition": { "title": "Запрос позиции, пожалуйста, подождите..." },
"sendingTraceroute": { "title": "Отправка трассировки, пожалуйста, подождите..." },
"tracerouteSent": { "title": "Трассировка отправлена." },
"savedChannel": { "title": "Сохранённый канал: {{channelName}}" },
"messages": {
"pkiEncryption": { "title": "Чат использует PKI-шифрование." },
"pskEncryption": { "title": "Чат использует PSK-шифрование." }
},
"configSaveError": {
"title": "Ошибка сохранения настроек",
"description": "Произошла ошибка при сохранении конфигурации."
},
"validationError": {
"title": "Ошибки в конфигурации",
"description": "Пожалуйста, исправьте ошибки в конфигурации перед сохранением."
},
"saveSuccess": {
"title": "Сохранение настроек",
"description": "Изменение конфигурации {{case}} сохранено."
},
"saveAllSuccess": {
"title": "Сохранено",
"description": "Все изменения конфигурации сохранены."
},
"favoriteNode": {
"title": "{{action}} {{nodeName}} {{direction}} избранное.",
"action": {
"added": "Добавлено",
"removed": "Удалено",
"to": "в",
"from": "из"
}
},
"ignoreNode": {
"title": "{{action}} {{nodeName}} {{direction}} список игнорирования",
"action": {
"added": "Добавлено",
"removed": "Удалено",
"to": "в",
"from": "из"
}
}
},
"notifications": {
"copied": {
"label": "Скопировано!"
},
"copyToClipboard": {
"label": "Скопировать в буфер обмена"
},
"hidePassword": {
"label": "Скрыть пароль"
},
"showPassword": {
"label": "Показать пароль"
},
"deliveryStatus": {
"delivered": "Доставлено",
"failed": "Доставка не удалась",
"waiting": "Ожидание",
"unknown": "Неизвестно"
}
},
"general": {
"label": "Общие"
},
"hardware": {
"label": "Аппаратное обеспечение"
},
"metrics": {
"label": "Метрики"
},
"role": {
"label": "Роль"
},
"filter": {
"label": "Фильтр"
},
"advanced": {
"label": "Дополнительно"
},
"clearInput": {
"label": "Очистить ввод"
},
"resetFilters": {
"label": "Сбросить фильтры"
},
"nodeName": {
"label": "Имя/номер узла",
"placeholder": "Meshtastic 1234"
},
"airtimeUtilization": {
"label": "Использование эфирного времени (%)",
"short": "Исп. эфира (%)"
},
"batteryLevel": {
"label": "Уровень заряда (%)",
"labelText": "Уровень заряда (%): {{value}}"
},
"batteryVoltage": {
"label": "Напряжение аккумулятора (В)",
"title": "Напряжение"
},
"channelUtilization": {
"label": "Использование канала (%)",
"short": "Исп. канала (%)"
},
"hops": {
"direct": "Прямое",
"label": "Количество переходов",
"text": "Количество переходов: {{value}}"
},
"lastHeard": {
"label": "Последний контакт",
"labelText": "Последний контакт: {{value}}",
"nowLabel": "Сейчас"
},
"snr": {
"label": "Отношение сигнал/шум (дБ)"
},
"favorites": {
"label": "Избранное"
},
"hide": {
"label": "Скрыть"
},
"showOnly": {
"label": "Показать только"
},
"viaMqtt": {
"label": "Подключено через MQTT"
},
"hopsUnknown": {
"label": "Неизвестное количество переходов"
},
"showUnheard": {
"label": "Неизвестно время последнего контакта"
},
"language": {
"label": "Язык",
"changeLanguage": "Изменить язык"
},
"theme": {
"dark": "Тёмная",
"light": "Светлая",
"system": "Автоматическая",
"changeTheme": "Изменить цветовую схему"
},
"errorPage": {
"title": "Это немного неловко...",
"description1": "Нам очень жаль, но в веб-клиенте произошла ошибка, из-за которой он завершил работу. <br /> Такого не должно было произойти, и мы усердно работаем над исправлением.",
"description2": "Лучший способ предотвратить повторение этой ошибки — сообщить нам о проблеме.",
"reportInstructions": "Пожалуйста, укажите в отчёте следующую информацию:",
"reportSteps": {
"step1": "Что вы делали, когда произошла ошибка",
"step2": "Что вы ожидали увидеть",
"step3": "Что произошло на самом деле",
"step4": "Любая другая актуальная информация"
},
"reportLink": "Вы можете сообщить о проблеме на нашем <0>GitHub</0>",
"dashboardLink": "Вернуться на <0>главную панель</0>",
"detailsSummary": "Детали ошибки",
"errorMessageLabel": "Сообщение об ошибке:",
"stackTraceLabel": "Трассировка стека:",
"fallbackError": "{{error}}"
},
"footer": {
"text": "Работает на <0>▲ Vercel</0> | Meshtastic® — зарегистрированный товарный знак Meshtastic LLC. | <1>Юридическая информация</1>",
"commitSha": "Коммит SHA: {{sha}}"
}
}

2
packages/web/src/i18n-config.ts

@ -18,6 +18,7 @@ export const supportedLanguages: Lang[] = [
{ code: "en", name: "English", flag: "🇺🇸" },
{ code: "fr", name: "Français", flag: "🇫🇷" },
{ code: "sv", name: "Svenska", flag: "🇸🇪" },
{ code: "ru", name: "Русский", flag: "🇷🇺​​" },
];
export const FALLBACK_LANGUAGE_CODE: LangCode = "en";
@ -45,6 +46,7 @@ i18next
fr: ["fr-FR", FALLBACK_LANGUAGE_CODE],
sv: ["sv-SE", FALLBACK_LANGUAGE_CODE],
de: ["de-DE", FALLBACK_LANGUAGE_CODE],
ru: ["ru-RU", FALLBACK_LANGUAGE_CODE],
},
fallbackNS: ["common", "ui", "dialog"],
debug: import.meta.env.MODE === "development",

Loading…
Cancel
Save