Перейти к содержимому

Расходы

Модуль расходов позволяет учитывать всё, что вы тратите на работу отеля — от электричества и тапочек до зарплат и аренды — и автоматически считать чистую прибыль (GOP), эффективность на номер (GOPPAR) и операционный доход (NOI).

Список расходов
Список расходов

До появления этого модуля система знала только доходную часть: бронирования, платежи, продажи услуг. Без расходов вы видели «сделали 12 млн ₸» и не могли ответить на главный вопрос — заработали или ушли в минус. Теперь финансовая картина полная.

Система использует международную стандартную классификацию расходов гостиничного бизнеса USALI (Uniform System of Accounts for the Lodging Industry). При создании нового проекта автоматически создаются 34 системные категории, разбитые по 11 группам:

ГруппаПримеры категорий
Расходы номеров (Rooms)Расходники для номеров, аменитис, прачечная, униформа, комиссии OTA
Питание (F&B)Продукты для завтраков, напитки и бар, посуда
Коммуналка (Utilities)Электричество, вода, газ, отопление, интернет и связь
Обслуживание (Maintenance)Текущий ремонт, сантехника, электрика, мебель, уборка территории
Зарплата (Payroll)Администраторы, горничные, кухня и F&B, налоги на ФОТ
Административные (A&G)Канцелярия, банковские комиссии, бухгалтерия, юристы, ПО
МаркетингРеклама онлайн, фото/видео, печать
АрендаПомещения, оборудование
Налоги и страховкаНалог на имущество, страхование
ФинансыПроценты по кредитам
ПрочееВсё остальное

Системные категории нельзя удалить — только архивировать или переименовать. Можно добавлять свои категории в любую группу.

Имена категорий мультиязычные: каждое название хранится сразу на нескольких языках (ru / en / kz / de), а интерфейс показывает его на языке пользователя. Поэтому в любой локали категория выглядит одинаково осмысленно.

Отдельная страница Финансы → Расходы → Категории — это «атлас» всех статей. Слева список 11 USALI-групп со счётчиками, справа — категории выбранной группы.

Что здесь видно и можно делать:

  • Сводка по группе — сколько всего категорий, сколько ваших, сколько системных, сколько зарплатных
  • Поиск — по любому из языков названия сразу по всем группам
  • Цвет и иконка — у каждой категории свой значок; для своих категорий можно задать собственный цвет (hex)
  • Бейдж «Зарплата» — зарплатные категории помечены замком
  • Создание / редактирование своих категорий, переименование системных
  • Удаление — только для своих категорий; системные защищены замком

Модуль использует гранулярные права, а не только роли:

ПравоЧто даёт
expenses.viewВидеть список расходов и агрегаты (без зарплат)
expenses.manageСоздавать/редактировать/отменять любые расходы (кроме зарплатных) и управлять категориями
expenses.manage_ownВидеть все non-payroll расходы проекта; редактировать и отменять — только свои, младше 24 часов
expenses.payroll.viewВидеть зарплатные категории и суммы
expenses.payroll.manageСоздавать и редактировать зарплатные расходы
financial_kpi.viewВидеть GOP, GOPPAR, NOI, ADR, RevPAR

Готовые пресеты в диалоге изменения прав участника проекта:

  • Владелец / Управляющий / Бухгалтер — полный доступ к финансам, включая зарплаты
  • Ресепшн — только expenses.manage_own (свои операционные расходы за смену)
  • Только чтение — просмотр без редактирования

На странице Финансы → Расходы → Все расходы — таблица со всеми расходами проекта.

Сверху — карточки-итоги за выбранный период: Всего, Оплачено, Запланировано. Если у вас нет права видеть зарплаты, появляется четвёртая карточка-предупреждение «Payroll скрыт» — она напоминает, что суммы в итогах посчитаны без фонда оплаты труда.

