Open Finapp
Справочник

Типы транзакций

Типы транзакций, логика корректировок, статистика.

Обзор

Финапка поддерживает три типа транзакций и одну специальную категорию:

ТипTrnTypeОписание
Расход0Потраченные деньги
Доход1Полученные деньги
Перевод2Перемещение денег между кошельками
Корректировка0 или 1Корректировка баланса (Расход или Доход с categoryId: 'adjustment')

Расход

Обычная транзакция расхода. Уменьшает баланс кошелька.

  • Требуется: кошелёк, категория, сумма
  • Отображается в статистике расходов
  • Сумма показывается со знаком минус

Доход

Обычная транзакция дохода. Увеличивает баланс кошелька.

  • Требуется: кошелёк, категория, сумма
  • Отображается в статистике доходов
  • Сумма показывается со знаком плюс

Перевод

Перемещение денег между двумя кошельками. Не влияет на статистику доходов/расходов.

  • Требуется: кошелёк расхода, кошелёк дохода, суммы для каждого
  • Поддерживает разные валюты (например, кошелёк USD → кошелёк EUR)
  • Использует системную категорию transfer (categoryId: 'transfer')
  • Доступен только при наличии 2+ кошельков

Корректировка

Корректировка баланса кошелька. Влияет на баланс кошелька, но исключается из статистики доходов/расходов.

Как это работает

Корректировка - это не отдельный тип транзакции. Это обычная транзакция Расхода или Дохода с системной категорией adjustment (categoryId === 'adjustment').

  • Расход + корректировка - уменьшает баланс кошелька (например, «потерянные деньги», корректировка вниз)
  • Доход + корректировка - увеличивает баланс кошелька (например, «найденные деньги», корректировка вверх)

Определение

Корректировка определяется по categoryId, не по type:

const isAdjustment = trn.categoryId === 'adjustment'

Поведение

  • Исключается из статистики доходов/расходов в getTotal()
  • Исключается из недавних категорий в recentCategoriesIds
  • Исключается из последней созданной транзакции в lastCreatedTrnId
  • Включается в расчёт баланса кошелька (как отдельное поле adjustment в итогах)
  • Не показывается в дереве категорий (системная категория)
  • Доступна в модальном окне выбора категории (Command Palette)

Системные категории

Две системные категории всегда присутствуют в хранилище и не могут быть изменены или удалены:

IDНазваниеНазначение
transferПереводИспользуется переводами
adjustmentКорректировкаИспользуется для корректировки баланса

Эти категории:

  • Автоматически добавляются в useCategoriesStore.setCategories()
  • Исключены из categoriesRootIds (не показываются в дереве категорий)
  • Защищены от редактирования/удаления в saveCategory() и deleteCategory()

Поведение при смене типа

При смене типа транзакции нормализация происходит на клиенте - в trnToRow (services/powersync/transforms.ts) при записи. Никакого серверного бэкенда для этого нет:

  • → Перевод: trnToRow устанавливает categoryId в 'transfer' и записывает expenseWalletId/incomeWalletId/expenseAmount/incomeAmount; поля одного кошелька (walletId, amount) записываются как null
  • → Расход/Доход: trnToRow записывает walletId/amount; поля перевода (expenseWalletId, incomeWalletId, expenseAmount, incomeAmount) записываются как null
  • → Корректировка: дополнительная очистка не требуется - корректировка использует обычные поля Расхода/Дохода с categoryId: 'adjustment'

Это гарантирует, что только поля, относящиеся к текущему типу, имеют ненулевые значения в локальной SQLite-строке и на сервере.

Статистика

getTotal() возвращает:

ПолеВключает
incomeТранзакции дохода (исключая переводы и корректировки)
expenseТранзакции расхода (исключая переводы и корректировки)
adjustmentТранзакции корректировки (влияет на баланс кошелька)
incomeTransfersСторона дохода перевода
expenseTransfersСторона расхода перевода
sumincome - expense
sumTransfersincomeTransfers - expenseTransfers

Следующие шаги