Files
BarevClub/apps/backoffice/src/i18n.tsx
T
zabudko-ruandClaude Opus 5.5 ac786cc5cc Backoffice stage 4: partners (agencies, venues) and sales CRM
- CRM: configurable pipeline (default: New → Contact → Meeting → Negotiation →
  Connected / Lost), drag-and-drop board, lead card with call/meeting/note history,
  photos and files, tasks with Telegram reminders at the due time, map of venues
  (OpenStreetMap via Leaflet), lost reason. Sales reps see only their own leads.
- "Connected" in one click: a venue becomes a club card partner with a one-time
  owner link to the work bot; an agency gets a code and a client link. The sales rep
  is recorded on the partner for the bonus.
- Sales bonus formula in settings (per venue, per agency, % of revenue from the
  rep's agency clients for N months); defaults are 0 until the owner sets them.
- Agencies (superadmin): clients, gift subscriptions, reward by month, payouts,
  client link, edit. Venues: offers by membership level (5 languages), staff,
  card checks, 8-week activity, owner link, map point.
- Schema: SalesStage/SalesLead/SalesActivity/SalesTask; salesId on Agency and
  Partner; lat/lng/phone/note on Partner; agencyId on Payout.
- Tests for stage rules, conversion, task reminders and bonus; dev:crm-demo.

Co-Authored-By: Claude Opus 5.5 (1M context) <noreply@anthropic.com>
2026-10-21 03:02:03 +04:00

2690 lines
136 KiB
TypeScript
Raw Blame History

This file contains ambiguous Unicode characters
This file contains Unicode characters that might be confused with other characters. If you think that this is intentional, you can safely ignore this warning. Use the Escape button to reveal them.
import { createT as createSharedT, formatAmd, formatDateTime, type Locale as SharedLocale } from '@barev/i18n';
import { createContext, useContext, useEffect, useMemo, useState, type ReactNode } from 'react';
/** Языки новой админки */
export const BO_LOCALES = ['ru', 'en', 'hy'] as const;
export type BoLocale = (typeof BO_LOCALES)[number];
export const BO_LOCALE_LABELS: Record<BoLocale, string> = { ru: 'Рус', en: 'Eng', hy: 'Հայ' };
const ru = {
'ui.save': 'Сохранить',
'ui.close': 'Закрыть',
'ui.loading': 'Загружаем…',
'ui.error': 'Не получилось: {msg}',
'ui.retry': 'Повторить',
'ui.copy': 'Скопировать',
'ui.copied': 'Скопировано',
'ui.days': '{n} дн.',
'ui.yes': 'Да',
'ui.no': 'Нет',
'ui.none': '—',
'err.PAYMENTS_NOT_CONFIGURED': 'Платёжная система ещё не подключена — отметьте оплату вручную.',
'err.REFUND_TOO_BIG': 'Сумма возврата больше, чем клиент заплатил.',
'err.ENDS_BEFORE_START': 'Подписка не может закончиться раньше, чем началась.',
'err.CANNOT_DEMOTE_SELF': 'Нельзя отключить себя или снять с себя роль суперадмина.',
'err.ROLE_FORBIDDEN': 'У вашей роли нет доступа к этому действию.',
'err.NO_ROLE': 'У вашего аккаунта нет ролей в новой админке. Попросите суперадмина их выдать.',
'login.coverWord': 'команда',
'login.title': 'Вход для команды',
'login.lead': 'Подтвердите вход в рабочем боте Barev Club. Пароль не нужен.',
'login.open': 'Подтвердить в Telegram',
'login.qr': 'С компьютера удобнее отсканировать код телефоном.',
'login.waiting': 'Ждём подтверждения в Telegram…',
'login.expired': 'Ссылка устарела.',
'login.retry': 'Получить новую ссылку',
'login.dev': 'Войти локально',
'login.devHint': 'Только на этом компьютере — на сервере этого блока нет.',
'login.noTelegram': 'Нет доступа? Попросите суперадмина добавить вас в команду и прислать ссылку для привязки Telegram.',
'nav.dashboard': 'Дашборд',
'nav.clients': 'Клиенты',
'nav.chats': 'Чаты',
'nav.orders': 'Заказы',
'nav.providers': 'Исполнители',
'nav.agencies': 'Агентства',
'nav.venues': 'Заведения',
'nav.crm': 'CRM',
'nav.products': 'Продукты',
'nav.journal': 'Журнал',
'nav.team': 'Команда',
'nav.more': 'Ещё',
'nav.soon': 'этап {n}',
'nav.groupWork': 'Работа',
'nav.groupPartners': 'Партнёры',
'nav.groupSetup': 'Настройка',
'role.SUPERADMIN': 'Суперадмин',
'role.SUPPORT': 'Поддержка',
'role.CONCIERGE': 'Консьерж',
'role.SALES': 'Продажи',
'roleHint.SUPERADMIN': 'Всё, включая деньги и команду',
'roleHint.SUPPORT': 'Чат поддержки, заказы, подписки',
'roleHint.CONCIERGE': 'Чат консьержа для подписчиков',
'roleHint.SALES': 'CRM: заведения и агентства',
'shell.logout': 'Выйти',
'shell.oldAdmin': 'Старая админка',
'shell.linkTg': 'Привяжите Telegram — через него вы входите и получаете уведомления.',
'shell.linkTgBtn': 'Привязать Telegram',
'soon.title': '{section} переезжает сюда',
'soon.text': 'Раздел появится на этапе {n}. Пока работайте в старой админке — данные общие.',
'soon.open': 'Открыть старую админку',
'dash.morning': 'Доброе утро, {name}',
'dash.day': 'Добрый день, {name}',
'dash.evening': 'Добрый вечер, {name}',
'dash.attention': 'Требует внимания',
'dash.allClear': 'Срочного нет — всё разобрано.',
'att.unassigned': 'Заказы без исполнителя',
'att.unreadChats': 'Ждут ответа в чатах',
'att.webRequests': 'Заявки с сайта',
'att.leads': 'Заявки на переезд',
'att.appRequests': 'Заявки из приложения',
'att.lowRatings': 'Оценки 3 и ниже за неделю',
'att.expiring': 'Подписки истекают за 7 дней',
'dash.money': 'Деньги',
'dash.today': 'Сегодня',
'dash.week': '7 дней',
'dash.month': '30 дней',
'dash.vsYesterday': 'вчера {sum}',
'dash.vsPrev': 'к прошлым {period}',
'dash.orders': 'заказы',
'dash.subs': 'подписки',
'dash.chart': 'Выручка по дням за 30 дней',
'dash.subsTitle': 'Подписки',
'dash.gifts': 'Из них подарочных: {n}',
'dash.expiring': 'Истекают в ближайшие 7 дней',
'dash.noExpiring': 'В ближайшую неделю ничего не истекает.',
'dash.conversion': 'Подарок → покупка',
'dash.conversionHint': '{paid} из {total} клиентов с подарком потом купили подписку',
'dash.growth': 'Рост',
'dash.newClients': 'Новые клиенты',
'dash.prevMonth': 'за прошлые 30 дней — {n}',
'dash.sources': 'Откуда пришли за 30 дней',
'dash.funnel': 'Воронка за 30 дней',
'funnel.leads': 'Заявки с сайта',
'funnel.clients': 'Клиенты в приложении',
'funnel.paying': 'Заплатили',
'dash.team': 'Команда и партнёры',
'dash.topProviders': 'Лучшие исполнители',
'dash.bottomProviders': 'Стоит поговорить',
'dash.topPartners': 'Заведения: сканы карты за 30 дней',
'dash.salesSoon': 'Результаты продажников появятся вместе с CRM.',
'dash.empty': 'Пока пусто',
'dash.feed': 'Лента',
'feed.subscription': '{plan} · {source}',
'feed.payment': 'Оплачен заказ №{number}',
'dash.ratings': '{n} оценок',
'dash.scans': '{n} сканов',
'source.organic': 'Сами нашли',
'source.deeplink': 'Ссылка агентства',
'source.manual_code': 'Код агентства',
'source.agency': 'Агентство «{name}»',
'source.utm': 'Реклама: {name}',
'plan.BAREV_PLUS': 'Barev+',
'plan.ELITE': 'Elite',
'plan.none': 'Без подписки',
'subSource.PAID': 'Покупка',
'subSource.MANUAL': 'Подарок команды',
'subSource.AGENCY_GIFT': 'Подарок агентства',
'subStatus.ACTIVE': 'Активна',
'subStatus.EXPIRED': 'Истекла',
'subStatus.CANCELLED': 'Отменена',
'pay.cash': 'Наличные',
'pay.transfer': 'Перевод',
'pay.card': 'Карта через терминал',
'pay.link': 'Ссылка на оплату',
'segment.MOVING': 'Переезжает',
'segment.LIVING': 'Живёт в Армении',
'clients.title': 'Клиенты',
'clients.search': 'Имя, @username, телефон или номер карты',
'clients.found': 'Найдено: {n}',
'clients.revenueTotal': 'принесли {sum}',
'col.client': 'Клиент',
'col.sub': 'Подписка',
'col.source': 'Откуда',
'col.revenue': 'Принёс',
'col.since': 'С нами с',
'filter.plan': 'Подписка',
'filter.all': 'Все',
'filter.any': 'С подпиской',
'filter.none': 'Без подписки',
'filter.subSource': 'Как получена',
'filter.source': 'Откуда',
'filter.agency': 'Агентство',
'filter.tag': 'Тег',
'filter.segment': 'Сценарий',
'filter.paying': 'Платили',
'filter.payingYes': 'Платили',
'filter.payingNo': 'Ни разу не платили',
'filter.expiring': 'Истекает за 7 дней',
'filter.reset': 'Сбросить фильтры',
'filter.more': 'Фильтры',
'filter.anyValue': 'Любое',
'sort.label': 'Порядок',
'sort.new': 'Сначала новые',
'sort.revenue': 'Больше принесли',
'sort.ends': 'Скоро истекает',
'segments.title': 'Мои выборки',
'segments.save': 'Сохранить выборку',
'segments.name': 'Название выборки',
'segments.saved': 'Выборка сохранена',
'segments.remove': 'Удалить выборку «{name}»',
'clients.export': 'Скачать для Excel',
'clients.exported': 'Файл скачан',
'clients.broadcast': 'Рассылка',
'clients.broadcastSoon': 'Рассылки по выборке появятся на этапе 5.',
'clients.empty': 'Под эти фильтры никто не подходит.',
'clients.emptyAll': 'Клиентов пока нет — они появятся, когда напишут боту.',
'clients.prev': 'Назад',
'clients.next': 'Дальше',
'clients.page': '{from}–{to} из {total}',
'card.back': 'Все клиенты',
'card.since': 'С нами с {date}',
'card.telegram': 'Открыть в Telegram',
'card.cardNo': 'Карта {code}',
'card.noSub': 'Нет активной подписки',
'card.noSubHint': 'Подарите или продайте подписку — клиент сразу получит скидки.',
'card.until': 'до {date}',
'card.daysLeft': 'осталось {n} дн.',
'card.history': 'Все подписки',
'card.grantedBy': 'начислил(а) {name}',
'card.giftFrom': 'подарок от «{name}»',
'card.paidVia': '{method}',
'card.refunded': 'возврат {sum}',
'card.cancelledAt': 'отменена {date}',
'card.upcoming': 'начнётся {date}',
'card.money': 'Принёс',
'card.fromOrders': 'заказы',
'card.fromSubs': 'подписки',
'card.orders': 'Заказы',
'card.noOrders': 'Заказов пока нет.',
'card.newOrder': 'Создать заказ',
'card.newOrderSoon': 'Заказ за клиента появится на этапе 3, вместе с разделом заказов.',
'card.profile': 'Профиль',
'card.source': 'Откуда пришёл',
'card.agency': 'Агентство',
'card.language': 'Язык',
'card.phone': 'Телефон',
'card.segment': 'Сценарий',
'card.consent': 'Согласие на обработку данных',
'card.tags': 'Теги',
'card.addTag': 'Новый тег',
'card.note': 'Заметка команды',
'card.notePh': 'Клиент не видит эту заметку',
'card.saved': 'Сохранено',
'card.activity': 'Журнал по клиенту',
'card.noActivity': 'Команда пока ничего не меняла.',
'card.stats': 'Активность',
'stat.cardUsages': 'сканов карты',
'stat.leads': 'заявок на переезд',
'stat.requests': 'заявок из приложения',
'stat.concierge': 'сообщений в чате',
'act.gift': 'Подарить',
'act.sell': 'Продать',
'act.extend': 'Изменить срок',
'act.cancel': 'Отменить',
'act.changePlan': 'Сменить тариф',
'act.refund': 'Вернуть деньги',
'audit.bo.clients.gift': 'подарил(а) подписку',
'audit.bo.clients.sell': 'продал(а) подписку',
'audit.bo.clients.extend': 'изменил(а) срок подписки',
'audit.bo.clients.cancel': 'отменил(а) подписку',
'audit.bo.clients.changePlan': 'сменил(а) тариф',
'audit.bo.clients.refund': 'оформил(а) возврат',
'audit.bo.clients.setTags': 'изменил(а) теги',
'audit.bo.clients.setNote': 'изменил(а) заметку',
'dlg.giftTitle': 'Подарить подписку',
'dlg.giftHint': 'Подписка будет помечена как подарок от вас.',
'dlg.sellTitle': 'Продать подписку',
'dlg.plan': 'Тариф',
'dlg.period': 'Срок',
'dlg.period1': '1 месяц',
'dlg.period3': '3 месяца',
'dlg.period6': '6 месяцев',
'dlg.period12': '1 год',
'dlg.periodCustom': 'Своё',
'dlg.days': 'Дней',
'dlg.amount': 'Сумма, ֏',
'dlg.method': 'Как оплатил',
'dlg.note': 'Комментарий для команды',
'dlg.linkSoon': 'Ссылку на оплату включим, когда подключим платёжную систему.',
'dlg.giftConfirm': 'Подарить',
'dlg.sellConfirm': 'Отметить оплату',
'dlg.extendTitle': 'Изменить срок',
'dlg.extendHint': 'Отрицательное число сокращает срок.',
'dlg.newEnd': 'Новая дата окончания: {date}',
'dlg.extendConfirm': 'Сохранить срок',
'dlg.cancelTitle': 'Отменить подписку',
'dlg.cancelHint': 'Клиент сразу потеряет скидки и привилегии подписки.',
'dlg.reason': 'Причина',
'dlg.cancelConfirm': 'Отменить подписку',
'dlg.planTitle': 'Сменить тариф',
'dlg.planConfirm': 'Сменить тариф',
'dlg.refundTitle': 'Вернуть деньги',
'dlg.refundPaid': 'Оплачено {sum}, уже возвращено {back}',
'dlg.refundCancel': 'Сразу отменить подписку',
'dlg.refundConfirm': 'Оформить возврат',
'done.gift': 'Подписка подарена',
'done.sell': 'Оплата отмечена',
'done.extend': 'Срок изменён',
'done.cancel': 'Подписка отменена',
'done.changePlan': 'Тариф изменён',
'done.refund': 'Возврат оформлен',
'team.title': 'Команда',
'team.lead': 'Кто работает в админке и что ему доступно. У одного человека может быть несколько ролей.',
'team.add': 'Добавить человека',
'team.name': 'Имя',
'team.roles': 'Роли',
'team.create': 'Добавить',
'team.linkTitle': 'Ссылка для {name}',
'team.linkHint': 'Отправьте её человеку. Он откроет рабочий бот, Telegram привяжется — и можно входить.',
'team.tgLinked': 'Telegram привязан',
'team.tgNotLinked': 'Telegram не привязан',
'team.newLink': 'Ссылка для привязки',
'team.disable': 'Отключить доступ',
'team.enable': 'Вернуть доступ',
'team.disabled': 'Доступ отключён',
'team.you': 'это вы',
'team.saved': 'Роли сохранены',
// ───── чаты (этап 2) ─────
'chat.title': 'Чаты',
'chat.all': 'Все',
'channel.SUPPORT': 'Поддержка',
'channel.CONCIERGE': 'Консьерж',
'chat.f.waiting': 'Ждут ответа',
'chat.f.mine': 'Мои',
'chat.f.unassigned': 'Без ответственного',
'chat.f.open': 'Открытые',
'chat.f.closed': 'Закрытые',
'chat.f.all': 'Все',
'chat.search': 'Имя, @username, телефон или текст',
'chat.emptyList': 'Здесь пусто. Новые сообщения появятся сами.',
'chat.emptyFilter': 'Ничего не нашли — попробуйте другой фильтр.',
'chat.pick': 'Выберите диалог',
'chat.pickHint': 'Сверху — те, кто ждёт ответа дольше всех.',
'chat.waiting': 'ждёт {t}',
'chat.you': 'Вы',
'chat.provider': 'Исполнитель',
'chat.unassigned': 'Никто не ведёт',
'chat.take': 'Взять себе',
'chat.transfer': 'Передать',
'chat.transferTo': 'Передать коллеге',
'chat.unassign': 'Снять ответственного',
'chat.close': 'Закрыть',
'chat.reopen': 'Открыть снова',
'chat.closedBanner': 'Диалог закрыт. Клиент напишет — откроется сам; ответить можно и сейчас.',
'chat.moveTo': 'Перенести в «{channel}»',
'chat.moved': 'Диалог перенесён в «{channel}»',
'chat.movedAway': 'Диалог перенесён в «{channel}». У вас нет доступа к этому каналу.',
'chat.other': 'Есть переписка в канале «{channel}»',
'chat.otherOpen': 'Открыть',
'chat.bot': 'Диалог ведёт ИИ-консьерж.',
'chat.botTake': 'Перехватить',
'chat.reply': 'Ответ',
'chat.note': 'Заметка',
'chat.replyPh': 'Ответ клиенту — придёт ему в Telegram',
'chat.notePh': 'Заметка для команды — клиент её не увидит',
'chat.send': 'Отправить',
'chat.saveNote': 'Сохранить заметку',
'chat.attach': 'Прикрепить файл',
'chat.templates': 'Шаблоны',
'chat.tplManage': 'Настроить шаблоны',
'chat.tplEmpty': 'Шаблонов пока нет.',
'chat.tplNew': 'Новый шаблон',
'chat.tplTitle': 'Название',
'chat.tplText': 'Текст',
'chat.tplTextHint': '{name} заменится на имя клиента',
'chat.tplChannel': 'Канал',
'chat.tplBoth': 'Оба канала',
'chat.tplDelete': 'Удалить',
'chat.tplSaved': 'Шаблон сохранён',
'chat.tplSearch': 'Найти шаблон',
'chat.noteLabel': 'Заметка · видит только команда',
'chat.fromApp': 'из приложения',
'chat.undelivered': 'Не доставлено: клиент заблокировал бота или ни разу его не открывал',
'chat.fileTooBig': 'Файл больше 10 МБ',
'chat.enterHint': 'Enter — отправить · Shift+Enter — новая строка',
'chat.providerNotLinked': 'Исполнитель ещё не открыл рабочий бот — пока можно оставить только заметку.',
'chat.client': 'О клиенте',
'chat.aboutProvider': 'Об исполнителе',
'chat.openCard': 'Карточка клиента',
'chat.write': 'Написать',
'chat.back': 'Все диалоги',
'chat.sys.took': '{name} взял(а) диалог',
'chat.sys.transferred': '{name} передал(а) диалог: {param}',
'chat.sys.unassigned': '{name} снял(а) ответственного',
'chat.sys.closed': '{name} закрыл(а) диалог',
'chat.sys.reopened': '{name} открыл(а) диалог снова',
'chat.sys.moved': '{name} перенёс(ла) диалог в «{param}»',
'chat.ago.now': 'только что',
'chat.ago.min': '{n} мин',
'chat.ago.h': '{n} ч',
'chat.ago.d': '{n} дн',
'chat.today': 'Сегодня',
'chat.yesterday': 'Вчера',
'chat.image': 'Фото',
'chat.file': 'Файл',
'chat.subUntil': 'до {date}',
'chat.orders': 'Заказы',
'chat.phone': 'Телефон',
'chat.lang': 'Язык',
'chat.source': 'Откуда',
'chat.linked': 'Рабочий бот открыт',
'chat.notLinked': 'Рабочий бот не открыт',
'chat.details': 'Подробнее',
'chat.more': 'Ещё действия',
// ───── партнёры и CRM (этап 4) ─────
'crm.title': 'CRM',
'crm.newLead': 'Новый лид',
'crm.editLead': 'Лид',
'crm.stagesBtn': 'Воронка',
'crm.tab.board': 'Воронка',
'crm.tab.tasks': 'Задачи',
'crm.tab.map': 'Карта',
'crm.search': 'Название, контакт, телефон или адрес',
'crm.kind.all': 'Все',
'crm.kind.VENUE': 'Заведения',
'crm.kind.AGENCY': 'Агентства',
'crm.kind1.VENUE': 'Заведение',
'crm.kind1.AGENCY': 'Агентство',
'crm.owner': 'Продажник',
'crm.allSales': 'Все продажники',
'crm.noOwner': 'Без продажника',
'crm.ownerIs': 'ведёт {name}',
'crm.connected': 'Подключён',
'crm.connect': 'Подключение',
'crm.days': '{n} дн',
'crm.inStage': 'Сколько дней на этом этапе',
'crm.dropHere': 'Перетащите сюда',
'crm.dragHint': 'Перетаскивайте карточки между этапами. «Подключён» сразу создаёт партнёра или агентство и выдаёт ссылку, «Отказ» спросит причину.',
'crm.overdue': 'просрочена',
'crm.tasksOpen': 'Открытые',
'crm.tasksDone': 'Выполненные',
'crm.addTask': 'Задача',
'crm.noTasks': 'Открытых задач нет.',
'crm.noDoneTasks': 'Выполненных задач пока нет.',
'crm.noLead': 'без лида',
'crm.tasksHint': 'В срок задачи придёт напоминание в рабочий бот (если привязан Telegram).',
'crm.taskTitle': 'Что сделать',
'crm.taskDay': 'День',
'crm.taskTime': 'Время',
'crm.taskHint': 'Напоминание придёт в рабочий бот в это время (по Еревану).',
'crm.tp.call': 'Позвонить',
'crm.tp.meet': 'Встреча',
'crm.tp.send': 'Отправить условия',
'crm.tp.check': 'Узнать решение',
'crm.partnerOnMap': 'партнёр клуба',
'crm.legendPartner': 'подключённые партнёры',
'crm.legendLead': 'лиды (цвет этапа)',
'crm.mapHint': 'Точка появляется, когда у лида есть координаты.',
'crm.name': 'Название',
'crm.namePhVenue': 'Например: Lumen Coffee',
'crm.namePhAgency': 'Например: Domik Realty',
'crm.category': 'Тип',
'crm.contactName': 'Контактное лицо',
'crm.contactPh': 'Имя и должность',
'crm.address': 'Адрес',
'crm.note': 'Заметка',
'crm.convert': 'Подключить',
'crm.convertTitle': 'Подключить «{name}»',
'crm.convertVenueHint': 'Создадим партнёра клубной карты и ссылку для собственника: он откроет рабочий бот и сможет проверять карты клиентов. Предложения по уровням добавите в карточке заведения.',
'crm.convertAgencyHint': 'Создадим агентство с кодом и ссылку для его клиентов: по ней они получают подарочный месяц и закрепляются за агентством.',
'crm.agencyCode': 'Код агентства',
'crm.agencyCodeHint': 'Латиница и цифры, клиенты могут ввести его вручную',
'crm.convertedTitle': 'Подключено 🎉',
'crm.convertedVenue': 'Отправьте эту ссылку собственнику заведения. Ссылка одноразовая.',
'crm.convertedAgency': 'Эту ссылку агентство раздаёт клиентам.',
'crm.openVenue': 'Карточка заведения',
'crm.openAgency': 'Карточка агентства',
'crm.ownerLinked': 'Собственник уже в рабочем боте.',
'crm.ownerNotYet': 'Собственник ещё не открыл ссылку. Отправьте её ещё раз:',
'crm.agencyInfo': 'Код {code}, клиентов: {n}',
'crm.lostTitle': 'Почему отказ?',
'crm.lostReason': 'Причина',
'crm.lr.price': 'Не устроили условия',
'crm.lr.notNow': 'Не сейчас, вернуться позже',
'crm.lr.noAnswer': 'Не выходят на связь',
'crm.lr.competitor': 'Работают с конкурентом',
'crm.lostBanner': 'Отказ: {reason}',
'crm.stagesTitle': 'Этапы воронки',
'crm.stagesHint': 'Порядок — стрелками. Нужен хотя бы один открытый этап и один «Подключён». Этап с лидами при удалении скрывается, лиды остаются.',
'crm.addStage': 'Этап',
'crm.stageKind.OPEN': 'в работе',
'crm.stageKind.WON': 'подключён',
'crm.stageKind.LOST': 'отказ',
'crm.bonusMonth': 'Бонус за месяц',
'crm.bonusMineSuper': 'Бонус (ваш), месяц',
'crm.bonusNotSet': 'не настроен',
'crm.bonusVenues': 'Заведения: {n} → {sum}',
'crm.bonusAgencies': 'Агентства: {n} → {sum}',
'crm.bonusRevenue': '{pct}% выручки клиентов агентств → {sum}',
'crm.bonusTitle': 'Формула бонуса продажника',
'crm.bonusHint': 'Бонус за месяц = подключённые заведения × ставка + агентства × ставка + % выручки клиентов агентств продажника (первые N месяцев после подключения). Выручка — оплаченные заказы и подписки.',
'crm.bonusPerVenue': 'За заведение, ֏',
'crm.bonusPerAgency': 'За агентство, ֏',
'crm.bonusPct': '% выручки клиентов агентств',
'crm.bonusMonths': 'Сколько месяцев',
'crm.back': 'CRM',
'crm.created': 'с {date}',
'crm.stage': 'Этап',
'crm.history': 'История контактов',
'crm.noHistory': 'Пока пусто — запишите первый звонок или встречу.',
'crm.act.CALL': 'Звонок',
'crm.act.MEETING': 'Встреча',
'crm.act.NOTE': 'Заметка',
'crm.act.FILE': 'Файл',
'crm.act.STAGE': 'Этап',
'crm.act.WON': 'Подключён',
'crm.actPh.CALL': 'О чём договорились по телефону?',
'crm.actPh.MEETING': 'Как прошла встреча, что дальше?',
'crm.actPh.NOTE': 'Заметка для себя и команды',
'crm.addAct': 'Записать',
'crm.attach': 'Фото или файл',
'crm.tasks': 'Задачи',
'crm.noLeadTasks': 'Задач нет. Поставьте следующий шаг — придёт напоминание.',
'crm.contacts': 'Контакты',
'crm.noCoords': 'На карте нет точки.',
'crm.coordsPh': 'Ссылка Google Maps или «40.18, 44.51»',
'crm.coordsBad': 'Не нашли координаты — вставьте ссылку из Google Maps или числа через запятую.',
'crm.remove': 'Удалить лид',
'crm.removeConfirm': 'Удалить лид вместе с историей и задачами?',
'venue.cat.cafe': 'Кафе',
'venue.cat.restaurant': 'Ресторан',
'venue.cat.shop': 'Магазин',
'venue.cat.beauty': 'Красота',
'venue.cat.other': 'Другое',
'ag.title': 'Агентства',
'ag.add': 'Новое агентство',
'ag.editTitle': 'Агентство',
'ag.empty': 'Агентств пока нет.',
'ag.col.name': 'Агентство',
'ag.col.clients': 'Клиенты',
'ag.col.gifts': 'Подарки',
'ag.col.month': 'Вознаграждение, месяц',
'ag.col.balance': 'К выплате',
'ag.hint': 'Вознаграждение — % от оплаченных заказов клиентов агентства, пока они закреплены за ним.',
'ag.inactive': 'выключено',
'ag.back': 'Все агентства',
'ag.pct': '{n}% с заказов клиентов',
'ag.byS': 'подключил(а) {name}',
'ag.link': 'Ссылка для клиентов',
'ag.linkHint': 'По ссылке клиент открывает бота, получает подарочный месяц и закрепляется за агентством. Или вводит код {code} командой /code.',
'ag.clients': 'Клиенты',
'ag.giftsN': 'подарков: {n}',
'ag.noClients': 'Клиентов пока нет.',
'ag.orders': 'заказов: {n}',
'ag.toPay': 'Вознаграждение к выплате',
'ag.accrued': 'Начислено',
'ag.payouts': 'Выплаты',
'ag.payoutTitle': 'Выплата агентству',
'ag.balanceHint': 'Начислено и не выплачено: {sum}',
'ag.pctLabel': 'Вознаграждение, %',
'ag.sales': 'Подключил продажник',
'ag.contactPh': 'Имя, телефон, Telegram',
'ag.active': 'Агентство работает (код принимается)',
'vn.title': 'Заведения',
'vn.add': 'Новое заведение',
'vn.editTitle': 'Заведение',
'vn.empty': 'Заведений пока нет.',
'vn.col.name': 'Заведение',
'vn.col.offers': 'Предложения',
'vn.col.staff': 'Сотрудники',
'vn.col.visits': 'Проверки за 30 дн',
'vn.col.last': 'Последняя проверка',
'vn.hint': 'Проверка — сотрудник заведения отсканировал клубную карту клиента в рабочем боте.',
'vn.noOwner': 'нет собственника',
'vn.noOffers': 'нет предложений',
'vn.back': 'Все заведения',
'vn.ownerHint': 'Собственник ещё не подключён — отправьте ему одноразовую ссылку в рабочий бот.',
'vn.makeLink': 'Создать ссылку',
'vn.offers': 'Предложения по уровням',
'vn.addOffer': 'Предложение',
'vn.editOffer': 'Предложение',
'vn.noOffersHint': 'Добавьте, что положено членам клуба: скидку, подарок, комплимент.',
'vn.level.any': 'Любой член клуба',
'vn.level.BAREV_PLUS': 'Barev+ и Elite',
'vn.level.ELITE': 'Только Elite',
'vn.limit.NONE': 'без ограничений',
'vn.limit.ONCE': 'один раз',
'vn.limit.WEEK': '{n} р. в неделю',
'vn.limit.MONTH': '{n} р. в месяц',
'vn.limitOpt.NONE': 'Без ограничений',
'vn.limitOpt.ONCE': 'Только первый визит',
'vn.limitOpt.WEEK': 'N раз в неделю',
'vn.limitOpt.MONTH': 'N раз в месяц',
'vn.offerOff': 'выключено',
'vn.offerTitle': 'Что получает клиент',
'vn.offerTitleHint': 'Например: «Капучино в подарок» или «−15% на всё меню»',
'vn.forWhom': 'Для кого',
'vn.howOften': 'Как часто',
'vn.times': 'Сколько раз',
'vn.offerActive': 'Предложение действует',
'vn.activity': 'Активность',
'vn.weeks8': 'за 8 недель',
'vn.checks': 'проверки карты',
'vn.redeemed': 'списания предложений',
'vn.cardCheck': 'проверка карты',
'vn.staff': 'Сотрудники',
'vn.noStaff': 'Пока никого.',
'vn.role.OWNER': 'собственник',
'vn.role.STAFF': 'сотрудник',
'vn.removeStaff': 'Убрать {name} из заведения?',
'vn.staffHint': 'Сотрудников приглашает собственник в рабочем боте (QR на сутки).',
'vn.newOwnerLink': 'Ссылка собственнику',
'vn.newOwnerLinkHint': 'Новая одноразовая ссылка — например, если сменился собственник',
'vn.blurb': 'Коротко о скидке (на карточке у клиента)',
'vn.blurbHint': 'Например: «−10% по клубной карте»',
'vn.coords': 'Точка на карте',
'vn.activeLabel': 'Заведение видно клиентам',
'err.LEAD_NOT_CONVERTED': 'Чтобы перевести в «Подключён», нажмите «Подключить» — так создастся партнёр.',
'err.ALREADY_CONVERTED': 'Лид уже подключён.',
'err.AGENCY_CODE_FORMAT': 'Код — латиница, цифры и «_», до 32 символов.',
'err.AGENCY_CODE_TAKEN': 'Такой код уже есть у другого агентства.',
'err.STAGES_INVALID': 'Нужен хотя бы один открытый этап и один «Подключён».',
'audit.bo.crm.create': 'добавил(а) лид',
'audit.bo.crm.update': 'изменил(а) лид',
'audit.bo.crm.move': 'перевёл(а) лид на другой этап',
'audit.bo.crm.convert': 'подключил(а) партнёра',
'audit.bo.crm.addActivity': 'записал(а) контакт',
'audit.bo.crm.saveStages': 'изменил(а) воронку',
'audit.bo.crm.setBonusRules': 'изменил(а) формулу бонуса',
'audit.bo.partners.saveAgency': 'изменил(а) агентство',
'audit.bo.partners.agencyPayout': 'отметил(а) выплату агентству',
'audit.bo.partners.saveVenue': 'изменил(а) заведение',
'audit.bo.partners.saveOffer': 'изменил(а) предложение заведения',
'audit.bo.partners.ownerInvite': 'выпустил(а) ссылку собственнику',
'audit.bo.partners.removeMember': 'убрал(а) сотрудника заведения',
// ───── заказы и исполнители (этап 3) ─────
'ord.title': 'Заказы',
'ord.new': 'Новый заказ',
'ord.search': '№, клиент, телефон, адрес или исполнитель',
'ord.period': 'Период',
'ord.period.all': 'Все даты',
'ord.period.today': 'Сегодня',
'ord.period.tomorrow': 'Завтра',
'ord.period.week': '7 дней',
'ord.period.past': 'Прошедшие',
'ord.group.active': 'В работе у команды',
'ord.group.new': 'Ждут исполнителя',
'ord.group.pending': 'Предложены',
'ord.group.assigned': 'Назначены',
'ord.group.in_progress': 'Выполняются',
'ord.group.done': 'Готово',
'ord.group.cancelled': 'Отменены',
'ord.today': 'Сегодня',
'ord.tomorrow': 'Завтра',
'ord.empty': 'Заказов с такими условиями нет.',
'ord.waitsAnswer': 'ждём ответа: {name}',
'ord.needsHuman': 'нужен диспетчер',
'ord.searching': 'система подбирает…',
'ord.overdue': 'время прошло, исполнителя нет',
'ord.needsDispatcher': 'Автораспределение не нашло исполнителя для заказов: {n}. Назначьте вручную.',
'ord.autoOn': 'Автораспределение включено',
'ord.autoOff': 'Автораспределение выключено',
'ord.autoHint': 'Новый заказ сам предлагается лучшему свободному исполнителю (язык клиента, район, загрузка, рейтинг). Нет ответа {minutes} мин или отказ — следующему; после {tries} попыток — диспетчеру.',
'ord.back': 'Все заказы',
'ord.progress': 'Ход заказа',
'ord.details': 'Детали',
'ord.when': 'Когда',
'ord.where': 'Где',
'ord.minutes': '{n} мин',
'ord.params': 'Параметры',
'ord.extras': 'Доп. услуги',
'ord.note': 'Комментарий клиента',
'ord.lang': 'Язык клиента',
'ord.created': 'Создан',
'ord.checklist': 'Чек-лист',
'ord.needsPhoto': 'нужно фото',
'ord.photo': 'Фото',
'ord.history': 'История',
'ord.client': 'Клиент',
'ord.writeClient': 'Написать клиенту',
'ord.writeProvider': 'Написать исполнителю',
'ord.call': 'Позвонить',
'ord.noPhone': 'Телефон исполнителя не указан — добавьте его в профиле',
'ord.money': 'Деньги',
'ord.base': 'Без скидки',
'ord.discount': 'Скидка {pct}%',
'ord.payout': 'Исполнителю',
'ord.cancelFee': 'Удержание за отмену',
'ord.payment': 'Оплата',
'ord.markPaid': 'Отметить оплату',
'ord.confirmPaid': 'Отметить, что клиент оплатил заказ?',
'ord.paidDone': 'Оплата отмечена',
'ord.actions': 'Действия',
'ord.setStatus': 'Статус: {status}',
'ord.confirmStatus': 'Перевести заказ в «{status}»? Клиент получит уведомление.',
'ord.statusChanged': 'Статус изменён',
'ord.reschedule': 'Перенести',
'ord.rescheduleTitle': 'Перенос заказа №{n}',
'ord.rescheduleHint': 'Если исполнитель занят в новое время, заказ вернётся в «Ждут исполнителя» и уйдёт в автораспределение.',
'ord.rescheduled': 'Заказ перенесён, исполнитель тот же',
'ord.rescheduledFree': 'Заказ перенесён; исполнитель занят — ищем нового',
'ord.comment': 'Комментарий',
'ord.commentPh': 'Например: клиент попросил по телефону',
'ord.cancel': 'Отменить заказ',
'ord.cancelTitle': 'Отмена заказа',
'ord.cancelReason': 'Причина отмены',
'ord.cancelReasonPh': 'Например: клиент передумал',
'ord.cancelFeeHint': 'Сколько удержать с клиента, ֏. Обычно 0.',
'ord.cancelHint': 'Клиент и исполнитель получат уведомление.',
'ord.cancelled': 'Заказ отменён',
'ord.rating': 'Оценка клиента',
'ord.noComment': 'Без комментария',
'ord.offers': 'Кому предлагали',
'ord.bySystem': 'система',
'ord.provider': 'Исполнитель',
'ord.unassign': 'Снять исполнителя',
'ord.revoke': 'Отозвать предложение',
'ord.confirmUnassign': 'Снять исполнителя? Заказ вернётся в «Ждут исполнителя».',
'ord.confirmRevoke': 'Отозвать предложение? Заказ снова будет ждать исполнителя.',
'ord.unassigned': 'Готово — заказ снова ждёт исполнителя',
'ord.pendingProvider': 'Предложен: {name}',
'ord.pendingCompany': 'Передан компании «{name}» — ждём, кого назначит диспетчер',
'ord.byAuto': 'предложила система',
'ord.minLeft': 'на ответ ≈ {n} мин',
'ord.pickHint': 'Свободные на это время — по порядку подбора. Или поручите выбор системе.',
'ord.autoPick': 'Подобрать автоматически',
'ord.autoOffered': 'Предложили: {name}',
'ord.autoNone': 'Свободных исполнителей не нашлось',
'ord.noFree': 'На это время все заняты. Перенесите заказ или договоритесь с исполнителем.',
'ord.busy': 'Заняты в это время: {n}',
'ord.company': 'компания',
'ord.tried': 'уже предлагали',
'ord.load': 'заказов в этот день: {n}',
'ord.offer': 'Предложить',
'ord.offered': 'Заказ отправлен исполнителю',
'ord.noProvider': 'Исполнитель не назначался.',
'ord.ev.created': 'Заказ создан',
'ord.ev.createdByStaff': 'Заказ оформила команда',
'ord.ev.offered': 'Предложен исполнителю',
'ord.ev.autoOffered': 'Автораспределение: предложен',
'ord.ev.autoNoCandidate': 'Автораспределение: свободных нет',
'ord.ev.autoGaveUp': 'Автораспределение остановлено — нужен диспетчер',
'no.title': 'Новый заказ',
'no.client': 'Клиент',
'no.clientPh': 'Имя, @username или телефон',
'no.noClients': 'Никого не нашли',
'no.changeClient': 'Другой клиент',
'no.service': 'Услуга',
'no.extras': 'Доп. услуги',
'no.address': 'Адрес',
'no.addressPh': 'Улица, дом, квартира',
'no.district': 'Район',
'no.when': 'Дата и время',
'no.day': 'День',
'no.noSlots': 'На этот день свободного времени нет — выберите другой день или «другое время».',
'no.otherTime': 'Другое время (договорились с исполнителем сами)',
'no.customTime': 'Время',
'no.customHint': 'По Еревану. Свободных исполнителей система не гарантирует.',
'no.note': 'Комментарий для исполнителя',
'no.notePh': 'Код домофона, животные…',
'no.payment': 'Оплата',
'no.hint': 'Цена — с учётом подписки клиента. Клиент получит уведомление в бота, заказ сразу уйдёт в автораспределение.',
'no.create': 'Оформить заказ',
'no.created': 'Заказ №{n} оформлен',
'prv.title': 'Исполнители',
'prv.add': 'Добавить',
'prv.search': 'Имя или телефон',
'prv.status.active': 'Работают',
'prv.status.blocked': 'Заблокированы',
'prv.status.all': 'Все',
'prv.empty': 'Никого не нашли.',
'prv.col.name': 'Исполнитель',
'prv.col.rating': 'Рейтинг',
'prv.col.done': 'Заказов',
'prv.col.refused': 'Отказы',
'prv.col.next': 'Ближайший заказ',
'prv.period30': 'Заказы, отказы и низкие оценки — за 30 дней.',
'prv.blocked': 'заблокирован',
'prv.onShift': 'на смене',
'prv.offShift': 'не на смене',
'prv.notLinked': 'не открыл бота',
'prv.noDocs': 'нет документов',
'prv.ratings': 'оценок: {n}',
'prv.low': 'низких: {n}',
'prv.today': 'сегодня: {n}',
'prv.back': 'Все исполнители',
'prv.write': 'Написать',
'prv.edit': 'Редактировать',
'prv.blockedSince': 'Заблокирован с {date}.',
'prv.unblock': 'Вернуть к работе',
'prv.inviteHint': 'Исполнитель ещё не открыл рабочий бот — отправьте ему ссылку.',
'prv.copyInvite': 'Скопировать ссылку',
'prv.quality': 'Качество',
'prv.days30': 'за 30 дней',
'prv.acceptRate': 'принял {a} из {n} предложений',
'prv.refusals': 'отказы: {d}, молчал: {e}',
'prv.lowRatings': 'оценок 3 и ниже',
'prv.upcoming': 'Ближайшие заказы',
'prv.noUpcoming': 'Назначенных заказов нет.',
'prv.recent': 'Последние выполненные',
'prv.balance': 'К выплате',
'prv.thisMonth': 'Этот месяц',
'prv.prevMonth': 'Прошлый',
'prv.paidTotal': 'Выплачено',
'prv.payout': 'Отметить выплату',
'prv.payoutTitle': 'Выплата исполнителю',
'prv.amount': 'Сумма, ֏',
'prv.balanceHint': 'Долг перед исполнителем: {sum}',
'prv.payoutNote': 'Как выплатили',
'prv.payoutNotePh': 'Наличные / перевод на карту…',
'prv.payoutConfirm': 'Выплачено',
'prv.payoutDone': 'Выплата отмечена',
'prv.rateCompany': 'ставка компании {v}',
'prv.rateOwn': 'ставка {v}',
'prv.ratePreset': 'по пресету «{name}»',
'prv.work': 'Работа',
'prv.languages': 'Языки',
'prv.districts': 'Районы',
'prv.anyDistrict': 'любые',
'prv.districtsHint': 'Подбор ставит выше тех, кто работает в районе заказа.',
'prv.docs': 'Документы для допуска',
'prv.noDocsHint': 'Паспорт, договор, справка — всё хранится в закрытом хранилище.',
'prv.docTitlePh': 'Название: паспорт, договор…',
'prv.upload': 'Загрузить',
'prv.docAdded': 'Документ добавлен',
'prv.removeDocConfirm': 'Удалить документ?',
'prv.access': 'Допуск',
'prv.block': 'Заблокировать',
'prv.blockTitle': 'Заблокировать исполнителя',
'prv.blockReason': 'Причина',
'prv.blockReasonPh': 'Например: жалобы клиентов, нет документов',
'prv.blockHint': 'Заказы ему больше не предлагаются, действующие предложения отзываются. Уже назначенные заказы остаются — переназначьте их вручную.',
'prv.resetInvite': 'Новая ссылка для входа в бот',
'prv.resetConfirm': 'Сделать новую ссылку? Текущая привязка к Telegram снимется — исполнителю нужно будет войти заново.',
'prv.since': 'С нами с {date}',
'prv.saved': 'Сохранено',
'prv.addTitle': 'Новый исполнитель',
'prv.editTitle': 'Профиль исполнителя',
'prv.name': 'Имя',
'prv.role': 'Роль',
'prv.company': 'Компания',
'prv.freelance': 'Частный исполнитель',
'prv.schedule': 'График',
'prv.rate': 'Ставка',
'prv.note': 'Заметка команды',
'err.REASON_REQUIRED': 'Укажите причину.',
'err.SLOT_UNAVAILABLE': 'Это время уже занято или прошло. Выберите другое или «другое время».',
'err.ALREADY_ASSIGNED': 'Заказ уже назначен или предложен — обновите страницу.',
'err.PROVIDER_BUSY': 'Исполнитель занят в это время.',
'err.TRANSITION_NOT_ALLOWED': 'Сейчас этот шаг для заказа недоступен.',
'err.CHECKLIST_INCOMPLETE': 'Сначала исполнитель должен закрыть чек-лист и приложить фото.',
'err.CONSENT_REQUIRED': 'Клиент ещё не дал согласие на обработку данных в боте — заказ оформить нельзя.',
'err.ADDRESS_REQUIRED': 'Укажите адрес и район.',
'err.INVALID_PARAMS': 'Проверьте параметры заказа.',
'err.OFFER_NOT_ACTIVE': 'Предложение уже неактуально.',
'err.BAD_FILE_TYPE_DOC': 'Можно фото или PDF.',
'audit.bo.orders.assign': 'предложил(а) заказ исполнителю',
'audit.bo.orders.auto': 'запустил(а) подбор исполнителя',
'audit.bo.orders.unassign': 'снял(а) исполнителя с заказа',
'audit.bo.orders.transition': 'сменил(а) статус заказа',
'audit.bo.orders.cancel': 'отменил(а) заказ',
'audit.bo.orders.reschedule': 'перенёс(ла) заказ',
'audit.bo.orders.markPaid': 'отметил(а) оплату заказа',
'audit.bo.orders.create': 'оформил(а) заказ за клиента',
'audit.bo.orders.setAutoSetting': 'изменил(а) автораспределение',
'audit.bo.providers.create': 'добавил(а) исполнителя',
'audit.bo.providers.update': 'изменил(а) профиль исполнителя',
'audit.bo.providers.setActive': 'изменил(а) допуск исполнителя',
'audit.bo.providers.resetInvite': 'выпустил(а) новую ссылку исполнителю',
'audit.bo.providers.removeDoc': 'удалил(а) документ исполнителя',
'audit.bo.providers.addDoc': 'загрузил(а) документ исполнителя',
'audit.bo.providers.payout': 'отметил(а) выплату исполнителю',
'chat.order': 'Заказ №{n}',
'chat.noOrder': 'Без заказа',
'chat.noOrderNow': 'Сейчас без заказа',
'chat.orderNow': 'Сейчас',
'chat.orderNext': 'Ближайший',
'chat.orderNoNext': 'Ближайших заказов нет',
'chat.orderClient': 'клиент {name}',
'chat.wroteNoOrder': 'писал(а) без заказа',
'err.CONCIERGE_SUBSCRIBERS_ONLY': 'Консьерж — только для подписчиков. Сначала выдайте клиенту подписку.',
'err.ASSIGNEE_NO_ACCESS': 'У этого сотрудника нет доступа к этому каналу.',
'err.PROVIDER_NOT_LINKED': 'Исполнитель ещё не открыл рабочий бот — написать ему пока некуда.',
'err.BAD_FILE_TYPE': 'Такой файл не подойдёт. Можно фото, PDF, Word, Excel, текст или ZIP.',
'audit.bo.chats.send': 'ответил(а) в чате',
'audit.bo.chats.sendFile': 'отправил(а) файл в чате',
'audit.bo.chats.assign': 'назначил(а) ответственного в чате',
'audit.bo.chats.close': 'закрыл(а) диалог',
'audit.bo.chats.reopen': 'открыл(а) диалог снова',
'audit.bo.chats.move': 'перенёс(ла) диалог в другой канал',
'audit.bo.chats.openFor': 'открыл(а) чат с клиентом',
'audit.bo.chats.templates.save': 'изменил(а) шаблон ответа',
'audit.bo.chats.templates.remove': 'удалил(а) шаблон ответа',
};
export type BoKey = keyof typeof ru;
type Dict = Record<BoKey, string>;
const en: Dict = {
'ui.save': 'Save',
'ui.close': 'Close',
'ui.loading': 'Loading…',
'ui.error': 'That didn’t work: {msg}',
'ui.retry': 'Try again',
'ui.copy': 'Copy',
'ui.copied': 'Copied',
'ui.days': '{n} d',
'ui.yes': 'Yes',
'ui.no': 'No',
'ui.none': '—',
'err.PAYMENTS_NOT_CONFIGURED': 'Online payments aren’t connected yet — mark the payment manually.',
'err.REFUND_TOO_BIG': 'The refund is larger than what the client paid.',
'err.ENDS_BEFORE_START': 'A subscription can’t end before it starts.',
'err.CANNOT_DEMOTE_SELF': 'You can’t disable yourself or remove your own super admin role.',
'err.ROLE_FORBIDDEN': 'Your role doesn’t have access to this action.',
'err.NO_ROLE': 'Your account has no roles in the new admin. Ask a super admin to grant them.',
'login.coverWord': 'team',
'login.title': 'Team sign-in',
'login.lead': 'Confirm sign-in in the Barev Club work bot. No password needed.',
'login.open': 'Confirm in Telegram',
'login.qr': 'On a computer, scan the code with your phone.',
'login.waiting': 'Waiting for confirmation in Telegram…',
'login.expired': 'The link has expired.',
'login.retry': 'Get a new link',
'login.dev': 'Local sign-in',
'login.devHint': 'Only on this computer — the server doesn’t show this block.',
'login.noTelegram': 'No access? Ask a super admin to add you to the team and send a Telegram link.',
'nav.dashboard': 'Dashboard',
'nav.clients': 'Clients',
'nav.chats': 'Chats',
'nav.orders': 'Orders',
'nav.providers': 'Providers',
'nav.agencies': 'Agencies',
'nav.venues': 'Venues',
'nav.crm': 'CRM',
'nav.products': 'Products',
'nav.journal': 'Activity log',
'nav.team': 'Team',
'nav.more': 'More',
'nav.soon': 'stage {n}',
'nav.groupWork': 'Work',
'nav.groupPartners': 'Partners',
'nav.groupSetup': 'Setup',
'role.SUPERADMIN': 'Super admin',
'role.SUPPORT': 'Support',
'role.CONCIERGE': 'Concierge',
'role.SALES': 'Sales',
'roleHint.SUPERADMIN': 'Everything, including money and the team',
'roleHint.SUPPORT': 'Support chat, orders, subscriptions',
'roleHint.CONCIERGE': 'Concierge chat for subscribers',
'roleHint.SALES': 'CRM: venues and agencies',
'shell.logout': 'Sign out',
'shell.oldAdmin': 'Old admin',
'shell.linkTg': 'Link Telegram — you sign in and get notifications through it.',
'shell.linkTgBtn': 'Link Telegram',
'soon.title': '{section} is moving here',
'soon.text': 'This section arrives in stage {n}. Until then, use the old admin — the data is shared.',
'soon.open': 'Open the old admin',
'dash.morning': 'Good morning, {name}',
'dash.day': 'Good afternoon, {name}',
'dash.evening': 'Good evening, {name}',
'dash.attention': 'Needs attention',
'dash.allClear': 'Nothing urgent — all caught up.',
'att.unassigned': 'Orders without a provider',
'att.unreadChats': 'Chats awaiting reply',
'att.webRequests': 'Website requests',
'att.leads': 'Relocation requests',
'att.appRequests': 'In-app requests',
'att.lowRatings': 'Ratings of 3 or lower this week',
'att.expiring': 'Subscriptions ending within 7 days',
'dash.money': 'Money',
'dash.today': 'Today',
'dash.week': '7 days',
'dash.month': '30 days',
'dash.vsYesterday': 'yesterday {sum}',
'dash.vsPrev': 'vs previous {period}',
'dash.orders': 'orders',
'dash.subs': 'subscriptions',
'dash.chart': 'Daily revenue, last 30 days',
'dash.subsTitle': 'Subscriptions',
'dash.gifts': 'Gifts among them: {n}',
'dash.expiring': 'Ending in the next 7 days',
'dash.noExpiring': 'Nothing ends in the coming week.',
'dash.conversion': 'Gift → purchase',
'dash.conversionHint': '{paid} of {total} gifted clients later bought a subscription',
'dash.growth': 'Growth',
'dash.newClients': 'New clients',
'dash.prevMonth': 'previous 30 days — {n}',
'dash.sources': 'Where they came from, 30 days',
'dash.funnel': 'Funnel, 30 days',
'funnel.leads': 'Website requests',
'funnel.clients': 'Clients in the app',
'funnel.paying': 'Paid',
'dash.team': 'Team and partners',
'dash.topProviders': 'Top providers',
'dash.bottomProviders': 'Worth a talk',
'dash.topPartners': 'Venues: card scans, 30 days',
'dash.salesSoon': 'Sales results will appear with the CRM.',
'dash.empty': 'Nothing yet',
'dash.feed': 'Feed',
'feed.subscription': '{plan} · {source}',
'feed.payment': 'Order #{number} paid',
'dash.ratings': '{n} ratings',
'dash.scans': '{n} scans',
'source.organic': 'Found us',
'source.deeplink': 'Agency link',
'source.manual_code': 'Agency code',
'source.agency': 'Agency “{name}”',
'source.utm': 'Ads: {name}',
'plan.BAREV_PLUS': 'Barev+',
'plan.ELITE': 'Elite',
'plan.none': 'No subscription',
'subSource.PAID': 'Purchase',
'subSource.MANUAL': 'Team gift',
'subSource.AGENCY_GIFT': 'Agency gift',
'subStatus.ACTIVE': 'Active',
'subStatus.EXPIRED': 'Expired',
'subStatus.CANCELLED': 'Cancelled',
'pay.cash': 'Cash',
'pay.transfer': 'Bank transfer',
'pay.card': 'Card via terminal',
'pay.link': 'Payment link',
'segment.MOVING': 'Relocating',
'segment.LIVING': 'Lives in Armenia',
'clients.title': 'Clients',
'clients.search': 'Name, @username, phone or card number',
'clients.found': 'Found: {n}',
'clients.revenueTotal': 'brought {sum}',
'col.client': 'Client',
'col.sub': 'Subscription',
'col.source': 'Source',
'col.revenue': 'Brought',
'col.since': 'Joined',
'filter.plan': 'Subscription',
'filter.all': 'All',
'filter.any': 'Subscribed',
'filter.none': 'Not subscribed',
'filter.subSource': 'How received',
'filter.source': 'Source',
'filter.agency': 'Agency',
'filter.tag': 'Tag',
'filter.segment': 'Scenario',
'filter.paying': 'Paid',
'filter.payingYes': 'Have paid',
'filter.payingNo': 'Never paid',
'filter.expiring': 'Ends within 7 days',
'filter.reset': 'Reset filters',
'filter.more': 'Filters',
'filter.anyValue': 'Any',
'sort.label': 'Order',
'sort.new': 'Newest first',
'sort.revenue': 'Brought the most',
'sort.ends': 'Ending soon',
'segments.title': 'My segments',
'segments.save': 'Save segment',
'segments.name': 'Segment name',
'segments.saved': 'Segment saved',
'segments.remove': 'Delete segment “{name}”',
'clients.export': 'Download for Excel',
'clients.exported': 'File downloaded',
'clients.broadcast': 'Broadcast',
'clients.broadcastSoon': 'Segment broadcasts arrive in stage 5.',
'clients.empty': 'No one matches these filters.',
'clients.emptyAll': 'No clients yet — they appear once they message the bot.',
'clients.prev': 'Back',
'clients.next': 'Next',
'clients.page': '{from}–{to} of {total}',
'card.back': 'All clients',
'card.since': 'With us since {date}',
'card.telegram': 'Open in Telegram',
'card.cardNo': 'Card {code}',
'card.noSub': 'No active subscription',
'card.noSubHint': 'Gift or sell a subscription — the client gets discounts right away.',
'card.until': 'until {date}',
'card.daysLeft': '{n} d left',
'card.history': 'All subscriptions',
'card.grantedBy': 'granted by {name}',
'card.giftFrom': 'gift from “{name}”',
'card.paidVia': '{method}',
'card.refunded': 'refund {sum}',
'card.cancelledAt': 'cancelled {date}',
'card.upcoming': 'starts {date}',
'card.money': 'Brought',
'card.fromOrders': 'orders',
'card.fromSubs': 'subscriptions',
'card.orders': 'Orders',
'card.noOrders': 'No orders yet.',
'card.newOrder': 'Create order',
'card.newOrderSoon': 'Ordering on a client’s behalf arrives in stage 3, together with the orders section.',
'card.profile': 'Profile',
'card.source': 'Source',
'card.agency': 'Agency',
'card.language': 'Language',
'card.phone': 'Phone',
'card.segment': 'Scenario',
'card.consent': 'Data processing consent',
'card.tags': 'Tags',
'card.addTag': 'New tag',
'card.note': 'Team note',
'card.notePh': 'The client doesn’t see this note',
'card.saved': 'Saved',
'card.activity': 'Client log',
'card.noActivity': 'The team hasn’t changed anything yet.',
'card.stats': 'Activity',
'stat.cardUsages': 'card scans',
'stat.leads': 'relocation requests',
'stat.requests': 'in-app requests',
'stat.concierge': 'chat messages',
'act.gift': 'Gift',
'act.sell': 'Sell',
'act.extend': 'Change term',
'act.cancel': 'Cancel',
'act.changePlan': 'Change plan',
'act.refund': 'Refund',
'audit.bo.clients.gift': 'gifted a subscription',
'audit.bo.clients.sell': 'sold a subscription',
'audit.bo.clients.extend': 'changed the subscription term',
'audit.bo.clients.cancel': 'cancelled a subscription',
'audit.bo.clients.changePlan': 'changed the plan',
'audit.bo.clients.refund': 'issued a refund',
'audit.bo.clients.setTags': 'changed tags',
'audit.bo.clients.setNote': 'changed the note',
'dlg.giftTitle': 'Gift a subscription',
'dlg.giftHint': 'It will be marked as a gift from you.',
'dlg.sellTitle': 'Sell a subscription',
'dlg.plan': 'Plan',
'dlg.period': 'Term',
'dlg.period1': '1 month',
'dlg.period3': '3 months',
'dlg.period6': '6 months',
'dlg.period12': '1 year',
'dlg.periodCustom': 'Custom',
'dlg.days': 'Days',
'dlg.amount': 'Amount, ֏',
'dlg.method': 'Paid by',
'dlg.note': 'Note for the team',
'dlg.linkSoon': 'Payment links turn on once a payment provider is connected.',
'dlg.giftConfirm': 'Gift',
'dlg.sellConfirm': 'Mark as paid',
'dlg.extendTitle': 'Change term',
'dlg.extendHint': 'A negative number shortens the term.',
'dlg.newEnd': 'New end date: {date}',
'dlg.extendConfirm': 'Save term',
'dlg.cancelTitle': 'Cancel subscription',
'dlg.cancelHint': 'The client loses subscription discounts and perks immediately.',
'dlg.reason': 'Reason',
'dlg.cancelConfirm': 'Cancel subscription',
'dlg.planTitle': 'Change plan',
'dlg.planConfirm': 'Change plan',
'dlg.refundTitle': 'Refund',
'dlg.refundPaid': 'Paid {sum}, already refunded {back}',
'dlg.refundCancel': 'Cancel the subscription too',
'dlg.refundConfirm': 'Issue refund',
'done.gift': 'Subscription gifted',
'done.sell': 'Payment recorded',
'done.extend': 'Term changed',
'done.cancel': 'Subscription cancelled',
'done.changePlan': 'Plan changed',
'done.refund': 'Refund issued',
'team.title': 'Team',
'team.lead': 'Who works in the admin and what they can access. One person can have several roles.',
'team.add': 'Add a person',
'team.name': 'Name',
'team.roles': 'Roles',
'team.create': 'Add',
'team.linkTitle': 'Link for {name}',
'team.linkHint': 'Send it to them. They open the work bot, Telegram gets linked, and they can sign in.',
'team.tgLinked': 'Telegram linked',
'team.tgNotLinked': 'Telegram not linked',
'team.newLink': 'Linking link',
'team.disable': 'Disable access',
'team.enable': 'Restore access',
'team.disabled': 'Access disabled',
'team.you': 'you',
'team.saved': 'Roles saved',
// ───── чаты (этап 2) ─────
'chat.title': 'Chats',
'chat.all': 'All',
'channel.SUPPORT': 'Support',
'channel.CONCIERGE': 'Concierge',
'chat.f.waiting': 'Awaiting reply',
'chat.f.mine': 'Mine',
'chat.f.unassigned': 'Unassigned',
'chat.f.open': 'Open',
'chat.f.closed': 'Closed',
'chat.f.all': 'All',
'chat.search': 'Name, @username, phone or text',
'chat.emptyList': 'Nothing here. New messages will appear on their own.',
'chat.emptyFilter': 'Nothing found — try another filter.',
'chat.pick': 'Pick a conversation',
'chat.pickHint': 'Those waiting longest are on top.',
'chat.waiting': 'waiting {t}',
'chat.you': 'You',
'chat.provider': 'Provider',
'chat.unassigned': 'Nobody assigned',
'chat.take': 'Take it',
'chat.transfer': 'Pass on',
'chat.transferTo': 'Pass to a colleague',
'chat.unassign': 'Remove assignee',
'chat.close': 'Close',
'chat.reopen': 'Reopen',
'chat.closedBanner': 'The conversation is closed. It reopens when the client writes; you can still reply now.',
'chat.moveTo': 'Move to {channel}',
'chat.moved': 'Moved to {channel}',
'chat.movedAway': 'Moved to {channel}. You have no access to that channel.',
'chat.other': 'There is also a {channel} conversation',
'chat.otherOpen': 'Open',
'chat.bot': 'The AI concierge is handling this conversation.',
'chat.botTake': 'Take over',
'chat.reply': 'Reply',
'chat.note': 'Note',
'chat.replyPh': 'Reply to the client — goes to their Telegram',
'chat.notePh': 'Note for the team — the client won’t see it',
'chat.send': 'Send',
'chat.saveNote': 'Save note',
'chat.attach': 'Attach a file',
'chat.templates': 'Templates',
'chat.tplManage': 'Manage templates',
'chat.tplEmpty': 'No templates yet.',
'chat.tplNew': 'New template',
'chat.tplTitle': 'Title',
'chat.tplText': 'Text',
'chat.tplTextHint': '{name} is replaced with the client’s name',
'chat.tplChannel': 'Channel',
'chat.tplBoth': 'Both channels',
'chat.tplDelete': 'Delete',
'chat.tplSaved': 'Template saved',
'chat.tplSearch': 'Find a template',
'chat.noteLabel': 'Note · team only',
'chat.fromApp': 'from the app',
'chat.undelivered': 'Not delivered: the client blocked the bot or never opened it',
'chat.fileTooBig': 'The file is larger than 10 MB',
'chat.enterHint': 'Enter to send · Shift+Enter for a new line',
'chat.providerNotLinked': 'The provider hasn’t opened the work bot yet — you can only leave a note for now.',
'chat.client': 'About the client',
'chat.aboutProvider': 'About the provider',
'chat.openCard': 'Client card',
'chat.write': 'Message',
'chat.back': 'All conversations',
'chat.sys.took': '{name} took the conversation',
'chat.sys.transferred': '{name} passed the conversation to {param}',
'chat.sys.unassigned': '{name} removed the assignee',
'chat.sys.closed': '{name} closed the conversation',
'chat.sys.reopened': '{name} reopened the conversation',
'chat.sys.moved': '{name} moved the conversation to {param}',
'chat.ago.now': 'just now',
'chat.ago.min': '{n} min',
'chat.ago.h': '{n} h',
'chat.ago.d': '{n} d',
'chat.today': 'Today',
'chat.yesterday': 'Yesterday',
'chat.image': 'Photo',
'chat.file': 'File',
'chat.subUntil': 'until {date}',
'chat.orders': 'Orders',
'chat.phone': 'Phone',
'chat.lang': 'Language',
'chat.source': 'Source',
'chat.linked': 'Work bot opened',
'chat.notLinked': 'Work bot not opened',
'chat.details': 'Details',
'chat.more': 'More actions',
// ───── партнёры и CRM (этап 4) ─────
'crm.title': 'CRM',
'crm.newLead': 'New lead',
'crm.editLead': 'Lead',
'crm.stagesBtn': 'Pipeline',
'crm.tab.board': 'Pipeline',
'crm.tab.tasks': 'Tasks',
'crm.tab.map': 'Map',
'crm.search': 'Name, contact, phone or address',
'crm.kind.all': 'All',
'crm.kind.VENUE': 'Venues',
'crm.kind.AGENCY': 'Agencies',
'crm.kind1.VENUE': 'Venue',
'crm.kind1.AGENCY': 'Agency',
'crm.owner': 'Sales rep',
'crm.allSales': 'All sales reps',
'crm.noOwner': 'Unassigned',
'crm.ownerIs': 'owned by {name}',
'crm.connected': 'Connected',
'crm.connect': 'Connecting',
'crm.days': '{n} d',
'crm.inStage': 'Days in this stage',
'crm.dropHere': 'Drop here',
'crm.dragHint': 'Drag cards between stages. “Connected” creates the partner or agency and gives you a link; “Lost” asks for a reason.',
'crm.overdue': 'overdue',
'crm.tasksOpen': 'Open',
'crm.tasksDone': 'Done',
'crm.addTask': 'Task',
'crm.noTasks': 'No open tasks.',
'crm.noDoneTasks': 'No completed tasks yet.',
'crm.noLead': 'no lead',
'crm.tasksHint': 'When a task is due you get a reminder in the work bot (if Telegram is linked).',
'crm.taskTitle': 'What to do',
'crm.taskDay': 'Day',
'crm.taskTime': 'Time',
'crm.taskHint': 'A reminder comes to the work bot at this time (Yerevan).',
'crm.tp.call': 'Call',
'crm.tp.meet': 'Meeting',
'crm.tp.send': 'Send the terms',
'crm.tp.check': 'Ask for a decision',
'crm.partnerOnMap': 'club partner',
'crm.legendPartner': 'connected partners',
'crm.legendLead': 'leads (stage colour)',
'crm.mapHint': 'A dot appears once a lead has coordinates.',
'crm.name': 'Name',
'crm.namePhVenue': 'E.g. Lumen Coffee',
'crm.namePhAgency': 'E.g. Domik Realty',
'crm.category': 'Type',
'crm.contactName': 'Contact person',
'crm.contactPh': 'Name and position',
'crm.address': 'Address',
'crm.note': 'Note',
'crm.convert': 'Connect',
'crm.convertTitle': 'Connect “{name}”',
'crm.convertVenueHint': 'We’ll create a club card partner and an owner link: the owner opens the work bot and can check client cards. Add offers in the venue card.',
'crm.convertAgencyHint': 'We’ll create the agency with a code and a client link: clients get a gift month and are attached to the agency.',
'crm.agencyCode': 'Agency code',
'crm.agencyCodeHint': 'Latin letters and digits; clients can type it in',
'crm.convertedTitle': 'Connected 🎉',
'crm.convertedVenue': 'Send this link to the venue owner. It works once.',
'crm.convertedAgency': 'The agency shares this link with clients.',
'crm.openVenue': 'Venue card',
'crm.openAgency': 'Agency card',
'crm.ownerLinked': 'The owner is already in the work bot.',
'crm.ownerNotYet': 'The owner hasn’t opened the link yet. Send it again:',
'crm.agencyInfo': 'Code {code}, clients: {n}',
'crm.lostTitle': 'Why lost?',
'crm.lostReason': 'Reason',
'crm.lr.price': 'Terms didn’t fit',
'crm.lr.notNow': 'Not now, come back later',
'crm.lr.noAnswer': 'Not responding',
'crm.lr.competitor': 'Work with a competitor',
'crm.lostBanner': 'Lost: {reason}',
'crm.stagesTitle': 'Pipeline stages',
'crm.stagesHint': 'Reorder with arrows. You need at least one open and one “Connected” stage. A stage with leads is hidden, not deleted.',
'crm.addStage': 'Stage',
'crm.stageKind.OPEN': 'open',
'crm.stageKind.WON': 'connected',
'crm.stageKind.LOST': 'lost',
'crm.bonusMonth': 'Bonus this month',
'crm.bonusMineSuper': 'Bonus (yours), month',
'crm.bonusNotSet': 'not set',
'crm.bonusVenues': 'Venues: {n} → {sum}',
'crm.bonusAgencies': 'Agencies: {n} → {sum}',
'crm.bonusRevenue': '{pct}% of agency client revenue → {sum}',
'crm.bonusTitle': 'Sales bonus formula',
'crm.bonusHint': 'Monthly bonus = connected venues × rate + agencies × rate + % of revenue from the rep’s agency clients (first N months). Revenue = paid orders and subscriptions.',
'crm.bonusPerVenue': 'Per venue, ֏',
'crm.bonusPerAgency': 'Per agency, ֏',
'crm.bonusPct': '% of agency client revenue',
'crm.bonusMonths': 'For how many months',
'crm.back': 'CRM',
'crm.created': 'since {date}',
'crm.stage': 'Stage',
'crm.history': 'Contact history',
'crm.noHistory': 'Empty so far — log the first call or meeting.',
'crm.act.CALL': 'Call',
'crm.act.MEETING': 'Meeting',
'crm.act.NOTE': 'Note',
'crm.act.FILE': 'File',
'crm.act.STAGE': 'Stage',
'crm.act.WON': 'Connected',
'crm.actPh.CALL': 'What did you agree on the call?',
'crm.actPh.MEETING': 'How did the meeting go, what’s next?',
'crm.actPh.NOTE': 'A note for yourself and the team',
'crm.addAct': 'Log it',
'crm.attach': 'Photo or file',
'crm.tasks': 'Tasks',
'crm.noLeadTasks': 'No tasks. Set the next step — you’ll get a reminder.',
'crm.contacts': 'Contacts',
'crm.noCoords': 'Not on the map yet.',
'crm.coordsPh': 'Google Maps link or “40.18, 44.51”',
'crm.coordsBad': 'No coordinates found — paste a Google Maps link or two numbers.',
'crm.remove': 'Delete lead',
'crm.removeConfirm': 'Delete the lead with its history and tasks?',
'venue.cat.cafe': 'Café',
'venue.cat.restaurant': 'Restaurant',
'venue.cat.shop': 'Shop',
'venue.cat.beauty': 'Beauty',
'venue.cat.other': 'Other',
'ag.title': 'Agencies',
'ag.add': 'New agency',
'ag.editTitle': 'Agency',
'ag.empty': 'No agencies yet.',
'ag.col.name': 'Agency',
'ag.col.clients': 'Clients',
'ag.col.gifts': 'Gifts',
'ag.col.month': 'Reward, month',
'ag.col.balance': 'To pay',
'ag.hint': 'Reward = % of paid orders of the agency’s clients while they’re attached.',
'ag.inactive': 'inactive',
'ag.back': 'All agencies',
'ag.pct': '{n}% of client orders',
'ag.byS': 'connected by {name}',
'ag.link': 'Client link',
'ag.linkHint': 'The client opens the bot, gets a gift month and is attached to the agency. Or types code {code} via /code.',
'ag.clients': 'Clients',
'ag.giftsN': 'gifts: {n}',
'ag.noClients': 'No clients yet.',
'ag.orders': 'orders: {n}',
'ag.toPay': 'Reward to pay',
'ag.accrued': 'Accrued',
'ag.payouts': 'Payouts',
'ag.payoutTitle': 'Payout to agency',
'ag.balanceHint': 'Accrued and unpaid: {sum}',
'ag.pctLabel': 'Reward, %',
'ag.sales': 'Connected by',
'ag.contactPh': 'Name, phone, Telegram',
'ag.active': 'Agency active (code accepted)',
'vn.title': 'Venues',
'vn.add': 'New venue',
'vn.editTitle': 'Venue',
'vn.empty': 'No venues yet.',
'vn.col.name': 'Venue',
'vn.col.offers': 'Offers',
'vn.col.staff': 'Staff',
'vn.col.visits': 'Checks, 30 d',
'vn.col.last': 'Last check',
'vn.hint': 'A check = venue staff scanned a client’s club card in the work bot.',
'vn.noOwner': 'no owner',
'vn.noOffers': 'no offers',
'vn.back': 'All venues',
'vn.ownerHint': 'The owner isn’t connected yet — send them a one-time work bot link.',
'vn.makeLink': 'Create link',
'vn.offers': 'Offers by level',
'vn.addOffer': 'Offer',
'vn.editOffer': 'Offer',
'vn.noOffersHint': 'Add what members get: a discount, a gift, a treat.',
'vn.level.any': 'Any member',
'vn.level.BAREV_PLUS': 'Barev+ and Elite',
'vn.level.ELITE': 'Elite only',
'vn.limit.NONE': 'unlimited',
'vn.limit.ONCE': 'once',
'vn.limit.WEEK': '{n}× a week',
'vn.limit.MONTH': '{n}× a month',
'vn.limitOpt.NONE': 'Unlimited',
'vn.limitOpt.ONCE': 'First visit only',
'vn.limitOpt.WEEK': 'N times a week',
'vn.limitOpt.MONTH': 'N times a month',
'vn.offerOff': 'off',
'vn.offerTitle': 'What the client gets',
'vn.offerTitleHint': 'E.g. “Free cappuccino” or “−15% on the menu”',
'vn.forWhom': 'For whom',
'vn.howOften': 'How often',
'vn.times': 'Times',
'vn.offerActive': 'Offer active',
'vn.activity': 'Activity',
'vn.weeks8': 'last 8 weeks',
'vn.checks': 'card checks',
'vn.redeemed': 'offers redeemed',
'vn.cardCheck': 'card check',
'vn.staff': 'Staff',
'vn.noStaff': 'Nobody yet.',
'vn.role.OWNER': 'owner',
'vn.role.STAFF': 'staff',
'vn.removeStaff': 'Remove {name} from the venue?',
'vn.staffHint': 'Staff are invited by the owner in the work bot (24-hour QR).',
'vn.newOwnerLink': 'Owner link',
'vn.newOwnerLinkHint': 'A new one-time link — e.g. if the owner changed',
'vn.blurb': 'Short offer line (shown to clients)',
'vn.blurbHint': 'E.g. “−10% with the club card”',
'vn.coords': 'Map point',
'vn.activeLabel': 'Visible to clients',
'err.LEAD_NOT_CONVERTED': 'To move to “Connected”, use “Connect” — it creates the partner.',
'err.ALREADY_CONVERTED': 'The lead is already connected.',
'err.AGENCY_CODE_FORMAT': 'Code: Latin letters, digits and “_”, up to 32.',
'err.AGENCY_CODE_TAKEN': 'This code is already taken.',
'err.STAGES_INVALID': 'You need at least one open and one “Connected” stage.',
'audit.bo.crm.create': 'added a lead',
'audit.bo.crm.update': 'edited a lead',
'audit.bo.crm.move': 'moved a lead',
'audit.bo.crm.convert': 'connected a partner',
'audit.bo.crm.addActivity': 'logged a contact',
'audit.bo.crm.saveStages': 'edited the pipeline',
'audit.bo.crm.setBonusRules': 'changed the bonus formula',
'audit.bo.partners.saveAgency': 'edited an agency',
'audit.bo.partners.agencyPayout': 'recorded an agency payout',
'audit.bo.partners.saveVenue': 'edited a venue',
'audit.bo.partners.saveOffer': 'edited a venue offer',
'audit.bo.partners.ownerInvite': 'issued an owner link',
'audit.bo.partners.removeMember': 'removed venue staff',
// ───── заказы и исполнители (этап 3) ─────
'ord.title': 'Orders',
'ord.new': 'New order',
'ord.search': 'No., client, phone, address or provider',
'ord.period': 'Period',
'ord.period.all': 'All dates',
'ord.period.today': 'Today',
'ord.period.tomorrow': 'Tomorrow',
'ord.period.week': '7 days',
'ord.period.past': 'Past',
'ord.group.active': 'Active',
'ord.group.new': 'Need a provider',
'ord.group.pending': 'Offered',
'ord.group.assigned': 'Assigned',
'ord.group.in_progress': 'In progress',
'ord.group.done': 'Done',
'ord.group.cancelled': 'Cancelled',
'ord.today': 'Today',
'ord.tomorrow': 'Tomorrow',
'ord.empty': 'No orders match these filters.',
'ord.waitsAnswer': 'awaiting: {name}',
'ord.needsHuman': 'needs a dispatcher',
'ord.searching': 'auto-assigning…',
'ord.overdue': 'time passed, no provider',
'ord.needsDispatcher': 'Auto-assignment found no provider for {n} order(s). Assign manually.',
'ord.autoOn': 'Auto-assign on',
'ord.autoOff': 'Auto-assign off',
'ord.autoHint': 'A new order is offered to the best free provider (client language, district, load, rating). No answer in {minutes} min or a decline — the next one; after {tries} tries — to a dispatcher.',
'ord.back': 'All orders',
'ord.progress': 'Progress',
'ord.details': 'Details',
'ord.when': 'When',
'ord.where': 'Where',
'ord.minutes': '{n} min',
'ord.params': 'Details',
'ord.extras': 'Extras',
'ord.note': 'Client comment',
'ord.lang': 'Client language',
'ord.created': 'Created',
'ord.checklist': 'Checklist',
'ord.needsPhoto': 'photo needed',
'ord.photo': 'Photo',
'ord.history': 'History',
'ord.client': 'Client',
'ord.writeClient': 'Message the client',
'ord.writeProvider': 'Message the provider',
'ord.call': 'Call',
'ord.noPhone': 'No phone number — add it to the profile',
'ord.money': 'Money',
'ord.base': 'Before discount',
'ord.discount': 'Discount {pct}%',
'ord.payout': 'To the provider',
'ord.cancelFee': 'Cancellation fee',
'ord.payment': 'Payment',
'ord.markPaid': 'Mark as paid',
'ord.confirmPaid': 'Mark the order as paid?',
'ord.paidDone': 'Marked as paid',
'ord.actions': 'Actions',
'ord.setStatus': 'Status: {status}',
'ord.confirmStatus': 'Move the order to “{status}”? The client will be notified.',
'ord.statusChanged': 'Status changed',
'ord.reschedule': 'Reschedule',
'ord.rescheduleTitle': 'Reschedule order #{n}',
'ord.rescheduleHint': 'If the provider is busy at the new time, the order goes back to “Need a provider” and to auto-assignment.',
'ord.rescheduled': 'Rescheduled, same provider',
'ord.rescheduledFree': 'Rescheduled; the provider is busy — looking for a new one',
'ord.comment': 'Comment',
'ord.commentPh': 'E.g. the client asked by phone',
'ord.cancel': 'Cancel order',
'ord.cancelTitle': 'Cancel the order',
'ord.cancelReason': 'Reason',
'ord.cancelReasonPh': 'E.g. the client changed their mind',
'ord.cancelFeeHint': 'How much to charge the client, ֏. Usually 0.',
'ord.cancelHint': 'The client and the provider will be notified.',
'ord.cancelled': 'Order cancelled',
'ord.rating': 'Client rating',
'ord.noComment': 'No comment',
'ord.offers': 'Offers',
'ord.bySystem': 'system',
'ord.provider': 'Provider',
'ord.unassign': 'Remove provider',
'ord.revoke': 'Withdraw offer',
'ord.confirmUnassign': 'Remove the provider? The order goes back to “Need a provider”.',
'ord.confirmRevoke': 'Withdraw the offer? The order will wait for a provider again.',
'ord.unassigned': 'Done — the order needs a provider again',
'ord.pendingProvider': 'Offered to {name}',
'ord.pendingCompany': 'Passed to {name} — waiting for their dispatcher',
'ord.byAuto': 'offered automatically',
'ord.minLeft': '≈ {n} min to answer',
'ord.pickHint': 'Free at this time, best match first. Or let the system pick.',
'ord.autoPick': 'Pick automatically',
'ord.autoOffered': 'Offered to {name}',
'ord.autoNone': 'No free provider found',
'ord.noFree': 'Everyone is busy at this time. Reschedule or arrange with a provider.',
'ord.busy': 'Busy at this time: {n}',
'ord.company': 'company',
'ord.tried': 'already offered',
'ord.load': '{n} orders that day',
'ord.offer': 'Offer',
'ord.offered': 'Offer sent',
'ord.noProvider': 'No provider was assigned.',
'ord.ev.created': 'Order created',
'ord.ev.createdByStaff': 'Created by the team',
'ord.ev.offered': 'Offered to a provider',
'ord.ev.autoOffered': 'Auto-assign: offered',
'ord.ev.autoNoCandidate': 'Auto-assign: nobody free',
'ord.ev.autoGaveUp': 'Auto-assign stopped — needs a dispatcher',
'no.title': 'New order',
'no.client': 'Client',
'no.clientPh': 'Name, @username or phone',
'no.noClients': 'Nobody found',
'no.changeClient': 'Another client',
'no.service': 'Service',
'no.extras': 'Extras',
'no.address': 'Address',
'no.addressPh': 'Street, building, apartment',
'no.district': 'District',
'no.when': 'Date and time',
'no.day': 'Day',
'no.noSlots': 'No free time that day — pick another day or “other time”.',
'no.otherTime': 'Other time (arranged with a provider directly)',
'no.customTime': 'Time',
'no.customHint': 'Yerevan time. A free provider is not guaranteed.',
'no.note': 'Comment for the provider',
'no.notePh': 'Door code, pets…',
'no.payment': 'Payment',
'no.hint': 'The price includes the client’s subscription discount. The client is notified and the order goes to auto-assignment.',
'no.create': 'Create order',
'no.created': 'Order #{n} created',
'prv.title': 'Providers',
'prv.add': 'Add',
'prv.search': 'Name or phone',
'prv.status.active': 'Active',
'prv.status.blocked': 'Blocked',
'prv.status.all': 'All',
'prv.empty': 'Nobody found.',
'prv.col.name': 'Provider',
'prv.col.rating': 'Rating',
'prv.col.done': 'Orders',
'prv.col.refused': 'Declines',
'prv.col.next': 'Next order',
'prv.period30': 'Orders, declines and low ratings — last 30 days.',
'prv.blocked': 'blocked',
'prv.onShift': 'on shift',
'prv.offShift': 'off shift',
'prv.notLinked': 'bot not opened',
'prv.noDocs': 'no documents',
'prv.ratings': '{n} ratings',
'prv.low': '{n} low',
'prv.today': 'today: {n}',
'prv.back': 'All providers',
'prv.write': 'Message',
'prv.edit': 'Edit',
'prv.blockedSince': 'Blocked since {date}.',
'prv.unblock': 'Unblock',
'prv.inviteHint': 'The provider hasn’t opened the work bot yet — send them the link.',
'prv.copyInvite': 'Copy link',
'prv.quality': 'Quality',
'prv.days30': 'last 30 days',
'prv.acceptRate': 'accepted {a} of {n} offers',
'prv.refusals': 'declined: {d}, no answer: {e}',
'prv.lowRatings': 'ratings of 3 or less',
'prv.upcoming': 'Upcoming orders',
'prv.noUpcoming': 'No assigned orders.',
'prv.recent': 'Recently done',
'prv.balance': 'To pay',
'prv.thisMonth': 'This month',
'prv.prevMonth': 'Last month',
'prv.paidTotal': 'Paid',
'prv.payout': 'Record a payout',
'prv.payoutTitle': 'Payout to provider',
'prv.amount': 'Amount, ֏',
'prv.balanceHint': 'Owed to the provider: {sum}',
'prv.payoutNote': 'How it was paid',
'prv.payoutNotePh': 'Cash / card transfer…',
'prv.payoutConfirm': 'Paid',
'prv.payoutDone': 'Payout recorded',
'prv.rateCompany': 'company rate {v}',
'prv.rateOwn': 'rate {v}',
'prv.ratePreset': 'preset “{name}”',
'prv.work': 'Work',
'prv.languages': 'Languages',
'prv.districts': 'Districts',
'prv.anyDistrict': 'any',
'prv.districtsHint': 'Assignment favors providers working in the order’s district.',
'prv.docs': 'Admission documents',
'prv.noDocsHint': 'Passport, contract, certificate — kept in private storage.',
'prv.docTitlePh': 'Title: passport, contract…',
'prv.upload': 'Upload',
'prv.docAdded': 'Document added',
'prv.removeDocConfirm': 'Delete the document?',
'prv.access': 'Access',
'prv.block': 'Block',
'prv.blockTitle': 'Block the provider',
'prv.blockReason': 'Reason',
'prv.blockReasonPh': 'E.g. client complaints, missing documents',
'prv.blockHint': 'No new offers; pending offers are withdrawn. Already assigned orders stay — reassign them manually.',
'prv.resetInvite': 'New bot link',
'prv.resetConfirm': 'Create a new link? The current Telegram link is removed — the provider will need to log in again.',
'prv.since': 'With us since {date}',
'prv.saved': 'Saved',
'prv.addTitle': 'New provider',
'prv.editTitle': 'Provider profile',
'prv.name': 'Name',
'prv.role': 'Role',
'prv.company': 'Company',
'prv.freelance': 'Freelancer',
'prv.schedule': 'Schedule',
'prv.rate': 'Rate',
'prv.note': 'Team note',
'err.REASON_REQUIRED': 'Please give a reason.',
'err.SLOT_UNAVAILABLE': 'This time is taken or has passed. Pick another one.',
'err.ALREADY_ASSIGNED': 'The order is already assigned or offered — refresh the page.',
'err.PROVIDER_BUSY': 'The provider is busy at this time.',
'err.TRANSITION_NOT_ALLOWED': 'This step isn’t available for the order now.',
'err.CHECKLIST_INCOMPLETE': 'The provider must finish the checklist and add photos first.',
'err.CONSENT_REQUIRED': 'The client hasn’t given data-processing consent in the bot yet.',
'err.ADDRESS_REQUIRED': 'Please enter the address and district.',
'err.INVALID_PARAMS': 'Check the order details.',
'err.OFFER_NOT_ACTIVE': 'The offer is no longer active.',
'err.BAD_FILE_TYPE_DOC': 'Photo or PDF only.',
'audit.bo.orders.assign': 'offered an order',
'audit.bo.orders.auto': 'ran auto-assignment',
'audit.bo.orders.unassign': 'removed a provider from an order',
'audit.bo.orders.transition': 'changed an order status',
'audit.bo.orders.cancel': 'cancelled an order',
'audit.bo.orders.reschedule': 'rescheduled an order',
'audit.bo.orders.markPaid': 'marked an order as paid',
'audit.bo.orders.create': 'created an order for a client',
'audit.bo.orders.setAutoSetting': 'changed auto-assignment',
'audit.bo.providers.create': 'added a provider',
'audit.bo.providers.update': 'edited a provider',
'audit.bo.providers.setActive': 'changed provider access',
'audit.bo.providers.resetInvite': 'reissued a provider link',
'audit.bo.providers.removeDoc': 'deleted a provider document',
'audit.bo.providers.addDoc': 'uploaded a provider document',
'audit.bo.providers.payout': 'recorded a payout',
'chat.order': 'Order #{n}',
'chat.noOrder': 'No order',
'chat.noOrderNow': 'No current order',
'chat.orderNow': 'Now',
'chat.orderNext': 'Next',
'chat.orderNoNext': 'No upcoming orders',
'chat.orderClient': 'client {name}',
'chat.wroteNoOrder': 'wrote without an order',
'err.CONCIERGE_SUBSCRIBERS_ONLY': 'The concierge is for members only. Give the client a subscription first.',
'err.ASSIGNEE_NO_ACCESS': 'This team member has no access to this channel.',
'err.PROVIDER_NOT_LINKED': 'The provider hasn’t opened the work bot yet.',
'err.BAD_FILE_TYPE': 'This file type isn’t supported. Use a photo, PDF, Word, Excel, text or ZIP.',
'audit.bo.chats.send': 'replied in a chat',
'audit.bo.chats.sendFile': 'sent a file in a chat',
'audit.bo.chats.assign': 'assigned a chat',
'audit.bo.chats.close': 'closed a conversation',
'audit.bo.chats.reopen': 'reopened a conversation',
'audit.bo.chats.move': 'moved a conversation to another channel',
'audit.bo.chats.openFor': 'opened a chat with a client',
'audit.bo.chats.templates.save': 'edited a reply template',
'audit.bo.chats.templates.remove': 'deleted a reply template',
};
const hy: Dict = {
'ui.save': 'Պահպանել',
'ui.close': 'Փակել',
'ui.loading': 'Բեռնվում է…',
'ui.error': 'Չստացվեց՝ {msg}',
'ui.retry': 'Կրկնել',
'ui.copy': 'Պատճենել',
'ui.copied': 'Պատճենված է',
'ui.days': '{n} օր',
'ui.yes': 'Այո',
'ui.no': 'Ոչ',
'ui.none': '—',
'err.PAYMENTS_NOT_CONFIGURED': 'Առցանց վճարումները դեռ միացված չեն․ նշեք վճարումը ձեռքով։',
'err.REFUND_TOO_BIG': 'Վերադարձի գումարը մեծ է հաճախորդի վճարածից։',
'err.ENDS_BEFORE_START': 'Բաժանորդագրությունը չի կարող ավարտվել սկսվելուց առաջ։',
'err.CANNOT_DEMOTE_SELF': 'Չեք կարող անջատել ինքներդ ձեզ կամ հանել ձեր սուպերադմինի դերը։',
'err.ROLE_FORBIDDEN': 'Ձեր դերը մուտք չունի այս գործողությանը։',
'err.NO_ROLE': 'Ձեր հաշիվը նոր ադմինում դերեր չունի։ Խնդրեք սուպերադմինին տրամադրել։',
'login.coverWord': 'թիմ',
'login.title': 'Մուտք թիմի համար',
'login.lead': 'Հաստատեք մուտքը Barev Club-ի աշխատանքային բոտում։ Գաղտնաբառ պետք չէ։',
'login.open': 'Հաստատել Telegram-ում',
'login.qr': 'Համակարգչից հարմար է կոդը սկանավորել հեռախոսով։',
'login.waiting': 'Սպասում ենք հաստատմանը Telegram-ում…',
'login.expired': 'Հղումը հնացել է։',
'login.retry': 'Ստանալ նոր հղում',
'login.dev': 'Տեղային մուտք',
'login.devHint': 'Միայն այս համակարգչում․ սերվերում այս բլոկը չկա։',
'login.noTelegram': 'Մուտք չունե՞ք։ Խնդրեք սուպերադմինին ավելացնել ձեզ թիմում և ուղարկել Telegram-ի կապման հղում։',
'nav.dashboard': 'Վահանակ',
'nav.clients': 'Հաճախորդներ',
'nav.chats': 'Չատեր',
'nav.orders': 'Պատվերներ',
'nav.providers': 'Կատարողներ',
'nav.agencies': 'Գործակալություններ',
'nav.venues': 'Հաստատություններ',
'nav.crm': 'CRM',
'nav.products': 'Ապրանքներ',
'nav.journal': 'Մատյան',
'nav.team': 'Թիմ',
'nav.more': 'Ավելին',
'nav.soon': 'փուլ {n}',
'nav.groupWork': 'Աշխատանք',
'nav.groupPartners': 'Գործընկերներ',
'nav.groupSetup': 'Կարգավորում',
'role.SUPERADMIN': 'Սուպերադմին',
'role.SUPPORT': 'Աջակցություն',
'role.CONCIERGE': 'Կոնսիերժ',
'role.SALES': 'Վաճառք',
'roleHint.SUPERADMIN': 'Ամեն ինչ, ներառյալ գումարներն ու թիմը',
'roleHint.SUPPORT': 'Աջակցության չատ, պատվերներ, բաժանորդագրություններ',
'roleHint.CONCIERGE': 'Կոնսիերժի չատ բաժանորդների համար',
'roleHint.SALES': 'CRM՝ հաստատություններ և գործակալություններ',
'shell.logout': 'Ելք',
'shell.oldAdmin': 'Հին ադմին',
'shell.linkTg': 'Կապեք Telegram-ը․ դրանով եք մուտք գործում և ստանում ծանուցումներ։',
'shell.linkTgBtn': 'Կապել Telegram-ը',
'soon.title': '{section} բաժինը տեղափոխվում է այստեղ',
'soon.text': 'Բաժինը կհայտնվի {n}-րդ փուլում։ Մինչ այդ աշխատեք հին ադմինում․ տվյալները ընդհանուր են։',
'soon.open': 'Բացել հին ադմինը',
'dash.morning': 'Բարի լույս, {name}',
'dash.day': 'Բարի օր, {name}',
'dash.evening': 'Բարի երեկո, {name}',
'dash.attention': 'Պահանջում է ուշադրություն',
'dash.allClear': 'Շտապ ոչինչ չկա․ ամեն ինչ արված է։',
'att.unassigned': 'Պատվերներ առանց կատարողի',
'att.unreadChats': 'Պատասխանի սպասող զրույցներ',
'att.webRequests': 'Հայտեր կայքից',
'att.leads': 'Տեղափոխման հայտեր',
'att.appRequests': 'Հայտեր հավելվածից',
'att.lowRatings': '3 և ցածր գնահատականներ այս շաբաթ',
'att.expiring': 'Ավարտվում են 7 օրում',
'dash.money': 'Գումար',
'dash.today': 'Այսօր',
'dash.week': '7 օր',
'dash.month': '30 օր',
'dash.vsYesterday': 'երեկ՝ {sum}',
'dash.vsPrev': 'նախորդ {period}-ի համեմատ',
'dash.orders': 'պատվերներ',
'dash.subs': 'բաժանորդագրություններ',
'dash.chart': 'Եկամուտն ըստ օրերի, 30 օր',
'dash.subsTitle': 'Բաժանորդագրություններ',
'dash.gifts': 'Որից նվեր՝ {n}',
'dash.expiring': 'Ավարտվում են առաջիկա 7 օրում',
'dash.noExpiring': 'Առաջիկա շաբաթ ոչինչ չի ավարտվում։',
'dash.conversion': 'Նվեր → գնում',
'dash.conversionHint': 'Նվեր ստացած {total} հաճախորդից {paid}-ը հետո գնել են',
'dash.growth': 'Աճ',
'dash.newClients': 'Նոր հաճախորդներ',
'dash.prevMonth': 'նախորդ 30 օրում՝ {n}',
'dash.sources': 'Որտեղից են եկել, 30 օր',
'dash.funnel': 'Ձագար, 30 օր',
'funnel.leads': 'Հայտեր կայքից',
'funnel.clients': 'Հաճախորդներ հավելվածում',
'funnel.paying': 'Վճարել են',
'dash.team': 'Թիմ և գործընկերներ',
'dash.topProviders': 'Լավագույն կատարողներ',
'dash.bottomProviders': 'Արժե խոսել',
'dash.topPartners': 'Հաստատություններ՝ քարտի սկանավորումներ, 30 օր',
'dash.salesSoon': 'Վաճառողների արդյունքները կհայտնվեն CRM-ի հետ։',
'dash.empty': 'Դեռ դատարկ է',
'dash.feed': 'Լրահոս',
'feed.subscription': '{plan} · {source}',
'feed.payment': '№{number} պատվերը վճարված է',
'dash.ratings': '{n} գնահատական',
'dash.scans': '{n} սկան',
'source.organic': 'Ինքն են գտել',
'source.deeplink': 'Գործակալության հղում',
'source.manual_code': 'Գործակալության կոդ',
'source.agency': '«{name}» գործակալություն',
'source.utm': 'Գովազդ՝ {name}',
'plan.BAREV_PLUS': 'Barev+',
'plan.ELITE': 'Elite',
'plan.none': 'Առանց բաժանորդագրության',
'subSource.PAID': 'Գնում',
'subSource.MANUAL': 'Թիմի նվեր',
'subSource.AGENCY_GIFT': 'Գործակալության նվեր',
'subStatus.ACTIVE': 'Ակտիվ',
'subStatus.EXPIRED': 'Ավարտված',
'subStatus.CANCELLED': 'Չեղարկված',
'pay.cash': 'Կանխիկ',
'pay.transfer': 'Փոխանցում',
'pay.card': 'Քարտ տերմինալով',
'pay.link': 'Վճարման հղում',
'segment.MOVING': 'Տեղափոխվում է',
'segment.LIVING': 'Ապրում է Հայաստանում',
'clients.title': 'Հաճախորդներ',
'clients.search': 'Անուն, @username, հեռախոս կամ քարտի համար',
'clients.found': 'Գտնվել է՝ {n}',
'clients.revenueTotal': 'բերել են {sum}',
'col.client': 'Հաճախորդ',
'col.sub': 'Բաժանորդագրություն',
'col.source': 'Աղբյուր',
'col.revenue': 'Բերել է',
'col.since': 'Մեզ հետ է',
'filter.plan': 'Բաժանորդագրություն',
'filter.all': 'Բոլորը',
'filter.any': 'Բաժանորդագրությամբ',
'filter.none': 'Առանց բաժանորդագրության',
'filter.subSource': 'Ինչպես է ստացել',
'filter.source': 'Աղբյուր',
'filter.agency': 'Գործակալություն',
'filter.tag': 'Պիտակ',
'filter.segment': 'Սցենար',
'filter.paying': 'Վճարել են',
'filter.payingYes': 'Վճարել են',
'filter.payingNo': 'Երբեք չեն վճարել',
'filter.expiring': 'Ավարտվում է 7 օրում',
'filter.reset': 'Զրոյացնել ֆիլտրերը',
'filter.more': 'Ֆիլտրեր',
'filter.anyValue': 'Ցանկացած',
'sort.label': 'Հերթականություն',
'sort.new': 'Նախ նորերը',
'sort.revenue': 'Ամենաշատը բերածները',
'sort.ends': 'Շուտով ավարտվող',
'segments.title': 'Իմ ընտրանիները',
'segments.save': 'Պահպանել ընտրանին',
'segments.name': 'Ընտրանու անունը',
'segments.saved': 'Ընտրանին պահպանված է',
'segments.remove': 'Ջնջել «{name}» ընտրանին',
'clients.export': 'Ներբեռնել Excel-ի համար',
'clients.exported': 'Ֆայլը ներբեռնված է',
'clients.broadcast': 'Առաքում',
'clients.broadcastSoon': 'Ըստ ընտրանու առաքումները կհայտնվեն 5-րդ փուլում։',
'clients.empty': 'Այս ֆիլտրերին ոչ ոք չի համապատասխանում։',
'clients.emptyAll': 'Հաճախորդներ դեռ չկան․ կհայտնվեն, երբ գրեն բոտին։',
'clients.prev': 'Հետ',
'clients.next': 'Առաջ',
'clients.page': '{from}–{to}՝ {total}-ից',
'card.back': 'Բոլոր հաճախորդները',
'card.since': 'Մեզ հետ է {date}-ից',
'card.telegram': 'Բացել Telegram-ում',
'card.cardNo': 'Քարտ {code}',
'card.noSub': 'Ակտիվ բաժանորդագրություն չկա',
'card.noSubHint': 'Նվիրեք կամ վաճառեք բաժանորդագրություն․ հաճախորդը միանգամից կստանա զեղչեր։',
'card.until': 'մինչև {date}',
'card.daysLeft': 'մնաց {n} օր',
'card.history': 'Բոլոր բաժանորդագրությունները',
'card.grantedBy': 'տրամադրել է {name}',
'card.giftFrom': 'նվեր «{name}»-ից',
'card.paidVia': '{method}',
'card.refunded': 'վերադարձ {sum}',
'card.cancelledAt': 'չեղարկված {date}',
'card.upcoming': 'կսկսվի {date}',
'card.money': 'Բերել է',
'card.fromOrders': 'պատվերներ',
'card.fromSubs': 'բաժանորդագրություններ',
'card.orders': 'Պատվերներ',
'card.noOrders': 'Պատվերներ դեռ չկան։',
'card.newOrder': 'Ստեղծել պատվեր',
'card.newOrderSoon': 'Պատվեր հաճախորդի անունից՝ 3-րդ փուլում, պատվերների բաժնի հետ։',
'card.profile': 'Պրոֆիլ',
'card.source': 'Որտեղից է եկել',
'card.agency': 'Գործակալություն',
'card.language': 'Լեզու',
'card.phone': 'Հեռախոս',
'card.segment': 'Սցենար',
'card.consent': 'Տվյալների մշակման համաձայնություն',
'card.tags': 'Պիտակներ',
'card.addTag': 'Նոր պիտակ',
'card.note': 'Թիմի նշում',
'card.notePh': 'Հաճախորդը չի տեսնում այս նշումը',
'card.saved': 'Պահպանված է',
'card.activity': 'Հաճախորդի մատյան',
'card.noActivity': 'Թիմը դեռ ոչինչ չի փոխել։',
'card.stats': 'Ակտիվություն',
'stat.cardUsages': 'քարտի սկան',
'stat.leads': 'տեղափոխման հայտ',
'stat.requests': 'հայտ հավելվածից',
'stat.concierge': 'հաղորդագրություն չատում',
'act.gift': 'Նվիրել',
'act.sell': 'Վաճառել',
'act.extend': 'Փոխել ժամկետը',
'act.cancel': 'Չեղարկել',
'act.changePlan': 'Փոխել սակագինը',
'act.refund': 'Վերադարձնել գումարը',
'audit.bo.clients.gift': 'նվիրել է բաժանորդագրություն',
'audit.bo.clients.sell': 'վաճառել է բաժանորդագրություն',
'audit.bo.clients.extend': 'փոխել է ժամկետը',
'audit.bo.clients.cancel': 'չեղարկել է բաժանորդագրությունը',
'audit.bo.clients.changePlan': 'փոխել է սակագինը',
'audit.bo.clients.refund': 'ձևակերպել է վերադարձ',
'audit.bo.clients.setTags': 'փոխել է պիտակները',
'audit.bo.clients.setNote': 'փոխել է նշումը',
'dlg.giftTitle': 'Նվիրել բաժանորդագրություն',
'dlg.giftHint': 'Այն կնշվի որպես ձեր նվերը։',
'dlg.sellTitle': 'Վաճառել բաժանորդագրություն',
'dlg.plan': 'Սակագին',
'dlg.period': 'Ժամկետ',
'dlg.period1': '1 ամիս',
'dlg.period3': '3 ամիս',
'dlg.period6': '6 ամիս',
'dlg.period12': '1 տարի',
'dlg.periodCustom': 'Այլ',
'dlg.days': 'Օր',
'dlg.amount': 'Գումար, ֏',
'dlg.method': 'Ինչպես է վճարել',
'dlg.note': 'Մեկնաբանություն թիմի համար',
'dlg.linkSoon': 'Վճարման հղումը կմիացնենք վճարային համակարգը միացնելուց հետո։',
'dlg.giftConfirm': 'Նվիրել',
'dlg.sellConfirm': 'Նշել վճարումը',
'dlg.extendTitle': 'Փոխել ժամկետը',
'dlg.extendHint': 'Բացասական թիվը կրճատում է ժամկետը։',
'dlg.newEnd': 'Նոր ավարտի ամսաթիվ՝ {date}',
'dlg.extendConfirm': 'Պահպանել ժամկետը',
'dlg.cancelTitle': 'Չեղարկել բաժանորդագրությունը',
'dlg.cancelHint': 'Հաճախորդը միանգամից կկորցնի զեղչերն ու արտոնությունները։',
'dlg.reason': 'Պատճառ',
'dlg.cancelConfirm': 'Չեղարկել բաժանորդագրությունը',
'dlg.planTitle': 'Փոխել սակագինը',
'dlg.planConfirm': 'Փոխել սակագինը',
'dlg.refundTitle': 'Վերադարձնել գումարը',
'dlg.refundPaid': 'Վճարված է {sum}, արդեն վերադարձված՝ {back}',
'dlg.refundCancel': 'Միանգամից չեղարկել բաժանորդագրությունը',
'dlg.refundConfirm': 'Ձևակերպել վերադարձ',
'done.gift': 'Բաժանորդագրությունը նվիրված է',
'done.sell': 'Վճարումը նշված է',
'done.extend': 'Ժամկետը փոխված է',
'done.cancel': 'Բաժանորդագրությունը չեղարկված է',
'done.changePlan': 'Սակագինը փոխված է',
'done.refund': 'Վերադարձը ձևակերպված է',
'team.title': 'Թիմ',
'team.lead': 'Ով է աշխատում ադմինում և ինչ հասանելիություն ունի։ Մեկ մարդը կարող է ունենալ մի քանի դեր։',
'team.add': 'Ավելացնել մարդու',
'team.name': 'Անուն',
'team.roles': 'Դերեր',
'team.create': 'Ավելացնել',
'team.linkTitle': 'Հղում {name}-ի համար',
'team.linkHint': 'Ուղարկեք նրան։ Կբացի աշխատանքային բոտը, Telegram-ը կկապվի, և կարող է մուտք գործել։',
'team.tgLinked': 'Telegram-ը կապված է',
'team.tgNotLinked': 'Telegram-ը կապված չէ',
'team.newLink': 'Կապման հղում',
'team.disable': 'Անջատել մուտքը',
'team.enable': 'Վերադարձնել մուտքը',
'team.disabled': 'Մուտքն անջատված է',
'team.you': 'դուք',
'team.saved': 'Դերերը պահպանված են',
// ───── чаты (этап 2) ─────
'chat.title': 'Զրույցներ',
'chat.all': 'Բոլորը',
'channel.SUPPORT': 'Աջակցություն',
'channel.CONCIERGE': 'Կոնսիերժ',
'chat.f.waiting': 'Սպասում են պատասխանի',
'chat.f.mine': 'Իմը',
'chat.f.unassigned': 'Առանց պատասխանատուի',
'chat.f.open': 'Բաց',
'chat.f.closed': 'Փակ',
'chat.f.all': 'Բոլորը',
'chat.search': 'Անուն, @username, հեռախոս կամ տեքստ',
'chat.emptyList': 'Այստեղ դատարկ է։ Նոր հաղորդագրությունները կհայտնվեն ինքնուրույն։',
'chat.emptyFilter': 'Ոչինչ չգտանք․ փորձեք այլ ֆիլտր։',
'chat.pick': 'Ընտրեք զրույցը',
'chat.pickHint': 'Վերևում նրանք են, ովքեր ամենաերկար են սպասում։',
'chat.waiting': 'սպասում է {t}',
'chat.you': 'Դուք',
'chat.provider': 'Կատարող',
'chat.unassigned': 'Պատասխանատու չկա',
'chat.take': 'Վերցնել ինձ',
'chat.transfer': 'Փոխանցել',
'chat.transferTo': 'Փոխանցել գործընկերոջը',
'chat.unassign': 'Հանել պատասխանատուին',
'chat.close': 'Փակել',
'chat.reopen': 'Կրկին բացել',
'chat.closedBanner': 'Զրույցը փակ է։ Կբացվի, երբ հաճախորդը գրի․ կարող եք պատասխանել նաև հիմա։',
'chat.moveTo': 'Տեղափոխել «{channel}»',
'chat.moved': 'Տեղափոխվեց «{channel}»',
'chat.movedAway': 'Տեղափոխվեց «{channel}»։ Դուք մուտք չունեք այդ ալիքին։',
'chat.other': 'Կա նաև զրույց «{channel}» ալիքում',
'chat.otherOpen': 'Բացել',
'chat.bot': 'Զրույցը վարում է ԱԲ կոնսիերժը։',
'chat.botTake': 'Վերցնել',
'chat.reply': 'Պատասխան',
'chat.note': 'Նշում',
'chat.replyPh': 'Պատասխան հաճախորդին՝ կգա Telegram-ում',
'chat.notePh': 'Նշում թիմի համար՝ հաճախորդը չի տեսնի',
'chat.send': 'Ուղարկել',
'chat.saveNote': 'Պահել նշումը',
'chat.attach': 'Կցել ֆայլ',
'chat.templates': 'Ձևանմուշներ',
'chat.tplManage': 'Կարգավորել ձևանմուշները',
'chat.tplEmpty': 'Ձևանմուշներ դեռ չկան։',
'chat.tplNew': 'Նոր ձևանմուշ',
'chat.tplTitle': 'Անվանում',
'chat.tplText': 'Տեքստ',
'chat.tplTextHint': '{name}-ը կփոխարինվի հաճախորդի անունով',
'chat.tplChannel': 'Ալիք',
'chat.tplBoth': 'Երկու ալիքները',
'chat.tplDelete': 'Ջնջել',
'chat.tplSaved': 'Ձևանմուշը պահպանված է',
'chat.tplSearch': 'Գտնել ձևանմուշ',
'chat.noteLabel': 'Նշում · տեսանելի է միայն թիմին',
'chat.fromApp': 'հավելվածից',
'chat.undelivered': 'Չի առաքվել․ հաճախորդը արգելափակել է բոտը կամ երբեք չի բացել',
'chat.fileTooBig': 'Ֆայլը 10 ՄԲ-ից մեծ է',
'chat.enterHint': 'Enter՝ ուղարկել · Shift+Enter՝ նոր տող',
'chat.providerNotLinked': 'Կատարողը դեռ չի բացել աշխատանքային բոտը․ առայժմ կարող եք թողնել միայն նշում։',
'chat.client': 'Հաճախորդի մասին',
'chat.aboutProvider': 'Կատարողի մասին',
'chat.openCard': 'Հաճախորդի քարտ',
'chat.write': 'Գրել',
'chat.back': 'Բոլոր զրույցները',
'chat.sys.took': '{name}-ը վերցրեց զրույցը',
'chat.sys.transferred': '{name}-ը զրույցը փոխանցեց {param}-ին',
'chat.sys.unassigned': '{name}-ը հանեց պատասխանատուին',
'chat.sys.closed': '{name}-ը փակեց զրույցը',
'chat.sys.reopened': '{name}-ը կրկին բացեց զրույցը',
'chat.sys.moved': '{name}-ը զրույցը տեղափոխեց «{param}»',
'chat.ago.now': 'հենց հիմա',
'chat.ago.min': '{n} ր',
'chat.ago.h': '{n} ժ',
'chat.ago.d': '{n} օր',
'chat.today': 'Այսօր',
'chat.yesterday': 'Երեկ',
'chat.image': 'Լուսանկար',
'chat.file': 'Ֆայլ',
'chat.subUntil': 'մինչև {date}',
'chat.orders': 'Պատվերներ',
'chat.phone': 'Հեռախոս',
'chat.lang': 'Լեզու',
'chat.source': 'Աղբյուր',
'chat.linked': 'Աշխատանքային բոտը բացված է',
'chat.notLinked': 'Աշխատանքային բոտը բացված չէ',
'chat.details': 'Մանրամասներ',
'chat.more': 'Այլ գործողություններ',
// ───── партнёры и CRM (этап 4) ─────
'crm.title': 'CRM',
'crm.newLead': 'Նոր լիդ',
'crm.editLead': 'Լիդ',
'crm.stagesBtn': 'Ձագար',
'crm.tab.board': 'Ձագար',
'crm.tab.tasks': 'Առաջադրանքներ',
'crm.tab.map': 'Քարտեզ',
'crm.search': 'Անուն, կոնտակտ, հեռախոս կամ հասցե',
'crm.kind.all': 'Բոլորը',
'crm.kind.VENUE': 'Հաստատություններ',
'crm.kind.AGENCY': 'Գործակալություններ',
'crm.kind1.VENUE': 'Հաստատություն',
'crm.kind1.AGENCY': 'Գործակալություն',
'crm.owner': 'Վաճառող',
'crm.allSales': 'Բոլոր վաճառողները',
'crm.noOwner': 'Առանց վաճառողի',
'crm.ownerIs': 'վարում է {name}',
'crm.connected': 'Միացված',
'crm.connect': 'Միացում',
'crm.days': '{n} օր',
'crm.inStage': 'Օրեր այս փուլում',
'crm.dropHere': 'Քաշեք այստեղ',
'crm.dragHint': 'Քաշեք քարտերը փուլերի միջև։ «Միացված»-ը ստեղծում է գործընկեր կամ գործակալություն։',
'crm.overdue': 'ժամկետանց',
'crm.tasksOpen': 'Բաց',
'crm.tasksDone': 'Կատարված',
'crm.addTask': 'Առաջադրանք',
'crm.noTasks': 'Բաց առաջադրանքներ չկան։',
'crm.noDoneTasks': 'Կատարված առաջադրանքներ դեռ չկան։',
'crm.noLead': 'առանց լիդի',
'crm.tasksHint': 'Ժամկետին հիշեցում կգա աշխատանքային բոտում։',
'crm.taskTitle': 'Ինչ անել',
'crm.taskDay': 'Օր',
'crm.taskTime': 'Ժամ',
'crm.taskHint': 'Հիշեցումը կգա այդ ժամին (Երևան)։',
'crm.tp.call': 'Զանգահարել',
'crm.tp.meet': 'Հանդիպում',
'crm.tp.send': 'Ուղարկել պայմանները',
'crm.tp.check': 'Իմանալ որոշումը',
'crm.partnerOnMap': 'ակումբի գործընկեր',
'crm.legendPartner': 'միացված գործընկերներ',
'crm.legendLead': 'լիդեր (փուլի գույն)',
'crm.mapHint': 'Կետը հայտնվում է կոորդինատներ ունենալիս։',
'crm.name': 'Անվանում',
'crm.namePhVenue': 'Օրինակ՝ Lumen Coffee',
'crm.namePhAgency': 'Օրինակ՝ Domik Realty',
'crm.category': 'Տեսակ',
'crm.contactName': 'Կոնտակտային անձ',
'crm.contactPh': 'Անուն և պաշտոն',
'crm.address': 'Հասցե',
'crm.note': 'Նշում',
'crm.convert': 'Միացնել',
'crm.convertTitle': 'Միացնել «{name}»',
'crm.convertVenueHint': 'Կստեղծենք գործընկեր և հղում սեփականատիրոջ համար։',
'crm.convertAgencyHint': 'Կստեղծենք գործակալություն կոդով և հղում հաճախորդների համար։',
'crm.agencyCode': 'Գործակալության կոդ',
'crm.agencyCodeHint': 'Լատինատառ և թվեր',
'crm.convertedTitle': 'Միացված է 🎉',
'crm.convertedVenue': 'Ուղարկեք այս հղումը սեփականատիրոջը։ Միանգամյա է։',
'crm.convertedAgency': 'Այս հղումը գործակալությունը տալիս է հաճախորդներին։',
'crm.openVenue': 'Հաստատության քարտ',
'crm.openAgency': 'Գործակալության քարտ',
'crm.ownerLinked': 'Սեփականատերն արդեն բոտում է։',
'crm.ownerNotYet': 'Սեփականատերը դեռ չի բացել հղումը։ Ուղարկեք կրկին՝',
'crm.agencyInfo': 'Կոդ {code}, հաճախորդներ՝ {n}',
'crm.lostTitle': 'Ինչու՞ հրաժարում',
'crm.lostReason': 'Պատճառ',
'crm.lr.price': 'Պայմանները չհամապատասխանեցին',
'crm.lr.notNow': 'Ոչ հիմա',
'crm.lr.noAnswer': 'Չեն պատասխանում',
'crm.lr.competitor': 'Աշխատում են մրցակցի հետ',
'crm.lostBanner': 'Հրաժարում՝ {reason}',
'crm.stagesTitle': 'Ձագարի փուլեր',
'crm.stagesHint': 'Հերթականությունը՝ սլաքներով։',
'crm.addStage': 'Փուլ',
'crm.stageKind.OPEN': 'ընթացքում',
'crm.stageKind.WON': 'միացված',
'crm.stageKind.LOST': 'հրաժարում',
'crm.bonusMonth': 'Բոնուս այս ամիս',
'crm.bonusMineSuper': 'Բոնուս (ձեր), ամիս',
'crm.bonusNotSet': 'կարգավորված չէ',
'crm.bonusVenues': 'Հաստատություններ՝ {n} → {sum}',
'crm.bonusAgencies': 'Գործակալություններ՝ {n} → {sum}',
'crm.bonusRevenue': '{pct}% եկամուտից → {sum}',
'crm.bonusTitle': 'Վաճառողի բոնուսի բանաձև',
'crm.bonusHint': 'Բոնուս = հաստատություններ × դրույք + գործակալություններ × դրույք + % եկամուտից։',
'crm.bonusPerVenue': 'Հաստատության համար, ֏',
'crm.bonusPerAgency': 'Գործակալության համար, ֏',
'crm.bonusPct': '% եկամուտից',
'crm.bonusMonths': 'Քանի ամիս',
'crm.back': 'CRM',
'crm.created': '{date}-ից',
'crm.stage': 'Փուլ',
'crm.history': 'Կոնտակտների պատմություն',
'crm.noHistory': 'Դեռ դատարկ է։',
'crm.act.CALL': 'Զանգ',
'crm.act.MEETING': 'Հանդիպում',
'crm.act.NOTE': 'Նշում',
'crm.act.FILE': 'Ֆայլ',
'crm.act.STAGE': 'Փուլ',
'crm.act.WON': 'Միացված',
'crm.actPh.CALL': 'Ինչի՞ մասին պայմանավորվեցիք',
'crm.actPh.MEETING': 'Ինչպե՞ս անցավ հանդիպումը',
'crm.actPh.NOTE': 'Նշում ձեզ և թիմի համար',
'crm.addAct': 'Գրանցել',
'crm.attach': 'Լուսանկար կամ ֆայլ',
'crm.tasks': 'Առաջադրանքներ',
'crm.noLeadTasks': 'Առաջադրանքներ չկան։',
'crm.contacts': 'Կոնտակտներ',
'crm.noCoords': 'Քարտեզում չկա։',
'crm.coordsPh': 'Google Maps հղում կամ «40.18, 44.51»',
'crm.coordsBad': 'Կոորդինատներ չգտնվեցին։',
'crm.remove': 'Ջնջել լիդը',
'crm.removeConfirm': 'Ջնջե՞լ լիդը։',
'venue.cat.cafe': 'Սրճարան',
'venue.cat.restaurant': 'Ռեստորան',
'venue.cat.shop': 'Խանութ',
'venue.cat.beauty': 'Գեղեցկություն',
'venue.cat.other': 'Այլ',
'ag.title': 'Գործակալություններ',
'ag.add': 'Նոր գործակալություն',
'ag.editTitle': 'Գործակալություն',
'ag.empty': 'Գործակալություններ դեռ չկան։',
'ag.col.name': 'Գործակալություն',
'ag.col.clients': 'Հաճախորդներ',
'ag.col.gifts': 'Նվերներ',
'ag.col.month': 'Պարգև, ամիս',
'ag.col.balance': 'Վճարման',
'ag.hint': 'Պարգև՝ % վճարված պատվերներից։',
'ag.inactive': 'անջատված',
'ag.back': 'Բոլոր գործակալությունները',
'ag.pct': '{n}% հաճախորդների պատվերներից',
'ag.byS': 'միացրել է {name}',
'ag.link': 'Հղում հաճախորդների համար',
'ag.linkHint': 'Հաճախորդը բացում է բոտը և ստանում նվեր ամիս։ Կամ մուտքագրում է {code} կոդը։',
'ag.clients': 'Հաճախորդներ',
'ag.giftsN': 'նվերներ՝ {n}',
'ag.noClients': 'Հաճախորդներ դեռ չկան։',
'ag.orders': 'պատվերներ՝ {n}',
'ag.toPay': 'Վճարման ենթակա պարգև',
'ag.accrued': 'Հաշվեգրված',
'ag.payouts': 'Վճարումներ',
'ag.payoutTitle': 'Վճարում գործակալությանը',
'ag.balanceHint': 'Չվճարված՝ {sum}',
'ag.pctLabel': 'Պարգև, %',
'ag.sales': 'Միացրել է',
'ag.contactPh': 'Անուն, հեռախոս, Telegram',
'ag.active': 'Գործակալությունն աշխատում է',
'vn.title': 'Հաստատություններ',
'vn.add': 'Նոր հաստատություն',
'vn.editTitle': 'Հաստատություն',
'vn.empty': 'Հաստատություններ դեռ չկան։',
'vn.col.name': 'Հաստատություն',
'vn.col.offers': 'Առաջարկներ',
'vn.col.staff': 'Աշխատակիցներ',
'vn.col.visits': 'Ստուգումներ, 30 օր',
'vn.col.last': 'Վերջին ստուգումը',
'vn.hint': 'Ստուգում՝ աշխատակիցը սկանավորել է ակումբային քարտը։',
'vn.noOwner': 'սեփականատեր չկա',
'vn.noOffers': 'առաջարկներ չկան',
'vn.back': 'Բոլոր հաստատությունները',
'vn.ownerHint': 'Սեփականատերը դեռ միացված չէ՝ ուղարկեք միանգամյա հղում։',
'vn.makeLink': 'Ստեղծել հղում',
'vn.offers': 'Առաջարկներ ըստ մակարդակի',
'vn.addOffer': 'Առաջարկ',
'vn.editOffer': 'Առաջարկ',
'vn.noOffersHint': 'Ավելացրեք, թե ինչ են ստանում անդամները։',
'vn.level.any': 'Ցանկացած անդամ',
'vn.level.BAREV_PLUS': 'Barev+ և Elite',
'vn.level.ELITE': 'Միայն Elite',
'vn.limit.NONE': 'առանց սահմանափակման',
'vn.limit.ONCE': 'մեկ անգամ',
'vn.limit.WEEK': 'շաբաթական {n} անգամ',
'vn.limit.MONTH': 'ամսական {n} անգամ',
'vn.limitOpt.NONE': 'Առանց սահմանափակման',
'vn.limitOpt.ONCE': 'Միայն առաջին այցը',
'vn.limitOpt.WEEK': 'N անգամ շաբաթական',
'vn.limitOpt.MONTH': 'N անգամ ամսական',
'vn.offerOff': 'անջատված',
'vn.offerTitle': 'Ինչ է ստանում հաճախորդը',
'vn.offerTitleHint': 'Օրինակ՝ «Կապուչինո նվեր»',
'vn.forWhom': 'Ում համար',
'vn.howOften': 'Որքան հաճախ',
'vn.times': 'Քանի անգամ',
'vn.offerActive': 'Առաջարկն ակտիվ է',
'vn.activity': 'Ակտիվություն',
'vn.weeks8': '8 շաբաթում',
'vn.checks': 'քարտի ստուգումներ',
'vn.redeemed': 'օգտագործված առաջարկներ',
'vn.cardCheck': 'քարտի ստուգում',
'vn.staff': 'Աշխատակիցներ',
'vn.noStaff': 'Դեռ ոչ ոք։',
'vn.role.OWNER': 'սեփականատեր',
'vn.role.STAFF': 'աշխատակից',
'vn.removeStaff': 'Հեռացնե՞լ {name}-ին։',
'vn.staffHint': 'Աշխատակիցներին հրավիրում է սեփականատերը։',
'vn.newOwnerLink': 'Հղում սեփականատիրոջը',
'vn.newOwnerLinkHint': 'Նոր միանգամյա հղում',
'vn.blurb': 'Կարճ նկարագրություն',
'vn.blurbHint': 'Օրինակ՝ «−10% ակումբային քարտով»',
'vn.coords': 'Քարտեզի կետ',
'vn.activeLabel': 'Տեսանելի է հաճախորդներին',
'err.LEAD_NOT_CONVERTED': 'Օգտագործեք «Միացնել»։',
'err.ALREADY_CONVERTED': 'Լիդն արդեն միացված է։',
'err.AGENCY_CODE_FORMAT': 'Կոդ՝ լատինատառ և թվեր։',
'err.AGENCY_CODE_TAKEN': 'Այս կոդն արդեն զբաղված է։',
'err.STAGES_INVALID': 'Անհրաժեշտ է գոնե մեկ բաց և մեկ «Միացված» փուլ։',
'audit.bo.crm.create': 'ավելացրեց լիդ',
'audit.bo.crm.update': 'փոխեց լիդը',
'audit.bo.crm.move': 'տեղափոխեց լիդը',
'audit.bo.crm.convert': 'միացրեց գործընկեր',
'audit.bo.crm.addActivity': 'գրանցեց կոնտակտ',
'audit.bo.crm.saveStages': 'փոխեց ձագարը',
'audit.bo.crm.setBonusRules': 'փոխեց բոնուսի բանաձևը',
'audit.bo.partners.saveAgency': 'փոխեց գործակալությունը',
'audit.bo.partners.agencyPayout': 'նշեց վճարում գործակալությանը',
'audit.bo.partners.saveVenue': 'փոխեց հաստատությունը',
'audit.bo.partners.saveOffer': 'փոխեց առաջարկը',
'audit.bo.partners.ownerInvite': 'հղում տվեց սեփականատիրոջը',
'audit.bo.partners.removeMember': 'հեռացրեց աշխատակցին',
// ───── заказы и исполнители (этап 3) ─────
'ord.title': 'Պատվերներ',
'ord.new': 'Նոր պատվեր',
'ord.search': '№, հաճախորդ, հեռախոս, հասցե կամ կատարող',
'ord.period': 'Ժամանակահատված',
'ord.period.all': 'Բոլոր օրերը',
'ord.period.today': 'Այսօր',
'ord.period.tomorrow': 'Վաղը',
'ord.period.week': '7 օր',
'ord.period.past': 'Անցածները',
'ord.group.active': 'Ակտիվ',
'ord.group.new': 'Սպասում են կատարողի',
'ord.group.pending': 'Առաջարկված',
'ord.group.assigned': 'Նշանակված',
'ord.group.in_progress': 'Կատարվում են',
'ord.group.done': 'Պատրաստ',
'ord.group.cancelled': 'Չեղարկված',
'ord.today': 'Այսօր',
'ord.tomorrow': 'Վաղը',
'ord.empty': 'Այս պայմաններով պատվերներ չկան։',
'ord.waitsAnswer': 'սպասում ենք՝ {name}',
'ord.needsHuman': 'պետք է դիսպետչեր',
'ord.searching': 'համակարգը ընտրում է…',
'ord.overdue': 'ժամն անցել է, կատարող չկա',
'ord.needsDispatcher': 'Ավտոմատ բաշխումը կատարող չգտավ {n} պատվերի համար։ Նշանակեք ձեռքով։',
'ord.autoOn': 'Ավտոմատ բաշխումը միացված է',
'ord.autoOff': 'Ավտոմատ բաշխումն անջատված է',
'ord.autoHint': 'Նոր պատվերն ինքնաբերաբար առաջարկվում է լավագույն ազատ կատարողին։ {minutes} րոպեում պատասխան չկա կամ հրաժարվեց՝ հաջորդին, {tries} փորձից հետո՝ դիսպետչերին։',
'ord.back': 'Բոլոր պատվերները',
'ord.progress': 'Ընթացք',
'ord.details': 'Մանրամասներ',
'ord.when': 'Երբ',
'ord.where': 'Որտեղ',
'ord.minutes': '{n} ր',
'ord.params': 'Պարամետրեր',
'ord.extras': 'Լրացուցիչ',
'ord.note': 'Հաճախորդի մեկնաբանություն',
'ord.lang': 'Հաճախորդի լեզուն',
'ord.created': 'Ստեղծված',
'ord.checklist': 'Ստուգացանկ',
'ord.needsPhoto': 'լուսանկար է պետք',
'ord.photo': 'Լուսանկար',
'ord.history': 'Պատմություն',
'ord.client': 'Հաճախորդ',
'ord.writeClient': 'Գրել հաճախորդին',
'ord.writeProvider': 'Գրել կատարողին',
'ord.call': 'Զանգահարել',
'ord.noPhone': 'Հեռախոսահամարը նշված չէ',
'ord.money': 'Գումար',
'ord.base': 'Առանց զեղչի',
'ord.discount': 'Զեղչ {pct}%',
'ord.payout': 'Կատարողին',
'ord.cancelFee': 'Չեղարկման պահում',
'ord.payment': 'Վճարում',
'ord.markPaid': 'Նշել վճարումը',
'ord.confirmPaid': 'Նշե՞լ, որ հաճախորդը վճարել է։',
'ord.paidDone': 'Վճարումը նշված է',
'ord.actions': 'Գործողություններ',
'ord.setStatus': 'Կարգավիճակ՝ {status}',
'ord.confirmStatus': 'Տեղափոխե՞լ «{status}»։ Հաճախորդը ծանուցում կստանա։',
'ord.statusChanged': 'Կարգավիճակը փոխված է',
'ord.reschedule': 'Տեղափոխել',
'ord.rescheduleTitle': 'Պատվեր №{n}-ի տեղափոխում',
'ord.rescheduleHint': 'Եթե կատարողը զբաղված է նոր ժամին, պատվերը կվերադառնա «Սպասում են կատարողի»։',
'ord.rescheduled': 'Տեղափոխված է, կատարողը նույնն է',
'ord.rescheduledFree': 'Տեղափոխված է, կատարողը զբաղված է՝ փնտրում ենք նորը',
'ord.comment': 'Մեկնաբանություն',
'ord.commentPh': 'Օրինակ՝ հաճախորդը խնդրեց հեռախոսով',
'ord.cancel': 'Չեղարկել պատվերը',
'ord.cancelTitle': 'Պատվերի չեղարկում',
'ord.cancelReason': 'Չեղարկման պատճառը',
'ord.cancelReasonPh': 'Օրինակ՝ հաճախորդը փոխեց միտքը',
'ord.cancelFeeHint': 'Որքան պահել հաճախորդից, ֏։ Սովորաբար 0։',
'ord.cancelHint': 'Հաճախորդը և կատարողը ծանուցում կստանան։',
'ord.cancelled': 'Պատվերը չեղարկված է',
'ord.rating': 'Հաճախորդի գնահատականը',
'ord.noComment': 'Առանց մեկնաբանության',
'ord.offers': 'Ում է առաջարկվել',
'ord.bySystem': 'համակարգ',
'ord.provider': 'Կատարող',
'ord.unassign': 'Հանել կատարողին',
'ord.revoke': 'Հետ կանչել առաջարկը',
'ord.confirmUnassign': 'Հանե՞լ կատարողին։ Պատվերը կվերադառնա։',
'ord.confirmRevoke': 'Հետ կանչե՞լ առաջարկը։',
'ord.unassigned': 'Պատվերը կրկին սպասում է կատարողի',
'ord.pendingProvider': 'Առաջարկված է՝ {name}',
'ord.pendingCompany': 'Հանձնված է «{name}» ընկերությանը',
'ord.byAuto': 'առաջարկել է համակարգը',
'ord.minLeft': 'պատասխանի համար ≈ {n} ր',
'ord.pickHint': 'Այս ժամին ազատներ՝ ըստ համապատասխանության։',
'ord.autoPick': 'Ընտրել ավտոմատ',
'ord.autoOffered': 'Առաջարկվեց՝ {name}',
'ord.autoNone': 'Ազատ կատարող չգտնվեց',
'ord.noFree': 'Այս ժամին բոլորը զբաղված են։',
'ord.busy': 'Զբաղված են՝ {n}',
'ord.company': 'ընկերություն',
'ord.tried': 'արդեն առաջարկվել է',
'ord.load': 'այդ օրը պատվերներ՝ {n}',
'ord.offer': 'Առաջարկել',
'ord.offered': 'Առաջարկն ուղարկված է',
'ord.noProvider': 'Կատարող չի նշանակվել։',
'ord.ev.created': 'Պատվերը ստեղծված է',
'ord.ev.createdByStaff': 'Ստեղծել է թիմը',
'ord.ev.offered': 'Առաջարկվել է կատարողին',
'ord.ev.autoOffered': 'Ավտոմատ բաշխում՝ առաջարկված',
'ord.ev.autoNoCandidate': 'Ավտոմատ բաշխում՝ ազատ չկա',
'ord.ev.autoGaveUp': 'Ավտոմատ բաշխումը կանգնեց',
'no.title': 'Նոր պատվեր',
'no.client': 'Հաճախորդ',
'no.clientPh': 'Անուն, @username կամ հեռախոս',
'no.noClients': 'Ոչ ոք չգտնվեց',
'no.changeClient': 'Այլ հաճախորդ',
'no.service': 'Ծառայություն',
'no.extras': 'Լրացուցիչ',
'no.address': 'Հասցե',
'no.addressPh': 'Փողոց, շենք, բնակարան',
'no.district': 'Վարչական շրջան',
'no.when': 'Օր և ժամ',
'no.day': 'Օր',
'no.noSlots': 'Այս օրը ազատ ժամ չկա։',
'no.otherTime': 'Այլ ժամ (պայմանավորվել ենք կատարողի հետ)',
'no.customTime': 'Ժամ',
'no.customHint': 'Երևանի ժամով։',
'no.note': 'Մեկնաբանություն կատարողի համար',
'no.notePh': 'Դոմոֆոնի կոդ, կենդանիներ…',
'no.payment': 'Վճարում',
'no.hint': 'Գինը՝ հաշվի առնելով բաժանորդագրությունը։ Հաճախորդը ծանուցում կստանա։',
'no.create': 'Ձևակերպել պատվերը',
'no.created': 'Պատվեր №{n}-ը ձևակերպված է',
'prv.title': 'Կատարողներ',
'prv.add': 'Ավելացնել',
'prv.search': 'Անուն կամ հեռախոս',
'prv.status.active': 'Աշխատում են',
'prv.status.blocked': 'Արգելափակված',
'prv.status.all': 'Բոլորը',
'prv.empty': 'Ոչ ոք չգտնվեց։',
'prv.col.name': 'Կատարող',
'prv.col.rating': 'Վարկանիշ',
'prv.col.done': 'Պատվերներ',
'prv.col.refused': 'Հրաժարումներ',
'prv.col.next': 'Մոտակա պատվերը',
'prv.period30': 'Պատվերներ, հրաժարումներ, ցածր գնահատականներ՝ 30 օրում։',
'prv.blocked': 'արգելափակված',
'prv.onShift': 'հերթափոխում',
'prv.offShift': 'հերթափոխում չէ',
'prv.notLinked': 'բոտը բացված չէ',
'prv.noDocs': 'փաստաթղթեր չկան',
'prv.ratings': 'գնահատականներ՝ {n}',
'prv.low': 'ցածր՝ {n}',
'prv.today': 'այսօր՝ {n}',
'prv.back': 'Բոլոր կատարողները',
'prv.write': 'Գրել',
'prv.edit': 'Խմբագրել',
'prv.blockedSince': 'Արգելափակված է {date}-ից։',
'prv.unblock': 'Վերադարձնել աշխատանքի',
'prv.inviteHint': 'Կատարողը դեռ չի բացել աշխատանքային բոտը՝ ուղարկեք հղումը։',
'prv.copyInvite': 'Պատճենել հղումը',
'prv.quality': 'Որակ',
'prv.days30': '30 օրում',
'prv.acceptRate': 'ընդունել է {a}-ը {n}-ից',
'prv.refusals': 'հրաժարվել՝ {d}, լռել՝ {e}',
'prv.lowRatings': 'գնահատական 3 և ցածր',
'prv.upcoming': 'Մոտակա պատվերներ',
'prv.noUpcoming': 'Նշանակված պատվերներ չկան։',
'prv.recent': 'Վերջին կատարվածները',
'prv.balance': 'Վճարման ենթակա',
'prv.thisMonth': 'Այս ամիս',
'prv.prevMonth': 'Անցյալ',
'prv.paidTotal': 'Վճարված',
'prv.payout': 'Նշել վճարումը',
'prv.payoutTitle': 'Վճարում կատարողին',
'prv.amount': 'Գումար, ֏',
'prv.balanceHint': 'Պարտք կատարողին՝ {sum}',
'prv.payoutNote': 'Ինչպես է վճարվել',
'prv.payoutNotePh': 'Կանխիկ / փոխանցում…',
'prv.payoutConfirm': 'Վճարված է',
'prv.payoutDone': 'Վճարումը նշված է',
'prv.rateCompany': 'ընկերության դրույք {v}',
'prv.rateOwn': 'դրույք {v}',
'prv.ratePreset': '«{name}» նախադրույքով',
'prv.work': 'Աշխատանք',
'prv.languages': 'Լեզուներ',
'prv.districts': 'Շրջաններ',
'prv.anyDistrict': 'ցանկացած',
'prv.districtsHint': 'Ընտրությունը նախապատվություն է տալիս շրջանում աշխատողներին։',
'prv.docs': 'Թույլտվության փաստաթղթեր',
'prv.noDocsHint': 'Անձնագիր, պայմանագիր, տեղեկանք՝ փակ պահոցում։',
'prv.docTitlePh': 'Անվանում՝ անձնագիր, պայմանագիր…',
'prv.upload': 'Վերբեռնել',
'prv.docAdded': 'Փաստաթուղթն ավելացված է',
'prv.removeDocConfirm': 'Ջնջե՞լ փաստաթուղթը։',
'prv.access': 'Թույլտվություն',
'prv.block': 'Արգելափակել',
'prv.blockTitle': 'Արգելափակել կատարողին',
'prv.blockReason': 'Պատճառը',
'prv.blockReasonPh': 'Օրինակ՝ բողոքներ, փաստաթղթեր չկան',
'prv.blockHint': 'Նոր առաջարկներ չեն լինի։ Նշանակված պատվերները վերանշանակեք ձեռքով։',
'prv.resetInvite': 'Նոր հղում բոտի համար',
'prv.resetConfirm': 'Ստեղծե՞լ նոր հղում։ Ընթացիկ կապը կհանվի։',
'prv.since': 'Մեզ հետ է {date}-ից',
'prv.saved': 'Պահպանված է',
'prv.addTitle': 'Նոր կատարող',
'prv.editTitle': 'Կատարողի պրոֆիլ',
'prv.name': 'Անուն',
'prv.role': 'Դեր',
'prv.company': 'Ընկերություն',
'prv.freelance': 'Անհատ կատարող',
'prv.schedule': 'Ժամանակացույց',
'prv.rate': 'Դրույք',
'prv.note': 'Թիմի նշում',
'err.REASON_REQUIRED': 'Նշեք պատճառը։',
'err.SLOT_UNAVAILABLE': 'Այս ժամը զբաղված է կամ անցել է։',
'err.ALREADY_ASSIGNED': 'Պատվերն արդեն նշանակված է։',
'err.PROVIDER_BUSY': 'Կատարողը զբաղված է այդ ժամին։',
'err.TRANSITION_NOT_ALLOWED': 'Այս քայլը հիմա հասանելի չէ։',
'err.CHECKLIST_INCOMPLETE': 'Կատարողը նախ պետք է ավարտի ստուգացանկը։',
'err.CONSENT_REQUIRED': 'Հաճախորդը դեռ համաձայնություն չի տվել։',
'err.ADDRESS_REQUIRED': 'Նշեք հասցեն և շրջանը։',
'err.INVALID_PARAMS': 'Ստուգեք պատվերի պարամետրերը։',
'err.OFFER_NOT_ACTIVE': 'Առաջարկն այլևս ակտիվ չէ։',
'err.BAD_FILE_TYPE_DOC': 'Միայն լուսանկար կամ PDF։',
'audit.bo.orders.assign': 'առաջարկեց պատվերը',
'audit.bo.orders.auto': 'գործարկեց ավտոմատ ընտրությունը',
'audit.bo.orders.unassign': 'հանեց կատարողին',
'audit.bo.orders.transition': 'փոխեց պատվերի կարգավիճակը',
'audit.bo.orders.cancel': 'չեղարկեց պատվերը',
'audit.bo.orders.reschedule': 'տեղափոխեց պատվերը',
'audit.bo.orders.markPaid': 'նշեց վճարումը',
'audit.bo.orders.create': 'ձևակերպեց պատվեր',
'audit.bo.orders.setAutoSetting': 'փոխեց ավտոմատ բաշխումը',
'audit.bo.providers.create': 'ավելացրեց կատարող',
'audit.bo.providers.update': 'փոխեց կատարողի պրոֆիլը',
'audit.bo.providers.setActive': 'փոխեց կատարողի թույլտվությունը',
'audit.bo.providers.resetInvite': 'նոր հղում տվեց կատարողին',
'audit.bo.providers.removeDoc': 'ջնջեց կատարողի փաստաթուղթը',
'audit.bo.providers.addDoc': 'վերբեռնեց կատարողի փաստաթուղթը',
'audit.bo.providers.payout': 'նշեց վճարում կատարողին',
'chat.order': 'Պատվեր №{n}',
'chat.noOrder': 'Առանց պատվերի',
'chat.noOrderNow': 'Այժմ պատվեր չկա',
'chat.orderNow': 'Այժմ',
'chat.orderNext': 'Հաջորդը',
'chat.orderNoNext': 'Մոտակա պատվերներ չկան',
'chat.orderClient': 'հաճախորդ {name}',
'chat.wroteNoOrder': 'գրել է առանց պատվերի',
'err.CONCIERGE_SUBSCRIBERS_ONLY': 'Կոնսիերժը միայն բաժանորդների համար է։ Նախ տրամադրեք բաժանորդագրություն։',
'err.ASSIGNEE_NO_ACCESS': 'Այս աշխատակիցը մուտք չունի այս ալիքին։',
'err.PROVIDER_NOT_LINKED': 'Կատարողը դեռ չի բացել աշխատանքային բոտը։',
'err.BAD_FILE_TYPE': 'Այս ֆայլը չի համապատասխանում։ Կարելի է լուսանկար, PDF, Word, Excel, տեքստ կամ ZIP։',
'audit.bo.chats.send': 'պատասխանեց զրույցում',
'audit.bo.chats.sendFile': 'ֆայլ ուղարկեց զրույցում',
'audit.bo.chats.assign': 'նշանակեց զրույցի պատասխանատու',
'audit.bo.chats.close': 'փակեց զրույցը',
'audit.bo.chats.reopen': 'կրկին բացեց զրույցը',
'audit.bo.chats.move': 'զրույցը տեղափոխեց այլ ալիք',
'audit.bo.chats.openFor': 'բացեց զրույց հաճախորդի հետ',
'audit.bo.chats.templates.save': 'փոխեց պատասխանի ձևանմուշը',
'audit.bo.chats.templates.remove': 'ջնջեց պատասխանի ձևանմուշը',
};
const DICTS: Record<BoLocale, Dict> = { ru, en, hy };
export type T = (key: BoKey | (string & {}), params?: Record<string, string | number | null | undefined>) => string;
function makeT(locale: BoLocale): T {
const dict = DICTS[locale];
return (key, params) => {
let s: string = (dict as Record<string, string>)[key] ?? (ru as Record<string, string>)[key] ?? key;
if (params) for (const [k, v] of Object.entries(params)) s = s.replaceAll(`{${k}}`, String(v ?? ''));
return s;
};
}
interface Ctx {
locale: BoLocale;
setLocale: (l: BoLocale) => void;
t: T;
/** общие переводы проекта: services.<code>.name, roles.<ROLE>, params.* и т.п. */
shared: (key: string, params?: Record<string, string | number>) => string;
/** время по Еревану: 14:00 */
time: (d: Date) => string;
/** общий t проекта целиком — для хелперов @barev/web (paramsSummary и т.п.) */
sharedT: ReturnType<typeof createSharedT>;
amd: (n: number) => string;
date: (d: Date) => string;
dateTime: (d: Date) => string;
/** сокращённая сумма для плотных мест: 1,2 млн */
amdShort: (n: number) => string;
}
const I18nCtx = createContext<Ctx | null>(null);
const KEY = 'barev.bo.locale';
function initialLocale(): BoLocale {
try {
const saved = localStorage.getItem(KEY);
if (saved && (BO_LOCALES as readonly string[]).includes(saved)) return saved as BoLocale;
} catch {
/* приватный режим */
}
const nav = navigator.language.slice(0, 2);
return (BO_LOCALES as readonly string[]).includes(nav) ? (nav as BoLocale) : 'ru';
}
export function BoI18nProvider({ children }: { children: ReactNode }) {
const [locale, setLocaleState] = useState<BoLocale>(initialLocale);
useEffect(() => {
document.documentElement.lang = locale;
}, [locale]);
const value = useMemo<Ctx>(() => {
const sharedT = createSharedT(locale as SharedLocale);
const intl = locale === 'en' ? 'en-GB' : locale === 'hy' ? 'hy-AM' : 'ru-RU';
const compact = new Intl.NumberFormat(intl, { notation: 'compact', maximumFractionDigits: 1 });
return {
locale,
setLocale: (l) => {
setLocaleState(l);
try {
localStorage.setItem(KEY, l);
} catch {
/* приватный режим */
}
},
t: makeT(locale),
shared: sharedT,
sharedT,
amd: (n) => formatAmd(locale as SharedLocale, n),
amdShort: (n) => `${compact.format(n)} ֏`,
date: (d) => formatDateTime(locale as SharedLocale, d, { day: 'numeric', month: 'short', year: 'numeric' }),
dateTime: (d) => formatDateTime(locale as SharedLocale, d, { day: 'numeric', month: 'short', hour: '2-digit', minute: '2-digit' }),
time: (d) => formatDateTime(locale as SharedLocale, d, { hour: '2-digit', minute: '2-digit' }),
};
}, [locale]);
return <I18nCtx.Provider value={value}>{children}</I18nCtx.Provider>;
}
export function useT() {
const v = useContext(I18nCtx);
if (!v) throw new Error('BoI18nProvider missing');
return v;
}
/** Текст ошибки API: код бизнес-ошибки → перевод, иначе сообщение */
export function errText(t: T, err: unknown): string {
const msg = (err as { message?: string })?.message ?? '';
const known = `err.${msg}`;
const tr = t(known);
return tr !== known ? tr : t('ui.error', { msg: msg || '—' });
}