Что здесь можно делать:

  • Поиск — по названию поставщика
  • Фильтры — по USALI-группе, статусу (Оплачен / Запланирован), периоду (с готовыми пресетами: сегодня, вчера, 7 дней, месяц, прошлый месяц, с начала года)
  • Активные фильтры показываются «пилюлями» — каждую можно снять одним кликом
  • Настройка колонок и плотности — можно прятать колонки и переключать компактный вид
  • Клик по строке — открывает детальную страницу расхода
  • Новый расход — кнопка в шапке открывает форму создания
  • Колонка «Кто создал» — видно, кто внёс расход (важно для контроля в сменах ресепшена)
  • НДС — если у расхода указан НДС, он показывается под суммой отдельной подписью
  • Пагинация — выбор размера страницы и переключение по номерам

При проваливании из портфельного P&L (?projectId=…) страница автоматически переключается на нужный отель — карточки и таблица показывают данные именно того объекта, в который вы перешли.

Форма создания расхода
Форма создания расхода
  1. Откройте Финансы → Расходы → Все расходы
  2. Нажмите «Новый расход»
  3. Заполните форму:
    • Сумма — обязательное поле, в тенге
    • Статус — Оплачен или Запланирован
    • Категория — выбирается из дерева USALI с поиском по всем языкам (зарплатные видят только владельцы)
    • Дата расхода — когда возникло обязательство (для P&L)
    • Дата оплаты — когда деньги реально ушли (для cash flow). Поле появляется только для статуса «Оплачен» и может отличаться от даты расхода
    • Способ оплаты — Наличные / Банк / Карта / Kaspi / Другое
    • Поставщик, номер счёта, описание — опционально

Расход сохраняется в статусе Оплачен (если поставили дату оплаты) или Запланирован.

Клик по строке в списке открывает детальную страницу — аналог страницы платежа.

Детальная страница расхода
Детальная страница расхода

На странице отображаются:

  • Сводка — крупная сумма, отдельной строкой НДС (если задан), категория, способ оплаты, поставщик, номер счёта, описание
  • Две даты с пояснением — дата расхода (попадает в P&L за этот месяц) и дата оплаты (попадает в движение денежных средств за этот день). Раскрывающаяся подпись объясняет, зачем нужны обе. Под датой расхода видно, был ли он проставлен задним числом; под датой оплаты — разрыв между начислением и оплатой (отсрочка поставщика или предоплата)
  • Категория — отдельным блоком, с группой USALI и бейджем «payroll» для зарплатных
  • Признак ночного аудита — попадает ли расход в сменный отчёт
  • Источник — если расход создан автоматически из повторяющегося правила, есть ссылка на него
  • Карточка автора — кто создал расход и когда
  • Хронология — таймлайн событий: создан → понесён → оплачен → отменён
  • История изменений (аудит) — сворачиваемый блок; раскрыт по умолчанию для аномалий (отменённые или внесённые задним числом расходы)

Если расход внесён задним числом (создан намного позже даты, которую вы указали), в шапке появляется предупреждающий бейдж — такая запись меняет P&L уже закрытого месяца.

Кнопка «Изменить» открывает форму со всеми полями расхода. Часть полей — дата расхода, дата оплаты, способ оплаты — можно менять прямо на странице, не открывая форму. Категорию изменить нельзя — это ограничение сделано специально, чтобы не ломать исторические агрегаты по группам USALI. Если категория выбрана неверно, отмените расход и создайте новый.

Кнопка «Отменить» открывает диалог с необязательным полем причины. Отменённые расходы не удаляются из базы, а переводятся в статус Отменён — их видно в списке с фильтром, и они исключены из всех финансовых расчётов (P&L, GOP, ночной аудит).

Ресепшн может отменять только свои расходы, созданные меньше 24 часов назад. Владелец, управляющий и бухгалтер могут отменить любой non-payroll расход (зарплатные — при наличии expenses.payroll.manage).

Для регулярных платежей — аренда, коммуналка, подписки — создайте правило в Финансы → Расходы → Повторяющиеся. Система сама сгенерирует запись в статусе «Запланирован» по расписанию.

Форма повторяющегося расхода
Форма повторяющегося расхода

Форма повторяющегося расхода запрашивает категорию, сумму, частоту (ежемесячно, ежеквартально, ежегодно), день начала и, при желании, день окончания. Каждую ночь система проверяет правила и создаёт по ним записи: новый расход появляется в статусе «Запланирован» без даты оплаты и со способом оплаты «Банк» — бухгалтер видит появившуюся строку и отдельно подтверждает фактическую оплату (или владелец правит сумму, если счёт отличается от правила).

Повторяющиеся расходы по умолчанию не попадают в ночной аудит — администратор видит их в общем списке расходов, но они не спамят сменный отчёт.

Оператор с правом expenses.manage_own:

  • Видит все non-payroll расходы проекта (чтобы понимать общую картину по смене и не создавать дубли)
  • Создаёт расходы от своего имени
  • Не видит зарплатные категории вообще
  • Может редактировать и отменять только свои расходы, и только если они созданы меньше 24 часов назад
  • Не может спрятать свой расход от ночного аудита — его записи всегда попадают в сменный отчёт
  • Не видит GOP, ADR, RevPAR, GOPPAR — только кассу

Это сделано специально, чтобы:

  1. Ресепшн отвечал за свои операционные закупки (тапочки за смену, батарейки в замки) — и они попадали в ночной аудит
  2. Финансовые KPI видели только те, кому они нужны для управления — владелец и управляющий

На странице Отчёты → Ночной аудит есть секция «Расходы за смену» — показываются non-payroll расходы, отмеченные для ночного аудита и возникшие в день аудита. Секция не видна пользователям без expenses.view.

На основе расходов автоматически считаются ключевые гостиничные KPI:

МетрикаФормулаЧто показывает
GOPВыручка − Операционные расходы (без аренды/налогов/финансов)Валовая операционная прибыль
GOP MarginGOP / Выручка × 100%Маржа
GOPPARGOP / Available Room-Nights за периодГлавная метрика эффективности собственника
NOIGOP − Аренда − Налоги − ФинансыЧистый операционный доход

Эти метрики требуют права financial_kpi.view. Если у пользователя нет expenses.payroll.view, зарплата не учитывается в расчёте, и GOP помечается как «неполный» — в интерфейсе появляется предупреждение, что цифра завышена на сумму скрытого PAYROLL.

GOP, GOPPAR и NOI отображаются на дашборде и в P&L отчёте. Расходы можно дополнительно разрезать по USALI Operating Department — этот срез используется для drill-down из P&L. Подробнее о том, как считается выручка для этих метрик — см. Признание выручки.

  • Модели: ExpenseCategory, Expense, RecurringExpense (см. apps/api/prisma/schema.prisma)
  • Имена категорий — мультиязычный JSON { ru, en, kz, de, … }; группа и USALI-департамент (department) — отдельные поля
  • У расхода есть опциональная привязка к зоне/корпусу и юниту (zoneId, unitId), поле НДС (vatAmount), валюта и вложения-чеки (attachments)
  • Сид системных категорий: apps/api/src/modules/expense-category/expenseCategorySeeds.ts
  • Ежедневный cron: RecurringExpenseCronService (03:00 серверного времени)
  • Мягкое удаление через isActive=false + status=CANCELLED
  • Все операции пишутся в AuditLog
  • Только KZT. Валюта хранится в каждой записи, но полноценная мультивалютность в TODO как критичная отложенная задача
  • PDF-экспорт ночного аудита не рендерит секцию расходов (только UI отображает)
  • Доступ к бронированиям по-прежнему определяется проектной ролью, не permissions. Поэтому пресет «Бухгалтер» даёт финансовые права, но бронирования и данные гостей всё ещё видны через роль OPERATOR/VIEWER. Изоляция бухгалтера от гостевых данных — в TODO как «RBAC Phase 2»